Sign media per user
This commit is contained in:
parent
8922ca1518
commit
387cef269a
@ -30,12 +30,13 @@ import {
|
||||
emitEvent,
|
||||
getPermission,
|
||||
getRights,
|
||||
uploadFile,
|
||||
uploadFile, Config, getUrlSignature,
|
||||
} from "@spacebar/util";
|
||||
import { Request, Response, Router } from "express";
|
||||
import { HTTPError } from "lambert-server";
|
||||
import multer from "multer";
|
||||
import { handleMessage, postHandleMessage, route } from "../../../../../util";
|
||||
import { URL } from "url";
|
||||
|
||||
const router = Router();
|
||||
// TODO: message content/embed string length limit
|
||||
@ -244,7 +245,7 @@ router.put(
|
||||
console.error("[Message] post-message handler failed", e),
|
||||
);
|
||||
|
||||
return res.json(message);
|
||||
return res.json(message.withSignedAttachments(req));
|
||||
},
|
||||
);
|
||||
|
||||
|
||||
@ -17,14 +17,20 @@
|
||||
*/
|
||||
|
||||
import { Server, ServerOptions } from "lambert-server";
|
||||
import { Config, initDatabase, registerRoutes, Sentry } from "@spacebar/util";
|
||||
import {
|
||||
Attachment,
|
||||
Config,
|
||||
initDatabase,
|
||||
registerRoutes,
|
||||
Sentry,
|
||||
} from "@spacebar/util";
|
||||
import { CORS, BodyParser } from "@spacebar/api";
|
||||
import path from "path";
|
||||
import avatarsRoute from "./routes/avatars";
|
||||
import guildProfilesRoute from "./routes/guild-profiles";
|
||||
import iconsRoute from "./routes/role-icons";
|
||||
import { CORS } from "../api/middlewares/CORS";
|
||||
import { BodyParser } from "../api/middlewares/BodyParser";
|
||||
import morgan from "morgan";
|
||||
import { Like, Or } from "typeorm";
|
||||
|
||||
export type CDNServerOptions = ServerOptions;
|
||||
|
||||
@ -38,6 +44,7 @@ export class CDNServer extends Server {
|
||||
async start() {
|
||||
await initDatabase();
|
||||
await Config.init();
|
||||
await this.cleanupSignaturesInDb();
|
||||
await Sentry.init(this.app);
|
||||
|
||||
const logRequests = process.env["LOG_REQUESTS"] != undefined;
|
||||
@ -124,4 +131,26 @@ export class CDNServer extends Server {
|
||||
async stop() {
|
||||
return super.stop();
|
||||
}
|
||||
|
||||
async cleanupSignaturesInDb() {
|
||||
this.log("verbose", "[Server] Cleaning up signatures in database");
|
||||
const attachmentsToFix = await Attachment.find({
|
||||
where: { url: Like("%?ex=%") },
|
||||
});
|
||||
if (attachmentsToFix.length === 0) {
|
||||
this.log("verbose", "[Server] No attachments to fix");
|
||||
return;
|
||||
}
|
||||
|
||||
this.log(
|
||||
"verbose",
|
||||
`[Server] Found ${attachmentsToFix.length} attachments to fix`,
|
||||
);
|
||||
for (const attachment of attachmentsToFix) {
|
||||
attachment.url = attachment.url.split("?ex=")[0];
|
||||
attachment.proxy_url = attachment.proxy_url?.split("?ex=")[0];
|
||||
await attachment.save();
|
||||
this.log("verbose", `[Server] Fixed attachment ${attachment.id}`);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -69,12 +69,7 @@ router.post(
|
||||
}
|
||||
}
|
||||
|
||||
let finalUrl = `${endpoint}/${path}`;
|
||||
|
||||
if (Config.get().security.cdnSignUrls) {
|
||||
const signatureData = getUrlSignature(path, req);
|
||||
finalUrl = `${finalUrl}?ex=${signatureData.expiresAt}&is=${signatureData.issuedAt}&hm=${signatureData.hash}&ip=${req.ip}`;
|
||||
}
|
||||
const finalUrl = `${endpoint}/${path}`;
|
||||
|
||||
const file = {
|
||||
id,
|
||||
@ -82,6 +77,7 @@ router.post(
|
||||
filename: filename,
|
||||
size,
|
||||
url: finalUrl,
|
||||
path,
|
||||
width,
|
||||
height,
|
||||
};
|
||||
|
||||
@ -21,6 +21,7 @@ import { createHmac, timingSafeEqual } from "crypto";
|
||||
import ms, { StringValue } from "ms";
|
||||
import { ParsedQs } from "qs";
|
||||
import { Request } from "express";
|
||||
import attachments from "../cdn/routes/attachments";
|
||||
|
||||
export const getUrlSignature = (
|
||||
path: string,
|
||||
|
||||
@ -28,6 +28,8 @@ import { URL } from "url";
|
||||
import { deleteFile } from "../util/cdn";
|
||||
import { BaseClass } from "./BaseClass";
|
||||
import { dbEngine } from "../util/Database";
|
||||
import { Request } from "express";
|
||||
import { resignUrl } from "../Signing";
|
||||
|
||||
@Entity({
|
||||
name: "attachments",
|
||||
@ -73,4 +75,11 @@ export class Attachment extends BaseClass {
|
||||
onDelete() {
|
||||
return deleteFile(new URL(this.url).pathname);
|
||||
}
|
||||
|
||||
signUrls(req: Request) {
|
||||
return {
|
||||
url: this.url + resignUrl(this.url, req),
|
||||
proxy_url: this.proxy_url + resignUrl(this.proxy_url, req),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -40,6 +40,7 @@ import { Webhook } from "./Webhook";
|
||||
import { Sticker } from "./Sticker";
|
||||
import { Attachment } from "./Attachment";
|
||||
import { dbEngine } from "../util/Database";
|
||||
import { Request } from "express";
|
||||
|
||||
export enum MessageType {
|
||||
DEFAULT = 0,
|
||||
@ -260,6 +261,15 @@ export class Message extends BaseClass {
|
||||
content: this.content ?? "",
|
||||
};
|
||||
}
|
||||
|
||||
withSignedAttachments(req: Request) {
|
||||
return {
|
||||
...this,
|
||||
attachments: this.attachments?.map((attachment: Attachment) =>
|
||||
attachment.signUrls(req)
|
||||
)
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
export interface MessageComponent {
|
||||
|
||||
Reference in New Issue
Block a user