diff options
author | TheArcaneBrony <myrainbowdash949@gmail.com> | 2022-08-23 19:02:05 +0200 |
---|---|---|
committer | TheArcaneBrony <myrainbowdash949@gmail.com> | 2022-08-23 19:02:05 +0200 |
commit | ba0ba4b61ede1404454b8ab89bd9da61851f8a6e (patch) | |
tree | 254cf1238adea372014b55555e22db6637683d72 /src/cdn/routes | |
parent | Merge remote-tracking branch 'Puyodead1/patch/prettier-config' into staging (diff) | |
parent | New db migration script - multiplatform, fix mariadb migrations (diff) | |
download | server-ba0ba4b61ede1404454b8ab89bd9da61851f8a6e.tar.xz |
Merge branch 'dev/cherry-plugins-improvements' into staging
Diffstat (limited to 'src/cdn/routes')
-rw-r--r-- | src/cdn/routes/attachments.ts | 145 | ||||
-rw-r--r-- | src/cdn/routes/avatars.ts | 78 | ||||
-rw-r--r-- | src/cdn/routes/external.ts | 15 | ||||
-rw-r--r-- | src/cdn/routes/ping.ts | 2 | ||||
-rw-r--r-- | src/cdn/routes/role-icons.ts | 76 |
5 files changed, 127 insertions, 189 deletions
diff --git a/src/cdn/routes/attachments.ts b/src/cdn/routes/attachments.ts index 723a6c03..013f03d8 100644 --- a/src/cdn/routes/attachments.ts +++ b/src/cdn/routes/attachments.ts @@ -1,100 +1,77 @@ -import { Router, Response, Request } from "express"; -import { Config, Snowflake } from "@fosscord/util"; -import { storage } from "../util/Storage"; +import { Config, HTTPError, Snowflake } from "@fosscord/util"; +import { Request, Response, Router } from "express"; import FileType from "file-type"; -import { HTTPError } from "@fosscord/util"; -import { multer } from "../util/multer"; import imageSize from "image-size"; +import { multer } from "../util/multer"; +import { storage } from "../util/Storage"; const router = Router(); -const SANITIZED_CONTENT_TYPE = [ - "text/html", - "text/mhtml", - "multipart/related", - "application/xhtml+xml", -]; - -router.post( - "/:channel_id", - multer.single("file"), - async (req: Request, res: Response) => { - if (req.headers.signature !== Config.get().security.requestSignature) - throw new HTTPError("Invalid request signature"); - if (!req.file) throw new HTTPError("file missing"); - - const { buffer, mimetype, size, originalname, fieldname } = req.file; - const { channel_id } = req.params; - const filename = originalname - .replaceAll(" ", "_") - .replace(/[^a-zA-Z0-9._]+/g, ""); - const id = Snowflake.generate(); - const path = `attachments/${channel_id}/${id}/${filename}`; - - const endpoint = - Config.get()?.cdn.endpointPublic || "http://localhost:3003"; - - await storage.set(path, buffer); - let width; - let height; - if (mimetype.includes("image")) { - const dimensions = imageSize(buffer); - if (dimensions) { - width = dimensions.width; - height = dimensions.height; - } +const SANITIZED_CONTENT_TYPE = ["text/html", "text/mhtml", "multipart/related", "application/xhtml+xml"]; + +router.post("/:channel_id", multer.single("file"), async (req: Request, res: Response) => { + if (req.headers.signature !== Config.get().security.requestSignature) throw new HTTPError("Invalid request signature"); + if (!req.file) throw new HTTPError("file missing"); + + const { buffer, mimetype, size, originalname, fieldname } = req.file; + const { channel_id } = req.params; + const filename = originalname.replaceAll(" ", "_").replace(/[^a-zA-Z0-9._]+/g, ""); + const id = Snowflake.generate(); + const path = `attachments/${channel_id}/${id}/${filename}`; + + const endpoint = Config.get()?.cdn.endpointPublic || "http://localhost:3003"; + + await storage.set(path, buffer); + let width; + let height; + if (mimetype.includes("image")) { + const dimensions = imageSize(buffer); + if (dimensions) { + width = dimensions.width; + height = dimensions.height; } + } - const file = { - id, - content_type: mimetype, - filename: filename, - size, - url: `${endpoint}/${path}`, - width, - height, - }; - - return res.json(file); + const file = { + id, + content_type: mimetype, + filename: filename, + size, + url: `${endpoint}/${path}`, + width, + height + }; + + return res.json(file); +}); + +router.get("/:channel_id/:id/:filename", async (req: Request, res: Response) => { + const { channel_id, id, filename } = req.params; + + const file = await storage.get(`attachments/${channel_id}/${id}/${filename}`); + if (!file) throw new HTTPError("File not found"); + const type = await FileType.fromBuffer(file); + let content_type = type?.mime || "application/octet-stream"; + + if (SANITIZED_CONTENT_TYPE.includes(content_type)) { + content_type = "application/octet-stream"; } -); - -router.get( - "/:channel_id/:id/:filename", - async (req: Request, res: Response) => { - const { channel_id, id, filename } = req.params; - - const file = await storage.get( - `attachments/${channel_id}/${id}/${filename}` - ); - if (!file) throw new HTTPError("File not found"); - const type = await FileType.fromBuffer(file); - let content_type = type?.mime || "application/octet-stream"; - - if (SANITIZED_CONTENT_TYPE.includes(content_type)) { - content_type = "application/octet-stream"; - } - res.set("Content-Type", content_type); - res.set("Cache-Control", "public, max-age=31536000"); + res.set("Content-Type", content_type); + res.set("Cache-Control", "public, max-age=31536000"); - return res.send(file); - } -); + return res.send(file); +}); -router.delete( - "/:channel_id/:id/:filename", - async (req: Request, res: Response) => { - if (req.headers.signature !== Config.get().security.requestSignature) - throw new HTTPError("Invalid request signature"); +router.delete("/:channel_id/:id/:filename", async (req: Request, res: Response) => { + if (req.headers.signature !== Config.get().security.requestSignature) throw new HTTPError("Invalid request signature"); - const { channel_id, id, filename } = req.params; - const path = `attachments/${channel_id}/${id}/${filename}`; + const { channel_id, id, filename } = req.params; + const path = `attachments/${channel_id}/${id}/${filename}`; - await storage.delete(path); + await storage.delete(path); - return res.send({ success: true }); - } -); + return res.send({ success: true }); +}); export default router; diff --git a/src/cdn/routes/avatars.ts b/src/cdn/routes/avatars.ts index 40705b2e..fa26938f 100644 --- a/src/cdn/routes/avatars.ts +++ b/src/cdn/routes/avatars.ts @@ -1,10 +1,9 @@ -import { Router, Response, Request } from "express"; -import { Config, Snowflake } from "@fosscord/util"; -import { storage } from "../util/Storage"; -import FileType from "file-type"; -import { HTTPError } from "@fosscord/util"; +import { Config, HTTPError, Snowflake } from "@fosscord/util"; import crypto from "crypto"; +import { Request, Response, Router } from "express"; +import FileType from "file-type"; import { multer } from "../util/multer"; +import { storage } from "../util/Storage"; // TODO: check premium and animated pfp are allowed in the config // TODO: generate different sizes of icon @@ -12,51 +11,35 @@ import { multer } from "../util/multer"; // TODO: delete old icons const ANIMATED_MIME_TYPES = ["image/apng", "image/gif", "image/gifv"]; -const STATIC_MIME_TYPES = [ - "image/png", - "image/jpeg", - "image/webp", - "image/svg+xml", - "image/svg", -]; +const STATIC_MIME_TYPES = ["image/png", "image/jpeg", "image/webp", "image/svg+xml", "image/svg"]; const ALLOWED_MIME_TYPES = [...ANIMATED_MIME_TYPES, ...STATIC_MIME_TYPES]; const router = Router(); -router.post( - "/:user_id", - multer.single("file"), - async (req: Request, res: Response) => { - if (req.headers.signature !== Config.get().security.requestSignature) - throw new HTTPError("Invalid request signature"); - if (!req.file) throw new HTTPError("Missing file"); - const { buffer, mimetype, size, originalname, fieldname } = req.file; - const { user_id } = req.params; - - let hash = crypto - .createHash("md5") - .update(Snowflake.generate()) - .digest("hex"); - - const type = await FileType.fromBuffer(buffer); - if (!type || !ALLOWED_MIME_TYPES.includes(type.mime)) - throw new HTTPError("Invalid file type"); - if (ANIMATED_MIME_TYPES.includes(type.mime)) hash = `a_${hash}`; // animated icons have a_ infront of the hash - - const path = `avatars/${user_id}/${hash}`; - const endpoint = - Config.get().cdn.endpointPublic || "http://localhost:3003"; - - await storage.set(path, buffer); - - return res.json({ - id: hash, - content_type: type.mime, - size, - url: `${endpoint}${req.baseUrl}/${user_id}/${hash}`, - }); - } -); +router.post("/:user_id", multer.single("file"), async (req: Request, res: Response) => { + if (req.headers.signature !== Config.get().security.requestSignature) throw new HTTPError("Invalid request signature"); + if (!req.file) throw new HTTPError("Missing file"); + const { buffer, mimetype, size, originalname, fieldname } = req.file; + const { user_id } = req.params; + + let hash = crypto.createHash("md5").update(Snowflake.generate()).digest("hex"); + + const type = await FileType.fromBuffer(buffer); + if (!type || !ALLOWED_MIME_TYPES.includes(type.mime)) throw new HTTPError("Invalid file type"); + if (ANIMATED_MIME_TYPES.includes(type.mime)) hash = `a_${hash}`; // animated icons have a_ infront of the hash + + const path = `avatars/${user_id}/${hash}`; + const endpoint = Config.get().cdn.endpointPublic || "http://localhost:3003"; + + await storage.set(path, buffer); + + return res.json({ + id: hash, + content_type: type.mime, + size, + url: `${endpoint}${req.baseUrl}/${user_id}/${hash}` + }); +}); router.get("/:user_id", async (req: Request, res: Response) => { let { user_id } = req.params; @@ -89,8 +72,7 @@ router.get("/:user_id/:hash", async (req: Request, res: Response) => { }); router.delete("/:user_id/:id", async (req: Request, res: Response) => { - if (req.headers.signature !== Config.get().security.requestSignature) - throw new HTTPError("Invalid request signature"); + if (req.headers.signature !== Config.get().security.requestSignature) throw new HTTPError("Invalid request signature"); const { user_id, id } = req.params; const path = `avatars/${user_id}/${id}`; diff --git a/src/cdn/routes/external.ts b/src/cdn/routes/external.ts index c9441fc2..7ccf9b8a 100644 --- a/src/cdn/routes/external.ts +++ b/src/cdn/routes/external.ts @@ -1,9 +1,8 @@ -import { Router, Response, Request } from "express"; +import { Config, HTTPError, Snowflake } from "@fosscord/util"; +import { Request, Response, Router } from "express"; +import FileType from "file-type"; import fetch from "node-fetch"; -import { HTTPError } from "@fosscord/util"; -import { Snowflake, Config } from "@fosscord/util"; import { storage } from "../util/Storage"; -import FileType from "file-type"; // TODO: somehow handle the deletion of images posted to the /external route @@ -12,17 +11,15 @@ const DEFAULT_FETCH_OPTIONS: any = { redirect: "follow", follow: 1, headers: { - "user-agent": - "Mozilla/5.0 (compatible Fosscordbot/0.1; +https://fosscord.com)", + "user-agent": "Mozilla/5.0 (compatible Fosscordbot/0.1; +https://fosscord.com)" }, size: 1024 * 1024 * 8, compress: true, - method: "GET", + method: "GET" }; router.post("/", async (req: Request, res: Response) => { - if (req.headers.signature !== Config.get().security.requestSignature) - throw new HTTPError("Invalid request signature"); + if (req.headers.signature !== Config.get().security.requestSignature) throw new HTTPError("Invalid request signature"); if (!req.body) throw new HTTPError("Invalid Body"); diff --git a/src/cdn/routes/ping.ts b/src/cdn/routes/ping.ts index 38daf81e..420cf567 100644 --- a/src/cdn/routes/ping.ts +++ b/src/cdn/routes/ping.ts @@ -1,4 +1,4 @@ -import { Router, Response, Request } from "express"; +import { Request, Response, Router } from "express"; const router = Router(); diff --git a/src/cdn/routes/role-icons.ts b/src/cdn/routes/role-icons.ts index 2e5c42dd..768e194f 100644 --- a/src/cdn/routes/role-icons.ts +++ b/src/cdn/routes/role-icons.ts @@ -1,10 +1,9 @@ -import { Router, Response, Request } from "express"; -import { Config, Snowflake } from "@fosscord/util"; -import { storage } from "../util/Storage"; -import FileType from "file-type"; -import { HTTPError } from "@fosscord/util"; +import { Config, HTTPError, Snowflake } from "@fosscord/util"; import crypto from "crypto"; +import { Request, Response, Router } from "express"; +import FileType from "file-type"; import { multer } from "../util/multer"; +import { storage } from "../util/Storage"; //Role icons ---> avatars.ts modified @@ -12,50 +11,34 @@ import { multer } from "../util/multer"; // TODO: generate different sizes of icon // TODO: generate different image types of icon -const STATIC_MIME_TYPES = [ - "image/png", - "image/jpeg", - "image/webp", - "image/svg+xml", - "image/svg", -]; +const STATIC_MIME_TYPES = ["image/png", "image/jpeg", "image/webp", "image/svg+xml", "image/svg"]; const ALLOWED_MIME_TYPES = [...STATIC_MIME_TYPES]; const router = Router(); -router.post( - "/:role_id", - multer.single("file"), - async (req: Request, res: Response) => { - if (req.headers.signature !== Config.get().security.requestSignature) - throw new HTTPError("Invalid request signature"); - if (!req.file) throw new HTTPError("Missing file"); - const { buffer, mimetype, size, originalname, fieldname } = req.file; - const { role_id } = req.params; - - let hash = crypto - .createHash("md5") - .update(Snowflake.generate()) - .digest("hex"); - - const type = await FileType.fromBuffer(buffer); - if (!type || !ALLOWED_MIME_TYPES.includes(type.mime)) - throw new HTTPError("Invalid file type"); - - const path = `role-icons/${role_id}/${hash}.png`; - const endpoint = - Config.get().cdn.endpointPublic || "http://localhost:3003"; - - await storage.set(path, buffer); - - return res.json({ - id: hash, - content_type: type.mime, - size, - url: `${endpoint}${req.baseUrl}/${role_id}/${hash}`, - }); - } -); +router.post("/:role_id", multer.single("file"), async (req: Request, res: Response) => { + if (req.headers.signature !== Config.get().security.requestSignature) throw new HTTPError("Invalid request signature"); + if (!req.file) throw new HTTPError("Missing file"); + const { buffer, mimetype, size, originalname, fieldname } = req.file; + const { role_id } = req.params; + + let hash = crypto.createHash("md5").update(Snowflake.generate()).digest("hex"); + + const type = await FileType.fromBuffer(buffer); + if (!type || !ALLOWED_MIME_TYPES.includes(type.mime)) throw new HTTPError("Invalid file type"); + + const path = `role-icons/${role_id}/${hash}.png`; + const endpoint = Config.get().cdn.endpointPublic || "http://localhost:3003"; + + await storage.set(path, buffer); + + return res.json({ + id: hash, + content_type: type.mime, + size, + url: `${endpoint}${req.baseUrl}/${role_id}/${hash}` + }); +}); router.get("/:role_id", async (req: Request, res: Response) => { let { role_id } = req.params; @@ -88,8 +71,7 @@ router.get("/:role_id/:hash", async (req: Request, res: Response) => { }); router.delete("/:role_id/:id", async (req: Request, res: Response) => { - if (req.headers.signature !== Config.get().security.requestSignature) - throw new HTTPError("Invalid request signature"); + if (req.headers.signature !== Config.get().security.requestSignature) throw new HTTPError("Invalid request signature"); const { role_id, id } = req.params; const path = `role-icons/${role_id}/${id}`; |