From 0ec4f87ef8b0f1eae9560ce6d9491fe1807e67e2 Mon Sep 17 00:00:00 2001 From: anatawa12 Date: Wed, 13 Aug 2025 00:51:44 +0900 Subject: [PATCH] feat: bootloader in frontend package (embed) --- packages/backend/src/config.ts | 4 +++- packages/backend/src/server/web/views/base-embed.pug | 4 ++-- packages/frontend-embed/@types/global.d.ts | 1 + .../boot.embed.js => frontend-embed/src/_bootloader.ts} | 8 ++++++-- packages/frontend-embed/vite.config.ts | 2 ++ scripts/build-assets.mjs | 2 +- 6 files changed, 15 insertions(+), 6 deletions(-) rename packages/{backend/src/server/web/boot.embed.js => frontend-embed/src/_bootloader.ts} (96%) diff --git a/packages/backend/src/config.ts b/packages/backend/src/config.ts index bab238c0c6..1e8bed97d4 100644 --- a/packages/backend/src/config.ts +++ b/packages/backend/src/config.ts @@ -188,6 +188,7 @@ export type Config = { frontendBootLoader: { file: string }; frontendManifestExists: boolean; frontendEmbedEntry: { file: string | null }; + frontendEmbedBootLoader: { file: string }; frontendEmbedManifestExists: boolean; mediaProxy: string; externalMediaProxyEnabled: boolean; @@ -239,7 +240,7 @@ export function loadConfig(): Config { : { 'src/_boot_.ts': { file: null }, 'src/_bootloader.ts': { file: 'src/_bootloader.ts' } }; const frontendEmbedManifest = frontendEmbedManifestExists ? JSON.parse(fs.readFileSync(`${_dirname}/../../../built/_frontend_embed_vite_/manifest.json`, 'utf-8')) - : { 'src/boot.ts': { file: null } }; + : { 'src/boot.ts': { file: null }, 'src/_bootloader.ts': { file: 'src/_bootloader.ts' } }; const config = yaml.load(fs.readFileSync(path, 'utf-8')) as Source; @@ -316,6 +317,7 @@ export function loadConfig(): Config { frontendBootLoader: frontendManifest['src/_bootloader.ts'], frontendManifestExists: frontendManifestExists, frontendEmbedEntry: frontendEmbedManifest['src/boot.ts'], + frontendEmbedBootLoader: frontendEmbedManifest['src/_bootloader.ts'], frontendEmbedManifestExists: frontendEmbedManifestExists, perChannelMaxNoteCacheCount: config.perChannelMaxNoteCacheCount ?? 1000, perUserNotificationsMaxCount: config.perUserNotificationsMaxCount ?? 500, diff --git a/packages/backend/src/server/web/views/base-embed.pug b/packages/backend/src/server/web/views/base-embed.pug index 29de86b8b6..e4e70acb22 100644 --- a/packages/backend/src/server/web/views/base-embed.pug +++ b/packages/backend/src/server/web/views/base-embed.pug @@ -2,6 +2,7 @@ block vars block loadClientEntry - const entry = config.frontendEmbedEntry; + - const bootLoader = config.frontendEmbedBootLoader; doctype html @@ -47,8 +48,7 @@ html(class='embed') script(type='application/json' id='misskey_embedCtx' data-generated-at=now) != embedCtx - script - include ../boot.embed.js + script(type='module', src=`/embed_vite/${bootLoader.file}`) body noscript: p diff --git a/packages/frontend-embed/@types/global.d.ts b/packages/frontend-embed/@types/global.d.ts index 8a067a78ec..d8bb566760 100644 --- a/packages/frontend-embed/@types/global.d.ts +++ b/packages/frontend-embed/@types/global.d.ts @@ -6,6 +6,7 @@ type FIXME = any; declare const _LANGS_: string[][]; +declare const _LANG_IDS_: string[]; declare const _VERSION_: string; declare const _ENV_: string; declare const _DEV_: boolean; diff --git a/packages/backend/src/server/web/boot.embed.js b/packages/frontend-embed/src/_bootloader.ts similarity index 96% rename from packages/backend/src/server/web/boot.embed.js rename to packages/frontend-embed/src/_bootloader.ts index 022ff064ad..420ce43685 100644 --- a/packages/backend/src/server/web/boot.embed.js +++ b/packages/frontend-embed/src/_bootloader.ts @@ -5,6 +5,10 @@ 'use strict'; +interface Window { + CLIENT_ENTRY: string | undefined; +} + // ブロックの中に入れないと、定義した変数がブラウザのグローバルスコープに登録されてしまい邪魔なので (async () => { window.onerror = (e) => { @@ -32,7 +36,7 @@ } //#region Detect language & fetch translations - const supportedLangs = LANGS; + const supportedLangs = _LANG_IDS_; /** @type { string } */ let lang = localStorage.getItem('lang'); if (lang == null || !supportedLangs.includes(lang)) { @@ -55,7 +59,7 @@ //#region Script async function importAppScript() { - await import(CLIENT_ENTRY ? `/embed_vite/${CLIENT_ENTRY.replace('scripts', lang)}` : '/embed_vite/src/_boot_.ts') + await import(`/embed_vite/${(window.CLIENT_ENTRY ?? 'src/boot.ts').replace('scripts', lang)}`) .catch(async e => { console.error(e); renderError('APP_IMPORT'); diff --git a/packages/frontend-embed/vite.config.ts b/packages/frontend-embed/vite.config.ts index 3ddee9b8a9..eae02c4909 100644 --- a/packages/frontend-embed/vite.config.ts +++ b/packages/frontend-embed/vite.config.ts @@ -121,6 +121,7 @@ export function getConfig(): UserConfig { define: { _VERSION_: JSON.stringify(meta.version), _LANGS_: JSON.stringify(Object.entries(locales).map(([k, v]) => [k, v._lang_])), + _LANG_IDS_: JSON.stringify(Object.keys(locales)), _ENV_: JSON.stringify(process.env.NODE_ENV), _DEV_: process.env.NODE_ENV !== 'production', _PERF_PREFIX_: JSON.stringify('Misskey:'), @@ -139,6 +140,7 @@ export function getConfig(): UserConfig { input: { i18n: './src/i18n.ts', entry: './src/boot.ts', + bootloader: './src/_bootloader.ts', }, external: externalPackages.map(p => p.match), preserveEntrySignatures: 'allow-extension', diff --git a/scripts/build-assets.mjs b/scripts/build-assets.mjs index 07c2c24dbe..0f260360e7 100644 --- a/scripts/build-assets.mjs +++ b/scripts/build-assets.mjs @@ -54,7 +54,7 @@ async function buildBackendScript() { for (const file of [ //'./packages/backend/src/server/web/boot.js', - './packages/backend/src/server/web/boot.embed.js', + //'./packages/backend/src/server/web/boot.embed.js', './packages/backend/src/server/web/bios.js', './packages/backend/src/server/web/cli.js', './packages/backend/src/server/web/error.js',