feat: add /api/emojis endpoint

This commit is contained in:
Nanaka Hiira 2023-12-23 05:04:54 +09:00 committed by naskya
parent 03cdccb28b
commit e98af2b2a7
Signed by: naskya
GPG key ID: 712D413B3A9FED5C
4 changed files with 91 additions and 0 deletions

View file

@ -38,6 +38,7 @@
## 細かい変更点
- `emojis` の API エンドポイントMisskey v13- 互換)を追加([firefish-mkdir](https://git.mkdir.uk/hiira/firefish-mkdir) から取り込み)
- Docker のベースイメージに Node v21 を使用
- HTML のコードに入るコメントアートを削除
- 全ページにこんなの入れなくても……

View file

@ -139,6 +139,7 @@ import * as ep___drive_folders_update from "./endpoints/drive/folders/update.js"
import * as ep___drive_stream from "./endpoints/drive/stream.js";
import * as ep___emailAddress_available from "./endpoints/email-address/available.js";
import * as ep___emoji from "./endpoints/emoji.js";
import * as ep___emojis from "./endpoints/emojis.js";
import * as ep___endpoint from "./endpoints/endpoint.js";
import * as ep___endpoints from "./endpoints/endpoints.js";
import * as ep___exportCustomEmojis from "./endpoints/export-custom-emojis.js";
@ -496,6 +497,7 @@ const eps = [
["drive/stream", ep___drive_stream],
["email-address/available", ep___emailAddress_available],
["emoji", ep___emoji],
["emojis", ep___emojis],
["endpoint", ep___endpoint],
["endpoints", ep___endpoints],
["export-custom-emojis", ep___exportCustomEmojis],

View file

@ -0,0 +1,50 @@
import { Emojis } from "@/models/index.js";
import define from "@/server/api/define.js";
import { IsNull } from "typeorm";
export const meta = {
tags: ["meta"],
requireCredential: false,
cacheSec: 3600,
res: {
type: "object",
optional: false,
nullable: false,
properties: {
emojis: {
type: "array",
optional: false,
nullable: false,
items: {
type: "object",
optional: false,
nullable: false,
ref: "Emoji",
},
},
},
},
} as const;
export const paramDef = {
type: "object",
properties: {},
required: [],
} as const;
export default define(meta, paramDef, async (ps, me) => {
const emojis = await Emojis.find({
where: {
host: IsNull(),
},
order: {
category: "ASC",
name: "ASC",
},
});
return {
emojis: await Emojis.packMany(emojis),
};
});

View file

@ -25,6 +25,7 @@ import {
Pages,
Channels,
Clips,
Emojis,
GalleryPosts,
} from "@/models/index.js";
import * as Acct from "@/misc/acct.js";
@ -111,6 +112,43 @@ app.use(async (ctx, next) => {
// Init router
const router = new Router();
router.get<{ Params: { path: string } }>("/emoji/:path(.*)", async (ctx) => {
const path = ctx.params.path;
ctx.set("Cache-Control", "public, max-age=86400");
if (!path.match(/^[a-zA-Z0-9\-_@\.]+?\.webp$/)) {
ctx.throw(400, "Bad Request");
return;
}
const name = path.split("@")[0].replace(/\.webp$/i, "");
const host = path.split("@")[1]?.replace(/\.webp$/i, "");
const emoji = await Emojis.findOneBy({
host: host == null || host === "." ? IsNull() : host,
name: name,
});
ctx.set(
"Content-Security-Policy",
"default-src 'none'; style-src 'unsafe-inline'",
);
if (emoji == null) {
ctx.throw(404, "Emoji not found");
return;
}
let url = new URL(`${config.mediaProxy || config.url + "/proxy"}/emoji.webp`);
// || emoji.originalUrl してるのは後方互換性のため
url.searchParams.append("url", emoji.publicUrl || emoji.originalUrl);
url.searchParams.append("emoji", "1");
if ("static" in ctx.query) url.searchParams.append("static", "1");
return ctx.redirect(url.toString());
});
//#region static assets
router.get("/static-assets/(.*)", async (ctx) => {