summaryrefslogtreecommitdiff
path: root/packages/frontend-embed
diff options
context:
space:
mode:
authorHazelnoot <acomputerdog@gmail.com>2025-02-03 14:31:26 -0500
committerHazelnoot <acomputerdog@gmail.com>2025-02-03 14:36:09 -0500
commita4e86758c1c53f4e623b6e8f613d4a6e34e96156 (patch)
treed09bf325b7f52512a1fe2a9d35f1953d2b310309 /packages/frontend-embed
parentmerge: Use package manager version from package.json (!883) (diff)
parentfix(build): corepackのバグの回避 (#15387) (diff)
downloadsharkey-a4e86758c1c53f4e623b6e8f613d4a6e34e96156.tar.gz
sharkey-a4e86758c1c53f4e623b6e8f613d4a6e34e96156.tar.bz2
sharkey-a4e86758c1c53f4e623b6e8f613d4a6e34e96156.zip
merge upstream 2025-02-03
Diffstat (limited to 'packages/frontend-embed')
-rw-r--r--packages/frontend-embed/package.json5
-rw-r--r--packages/frontend-embed/src/boot.ts20
-rw-r--r--packages/frontend-embed/src/components/EmAcct.vue2
-rw-r--r--packages/frontend-embed/src/components/EmMention.vue2
-rw-r--r--packages/frontend-embed/src/components/EmNotes.vue3
-rw-r--r--packages/frontend-embed/src/components/EmUrl.vue2
-rw-r--r--packages/frontend-embed/src/index.html38
-rw-r--r--packages/frontend-embed/src/theme.ts23
-rw-r--r--packages/frontend-embed/tsconfig.json4
-rw-r--r--packages/frontend-embed/vite.config.local-dev.ts96
-rw-r--r--packages/frontend-embed/vite.config.ts13
11 files changed, 54 insertions, 154 deletions
diff --git a/packages/frontend-embed/package.json b/packages/frontend-embed/package.json
index 528faf0a85..163e6096f8 100644
--- a/packages/frontend-embed/package.json
+++ b/packages/frontend-embed/package.json
@@ -4,7 +4,6 @@
"type": "module",
"scripts": {
"watch": "vite",
- "dev": "vite --config vite.config.local-dev.ts --debug hmr",
"build": "vite build",
"typecheck": "vue-tsc --noEmit",
"eslint": "eslint --quiet \"{src,test,js,@types}/**/*.{js,jsx,ts,tsx,vue}\" --cache",
@@ -25,7 +24,7 @@
"estree-walker": "3.0.3",
"misskey-js": "workspace:*",
"frontend-shared": "workspace:*",
- "punycode": "2.3.1",
+ "punycode.js": "2.3.1",
"rollup": "4.26.0",
"sass": "1.79.4",
"shiki": "1.22.2",
@@ -44,7 +43,7 @@
"@types/estree": "1.0.6",
"@types/micromatch": "4.0.9",
"@types/node": "22.9.0",
- "@types/punycode": "2.1.4",
+ "@types/punycode.js": "npm:@types/punycode@2.1.4",
"@types/tinycolor2": "1.4.6",
"@types/uuid": "10.0.0",
"@types/ws": "8.5.13",
diff --git a/packages/frontend-embed/src/boot.ts b/packages/frontend-embed/src/boot.ts
index 71a3156311..c5072caba4 100644
--- a/packages/frontend-embed/src/boot.ts
+++ b/packages/frontend-embed/src/boot.ts
@@ -15,11 +15,11 @@ import { applyTheme, assertIsTheme } from '@/theme.js';
import { fetchCustomEmojis } from '@/custom-emojis.js';
import { DI } from '@/di.js';
import { serverMetadata } from '@/server-metadata.js';
-import { url } from '@@/js/config.js';
+import { url, version, locale, lang, updateLocale } from '@@/js/config.js';
import { parseEmbedParams } from '@@/js/embed-page.js';
import { postMessageToParentWindow, setIframeId } from '@/post-message.js';
import { serverContext } from '@/server-context.js';
-import { i18n } from '@/i18n.js';
+import { i18n, updateI18n } from '@/i18n.js';
import type { Theme } from '@/theme.js';
@@ -69,6 +69,22 @@ if (embedParams.colorMode === 'dark') {
}
//#endregion
+//#region Detect language & fetch translations
+const localeVersion = localStorage.getItem('localeVersion');
+const localeOutdated = (localeVersion == null || localeVersion !== version || locale == null);
+if (localeOutdated) {
+ const res = await window.fetch(`/assets/locales/${lang}.${version}.json`);
+ if (res.status === 200) {
+ const newLocale = await res.text();
+ const parsedNewLocale = JSON.parse(newLocale);
+ localStorage.setItem('locale', newLocale);
+ localStorage.setItem('localeVersion', version);
+ updateLocale(parsedNewLocale);
+ updateI18n(parsedNewLocale);
+ }
+}
+//#endregion
+
// サイズの制限
document.documentElement.style.maxWidth = '500px';
diff --git a/packages/frontend-embed/src/components/EmAcct.vue b/packages/frontend-embed/src/components/EmAcct.vue
index 6856b8272e..ff794d9b6e 100644
--- a/packages/frontend-embed/src/components/EmAcct.vue
+++ b/packages/frontend-embed/src/components/EmAcct.vue
@@ -12,7 +12,7 @@ SPDX-License-Identifier: AGPL-3.0-only
<script lang="ts" setup>
import * as Misskey from 'misskey-js';
-import { toUnicode } from 'punycode/';
+import { toUnicode } from 'punycode.js';
import { host as hostRaw } from '@@/js/config.js';
defineProps<{
diff --git a/packages/frontend-embed/src/components/EmMention.vue b/packages/frontend-embed/src/components/EmMention.vue
index a71364237d..b5aaa95894 100644
--- a/packages/frontend-embed/src/components/EmMention.vue
+++ b/packages/frontend-embed/src/components/EmMention.vue
@@ -13,7 +13,7 @@ SPDX-License-Identifier: AGPL-3.0-only
</template>
<script lang="ts" setup>
-import { toUnicode } from 'punycode';
+import { toUnicode } from 'punycode.js';
import { } from 'vue';
import tinycolor from 'tinycolor2';
import { host as localHost } from '@@/js/config.js';
diff --git a/packages/frontend-embed/src/components/EmNotes.vue b/packages/frontend-embed/src/components/EmNotes.vue
index 4211261e19..4e0ae005df 100644
--- a/packages/frontend-embed/src/components/EmNotes.vue
+++ b/packages/frontend-embed/src/components/EmNotes.vue
@@ -13,7 +13,7 @@ SPDX-License-Identifier: AGPL-3.0-only
<template #default="{ items: notes }">
<div :class="[$style.root]">
- <EmNote v-for="note in notes" :key="note._featuredId_ || note._prId_ || note.id" :class="$style.note" :note="note"/>
+ <EmNote v-for="note in notes" :key="note._featuredId_ || note._prId_ || note.id" :class="$style.note" :note="note as Misskey.entities.Note"/>
</div>
</template>
</EmPagination>
@@ -24,6 +24,7 @@ import { useTemplateRef } from 'vue';
import EmNote from '@/components/EmNote.vue';
import EmPagination, { Paging } from '@/components/EmPagination.vue';
import { i18n } from '@/i18n.js';
+import * as Misskey from 'misskey-js';
withDefaults(defineProps<{
pagination: Paging;
diff --git a/packages/frontend-embed/src/components/EmUrl.vue b/packages/frontend-embed/src/components/EmUrl.vue
index 94424cab28..2dbbe90858 100644
--- a/packages/frontend-embed/src/components/EmUrl.vue
+++ b/packages/frontend-embed/src/components/EmUrl.vue
@@ -25,7 +25,7 @@ SPDX-License-Identifier: AGPL-3.0-only
<script lang="ts" setup>
import { ref } from 'vue';
-import { toUnicode as decodePunycode } from 'punycode/';
+import { toUnicode as decodePunycode } from 'punycode.js';
import EmA from './EmA.vue';
import { url as local } from '@@/js/config.js';
diff --git a/packages/frontend-embed/src/index.html b/packages/frontend-embed/src/index.html
index d94ada5ea8..e69de29bb2 100644
--- a/packages/frontend-embed/src/index.html
+++ b/packages/frontend-embed/src/index.html
@@ -1,38 +0,0 @@
-<!--
- SPDX-FileCopyrightText: syuilo and misskey-project
- SPDX-License-Identifier: AGPL-3.0-only
--->
-
-<!--
- 開発モードのviteはこのファイルを起点にサーバーを起動します。
- このファイルに書かれた [t]js のリンクと (s)cssのリンクと、その依存関係にあるファイルはビルドされます
--->
-
-<!DOCTYPE html>
-<html>
-<head>
- <meta charset="UTF-8" />
- <title>[DEV] Loading...</title>
- <!-- https://developer.mozilla.org/en-US/docs/Web/HTTP/CSP -->
- <meta
- http-equiv="Content-Security-Policy"
- content="default-src 'self' https://newassets.hcaptcha.com/ https://challenges.cloudflare.com/ http://localhost:7493/;
- worker-src 'self';
- script-src 'self' 'unsafe-eval' https://*.hcaptcha.com https://challenges.cloudflare.com https://esm.sh https://cdn.jsdelivr.net;
- style-src 'self' 'unsafe-inline';
- img-src 'self' data: blob: www.google.com xn--931a.moe localhost:3000 localhost:5173 127.0.0.1:5173 127.0.0.1:3000;
- media-src 'self' localhost:3000 localhost:5173 127.0.0.1:5173 127.0.0.1:3000;
- connect-src 'self' localhost:3000 localhost:5173 127.0.0.1:5173 127.0.0.1:3000 https://newassets.hcaptcha.com;
- frame-src *;"
- />
- <meta property="og:site_name" content="[DEV BUILD] Sharkey" />
- <meta name="viewport" content="width=device-width, initial-scale=1">
- <link rel='stylesheet' href='/assets/phosphor-icons/bold/style.css'>
- <link rel='stylesheet' href='/static-assets/fonts/sharkey-icons/style.css'>
-</head>
-
-<body>
-<div id="sharkey_app"></div>
-<script type="module" src="./boot.ts"></script>
-</body>
-</html>
diff --git a/packages/frontend-embed/src/theme.ts b/packages/frontend-embed/src/theme.ts
index 4664ad4880..680ab80167 100644
--- a/packages/frontend-embed/src/theme.ts
+++ b/packages/frontend-embed/src/theme.ts
@@ -75,16 +75,21 @@ function compile(theme: Theme): Record<string, string> {
return getColor(theme.props[val]);
} else if (val[0] === ':') { // func
const parts = val.split('<');
- const func = parts.shift().substring(1);
- const arg = parseFloat(parts.shift());
- const color = getColor(parts.join('<'));
+ const funcTxt = parts.shift();
+ const argTxt = parts.shift();
- switch (func) {
- case 'darken': return color.darken(arg);
- case 'lighten': return color.lighten(arg);
- case 'alpha': return color.setAlpha(arg);
- case 'hue': return color.spin(arg);
- case 'saturate': return color.saturate(arg);
+ if (funcTxt && argTxt) {
+ const func = funcTxt.substring(1);
+ const arg = parseFloat(argTxt);
+ const color = getColor(parts.join('<'));
+
+ switch (func) {
+ case 'darken': return color.darken(arg);
+ case 'lighten': return color.lighten(arg);
+ case 'alpha': return color.setAlpha(arg);
+ case 'hue': return color.spin(arg);
+ case 'saturate': return color.saturate(arg);
+ }
}
}
diff --git a/packages/frontend-embed/tsconfig.json b/packages/frontend-embed/tsconfig.json
index 1af34f378c..ff04a689bf 100644
--- a/packages/frontend-embed/tsconfig.json
+++ b/packages/frontend-embed/tsconfig.json
@@ -10,8 +10,8 @@
"declaration": false,
"sourceMap": false,
"target": "ES2022",
- "module": "nodenext",
- "moduleResolution": "nodenext",
+ "module": "ES2022",
+ "moduleResolution": "Bundler",
"removeComments": false,
"noLib": false,
"strict": true,
diff --git a/packages/frontend-embed/vite.config.local-dev.ts b/packages/frontend-embed/vite.config.local-dev.ts
deleted file mode 100644
index bf2f478887..0000000000
--- a/packages/frontend-embed/vite.config.local-dev.ts
+++ /dev/null
@@ -1,96 +0,0 @@
-import dns from 'dns';
-import { readFile } from 'node:fs/promises';
-import type { IncomingMessage } from 'node:http';
-import { defineConfig } from 'vite';
-import type { UserConfig } from 'vite';
-import * as yaml from 'js-yaml';
-import locales from '../../locales/index.js';
-import { getConfig } from './vite.config.js';
-
-dns.setDefaultResultOrder('ipv4first');
-
-const defaultConfig = getConfig();
-
-const { port } = yaml.load(await readFile('../../.config/default.yml', 'utf-8'));
-
-const httpUrl = `http://localhost:${port}/`;
-const websocketUrl = `ws://localhost:${port}/`;
-
-// activitypubリクエストはProxyを通し、それ以外はViteの開発サーバーを返す
-function varyHandler(req: IncomingMessage) {
- if (req.headers.accept?.includes('application/activity+json')) {
- return null;
- }
- return '/index.html';
-}
-
-const devConfig: UserConfig = {
- // 基本の設定は vite.config.js から引き継ぐ
- ...defaultConfig,
- root: 'src',
- publicDir: '../assets',
- base: '/embed',
- server: {
- host: 'localhost',
- port: 5174,
- proxy: {
- '/api': {
- changeOrigin: true,
- target: httpUrl,
- },
- '/assets': httpUrl,
- '/static-assets': httpUrl,
- '/client-assets': httpUrl,
- '/files': httpUrl,
- '/twemoji': httpUrl,
- '/fluent-emoji': httpUrl,
- '/sw.js': httpUrl,
- '/streaming': {
- target: websocketUrl,
- ws: true,
- },
- '/favicon.ico': httpUrl,
- '/robots.txt': httpUrl,
- '/embed.js': httpUrl,
- '/identicon': {
- target: httpUrl,
- rewrite(path) {
- return path.replace('@localhost:5173', '');
- },
- },
- '/url': httpUrl,
- '/proxy': httpUrl,
- '/_info_card_': httpUrl,
- '/bios': httpUrl,
- '/cli': httpUrl,
- '/inbox': httpUrl,
- '/emoji/': httpUrl,
- '/notes': {
- target: httpUrl,
- bypass: varyHandler,
- },
- '/users': {
- target: httpUrl,
- bypass: varyHandler,
- },
- '/.well-known': {
- target: httpUrl,
- },
- },
- },
- build: {
- ...defaultConfig.build,
- rollupOptions: {
- ...defaultConfig.build?.rollupOptions,
- input: 'index.html',
- },
- },
-
- define: {
- ...defaultConfig.define,
- _LANGS_FULL_: JSON.stringify(Object.entries(locales)),
- },
-};
-
-export default defineConfig(({ command, mode }) => devConfig);
-
diff --git a/packages/frontend-embed/vite.config.ts b/packages/frontend-embed/vite.config.ts
index bf6f558893..13f272612c 100644
--- a/packages/frontend-embed/vite.config.ts
+++ b/packages/frontend-embed/vite.config.ts
@@ -2,12 +2,18 @@ import path from 'path';
import pluginVue from '@vitejs/plugin-vue';
import { type UserConfig, defineConfig } from 'vite';
import { localesVersion } from '../../locales/version.js';
+import * as yaml from 'js-yaml';
+import { promises as fsp } from 'fs';
+
import locales from '../../locales/index.js';
import meta from '../../package.json';
import packageInfo from './package.json' with { type: 'json' };
import pluginJson5 from './vite.json5.js';
import { pluginReplaceIcons } from '../frontend/vite.replaceIcons.js';
+const url = process.env.NODE_ENV === 'development' ? yaml.load(await fsp.readFile('../../.config/default.yml', 'utf-8')).url : null;
+const host = url ? (new URL(url)).hostname : undefined;
+
const extensions = ['.ts', '.tsx', '.js', '.jsx', '.mjs', '.json', '.json5', '.svg', '.sass', '.scss', '.css', '.vue'];
/**
@@ -63,7 +69,14 @@ export function getConfig(): UserConfig {
base: '/embed_vite/',
server: {
+ host,
port: 5174,
+ hmr: {
+ // バックエンド経由での起動時、Viteは5174経由でアセットを参照していると思い込んでいるが実際は3000から配信される
+ // そのため、バックエンドのWSサーバーにHMRのWSリクエストが吸収されてしまい、正しくHMRが機能しない
+ // クライアント側のWSポートをViteサーバーのポートに強制させることで、正しくHMRが機能するようになる
+ clientPort: 5174,
+ },
},
plugins: [