From f691aa4c5aa47c8a8085c7b01912a1c403ce8732 Mon Sep 17 00:00:00 2001 From: Flam3rboy <34555296+Flam3rboy@users.noreply.github.com> Date: Tue, 14 Sep 2021 22:15:55 +0200 Subject: :construction: webhook --- util/src/entities/Webhook.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'util/src/entities/Webhook.ts') diff --git a/util/src/entities/Webhook.ts b/util/src/entities/Webhook.ts index 12ba0d08..d0d98804 100644 --- a/util/src/entities/Webhook.ts +++ b/util/src/entities/Webhook.ts @@ -18,13 +18,13 @@ export class Webhook extends BaseClass { @Column({ type: "simple-enum", enum: WebhookType }) type: WebhookType; - @Column({ nullable: true }) - name?: string; + @Column() + name: string; @Column({ nullable: true }) avatar?: string; - @Column({ nullable: true }) + @Column({ nullable: true, select: false }) token?: string; @Column({ nullable: true }) -- cgit 1.5.1 From 1cd4b819171f9bbadb00b2e87d1a710ead355f95 Mon Sep 17 00:00:00 2001 From: Flam3rboy <34555296+Flam3rboy@users.noreply.github.com> Date: Thu, 16 Sep 2021 20:49:07 +0200 Subject: Revert ":construction: webhook" This reverts commit f691aa4c5aa47c8a8085c7b01912a1c403ce8732. --- api/assets/schemas.json | 255 +----------------------- api/client_test/index.html | 2 +- api/src/middlewares/Authentication.ts | 4 +- api/src/middlewares/ErrorHandler.ts | 7 +- api/src/routes/discoverable-guilds.ts | 2 +- api/src/routes/guilds/#guild_id/integrations.ts | 10 - api/src/routes/template.ts.disabled | 2 +- api/src/routes/webhooks/#webhook_id/index.ts | 89 --------- api/src/util/route.ts | 8 +- util/src/entities/Webhook.ts | 6 +- util/src/util/Regex.ts | 2 +- 11 files changed, 18 insertions(+), 369 deletions(-) delete mode 100644 api/src/routes/guilds/#guild_id/integrations.ts delete mode 100644 api/src/routes/webhooks/#webhook_id/index.ts (limited to 'util/src/entities/Webhook.ts') diff --git a/api/assets/schemas.json b/api/assets/schemas.json index 88558cfa..9c34f968 100644 --- a/api/assets/schemas.json +++ b/api/assets/schemas.json @@ -1770,6 +1770,10 @@ } }, "additionalProperties": false, + "required": [ + "avatar", + "name" + ], "definitions": { "ChannelType": { "enum": [ @@ -7442,256 +7446,5 @@ } }, "$schema": "http://json-schema.org/draft-07/schema#" - }, - "WebhookModifySchema": { - "type": "object", - "properties": { - "name": { - "type": "string" - }, - "avatar": { - "type": "string" - } - }, - "additionalProperties": false, - "definitions": { - "ChannelType": { - "enum": [ - 0, - 1, - 10, - 11, - 12, - 13, - 2, - 3, - 4, - 5, - 6 - ], - "type": "number" - }, - "ChannelPermissionOverwriteType": { - "enum": [ - 0, - 1 - ], - "type": "number" - }, - "Embed": { - "type": "object", - "properties": { - "title": { - "type": "string" - }, - "type": { - "enum": [ - "article", - "gifv", - "image", - "link", - "rich", - "video" - ], - "type": "string" - }, - "description": { - "type": "string" - }, - "url": { - "type": "string" - }, - "timestamp": { - "type": "string", - "format": "date-time" - }, - "color": { - "type": "integer" - }, - "footer": { - "type": "object", - "properties": { - "text": { - "type": "string" - }, - "icon_url": { - "type": "string" - }, - "proxy_icon_url": { - "type": "string" - } - }, - "additionalProperties": false, - "required": [ - "text" - ] - }, - "image": { - "$ref": "#/definitions/EmbedImage" - }, - "thumbnail": { - "$ref": "#/definitions/EmbedImage" - }, - "video": { - "$ref": "#/definitions/EmbedImage" - }, - "provider": { - "type": "object", - "properties": { - "name": { - "type": "string" - }, - "url": { - "type": "string" - } - }, - "additionalProperties": false - }, - "author": { - "type": "object", - "properties": { - "name": { - "type": "string" - }, - "url": { - "type": "string" - }, - "icon_url": { - "type": "string" - }, - "proxy_icon_url": { - "type": "string" - } - }, - "additionalProperties": false - }, - "fields": { - "type": "array", - "items": { - "type": "object", - "properties": { - "name": { - "type": "string" - }, - "value": { - "type": "string" - }, - "inline": { - "type": "boolean" - } - }, - "additionalProperties": false, - "required": [ - "name", - "value" - ] - } - } - }, - "additionalProperties": false - }, - "EmbedImage": { - "type": "object", - "properties": { - "url": { - "type": "string" - }, - "proxy_url": { - "type": "string" - }, - "height": { - "type": "integer" - }, - "width": { - "type": "integer" - } - }, - "additionalProperties": false - }, - "ChannelModifySchema": { - "type": "object", - "properties": { - "name": { - "maxLength": 100, - "type": "string" - }, - "type": { - "$ref": "#/definitions/ChannelType" - }, - "topic": { - "type": "string" - }, - "bitrate": { - "type": "integer" - }, - "user_limit": { - "type": "integer" - }, - "rate_limit_per_user": { - "type": "integer" - }, - "position": { - "type": "integer" - }, - "permission_overwrites": { - "type": "array", - "items": { - "type": "object", - "properties": { - "id": { - "type": "string" - }, - "type": { - "$ref": "#/definitions/ChannelPermissionOverwriteType" - }, - "allow": { - "type": "bigint" - }, - "deny": { - "type": "bigint" - } - }, - "additionalProperties": false, - "required": [ - "allow", - "deny", - "id", - "type" - ] - } - }, - "parent_id": { - "type": "string" - }, - "id": { - "type": "string" - }, - "nsfw": { - "type": "boolean" - }, - "rtc_region": { - "type": "string" - }, - "default_auto_archive_duration": { - "type": "integer" - } - }, - "additionalProperties": false, - "required": [ - "name", - "type" - ] - }, - "RelationshipType": { - "enum": [ - 1, - 2, - 3, - 4 - ], - "type": "number" - } - }, - "$schema": "http://json-schema.org/draft-07/schema#" } } \ No newline at end of file diff --git a/api/client_test/index.html b/api/client_test/index.html index 335b477c..ac66df06 100644 --- a/api/client_test/index.html +++ b/api/client_test/index.html @@ -11,7 +11,7 @@ window.__OVERLAY__ = /overlay/.test(location.pathname); window.__BILLING_STANDALONE__ = /^\/billing/.test(location.pathname); window.GLOBAL_ENV = { - API_ENDPOINT: `//${location.host}/api`, + API_ENDPOINT: "/api", API_VERSION: 9, GATEWAY_ENDPOINT: `${location.protocol === "https:" ? "wss://" : "ws://"}${location.hostname}:3002`, WEBAPP_ENDPOINT: "", diff --git a/api/src/middlewares/Authentication.ts b/api/src/middlewares/Authentication.ts index 32307f42..a300c786 100644 --- a/api/src/middlewares/Authentication.ts +++ b/api/src/middlewares/Authentication.ts @@ -5,11 +5,11 @@ import { checkToken, Config } from "@fosscord/util"; export const NO_AUTHORIZATION_ROUTES = [ "/auth/login", "/auth/register", + "/webhooks/", "/ping", "/gateway", "/experiments", - /\/guilds\/\d+\/widget\.(json|png)/, - /\/webhooks\/\d+\/\w+/ // only exclude webhook calls with webhook token + /\/guilds\/\d+\/widget\.(json|png)/ ]; export const API_PREFIX = /^\/api(\/v\d+)?/; diff --git a/api/src/middlewares/ErrorHandler.ts b/api/src/middlewares/ErrorHandler.ts index 338da8d5..d288f3fb 100644 --- a/api/src/middlewares/ErrorHandler.ts +++ b/api/src/middlewares/ErrorHandler.ts @@ -1,10 +1,9 @@ import { NextFunction, Request, Response } from "express"; import { HTTPError } from "lambert-server"; +import { EntityNotFoundError } from "typeorm"; import { FieldError } from "@fosscord/api"; import { ApiError } from "@fosscord/util"; -const EntityNotFoundErrorRegex = /"(\w+)"/; - export function ErrorHandler(error: Error, req: Request, res: Response, next: NextFunction) { if (!error) return next(); @@ -19,8 +18,8 @@ export function ErrorHandler(error: Error, req: Request, res: Response, next: Ne code = error.code; message = error.message; httpcode = error.httpStatus; - } else if (error.name === "EntityNotFoundError") { - message = `${error.message.match(EntityNotFoundErrorRegex)?.[1] || "Item"} could not be found`; + } else if (error instanceof EntityNotFoundError) { + message = `${(error as any).stringifyTarget || "Item"} could not be found`; code = 404; } else if (error instanceof FieldError) { code = Number(error.code); diff --git a/api/src/routes/discoverable-guilds.ts b/api/src/routes/discoverable-guilds.ts index 71789123..f667eb2a 100644 --- a/api/src/routes/discoverable-guilds.ts +++ b/api/src/routes/discoverable-guilds.ts @@ -10,7 +10,7 @@ router.get("/", route({}), async (req: Request, res: Response) => { // ! this only works using SQL querys // TODO: implement this with default typeorm query // const guilds = await Guild.find({ where: { features: "DISCOVERABLE" } }); //, take: Math.abs(Number(limit)) }); - const guilds = await Guild.find({ where: `"features" LIKE 'COMMUNITY'`, take: Math.abs(Number(limit) || 50) }); + const guilds = await Guild.find({ where: `"features" LIKE 'COMMUNITY'`, take: Math.abs(Number(limit)) }); res.send({ guilds: guilds }); }); diff --git a/api/src/routes/guilds/#guild_id/integrations.ts b/api/src/routes/guilds/#guild_id/integrations.ts deleted file mode 100644 index f6b8e99d..00000000 --- a/api/src/routes/guilds/#guild_id/integrations.ts +++ /dev/null @@ -1,10 +0,0 @@ -import { route } from "@fosscord/api"; -import { Router, Request, Response } from "express"; -const router = Router(); - -router.get("/", route({ permission: "MANAGE_GUILD" }), async (req: Request, res: Response) => { - // TODO: integrations (followed channels, youtube, twitch) - res.send([]); -}); - -export default router; diff --git a/api/src/routes/template.ts.disabled b/api/src/routes/template.ts.disabled index 524e981b..ad785f10 100644 --- a/api/src/routes/template.ts.disabled +++ b/api/src/routes/template.ts.disabled @@ -4,7 +4,7 @@ import { Router, Request, Response } from "express"; const router = Router(); router.get("/", async (req: Request, res: Response) => { - res.json({}); + res.send({}); }); export default router; diff --git a/api/src/routes/webhooks/#webhook_id/index.ts b/api/src/routes/webhooks/#webhook_id/index.ts deleted file mode 100644 index e9b40ebf..00000000 --- a/api/src/routes/webhooks/#webhook_id/index.ts +++ /dev/null @@ -1,89 +0,0 @@ -import { Channel, Config, emitEvent, JWTOptions, Webhook, WebhooksUpdateEvent } from "@fosscord/util"; -import { route, Authentication, handleFile } from "@fosscord/api"; -import { Router, Request, Response, NextFunction } from "express"; -import jwt from "jsonwebtoken"; -import { HTTPError } from "lambert-server"; -const router = Router(); - -export interface WebhookModifySchema { - name?: string; - avatar?: string; - // channel_id?: string; // TODO -} - -function validateWebhookToken(req: Request, res: Response, next: NextFunction) { - const { jwtSecret } = Config.get().security; - - jwt.verify(req.params.token, jwtSecret, JWTOptions, async (err, decoded: any) => { - if (err) return next(new HTTPError("Invalid Token", 401)); - next(); - }); -} - -router.get("/", route({}), async (req: Request, res: Response) => { - res.json(await Webhook.findOneOrFail({ id: req.params.webhook_id })); -}); - -router.get("/:token", route({}), validateWebhookToken, async (req: Request, res: Response) => { - res.json(await Webhook.findOneOrFail({ id: req.params.webhook_id })); -}); - -router.patch("/", route({ body: "WebhookModifySchema", permission: "MANAGE_WEBHOOKS" }), (req: Request, res: Response) => { - return updateWebhook(req, res); -}); - -router.patch("/:token", route({ body: "WebhookModifySchema" }), validateWebhookToken, (req: Request, res: Response) => { - return updateWebhook(req, res); -}); - -async function updateWebhook(req: Request, res: Response) { - const webhook = await Webhook.findOneOrFail({ id: req.params.webhook_id }); - if (req.body.channel_id) await Channel.findOneOrFail({ id: req.body.channel_id, guild_id: webhook.guild_id }); - - webhook.assign({ - ...req.body, - avatar: await handleFile(`/icons/${req.params.webhook_id}`, req.body.avatar) - }); - - await Promise.all([ - emitEvent({ - event: "WEBHOOKS_UPDATE", - channel_id: webhook.channel_id, - data: { - channel_id: webhook.channel_id, - guild_id: webhook.guild_id - } - } as WebhooksUpdateEvent), - webhook.save() - ]); - - res.json(webhook); -} - -router.delete("/", route({ permission: "MANAGE_WEBHOOKS" }), async (req: Request, res: Response) => { - return deleteWebhook(req, res); -}); - -router.delete("/:token", route({}), validateWebhookToken, (req: Request, res: Response) => { - return deleteWebhook(req, res); -}); - -async function deleteWebhook(req: Request, res: Response) { - const webhook = await Webhook.findOneOrFail({ id: req.params.webhook_id }); - - await Promise.all([ - emitEvent({ - event: "WEBHOOKS_UPDATE", - channel_id: webhook.channel_id, - data: { - channel_id: webhook.channel_id, - guild_id: webhook.guild_id - } - } as WebhooksUpdateEvent), - webhook.remove() - ]); - - res.sendStatus(204); -} - -export default router; diff --git a/api/src/util/route.ts b/api/src/util/route.ts index 1e2beb5d..6cd8f622 100644 --- a/api/src/util/route.ts +++ b/api/src/util/route.ts @@ -1,4 +1,4 @@ -import { DiscordApiErrors, Event, EventData, getPermission, PermissionResolvable, Permissions, Webhook } from "@fosscord/util"; +import { DiscordApiErrors, Event, EventData, getPermission, PermissionResolvable, Permissions } from "@fosscord/util"; import { NextFunction, Request, Response } from "express"; import fs from "fs"; import path from "path"; @@ -54,13 +54,9 @@ export function route(opts: RouteOptions) { return async (req: Request, res: Response, next: NextFunction) => { if (opts.permission) { const required = new Permissions(opts.permission); - if (req.params.webhook_id) { - const webhook = await Webhook.findOneOrFail({ id: req.params.webhook_id }); - req.params.channel_id = webhook.channel_id; - req.params.guild_id = webhook.guild_id; - } const permission = await getPermission(req.user_id, req.params.guild_id, req.params.channel_id); + // bitfield comparison: check if user lacks certain permission if (!permission.has(required)) { throw DiscordApiErrors.MISSING_PERMISSIONS.withParams(opts.permission as string); } diff --git a/util/src/entities/Webhook.ts b/util/src/entities/Webhook.ts index d0d98804..12ba0d08 100644 --- a/util/src/entities/Webhook.ts +++ b/util/src/entities/Webhook.ts @@ -18,13 +18,13 @@ export class Webhook extends BaseClass { @Column({ type: "simple-enum", enum: WebhookType }) type: WebhookType; - @Column() - name: string; + @Column({ nullable: true }) + name?: string; @Column({ nullable: true }) avatar?: string; - @Column({ nullable: true, select: false }) + @Column({ nullable: true }) token?: string; @Column({ nullable: true }) diff --git a/util/src/util/Regex.ts b/util/src/util/Regex.ts index b5d23b7f..83fc9fe8 100644 --- a/util/src/util/Regex.ts +++ b/util/src/util/Regex.ts @@ -1,5 +1,5 @@ export const DOUBLE_WHITE_SPACE = /\s\s+/g; -export const SPECIAL_CHAR = /[@#\r\n\t\f\v]/gu; +export const SPECIAL_CHAR = /[@#`:\r\n\t\f\v\p{C}]/gu; export const CHANNEL_MENTION = /<#(\d+)>/g; export const USER_MENTION = /<@!?(\d+)>/g; export const ROLE_MENTION = /<@&(\d+)>/g; -- cgit 1.5.1 From 576cbf5794b2e146892d7080b699882c2ba6ec6a Mon Sep 17 00:00:00 2001 From: Flam3rboy <34555296+Flam3rboy@users.noreply.github.com> Date: Mon, 20 Sep 2021 20:22:56 +0200 Subject: :bug: fix .delete -> add onDelete: "CASCADE" --- api/src/routes/guilds/#guild_id/delete.ts | 12 +---- util/src/entities/Application.ts | 4 +- util/src/entities/Attachment.ts | 4 +- util/src/entities/Ban.ts | 8 +++- util/src/entities/BaseClass.ts | 74 +++++++++++++++---------------- util/src/entities/Channel.ts | 10 ++--- util/src/entities/ConnectedAccount.ts | 4 +- util/src/entities/Emoji.ts | 4 +- util/src/entities/Guild.ts | 2 - util/src/entities/Invite.ts | 12 +++-- util/src/entities/Member.ts | 9 ++-- util/src/entities/Message.ts | 13 ++++-- util/src/entities/ReadState.ts | 8 +++- util/src/entities/Recipient.ts | 8 +++- util/src/entities/Relationship.ts | 8 +++- util/src/entities/Role.ts | 4 +- util/src/entities/Session.ts | 4 +- util/src/entities/Sticker.ts | 4 +- util/src/entities/Team.ts | 4 +- util/src/entities/TeamMember.ts | 8 +++- util/src/entities/User.ts | 10 ++++- util/src/entities/VoiceState.ts | 16 +++++-- util/src/entities/Webhook.ts | 20 ++++++--- 23 files changed, 153 insertions(+), 97 deletions(-) (limited to 'util/src/entities/Webhook.ts') diff --git a/api/src/routes/guilds/#guild_id/delete.ts b/api/src/routes/guilds/#guild_id/delete.ts index 7c3c5530..bd158c56 100644 --- a/api/src/routes/guilds/#guild_id/delete.ts +++ b/api/src/routes/guilds/#guild_id/delete.ts @@ -13,15 +13,8 @@ router.post("/", route({}), async (req: Request, res: Response) => { const guild = await Guild.findOneOrFail({ where: { id: guild_id }, select: ["owner_id"] }); if (guild.owner_id !== req.user_id) throw new HTTPError("You are not the owner of this guild", 401); - // do not put everything into promise all, because of "QueryFailedError: SQLITE_CONSTRAINT: FOREIGN KEY constraint failed" - - await Message.delete({ guild_id }); // messages must be deleted before channel - await Promise.all([ - Role.delete({ guild_id }), - Channel.delete({ guild_id }), - Emoji.delete({ guild_id }), - Member.delete({ guild_id }), + Guild.delete({ id: guild_id }), // this will also delete all guild related data emitEvent({ event: "GUILD_DELETE", data: { @@ -31,9 +24,6 @@ router.post("/", route({}), async (req: Request, res: Response) => { } as GuildDeleteEvent) ]); - await Invite.delete({ guild_id }); // invite must be deleted after channel - await Guild.delete({ id: guild_id }); // guild must be deleted after everything else - return res.sendStatus(204); }); diff --git a/util/src/entities/Application.ts b/util/src/entities/Application.ts index 2092cd4e..fab3d93f 100644 --- a/util/src/entities/Application.ts +++ b/util/src/entities/Application.ts @@ -41,7 +41,9 @@ export class Application extends BaseClass { verify_key: string; @JoinColumn({ name: "team_id" }) - @ManyToOne(() => Team) + @ManyToOne(() => Team, { + onDelete: "CASCADE", + }) team?: Team; @JoinColumn({ name: "guild_id" }) diff --git a/util/src/entities/Attachment.ts b/util/src/entities/Attachment.ts index 82c5ecf5..7b4b17eb 100644 --- a/util/src/entities/Attachment.ts +++ b/util/src/entities/Attachment.ts @@ -31,7 +31,9 @@ export class Attachment extends BaseClass { message_id: string; @JoinColumn({ name: "message_id" }) - @ManyToOne(() => require("./Message").Message, (message: import("./Message").Message) => message.attachments) + @ManyToOne(() => require("./Message").Message, (message: import("./Message").Message) => message.attachments, { + onDelete: "CASCADE", + }) message: import("./Message").Message; @BeforeRemove() diff --git a/util/src/entities/Ban.ts b/util/src/entities/Ban.ts index e8a6d648..9504bd8e 100644 --- a/util/src/entities/Ban.ts +++ b/util/src/entities/Ban.ts @@ -10,7 +10,9 @@ export class Ban extends BaseClass { user_id: string; @JoinColumn({ name: "user_id" }) - @ManyToOne(() => User) + @ManyToOne(() => User, { + onDelete: "CASCADE", + }) user: User; @Column({ nullable: true }) @@ -18,7 +20,9 @@ export class Ban extends BaseClass { guild_id: string; @JoinColumn({ name: "guild_id" }) - @ManyToOne(() => Guild) + @ManyToOne(() => Guild, { + onDelete: "CASCADE", + }) guild: Guild; @Column({ nullable: true }) diff --git a/util/src/entities/BaseClass.ts b/util/src/entities/BaseClass.ts index 8a0b7a26..d18757f2 100644 --- a/util/src/entities/BaseClass.ts +++ b/util/src/entities/BaseClass.ts @@ -6,6 +6,7 @@ import { EntityMetadata, FindConditions, getConnection, + getManager, PrimaryColumn, RemoveOptions, } from "typeorm"; @@ -79,44 +80,41 @@ export class BaseClassWithoutId extends BaseEntity { return repository.decrement(conditions, propertyPath, value); } - static async delete(criteria: FindConditions, options?: RemoveOptions) { - if (!criteria) throw new Error("You need to specify delete criteria"); - - const repository = this.getRepository(); - const promises = repository.metadata.relations.map(async (x) => { - if (x.orphanedRowAction !== "delete") return; - if (typeof x.type === "string") return; - - const foreignKey = - x.foreignKeys.find((key) => key.entityMetadata === repository.metadata) || - x.inverseRelation?.foreignKeys[0]; // find foreign key for this entity - if (!foreignKey) { - throw new Error( - `Foreign key not found for entity ${repository.metadata.name} in relation ${x.propertyName}` - ); - } - const id = (criteria as any)[foreignKey.referencedColumnNames[0]]; - if (!id) throw new Error("id missing in criteria options"); - - if (x.relationType === "many-to-many") { - return getConnection() - .createQueryBuilder() - .relation(this, x.propertyName) - .of(id) - .remove({ [foreignKey.columnNames[0]]: id }); - } else if ( - x.relationType === "one-to-one" || - x.relationType === "many-to-one" || - x.relationType === "one-to-many" - ) { - return getConnection() - .getRepository(x.inverseEntityMetadata.target) - .delete({ [foreignKey.columnNames[0]]: id }); - } - }); - await Promise.all(promises); - return super.delete(criteria, options); - } + // static async delete(criteria: FindConditions, options?: RemoveOptions) { + // if (!criteria) throw new Error("You need to specify delete criteria"); + + // const repository = this.getRepository(); + // const promises = repository.metadata.relations.map(async (x) => { + // if (x.orphanedRowAction !== "delete") return; + + // const foreignKey = + // x.foreignKeys.find((key) => key.entityMetadata === repository.metadata) || + // x.inverseRelation?.foreignKeys[0]; // find foreign key for this entity + // if (!foreignKey) { + // throw new Error( + // `Foreign key not found for entity ${repository.metadata.name} in relation ${x.propertyName}` + // ); + // } + // const id = (criteria as any)[foreignKey.referencedColumnNames[0]]; + // if (!id) throw new Error("id missing in criteria options " + foreignKey.referencedColumnNames); + + // if (x.relationType === "many-to-many") { + // return getConnection() + // .createQueryBuilder() + // .relation(this, x.propertyName) + // .of(id) + // .remove({ [foreignKey.columnNames[0]]: id }); + // } else if ( + // x.relationType === "one-to-one" || + // x.relationType === "many-to-one" || + // x.relationType === "one-to-many" + // ) { + // return (x.inverseEntityMetadata.target as any).delete({ [foreignKey.columnNames[0]]: id }); + // } + // }); + // await Promise.all(promises); + // return super.delete(criteria, options); + // } } export class BaseClass extends BaseClassWithoutId { diff --git a/util/src/entities/Channel.ts b/util/src/entities/Channel.ts index 74611eea..ece82bd0 100644 --- a/util/src/entities/Channel.ts +++ b/util/src/entities/Channel.ts @@ -45,7 +45,6 @@ export class Channel extends BaseClass { @OneToMany(() => Recipient, (recipient: Recipient) => recipient.channel, { cascade: true, orphanedRowAction: "delete", - onDelete: "CASCADE", }) recipients?: Recipient[]; @@ -57,7 +56,9 @@ export class Channel extends BaseClass { guild_id?: string; @JoinColumn({ name: "guild_id" }) - @ManyToOne(() => Guild) + @ManyToOne(() => Guild, { + onDelete: "CASCADE", + }) guild: Guild; @Column({ nullable: true }) @@ -110,35 +111,30 @@ export class Channel extends BaseClass { @OneToMany(() => Invite, (invite: Invite) => invite.channel, { cascade: true, orphanedRowAction: "delete", - onDelete: "CASCADE", }) invites?: Invite[]; @OneToMany(() => Message, (message: Message) => message.channel, { cascade: true, orphanedRowAction: "delete", - onDelete: "CASCADE", }) messages?: Message[]; @OneToMany(() => VoiceState, (voice_state: VoiceState) => voice_state.channel, { cascade: true, orphanedRowAction: "delete", - onDelete: "CASCADE", }) voice_states?: VoiceState[]; @OneToMany(() => ReadState, (read_state: ReadState) => read_state.channel, { cascade: true, orphanedRowAction: "delete", - onDelete: "CASCADE", }) read_states?: ReadState[]; @OneToMany(() => Webhook, (webhook: Webhook) => webhook.channel, { cascade: true, orphanedRowAction: "delete", - onDelete: "CASCADE", }) webhooks?: Webhook[]; diff --git a/util/src/entities/ConnectedAccount.ts b/util/src/entities/ConnectedAccount.ts index 59a8f423..b8aa2889 100644 --- a/util/src/entities/ConnectedAccount.ts +++ b/util/src/entities/ConnectedAccount.ts @@ -11,7 +11,9 @@ export class ConnectedAccount extends BaseClass { user_id: string; @JoinColumn({ name: "user_id" }) - @ManyToOne(() => User) + @ManyToOne(() => User, { + onDelete: "CASCADE", + }) user: User; @Column({ select: false }) diff --git a/util/src/entities/Emoji.ts b/util/src/entities/Emoji.ts index 181aff2c..a252d9f4 100644 --- a/util/src/entities/Emoji.ts +++ b/util/src/entities/Emoji.ts @@ -15,7 +15,9 @@ export class Emoji extends BaseClass { guild_id: string; @JoinColumn({ name: "guild_id" }) - @ManyToOne(() => Guild) + @ManyToOne(() => Guild, { + onDelete: "CASCADE", + }) guild: Guild; @Column() diff --git a/util/src/entities/Guild.ts b/util/src/entities/Guild.ts index d46d2161..e107937d 100644 --- a/util/src/entities/Guild.ts +++ b/util/src/entities/Guild.ts @@ -84,7 +84,6 @@ export class Guild extends BaseClass { @OneToMany(() => Ban, (ban: Ban) => ban.guild, { cascade: true, orphanedRowAction: "delete", - onDelete: "CASCADE", }) bans: Ban[]; @@ -147,7 +146,6 @@ export class Guild extends BaseClass { @OneToMany(() => Channel, (channel: Channel) => channel.guild, { cascade: true, orphanedRowAction: "delete", - onDelete: "CASCADE", }) channels: Channel[]; diff --git a/util/src/entities/Invite.ts b/util/src/entities/Invite.ts index afad9c02..cb308823 100644 --- a/util/src/entities/Invite.ts +++ b/util/src/entities/Invite.ts @@ -34,7 +34,9 @@ export class Invite extends BaseClass { guild_id: string; @JoinColumn({ name: "guild_id" }) - @ManyToOne(() => Guild) + @ManyToOne(() => Guild, { + onDelete: "CASCADE", + }) guild: Guild; @Column({ nullable: true }) @@ -42,7 +44,9 @@ export class Invite extends BaseClass { channel_id: string; @JoinColumn({ name: "channel_id" }) - @ManyToOne(() => Channel) + @ManyToOne(() => Channel, { + onDelete: "CASCADE", + }) channel: Channel; @Column({ nullable: true }) @@ -58,7 +62,9 @@ export class Invite extends BaseClass { target_user_id: string; @JoinColumn({ name: "target_user_id" }) - @ManyToOne(() => User) + @ManyToOne(() => User, { + onDelete: "CASCADE", + }) target_user?: string; // could be used for "User specific invites" https://github.com/fosscord/fosscord/issues/62 @Column({ nullable: true }) diff --git a/util/src/entities/Member.ts b/util/src/entities/Member.ts index 66f5d9a1..feb9c069 100644 --- a/util/src/entities/Member.ts +++ b/util/src/entities/Member.ts @@ -39,7 +39,9 @@ export class Member extends BaseClassWithoutId { id: string; @JoinColumn({ name: "id" }) - @ManyToOne(() => User) + @ManyToOne(() => User, { + onDelete: "CASCADE", + }) user: User; @Column() @@ -47,7 +49,9 @@ export class Member extends BaseClassWithoutId { guild_id: string; @JoinColumn({ name: "guild_id" }) - @ManyToOne(() => Guild) + @ManyToOne(() => Guild, { + onDelete: "CASCADE", + }) guild: Guild; @Column({ nullable: true }) @@ -55,7 +59,6 @@ export class Member extends BaseClassWithoutId { @JoinTable({ name: "member_roles", - joinColumn: { name: "index", referencedColumnName: "index" }, inverseJoinColumn: { name: "role_id", diff --git a/util/src/entities/Message.ts b/util/src/entities/Message.ts index 0712f545..c4901693 100644 --- a/util/src/entities/Message.ts +++ b/util/src/entities/Message.ts @@ -54,7 +54,9 @@ export class Message extends BaseClass { channel_id: string; @JoinColumn({ name: "channel_id" }) - @ManyToOne(() => Channel) + @ManyToOne(() => Channel, { + onDelete: "CASCADE", + }) channel: Channel; @Column({ nullable: true }) @@ -62,7 +64,9 @@ export class Message extends BaseClass { guild_id?: string; @JoinColumn({ name: "guild_id" }) - @ManyToOne(() => Guild) + @ManyToOne(() => Guild, { + onDelete: "CASCADE", + }) guild?: Guild; @Column({ nullable: true }) @@ -70,7 +74,9 @@ export class Message extends BaseClass { author_id: string; @JoinColumn({ name: "author_id", referencedColumnName: "id" }) - @ManyToOne(() => User) + @ManyToOne(() => User, { + onDelete: "CASCADE", + }) author?: User; @Column({ nullable: true }) @@ -132,7 +138,6 @@ export class Message extends BaseClass { @OneToMany(() => Attachment, (attachment: Attachment) => attachment.message, { cascade: true, orphanedRowAction: "delete", - onDelete: "CASCADE", }) attachments?: Attachment[]; diff --git a/util/src/entities/ReadState.ts b/util/src/entities/ReadState.ts index 8dd05b21..68e867a0 100644 --- a/util/src/entities/ReadState.ts +++ b/util/src/entities/ReadState.ts @@ -15,7 +15,9 @@ export class ReadState extends BaseClass { channel_id: string; @JoinColumn({ name: "channel_id" }) - @ManyToOne(() => Channel) + @ManyToOne(() => Channel, { + onDelete: "CASCADE", + }) channel: Channel; @Column({ nullable: true }) @@ -23,7 +25,9 @@ export class ReadState extends BaseClass { user_id: string; @JoinColumn({ name: "user_id" }) - @ManyToOne(() => User) + @ManyToOne(() => User, { + onDelete: "CASCADE", + }) user: User; @Column({ nullable: true }) diff --git a/util/src/entities/Recipient.ts b/util/src/entities/Recipient.ts index bb280588..a945f938 100644 --- a/util/src/entities/Recipient.ts +++ b/util/src/entities/Recipient.ts @@ -8,7 +8,9 @@ export class Recipient extends BaseClass { channel_id: string; @JoinColumn({ name: "channel_id" }) - @ManyToOne(() => require("./Channel").Channel) + @ManyToOne(() => require("./Channel").Channel, { + onDelete: "CASCADE", + }) channel: import("./Channel").Channel; @Column() @@ -16,7 +18,9 @@ export class Recipient extends BaseClass { user_id: string; @JoinColumn({ name: "user_id" }) - @ManyToOne(() => require("./User").User) + @ManyToOne(() => require("./User").User, { + onDelete: "CASCADE", + }) user: import("./User").User; @Column({ default: false }) diff --git a/util/src/entities/Relationship.ts b/util/src/entities/Relationship.ts index 61b3ac82..e016b36b 100644 --- a/util/src/entities/Relationship.ts +++ b/util/src/entities/Relationship.ts @@ -17,7 +17,9 @@ export class Relationship extends BaseClass { from_id: string; @JoinColumn({ name: "from_id" }) - @ManyToOne(() => User) + @ManyToOne(() => User, { + onDelete: "CASCADE", + }) from: User; @Column({}) @@ -25,7 +27,9 @@ export class Relationship extends BaseClass { to_id: string; @JoinColumn({ name: "to_id" }) - @ManyToOne(() => User) + @ManyToOne(() => User, { + onDelete: "CASCADE", + }) to: User; @Column({ nullable: true }) diff --git a/util/src/entities/Role.ts b/util/src/entities/Role.ts index 33c8d272..9fca99a5 100644 --- a/util/src/entities/Role.ts +++ b/util/src/entities/Role.ts @@ -10,7 +10,9 @@ export class Role extends BaseClass { guild_id: string; @JoinColumn({ name: "guild_id" }) - @ManyToOne(() => Guild) + @ManyToOne(() => Guild, { + onDelete: "CASCADE", + }) guild: Guild; @Column() diff --git a/util/src/entities/Session.ts b/util/src/entities/Session.ts index d42a8f98..7cc325f5 100644 --- a/util/src/entities/Session.ts +++ b/util/src/entities/Session.ts @@ -11,7 +11,9 @@ export class Session extends BaseClass { user_id: string; @JoinColumn({ name: "user_id" }) - @ManyToOne(() => User) + @ManyToOne(() => User, { + onDelete: "CASCADE", + }) user: User; //TODO check, should be 32 char long hex string diff --git a/util/src/entities/Sticker.ts b/util/src/entities/Sticker.ts index 7730a86a..ab224d1d 100644 --- a/util/src/entities/Sticker.ts +++ b/util/src/entities/Sticker.ts @@ -31,7 +31,9 @@ export class Sticker extends BaseClass { guild_id?: string; @JoinColumn({ name: "guild_id" }) - @ManyToOne(() => Guild) + @ManyToOne(() => Guild, { + onDelete: "CASCADE", + }) guild?: Guild; @Column({ type: "simple-enum", enum: StickerType }) diff --git a/util/src/entities/Team.ts b/util/src/entities/Team.ts index beb8bf68..22140b7f 100644 --- a/util/src/entities/Team.ts +++ b/util/src/entities/Team.ts @@ -9,7 +9,9 @@ export class Team extends BaseClass { icon?: string; @JoinColumn({ name: "member_ids" }) - @OneToMany(() => TeamMember, (member: TeamMember) => member.team) + @OneToMany(() => TeamMember, (member: TeamMember) => member.team, { + orphanedRowAction: "delete", + }) members: TeamMember[]; @Column() diff --git a/util/src/entities/TeamMember.ts b/util/src/entities/TeamMember.ts index 6b184d08..bdfdccf0 100644 --- a/util/src/entities/TeamMember.ts +++ b/util/src/entities/TeamMember.ts @@ -20,7 +20,9 @@ export class TeamMember extends BaseClass { team_id: string; @JoinColumn({ name: "team_id" }) - @ManyToOne(() => require("./Team").Team, (team: import("./Team").Team) => team.members) + @ManyToOne(() => require("./Team").Team, (team: import("./Team").Team) => team.members, { + onDelete: "CASCADE", + }) team: import("./Team").Team; @Column({ nullable: true }) @@ -28,6 +30,8 @@ export class TeamMember extends BaseClass { user_id: string; @JoinColumn({ name: "user_id" }) - @ManyToOne(() => User) + @ManyToOne(() => User, { + onDelete: "CASCADE", + }) user: User; } diff --git a/util/src/entities/User.ts b/util/src/entities/User.ts index cef88777..4c86b2d8 100644 --- a/util/src/entities/User.ts +++ b/util/src/entities/User.ts @@ -127,11 +127,17 @@ export class User extends BaseClass { public_flags: number; @JoinColumn({ name: "relationship_ids" }) - @OneToMany(() => Relationship, (relationship: Relationship) => relationship.from) + @OneToMany(() => Relationship, (relationship: Relationship) => relationship.from, { + cascade: true, + orphanedRowAction: "delete", + }) relationships: Relationship[]; @JoinColumn({ name: "connected_account_ids" }) - @OneToMany(() => ConnectedAccount, (account: ConnectedAccount) => account.user) + @OneToMany(() => ConnectedAccount, (account: ConnectedAccount) => account.user, { + cascade: true, + orphanedRowAction: "delete", + }) connected_accounts: ConnectedAccount[]; @Column({ type: "simple-json", select: false }) diff --git a/util/src/entities/VoiceState.ts b/util/src/entities/VoiceState.ts index 56eb244e..75748a01 100644 --- a/util/src/entities/VoiceState.ts +++ b/util/src/entities/VoiceState.ts @@ -13,7 +13,9 @@ export class VoiceState extends BaseClass { guild_id: string; @JoinColumn({ name: "guild_id" }) - @ManyToOne(() => Guild) + @ManyToOne(() => Guild, { + onDelete: "CASCADE", + }) guild?: Guild; @Column({ nullable: true }) @@ -21,7 +23,9 @@ export class VoiceState extends BaseClass { channel_id: string; @JoinColumn({ name: "channel_id" }) - @ManyToOne(() => Channel) + @ManyToOne(() => Channel, { + onDelete: "CASCADE", + }) channel: Channel; @Column({ nullable: true }) @@ -29,11 +33,15 @@ export class VoiceState extends BaseClass { user_id: string; @JoinColumn({ name: "user_id" }) - @ManyToOne(() => User) + @ManyToOne(() => User, { + onDelete: "CASCADE", + }) user: User; // @JoinColumn([{ name: "user_id", referencedColumnName: "id" },{ name: "guild_id", referencedColumnName: "guild_id" }]) - // @ManyToOne(() => Member) + // @ManyToOne(() => Member, { + // onDelete: "CASCADE", + // }) //TODO find a way to make it work without breaking Guild.voice_states member: Member; diff --git a/util/src/entities/Webhook.ts b/util/src/entities/Webhook.ts index 12ba0d08..8382435f 100644 --- a/util/src/entities/Webhook.ts +++ b/util/src/entities/Webhook.ts @@ -32,7 +32,9 @@ export class Webhook extends BaseClass { guild_id: string; @JoinColumn({ name: "guild_id" }) - @ManyToOne(() => Guild) + @ManyToOne(() => Guild, { + onDelete: "CASCADE", + }) guild: Guild; @Column({ nullable: true }) @@ -40,7 +42,9 @@ export class Webhook extends BaseClass { channel_id: string; @JoinColumn({ name: "channel_id" }) - @ManyToOne(() => Channel) + @ManyToOne(() => Channel, { + onDelete: "CASCADE", + }) channel: Channel; @Column({ nullable: true }) @@ -48,7 +52,9 @@ export class Webhook extends BaseClass { application_id: string; @JoinColumn({ name: "application_id" }) - @ManyToOne(() => Application) + @ManyToOne(() => Application, { + onDelete: "CASCADE", + }) application: Application; @Column({ nullable: true }) @@ -56,7 +62,9 @@ export class Webhook extends BaseClass { user_id: string; @JoinColumn({ name: "user_id" }) - @ManyToOne(() => User) + @ManyToOne(() => User, { + onDelete: "CASCADE", + }) user: User; @Column({ nullable: true }) @@ -64,6 +72,8 @@ export class Webhook extends BaseClass { source_guild_id: string; @JoinColumn({ name: "source_guild_id" }) - @ManyToOne(() => Guild) + @ManyToOne(() => Guild, { + onDelete: "CASCADE", + }) source_guild: Guild; } -- cgit 1.5.1