Add application command schema
This commit is contained in:
parent
7096881e7e
commit
5c798af16d
2
.idea/runConfigurations/Start_API.xml
generated
2
.idea/runConfigurations/Start_API.xml
generated
@ -5,7 +5,7 @@
|
||||
<scripts>
|
||||
<script value="start:api" />
|
||||
</scripts>
|
||||
<node-interpreter value="/nix/store/dcdc33kdjdhjnzg6rkmd0cx4kpwl8cac-nodejs-20.17.0/bin/node" />
|
||||
<node-interpreter value="/run/current-system/sw/bin/node" />
|
||||
<package-manager value="npm" />
|
||||
<envs />
|
||||
<EXTENSION ID="com.fapiko.jetbrains.plugins.better_direnv.runconfigs.NodeRunConfiguration">
|
||||
|
||||
74
.idea/workspace.xml
generated
74
.idea/workspace.xml
generated
@ -43,50 +43,50 @@
|
||||
<option name="hideEmptyMiddlePackages" value="true" />
|
||||
<option name="showLibraryContents" value="true" />
|
||||
</component>
|
||||
<component name="PropertiesComponent">{
|
||||
"keyToString": {
|
||||
"NIXITCH_NIXPKGS_CONFIG": "/etc/nix/nixpkgs-config.nix",
|
||||
"NIXITCH_NIX_CONF_DIR": "",
|
||||
"NIXITCH_NIX_OTHER_STORES": "",
|
||||
"NIXITCH_NIX_PATH": "/home/Rory/.nix-defexpr/channels:nixpkgs=/nix/store/wb6agba4kfsxpbnb5hzlq58vkjzvbsk6-source",
|
||||
"NIXITCH_NIX_PROFILES": "/run/current-system/sw /nix/var/nix/profiles/default /etc/profiles/per-user/Rory /home/Rory/.local/state/nix/profile /nix/profile /home/Rory/.nix-profile",
|
||||
"NIXITCH_NIX_REMOTE": "",
|
||||
"NIXITCH_NIX_USER_PROFILE_DIR": "/nix/var/nix/profiles/per-user/Rory",
|
||||
"Node.js.Server.ts.executor": "Debug",
|
||||
"RunOnceActivity.ShowReadmeOnStart": "true",
|
||||
"RunOnceActivity.git.unshallow": "true",
|
||||
"javascript.nodejs.core.library.configured.version": "24.8.0",
|
||||
"javascript.nodejs.core.library.typings.version": "24.7.0",
|
||||
"last_opened_file_path": "/home/Rory/git/spacebar/server-master/src/schemas/api/guilds",
|
||||
"node.js.detected.package.eslint": "true",
|
||||
"node.js.selected.package.eslint": "(autodetect)",
|
||||
"node.js.selected.package.tslint": "(autodetect)",
|
||||
"nodejs_interpreter_path": "node",
|
||||
"nodejs_package_manager_path": "npm",
|
||||
"npm.Start API.executor": "Run",
|
||||
"npm.Start CDN.executor": "Run",
|
||||
"npm.Start Gateway.executor": "Run",
|
||||
"npm.build.executor": "Run",
|
||||
"npm.start.executor": "Debug",
|
||||
"prettierjs.PrettierConfiguration.Package": "/home/Rory/git/spacebar/server-master/node_modules/prettier",
|
||||
"settings.editor.selected.configurable": "preferences.pluginManager",
|
||||
"ts.external.directory.path": "/home/Rory/git/spacebar/server-master/node_modules/typescript/lib"
|
||||
<component name="PropertiesComponent"><![CDATA[{
|
||||
"keyToString": {
|
||||
"NIXITCH_NIXPKGS_CONFIG": "/etc/nix/nixpkgs-config.nix",
|
||||
"NIXITCH_NIX_CONF_DIR": "",
|
||||
"NIXITCH_NIX_OTHER_STORES": "",
|
||||
"NIXITCH_NIX_PATH": "/home/Rory/.nix-defexpr/channels:nixpkgs=/nix/store/wb6agba4kfsxpbnb5hzlq58vkjzvbsk6-source",
|
||||
"NIXITCH_NIX_PROFILES": "/run/current-system/sw /nix/var/nix/profiles/default /etc/profiles/per-user/Rory /home/Rory/.local/state/nix/profile /nix/profile /home/Rory/.nix-profile",
|
||||
"NIXITCH_NIX_REMOTE": "",
|
||||
"NIXITCH_NIX_USER_PROFILE_DIR": "/nix/var/nix/profiles/per-user/Rory",
|
||||
"Node.js.Server.ts.executor": "Debug",
|
||||
"RunOnceActivity.ShowReadmeOnStart": "true",
|
||||
"RunOnceActivity.git.unshallow": "true",
|
||||
"javascript.nodejs.core.library.configured.version": "24.8.0",
|
||||
"javascript.nodejs.core.library.typings.version": "24.7.0",
|
||||
"last_opened_file_path": "/home/Rory/git/spacebar/server-master/src/util/migration/postgres",
|
||||
"node.js.detected.package.eslint": "true",
|
||||
"node.js.selected.package.eslint": "(autodetect)",
|
||||
"node.js.selected.package.tslint": "(autodetect)",
|
||||
"nodejs_interpreter_path": "node",
|
||||
"nodejs_package_manager_path": "npm",
|
||||
"npm.Start API.executor": "Run",
|
||||
"npm.Start CDN.executor": "Run",
|
||||
"npm.Start Gateway.executor": "Run",
|
||||
"npm.build.executor": "Run",
|
||||
"npm.start.executor": "Debug",
|
||||
"prettierjs.PrettierConfiguration.Package": "/home/Rory/git/spacebar/server-master/node_modules/prettier",
|
||||
"settings.editor.selected.configurable": "preferences.pluginManager",
|
||||
"ts.external.directory.path": "/home/Rory/git/spacebar/server-master/node_modules/typescript/lib"
|
||||
},
|
||||
"keyToStringList": {
|
||||
"GitStage.ChangesTree.GroupingKeys": [
|
||||
"directory",
|
||||
"module",
|
||||
"repository"
|
||||
"keyToStringList": {
|
||||
"GitStage.ChangesTree.GroupingKeys": [
|
||||
"directory",
|
||||
"module",
|
||||
"repository"
|
||||
]
|
||||
}
|
||||
}</component>
|
||||
}]]></component>
|
||||
<component name="RecentsManager">
|
||||
<key name="CopyFile.RECENT_KEYS">
|
||||
<recent name="$PROJECT_DIR$/src/util/migration/postgres" />
|
||||
<recent name="$PROJECT_DIR$/src/util/entities" />
|
||||
<recent name="$PROJECT_DIR$/src/schemas/api/guilds" />
|
||||
<recent name="$PROJECT_DIR$/src/schemas" />
|
||||
<recent name="$PROJECT_DIR$/src/schemas/api/users" />
|
||||
<recent name="$PROJECT_DIR$/src/schemas/api/messages" />
|
||||
<recent name="$PROJECT_DIR$/src/admin-api/routes/v0" />
|
||||
</key>
|
||||
<key name="MoveFile.RECENT_KEYS">
|
||||
<recent name="$PROJECT_DIR$/src/schemas/api/guilds" />
|
||||
@ -103,7 +103,7 @@
|
||||
</set>
|
||||
</option>
|
||||
</component>
|
||||
<component name="RunManager" selected="Compound.Start separated">
|
||||
<component name="RunManager" selected="npm.Start API">
|
||||
<list>
|
||||
<item itemvalue="Compound.Start separated" />
|
||||
<item itemvalue="npm.Start bundle" />
|
||||
|
||||
Binary file not shown.
Binary file not shown.
57
src/schemas/api/bots/ApplicationCommandSchema.ts
Normal file
57
src/schemas/api/bots/ApplicationCommandSchema.ts
Normal file
@ -0,0 +1,57 @@
|
||||
import { ApplicationCommandOption, Snowflake } from "@spacebar/schemas";
|
||||
|
||||
export interface ApplicationCommandSchema {
|
||||
id?: Snowflake;
|
||||
type?: ApplicationCommandType;
|
||||
application_id: Snowflake;
|
||||
guild_id?: Snowflake;
|
||||
name: string;
|
||||
name_localizations?: Record<string, string>;
|
||||
name_localized?: string | null;
|
||||
description: string;
|
||||
description_localizations?: Record<string, string>;
|
||||
description_localized?: string | null;
|
||||
options?: ApplicationCommandOption[];
|
||||
default_member_permissions: string | null;
|
||||
/*
|
||||
* @deprecated
|
||||
*/
|
||||
dm_permission?: boolean;
|
||||
permissions?: ApplicationCommandIndexPermissions;
|
||||
nsfw?: boolean;
|
||||
integration_types?: ApplicationIntegrationType[];
|
||||
global_popularity_rank?: number;
|
||||
contexts?: InteractionContextType[];
|
||||
version: Snowflake;
|
||||
handler?: ApplicationCommandHandlerType;
|
||||
}
|
||||
|
||||
export interface ApplicationCommandIndexPermissions {
|
||||
user?: boolean;
|
||||
roles?: Record<Snowflake, boolean>;
|
||||
channels?: Record<Snowflake, boolean>;
|
||||
}
|
||||
|
||||
export enum ApplicationCommandType {
|
||||
CHAT_INPUT = 1,
|
||||
USER = 2,
|
||||
MESSAGE = 3,
|
||||
PRIMARY_ENTRY_POINT = 4,
|
||||
}
|
||||
|
||||
export enum ApplicationCommandHandlerType {
|
||||
APP_HANDLER = 1,
|
||||
DISCORD_LAUNCH_ACTIVITY = 2,
|
||||
APP_HANDLER_LAUNCH_ACTIVITY = 3,
|
||||
}
|
||||
|
||||
export enum InteractionContextType {
|
||||
GUILD = 0,
|
||||
BOT_DM = 1,
|
||||
PRIVATE_CHANNEL = 2,
|
||||
}
|
||||
|
||||
export enum ApplicationIntegrationType {
|
||||
GUILD_INSTALL = 0,
|
||||
USER_INSTALL = 1,
|
||||
}
|
||||
18
src/schemas/api/bots/index.ts
Normal file
18
src/schemas/api/bots/index.ts
Normal file
@ -0,0 +1,18 @@
|
||||
/*
|
||||
Spacebar: A FOSS re-implementation and extension of the Discord.com backend.
|
||||
Copyright (C) 2025 Spacebar and Spacebar Contributors
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as published
|
||||
by the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
export * from "./ApplicationCommandSchema";
|
||||
@ -15,6 +15,7 @@
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
export * from "./bots";
|
||||
export * from "./channels";
|
||||
export * from "./developers";
|
||||
export * from "./guilds";
|
||||
|
||||
88
src/util/entities/ApplicationCommand.ts
Normal file
88
src/util/entities/ApplicationCommand.ts
Normal file
@ -0,0 +1,88 @@
|
||||
/*
|
||||
Spacebar: A FOSS re-implementation and extension of the Discord.com backend.
|
||||
Copyright (C) 2023 Spacebar and Spacebar Contributors
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as published
|
||||
by the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import { Column, Entity } from "typeorm";
|
||||
import { BaseClass } from "./BaseClass";
|
||||
import {
|
||||
ApplicationCommandHandlerType,
|
||||
ApplicationCommandOption,
|
||||
ApplicationCommandIndexPermissions,
|
||||
ApplicationCommandType,
|
||||
Snowflake,
|
||||
ApplicationIntegrationType,
|
||||
InteractionContextType,
|
||||
} from "@spacebar/schemas";
|
||||
|
||||
@Entity({
|
||||
name: "application_commands",
|
||||
})
|
||||
export class ApplicationCommand extends BaseClass {
|
||||
@Column({ default: ApplicationCommandType.CHAT_INPUT })
|
||||
type?: ApplicationCommandType;
|
||||
|
||||
@Column()
|
||||
application_id: Snowflake;
|
||||
|
||||
@Column({ nullable: true })
|
||||
guild_id?: Snowflake;
|
||||
|
||||
@Column()
|
||||
name: string;
|
||||
|
||||
@Column({ nullable: true, type: "simple-json" })
|
||||
name_localizations?: Record<string, string>;
|
||||
|
||||
@Column()
|
||||
description: string;
|
||||
|
||||
@Column({ nullable: true, type: "simple-json" })
|
||||
description_localizations?: Record<string, string>;
|
||||
|
||||
@Column({ nullable: true, type: "simple-json" })
|
||||
options?: ApplicationCommandOption[];
|
||||
|
||||
@Column({ nullable: true, type: String })
|
||||
default_member_permissions: string | null;
|
||||
|
||||
/*
|
||||
* @deprecated
|
||||
*/
|
||||
@Column({ default: true })
|
||||
dm_permission?: boolean;
|
||||
|
||||
@Column({ nullable: true, type: "simple-json" })
|
||||
permissions?: ApplicationCommandIndexPermissions;
|
||||
|
||||
@Column({ default: false })
|
||||
nsfw?: boolean;
|
||||
|
||||
@Column({ nullable: true, type: "simple-json" })
|
||||
integration_types?: ApplicationIntegrationType[];
|
||||
|
||||
@Column({ default: 0 })
|
||||
global_popularity_rank?: number;
|
||||
|
||||
@Column({ nullable: true, type: "simple-json" })
|
||||
contexts?: InteractionContextType[];
|
||||
|
||||
@Column({ default: 0 })
|
||||
version: Snowflake;
|
||||
|
||||
@Column({ default: 0 })
|
||||
handler?: ApplicationCommandHandlerType;
|
||||
}
|
||||
@ -17,6 +17,7 @@
|
||||
*/
|
||||
|
||||
export * from "./Application";
|
||||
export * from "./ApplicationCommand";
|
||||
export * from "./Attachment";
|
||||
export * from "./AuditLog";
|
||||
export * from "./AutomodRule";
|
||||
|
||||
@ -0,0 +1,14 @@
|
||||
import { MigrationInterface, QueryRunner } from "typeorm";
|
||||
|
||||
export class ApplicationCommands1760622755598 implements MigrationInterface {
|
||||
name = 'ApplicationCommands1760622755598'
|
||||
|
||||
public async up(queryRunner: QueryRunner): Promise<void> {
|
||||
await queryRunner.query(`CREATE TABLE "application_commands" ("id" character varying NOT NULL, "type" integer NOT NULL DEFAULT '1', "application_id" character varying NOT NULL, "guild_id" character varying, "name" character varying NOT NULL, "name_localizations" text, "description" character varying NOT NULL, "description_localizations" text, "options" text, "default_member_permissions" character varying, "dm_permission" boolean NOT NULL DEFAULT true, "permissions" text, "nsfw" boolean NOT NULL DEFAULT false, "integration_types" text, "global_popularity_rank" integer NOT NULL DEFAULT '0', "contexts" text, "version" character varying NOT NULL DEFAULT '0', "handler" integer NOT NULL DEFAULT '0', CONSTRAINT "PK_0f73c2f025989c407947e1f75fe" PRIMARY KEY ("id"))`);
|
||||
}
|
||||
|
||||
public async down(queryRunner: QueryRunner): Promise<void> {
|
||||
await queryRunner.query(`DROP TABLE "application_commands"`);
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,74 @@
|
||||
// import { MigrationInterface, QueryRunner } from "typeorm";
|
||||
//
|
||||
// export class ApplicationCommands1760622755598 implements MigrationInterface {
|
||||
// name = 'ApplicationCommands1760622755598'
|
||||
//
|
||||
// public async up(queryRunner: QueryRunner): Promise<void> {
|
||||
// await queryRunner.query(`ALTER TABLE "webhooks" DROP CONSTRAINT "fk_d64f38834fa676f6caa4786ddd6"`);
|
||||
// await queryRunner.query(`ALTER TABLE "webhooks" DROP COLUMN "source_channel_id"`);
|
||||
// await queryRunner.query(`ALTER TABLE "webhooks" ADD "source_channel_id" character varying`);
|
||||
// await queryRunner.query(`ALTER TABLE "messages" DROP COLUMN "username"`);
|
||||
// await queryRunner.query(`ALTER TABLE "messages" ADD "username" character varying`);
|
||||
// await queryRunner.query(`ALTER TABLE "messages" DROP COLUMN "avatar"`);
|
||||
// await queryRunner.query(`ALTER TABLE "messages" ADD "avatar" character varying`);
|
||||
// await queryRunner.query(`ALTER TABLE "channels" ALTER COLUMN "default_thread_rate_limit_per_user" DROP NOT NULL`);
|
||||
// await queryRunner.query(`ALTER TABLE "sessions" ALTER COLUMN "client_status" SET NOT NULL`);
|
||||
// await queryRunner.query(`ALTER TABLE "user_settings" ALTER COLUMN "friend_discovery_flags" DROP DEFAULT`);
|
||||
// await queryRunner.query(`ALTER TABLE "user_settings" ALTER COLUMN "view_nsfw_guilds" DROP DEFAULT`);
|
||||
// await queryRunner.query(`ALTER TABLE "users" DROP COLUMN "flags"`);
|
||||
// await queryRunner.query(`ALTER TABLE "users" ADD "flags" integer NOT NULL`);
|
||||
// await queryRunner.query(`ALTER TABLE "users" DROP COLUMN "public_flags"`);
|
||||
// await queryRunner.query(`ALTER TABLE "users" ADD "public_flags" integer NOT NULL`);
|
||||
// await queryRunner.query(`ALTER TABLE "users" DROP COLUMN "purchased_flags"`);
|
||||
// await queryRunner.query(`ALTER TABLE "users" ADD "purchased_flags" integer NOT NULL`);
|
||||
// await queryRunner.query(`ALTER TABLE "team_members" DROP COLUMN "role"`);
|
||||
// await queryRunner.query(`ALTER TABLE "team_members" ADD "role" character varying NOT NULL`);
|
||||
// await queryRunner.query(`ALTER TABLE "applications" DROP COLUMN "guild_id"`);
|
||||
// await queryRunner.query(`ALTER TABLE "applications" ADD "guild_id" character varying`);
|
||||
// await queryRunner.query(`ALTER TABLE "applications" DROP COLUMN "custom_install_url"`);
|
||||
// await queryRunner.query(`ALTER TABLE "applications" ADD "custom_install_url" character varying`);
|
||||
// await queryRunner.query(`ALTER TABLE "categories" DROP COLUMN "icon"`);
|
||||
// await queryRunner.query(`ALTER TABLE "categories" ADD "icon" character varying`);
|
||||
// await queryRunner.query(`ALTER TABLE "user_settings_protos" DROP COLUMN "userSettings"`);
|
||||
// await queryRunner.query(`ALTER TABLE "user_settings_protos" ADD "userSettings" character varying`);
|
||||
// await queryRunner.query(`ALTER TABLE "user_settings_protos" DROP COLUMN "frecencySettings"`);
|
||||
// await queryRunner.query(`ALTER TABLE "user_settings_protos" ADD "frecencySettings" character varying`);
|
||||
// await queryRunner.query(`ALTER TABLE "webhooks" ADD CONSTRAINT "FK_4495b7032a33c6b8b605d030398" FOREIGN KEY ("source_channel_id") REFERENCES "channels"("id") ON DELETE CASCADE ON UPDATE NO ACTION`);
|
||||
// await queryRunner.query(`ALTER TABLE "applications" ADD CONSTRAINT "FK_e5bf78cdbbe9ba91062d74c5aba" FOREIGN KEY ("guild_id") REFERENCES "guilds"("id") ON DELETE NO ACTION ON UPDATE NO ACTION`);
|
||||
// }
|
||||
//
|
||||
// public async down(queryRunner: QueryRunner): Promise<void> {
|
||||
// await queryRunner.query(`ALTER TABLE "applications" DROP CONSTRAINT "FK_e5bf78cdbbe9ba91062d74c5aba"`);
|
||||
// await queryRunner.query(`ALTER TABLE "webhooks" DROP CONSTRAINT "FK_4495b7032a33c6b8b605d030398"`);
|
||||
// await queryRunner.query(`ALTER TABLE "user_settings_protos" DROP COLUMN "frecencySettings"`);
|
||||
// await queryRunner.query(`ALTER TABLE "user_settings_protos" ADD "frecencySettings" text`);
|
||||
// await queryRunner.query(`ALTER TABLE "user_settings_protos" DROP COLUMN "userSettings"`);
|
||||
// await queryRunner.query(`ALTER TABLE "user_settings_protos" ADD "userSettings" text`);
|
||||
// await queryRunner.query(`ALTER TABLE "categories" DROP COLUMN "icon"`);
|
||||
// await queryRunner.query(`ALTER TABLE "categories" ADD "icon" text`);
|
||||
// await queryRunner.query(`ALTER TABLE "applications" DROP COLUMN "custom_install_url"`);
|
||||
// await queryRunner.query(`ALTER TABLE "applications" ADD "custom_install_url" text`);
|
||||
// await queryRunner.query(`ALTER TABLE "applications" DROP COLUMN "guild_id"`);
|
||||
// await queryRunner.query(`ALTER TABLE "applications" ADD "guild_id" text`);
|
||||
// await queryRunner.query(`ALTER TABLE "team_members" DROP COLUMN "role"`);
|
||||
// await queryRunner.query(`ALTER TABLE "team_members" ADD "role" text NOT NULL`);
|
||||
// await queryRunner.query(`ALTER TABLE "users" DROP COLUMN "purchased_flags"`);
|
||||
// await queryRunner.query(`ALTER TABLE "users" ADD "purchased_flags" bigint NOT NULL`);
|
||||
// await queryRunner.query(`ALTER TABLE "users" DROP COLUMN "public_flags"`);
|
||||
// await queryRunner.query(`ALTER TABLE "users" ADD "public_flags" bigint NOT NULL`);
|
||||
// await queryRunner.query(`ALTER TABLE "users" DROP COLUMN "flags"`);
|
||||
// await queryRunner.query(`ALTER TABLE "users" ADD "flags" bigint NOT NULL`);
|
||||
// await queryRunner.query(`ALTER TABLE "user_settings" ALTER COLUMN "view_nsfw_guilds" SET DEFAULT true`);
|
||||
// await queryRunner.query(`ALTER TABLE "user_settings" ALTER COLUMN "friend_discovery_flags" SET DEFAULT '0'`);
|
||||
// await queryRunner.query(`ALTER TABLE "sessions" ALTER COLUMN "client_status" DROP NOT NULL`);
|
||||
// await queryRunner.query(`ALTER TABLE "channels" ALTER COLUMN "default_thread_rate_limit_per_user" SET NOT NULL`);
|
||||
// await queryRunner.query(`ALTER TABLE "messages" DROP COLUMN "avatar"`);
|
||||
// await queryRunner.query(`ALTER TABLE "messages" ADD "avatar" text`);
|
||||
// await queryRunner.query(`ALTER TABLE "messages" DROP COLUMN "username"`);
|
||||
// await queryRunner.query(`ALTER TABLE "messages" ADD "username" text`);
|
||||
// await queryRunner.query(`ALTER TABLE "webhooks" DROP COLUMN "source_channel_id"`);
|
||||
// await queryRunner.query(`ALTER TABLE "webhooks" ADD "source_channel_id" character varying(255) DEFAULT NULL`);
|
||||
// await queryRunner.query(`ALTER TABLE "webhooks" ADD CONSTRAINT "fk_d64f38834fa676f6caa4786ddd6" FOREIGN KEY ("source_channel_id") REFERENCES "channels"("id") ON DELETE CASCADE ON UPDATE NO ACTION`);
|
||||
// }
|
||||
//
|
||||
// }
|
||||
Reference in New Issue
Block a user