@h-ai/cli 1.0.0-beta.2 → 1.0.0-beta.21
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.en.md +74 -154
- package/README.ja.md +74 -154
- package/README.md +74 -154
- package/dist/{chunk-AKV2CQZV.js → chunk-2ZL5ORQ2.js} +316 -97
- package/dist/chunk-2ZL5ORQ2.js.map +1 -0
- package/dist/{chunk-EF7WOFWZ.js → chunk-L53P43B2.js} +1312 -163
- package/dist/chunk-L53P43B2.js.map +1 -0
- package/dist/cli-config-templates-LWMD2I6V.js +5 -0
- package/dist/{cli-config-templates-HHFHNXBN.js.map → cli-config-templates-LWMD2I6V.js.map} +1 -1
- package/dist/{cli-skill-templates-PN4FLGBC.js → cli-skill-templates-D6S2OQ6X.js} +3 -3
- package/dist/{cli-skill-templates-PN4FLGBC.js.map → cli-skill-templates-D6S2OQ6X.js.map} +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +30118 -3253
- package/dist/index.js.map +1 -1
- package/dist/metafile-esm.json +1 -1
- package/package.json +22 -18
- package/templates/README.md +45 -30
- package/templates/apps/admin/src/routes/+layout.svelte.hbs +16 -10
- package/templates/apps/admin/src/routes/+page.svelte.hbs +4 -4
- package/templates/apps/admin/src/routes/admin/+layout.svelte.hbs +17 -7
- package/templates/apps/admin/src/routes/admin/+page.svelte.hbs +26 -6
- package/templates/apps/admin/src/routes/admin/settings/+page.svelte.hbs +2 -2
- package/templates/apps/api/.dockerignore.hbs +10 -0
- package/templates/apps/api/apps/{{projectName}}-contract/README.md.hbs +8 -0
- package/templates/apps/api/apps/{{projectName}}-contract/src/app-schemas.ts.hbs +6 -1
- package/templates/apps/api/apps/{{projectName}}-contract/src/{{projectName}}-contract.ts.hbs +13 -5
- package/templates/apps/api/apps/{{projectName}}-contract/tests/contract.test.ts.hbs +13 -5
- package/templates/apps/api/apps/{{projectName}}-contract/tsup.config.ts.hbs +3 -1
- package/templates/apps/api/apps/{{projectName}}-serv/README.md.hbs +6 -2
- package/templates/apps/api/apps/{{projectName}}-serv/config/_serv.yml.hbs +24 -2
- package/templates/apps/api/apps/{{projectName}}-serv/package.json.hbs +4 -4
- package/templates/apps/api/apps/{{projectName}}-serv/src/app.ts.hbs +74 -24
- package/templates/apps/api/apps/{{projectName}}-serv/src/build-metadata.ts.hbs +0 -1
- package/templates/apps/api/apps/{{projectName}}-serv/src/lib/server/init.ts.hbs +153 -37
- package/templates/apps/api/apps/{{projectName}}-serv/src/server/procedures/index.ts.hbs +39 -13
- package/templates/apps/api/apps/{{projectName}}-serv/tests/service.test.ts.hbs +106 -33
- package/templates/apps/api/apps/{{projectName}}-serv/tsup.config.ts.hbs +3 -1
- package/templates/apps/api/apps/{{projectName}}-serv/vitest.config.ts.hbs +3 -1
- package/templates/apps/api/e2e/api-serv.spec.ts.hbs +20 -3
- package/templates/apps/api/e2e/capture-evidence.ts.hbs +4 -1
- package/templates/apps/api/eslint.config.js.hbs +3 -1
- package/templates/apps/api/images/serv.Dockerfile.hbs +15 -10
- package/templates/apps/api/playwright.config.ts.hbs +23 -19
- package/templates/apps/api/pnpm-workspace.yaml.hbs +27 -16
- package/templates/apps/fullstack/.dockerignore.hbs +10 -0
- package/templates/apps/fullstack/.gitignore.hbs +7 -2
- package/templates/apps/fullstack/apps/{{projectName}}-app/README.md.hbs +14 -12
- package/templates/apps/fullstack/apps/{{projectName}}-app/capacitor.config.ts.hbs +5 -3
- package/templates/apps/fullstack/apps/{{projectName}}-app/eslint.config.js.hbs +10 -2
- package/templates/apps/fullstack/apps/{{projectName}}-app/package.json.hbs +1 -1
- package/templates/apps/fullstack/apps/{{projectName}}-app/src/App.svelte.hbs +10 -2
- package/templates/apps/fullstack/apps/{{projectName}}-app/src/build-metadata.ts.hbs +0 -1
- package/templates/apps/fullstack/apps/{{projectName}}-app/src/lib/capacitor.ts.hbs +0 -1
- package/templates/apps/fullstack/apps/{{projectName}}-app/svelte.config.js.hbs +4 -1
- package/templates/apps/fullstack/apps/{{projectName}}-app/vite.config.ts.hbs +16 -4
- package/templates/apps/fullstack/apps/{{projectName}}-desktop/README.md.hbs +10 -8
- package/templates/apps/fullstack/apps/{{projectName}}-desktop/package.json.hbs +3 -3
- package/templates/apps/fullstack/apps/{{projectName}}-desktop/src/App.svelte.hbs +8 -2
- package/templates/apps/fullstack/apps/{{projectName}}-desktop/src/build-metadata.ts.hbs +0 -1
- package/templates/apps/fullstack/apps/{{projectName}}-desktop/src-tauri/tauri.conf.json.hbs +0 -2
- package/templates/apps/fullstack/apps/{{projectName}}-desktop/svelte.config.js.hbs +4 -1
- package/templates/apps/fullstack/apps/{{projectName}}-desktop/vite.config.ts.hbs +16 -4
- package/templates/apps/fullstack/apps/{{projectName}}-miniapp/README.md.hbs +2 -0
- package/templates/apps/fullstack/apps/{{projectName}}-web/README.md.hbs +9 -9
- package/templates/apps/fullstack/apps/{{projectName}}-web/eslint.config.js.hbs +10 -2
- package/templates/apps/fullstack/apps/{{projectName}}-web/index.html.hbs +1 -0
- package/templates/apps/fullstack/apps/{{projectName}}-web/src/build-metadata.ts.hbs +0 -1
- package/templates/apps/fullstack/apps/{{projectName}}-web/src/main.ts.hbs +0 -2
- package/templates/apps/fullstack/apps/{{projectName}}-web/svelte.config.js.hbs +4 -1
- package/templates/apps/fullstack/apps/{{projectName}}-web/vite.config.ts.hbs +19 -5
- package/templates/apps/fullstack/docs/security-configuration.md.hbs +4 -1
- package/templates/apps/fullstack/e2e/fullstack.spec.ts.hbs +140 -28
- package/templates/apps/fullstack/e2e/session-close.spec.ts.hbs +19 -5
- package/templates/apps/fullstack/eslint.config.js.hbs +3 -1
- package/templates/apps/fullstack/images/serv.Dockerfile.hbs +19 -11
- package/templates/apps/fullstack/images/web.Dockerfile.hbs +17 -8
- package/templates/apps/fullstack/package.json.hbs +2 -1
- package/templates/apps/fullstack/packages/{{projectName}}-contract/README.md.hbs +7 -5
- package/templates/apps/fullstack/packages/{{projectName}}-contract/src/admin-contract.ts.hbs +114 -23
- package/templates/apps/fullstack/packages/{{projectName}}-contract/src/admin-schemas.ts.hbs +57 -11
- package/templates/apps/fullstack/packages/{{projectName}}-contract/tsup.config.ts.hbs +3 -1
- package/templates/apps/fullstack/packages/{{projectName}}-serv/README.md.hbs +17 -7
- package/templates/apps/fullstack/packages/{{projectName}}-serv/config/_reach.yml.hbs +13 -7
- package/templates/apps/fullstack/packages/{{projectName}}-serv/config/_serv.yml.hbs +17 -7
- package/templates/apps/fullstack/packages/{{projectName}}-serv/package.json.hbs +10 -4
- package/templates/apps/fullstack/packages/{{projectName}}-serv/src/app-server.ts.hbs +65 -30
- package/templates/apps/fullstack/packages/{{projectName}}-serv/src/build-metadata.ts.hbs +0 -1
- package/templates/apps/fullstack/packages/{{projectName}}-serv/src/index.ts.hbs +1 -2
- package/templates/apps/fullstack/packages/{{projectName}}-serv/src/server/admin-service.ts.hbs +69 -21
- package/templates/apps/fullstack/packages/{{projectName}}-serv/src/server/business-settings.ts.hbs +21 -5
- package/templates/apps/fullstack/packages/{{projectName}}-serv/src/server/procedures/admin-procedures.ts.hbs +63 -11
- package/templates/apps/fullstack/packages/{{projectName}}-serv/src/server/procedures/app-procedures.ts.hbs +6 -1
- package/templates/apps/fullstack/packages/{{projectName}}-serv/src/server/procedures/index.ts.hbs +3 -1
- package/templates/apps/fullstack/packages/{{projectName}}-serv/src/server/runtime.ts.hbs +147 -33
- package/templates/apps/fullstack/packages/{{projectName}}-serv/src/server/security-roles.ts.hbs +43 -12
- package/templates/apps/fullstack/packages/{{projectName}}-serv/tests/app-server.test.ts.hbs +146 -30
- package/templates/apps/fullstack/packages/{{projectName}}-serv/tests/runtime.test.ts.hbs +33 -10
- package/templates/apps/fullstack/packages/{{projectName}}-serv/tests/security.test.ts.hbs +142 -26
- package/templates/apps/fullstack/packages/{{projectName}}-serv/tsup.config.ts.hbs +6 -2
- package/templates/apps/fullstack/packages/{{projectName}}-serv/vitest.config.ts.hbs +3 -1
- package/templates/apps/fullstack/packages/{{projectName}}-shared/README.md.hbs +48 -66
- package/templates/apps/fullstack/packages/{{projectName}}-shared/messages/en-US.json.hbs +1 -0
- package/templates/apps/fullstack/packages/{{projectName}}-shared/messages/ja-JP.json.hbs +1 -0
- package/templates/apps/fullstack/packages/{{projectName}}-shared/messages/zh-CN.json.hbs +1 -0
- package/templates/apps/fullstack/packages/{{projectName}}-shared/src/lib/api/api-client.ts.hbs +9 -2
- package/templates/apps/fullstack/packages/{{projectName}}-shared/src/lib/api/feedback-client.ts.hbs +0 -3
- package/templates/apps/fullstack/packages/{{projectName}}-shared/src/lib/api/sensitive-actions.svelte.ts.hbs +15 -3
- package/templates/apps/fullstack/packages/{{projectName}}-shared/src/lib/components/AppShell.svelte.hbs +33 -7
- package/templates/apps/fullstack/packages/{{projectName}}-shared/src/lib/components/FeedbackEntry.svelte.hbs +16 -2
- package/templates/apps/fullstack/packages/{{projectName}}-shared/src/lib/pages/audit.svelte.hbs +104 -13
- package/templates/apps/fullstack/packages/{{projectName}}-shared/src/lib/pages/feedback.svelte.hbs +37 -7
- package/templates/apps/fullstack/packages/{{projectName}}-shared/src/lib/pages/roles.svelte.hbs +9 -3
- package/templates/apps/fullstack/packages/{{projectName}}-shared/src/lib/pages/settings.svelte.hbs +25 -3
- package/templates/apps/fullstack/packages/{{projectName}}-shared/src/lib/pages/users.svelte.hbs +133 -19
- package/templates/apps/fullstack/packages/{{projectName}}-shared/src/lib/security/role-label.ts.hbs +14 -2
- package/templates/apps/fullstack/packages/{{projectName}}-shared/src/lib/stores/guide-store.ts.hbs +66 -34
- package/templates/apps/fullstack/packages/{{projectName}}-shared/src/lib/stores/management-store.svelte.ts.hbs +132 -30
- package/templates/apps/fullstack/packages/{{projectName}}-shared/src/lib/stores/theme-store.svelte.ts.hbs +8 -2
- package/templates/apps/fullstack/packages/{{projectName}}-shared/tests/api-client.test.ts.hbs +23 -5
- package/templates/apps/fullstack/packages/{{projectName}}-shared/tests/management-store.test.ts.hbs +143 -21
- package/templates/apps/fullstack/packages/{{projectName}}-shared/vitest.config.ts.hbs +7 -2
- package/templates/apps/fullstack/playwright.config.ts.hbs +25 -3
- package/templates/apps/fullstack/pnpm-workspace.yaml.hbs +30 -14
- package/templates/apps/h5/src/routes/+layout.svelte.hbs +74 -30
- package/templates/apps/h5/src/routes/+page.svelte.hbs +2 -2
- package/templates/apps/h5/src/routes/discover/+page.svelte.hbs +2 -2
- package/templates/apps/h5/src/routes/profile/+page.svelte.hbs +2 -2
- package/templates/apps/mobile-app/capacitor.config.ts.hbs +5 -2
- package/templates/apps/mobile-app/messages/en-US.json +2 -2
- package/templates/apps/mobile-app/messages/ja-JP.json +2 -2
- package/templates/apps/mobile-app/messages/zh-CN.json +2 -2
- package/templates/apps/mobile-app/src/App.svelte.hbs +17 -5
- package/templates/apps/mobile-app/src/lib/api.ts.hbs +20 -6
- package/templates/apps/mobile-app/src/lib/app-config.ts.hbs +8 -1
- package/templates/apps/mobile-app/src/lib/pages/home.svelte.hbs +6 -2
- package/templates/apps/mobile-app/src/lib/pages/profile.svelte.hbs +13 -1
- package/templates/apps/mobile-app/src/lib/pages/tasks.svelte.hbs +5 -1
- package/templates/apps/website/scripts/static-website.mjs.hbs +19 -6
- package/templates/apps/website/src/routes/+layout.svelte.hbs +56 -29
- package/templates/apps/website/src/routes/+page.svelte.hbs +4 -4
- package/templates/apps/website/src/routes/about/+page.svelte.hbs +2 -2
- package/templates/apps/website/src/routes/contact/+page.svelte.hbs +2 -2
- package/templates/apps/website/src/routes/services/+page.svelte.hbs +20 -5
- package/templates/base/.dockerignore.hbs +10 -0
- package/templates/base/.gitignore.hbs +7 -2
- package/templates/base/e2e/app.spec.ts.hbs +130 -36
- package/templates/base/eslint-rules.js +44 -25
- package/templates/base/eslint.config.js.hbs +3 -1
- package/templates/base/images/web.Dockerfile.hbs +25 -14
- package/templates/base/package.json.hbs +13 -7
- package/templates/base/patches/daisyui-5.7.50.patch +8 -0
- package/templates/base/patches/deepmerge-4.3.1.patch +51 -0
- package/templates/base/playwright.config.ts +3 -1
- package/templates/base/pnpm-workspace.yaml.hbs +33 -16
- package/templates/base/src/app.d.ts.hbs +1 -1
- package/templates/base/src/app.html.hbs +1 -0
- package/templates/base/src/hooks.server.ts.hbs +44 -33
- package/templates/base/src/lib/build-metadata.ts.hbs +0 -1
- package/templates/base/src/lib/server/init.ts.hbs +146 -35
- package/templates/base/src/lib/server/kit-config.ts.hbs +7 -4
- package/templates/base/src/routes/+layout.server.ts.hbs +2 -2
- package/templates/base/svelte.config.js.hbs +10 -100
- package/templates/base/tests/scaffold.test.ts.hbs +12 -3
- package/templates/base/tsconfig.json.hbs +7 -4
- package/templates/base/vite.config.ts.hbs +108 -14
- package/templates/base/vitest.config.ts.hbs +6 -2
- package/templates/features/ai/routes/api/chat/+server.ts +3 -1
- package/templates/features/iam/routes-admin/(auth)/auth/forgot-password/+page.svelte.hbs +3 -3
- package/templates/features/iam/routes-admin/(auth)/auth/login/+page.svelte.hbs +3 -3
- package/templates/features/iam/routes-admin/(auth)/auth/register/+page.svelte.hbs +3 -3
- package/templates/features/iam/routes-admin/(auth)/auth/reset-password/+page.svelte.hbs +3 -3
- package/templates/features/iam/routes-h5/auth/forgot-password/+page.svelte.hbs +3 -3
- package/templates/features/iam/routes-h5/auth/login/+page.svelte.hbs +3 -3
- package/templates/features/iam/routes-h5/auth/register/+page.svelte.hbs +3 -3
- package/templates/features/iam/routes-h5/auth/reset-password/+page.svelte.hbs +3 -3
- package/templates/features/iam/routes-website/auth/forgot-password/+page.svelte.hbs +3 -3
- package/templates/features/iam/routes-website/auth/login/+page.svelte.hbs +3 -3
- package/templates/features/iam/routes-website/auth/register/+page.svelte.hbs +3 -3
- package/templates/features/iam/routes-website/auth/reset-password/+page.svelte.hbs +3 -3
- package/templates/features/payment/routes/api/v1/payment/create/+server.ts +14 -3
- package/templates/shared/browser-check/startup.js +115 -0
- package/templates/shared/browser-check/update.css +37 -0
- package/templates/shared/browser-check/update.html +19 -0
- package/templates/shared/browser-startup.spec.ts +23 -0
- package/templates/shared/build-metadata.ts +18 -4
- package/templates/shared/e2e-env.ts +22 -6
- package/templates/shared/native-name.d.mts +5 -0
- package/templates/shared/native-name.mjs +94 -0
- package/templates/shared/public-base-path.mjs +17 -4
- package/templates/shared/run-e2e.mjs +46 -12
- package/templates/shared/run-node.mjs +56 -0
- package/templates/shared/run-tauri.mjs +74 -0
- package/templates/shared/vite-runtime-config.ts +9 -3
- package/templates/skills/AGENTS.md +10 -73
- package/templates/skills/bridges/admin/AGENTS.md +9 -65
- package/templates/skills/bridges/api/AGENTS.md +8 -59
- package/templates/skills/bridges/fullstack/AGENTS.md.hbs +9 -54
- package/templates/skills/bridges/h5/AGENTS.md +8 -63
- package/templates/skills/bridges/mobile-app/AGENTS.md +8 -62
- package/templates/skills/bridges/website/AGENTS.md +8 -63
- package/templates/skills/hai-ai/SKILL.md +6 -2
- package/templates/skills/hai-ai/acp.md +153 -0
- package/templates/skills/hai-ai/guide.md +27 -12
- package/templates/skills/hai-ai/reference.md +24 -15
- package/templates/skills/hai-ai/resources.md +69 -0
- package/templates/skills/hai-api-client/SKILL.md +1 -1
- package/templates/skills/hai-api-client/reference.md +3 -1
- package/templates/skills/hai-app-create/collaboration.md +7 -0
- package/templates/skills/hai-app-create/development.md +19 -10
- package/templates/skills/hai-app-create/project.md +33 -0
- package/templates/skills/hai-app-create/reference.md +10 -10
- package/templates/skills/hai-app-tests/reference.md +1 -1
- package/templates/skills/hai-app-tests/validation.md +1 -0
- package/templates/skills/hai-build/SKILL.md +19 -9
- package/templates/skills/hai-build/paths.md +4 -2
- package/templates/skills/hai-build/reference.md +26 -8
- package/templates/skills/hai-cache/reference.md +6 -2
- package/templates/skills/hai-capacitor/SKILL.md +1 -0
- package/templates/skills/hai-capacitor/reference.md +24 -0
- package/templates/skills/hai-ci/SKILL.md +3 -0
- package/templates/skills/hai-core/SKILL.md +9 -4
- package/templates/skills/hai-core/reference.md +40 -10
- package/templates/skills/hai-core/request-access.md +2 -2
- package/templates/skills/hai-crypto/SKILL.md +2 -2
- package/templates/skills/hai-crypto/reference.md +7 -3
- package/templates/skills/hai-deploy/SKILL.md +41 -5
- package/templates/skills/hai-deploy/middleware.md +26 -14
- package/templates/skills/hai-framework-sync/SKILL.md +13 -9
- package/templates/skills/hai-framework-sync/sync.md +2 -0
- package/templates/skills/hai-iam/reference.md +2 -2
- package/templates/skills/hai-kit/SKILL.md +1 -1
- package/templates/skills/hai-kit/reference.md +19 -5
- package/templates/skills/hai-payment/reference.md +41 -17
- package/templates/skills/hai-reach/SKILL.md +3 -1
- package/templates/skills/hai-reach/reference.md +29 -9
- package/templates/skills/hai-reldb/SKILL.md +1 -1
- package/templates/skills/hai-reldb/reference.md +9 -2
- package/templates/skills/hai-scheduler/reference.md +1 -1
- package/templates/skills/hai-serv/SKILL.md +2 -1
- package/templates/skills/hai-serv/reference.md +26 -15
- package/templates/skills/hai-storage/reference.md +23 -6
- package/templates/skills/hai-ui/SKILL.md +11 -6
- package/templates/skills/hai-ui/charts.md +51 -0
- package/templates/skills/hai-ui/guide.md +1 -1
- package/templates/skills/hai-ui/reference.md +58 -38
- package/templates/skills/hai-vecdb/reference.md +8 -3
- package/dist/chunk-AKV2CQZV.js.map +0 -1
- package/dist/chunk-EF7WOFWZ.js.map +0 -1
- package/dist/chunk-MUHRBJSW.js +0 -29272
- package/dist/chunk-MUHRBJSW.js.map +0 -1
- package/dist/cli-config-templates-HHFHNXBN.js +0 -5
- package/dist/src-TEBHR5I5.js +0 -5
- package/dist/src-TEBHR5I5.js.map +0 -1
- package/templates/apps/fullstack/playwright.session-close.config.ts.hbs +0 -18
|
@@ -2,6 +2,11 @@ import { svelte } from '@sveltejs/vite-plugin-svelte'
|
|
|
2
2
|
import { defineConfig } from 'vitest/config'
|
|
3
3
|
|
|
4
4
|
export default defineConfig({
|
|
5
|
-
plugins: [
|
|
6
|
-
|
|
5
|
+
plugins: [
|
|
6
|
+
svelte(),
|
|
7
|
+
],
|
|
8
|
+
test: {
|
|
9
|
+
environment: 'node',
|
|
10
|
+
include: ['tests/**/*.test.ts'],
|
|
11
|
+
},
|
|
7
12
|
})
|
|
@@ -2,6 +2,9 @@ import process from 'node:process'
|
|
|
2
2
|
import { defineConfig } from '@playwright/test'
|
|
3
3
|
import { createE2eNotificationEnv, createE2eServerEnv, createE2eTransportRing } from './scripts/e2e-env.js'
|
|
4
4
|
|
|
5
|
+
{{#if fullstack.e2eFrontend}}
|
|
6
|
+
const sessionClose = process.env.HAI_E2E_GROUP === 'session-close'
|
|
7
|
+
{{/if}}
|
|
5
8
|
const defaultBaseURL = '{{#if fullstack.e2eFrontend}}http://127.0.0.1:{{fullstack.e2eFrontend.port}}{{else}}http://127.0.0.1:3000{{/if}}'
|
|
6
9
|
const defaultServiceBaseURL = 'http://127.0.0.1:3000'
|
|
7
10
|
const baseURL = process.env.BASE_URL || defaultBaseURL
|
|
@@ -41,7 +44,9 @@ function resolvePortFromBaseUrl(urlString: string, fallbackPort: string): string
|
|
|
41
44
|
return url.port
|
|
42
45
|
}
|
|
43
46
|
|
|
44
|
-
return url.protocol === 'https:'
|
|
47
|
+
return url.protocol === 'https:'
|
|
48
|
+
? '443'
|
|
49
|
+
: '80'
|
|
45
50
|
}
|
|
46
51
|
catch {
|
|
47
52
|
return fallbackPort
|
|
@@ -50,7 +55,11 @@ function resolvePortFromBaseUrl(urlString: string, fallbackPort: string): string
|
|
|
50
55
|
|
|
51
56
|
export default defineConfig({
|
|
52
57
|
testDir: './e2e',
|
|
53
|
-
|
|
58
|
+
{{#if fullstack.e2eFrontend}}
|
|
59
|
+
...(sessionClose
|
|
60
|
+
? { testMatch: '**/session-close.spec.ts' }
|
|
61
|
+
: { testIgnore: '**/session-close.spec.ts' }),
|
|
62
|
+
{{/if}}
|
|
54
63
|
// 多个界面验收共用管理员资料与引导状态,保留串行以免互相覆盖。
|
|
55
64
|
fullyParallel: false,
|
|
56
65
|
forbidOnly: !!process.env.CI,
|
|
@@ -87,6 +96,17 @@ export default defineConfig({
|
|
|
87
96
|
HAI_IAM_CAPTCHA_COST: '100',
|
|
88
97
|
HAI_IAM_CAPTCHA_MAXCOUNTER: '2',
|
|
89
98
|
HAI_IAM_INITIALCREDENTIALS_ENABLED: 'true',
|
|
99
|
+
{{#if fullstack.e2eFrontend}}
|
|
100
|
+
// 会话回归单独启动服务,短超时和首次改密仅应用于这一轮。
|
|
101
|
+
...(sessionClose
|
|
102
|
+
? {
|
|
103
|
+
HAI_IAM_SESSION_ENDONPAGEHIDE: 'true',
|
|
104
|
+
HAI_IAM_SESSION_IDLETIMEOUT: '5',
|
|
105
|
+
HAI_IAM_SESSION_ABSOLUTETIMEOUT: '60',
|
|
106
|
+
HAI_IAM_PASSWORD_REQUIREINITIALCHANGE: 'true',
|
|
107
|
+
}
|
|
108
|
+
: {}),
|
|
109
|
+
{{/if}}
|
|
90
110
|
HAI_IAM_REAUTHENTICATION_ENABLED: 'true',
|
|
91
111
|
HAI_IAM_REAUTHENTICATION_OPERATIONS: JSON.stringify(['iam.users.invite', 'audit.backup']),
|
|
92
112
|
HAI_AUDIT_BACKUP_ENABLED: 'true',
|
|
@@ -100,7 +120,9 @@ export default defineConfig({
|
|
|
100
120
|
timeout: 120_000,
|
|
101
121
|
},
|
|
102
122
|
...frontends.map((frontend) => {
|
|
103
|
-
const url = frontend.target === primaryFrontend
|
|
123
|
+
const url = frontend.target === primaryFrontend
|
|
124
|
+
? baseURL
|
|
125
|
+
: frontend.url
|
|
104
126
|
return {
|
|
105
127
|
name: frontend.name,
|
|
106
128
|
command: `pnpm --filter ${frontend.name} exec vite preview --host ${resolveHostFromBaseUrl(url, '127.0.0.1')} --port ${resolvePortFromBaseUrl(url, '3000')} --strictPort`,
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
{{! @skipIfEmpty }}
|
|
2
|
-
|
|
2
|
+
minimumReleaseAgeExcludePrune: true
|
|
3
3
|
|
|
4
4
|
trustPolicy: no-downgrade
|
|
5
5
|
# 上游构建工具仍要求 4.x;4.0.3 tarball 已核对原 lockfile 的 SHA-512。
|
|
@@ -8,31 +8,47 @@ trustPolicyExclude:
|
|
|
8
8
|
|
|
9
9
|
# pnpm 12 配置;原生依赖仅运行明确列出的安装脚本。
|
|
10
10
|
nodeLinker: hoisted
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
core-js: false
|
|
11
|
+
shellEmulator: true
|
|
12
|
+
|
|
13
|
+
packages:
|
|
14
|
+
- packages/*
|
|
15
|
+
- apps/*
|
|
17
16
|
|
|
17
|
+
# 构建与浏览器依赖的安全修复;版本与框架工作区同步维护。
|
|
18
18
|
overrides:
|
|
19
|
-
|
|
19
|
+
'@ai-sdk/provider-utils@>=4.0.0 <4.0.33': 4.0.57
|
|
20
|
+
'@types/node': {{versions.nodeTypes}}
|
|
21
|
+
body-parser@>=2 <2.4.0: 2.4.0
|
|
20
22
|
cookie@<0.7.0: 0.7.2
|
|
23
|
+
dompurify@>=3 <3.4.17: 3.4.17
|
|
21
24
|
esbuild@<0.28.1: 0.28.2
|
|
25
|
+
fast-uri@>=3 <3.1.9: 3.1.9
|
|
26
|
+
follow-redirects@>=1.16.0 <1.16.2: 1.16.2
|
|
27
|
+
glob@>=9 <=14.0.1: 14.0.4
|
|
28
|
+
ip-address@<=10.7.3: 10.7.6
|
|
22
29
|
katex@<0.18.2: 0.18.10
|
|
30
|
+
minimatch@>=7 <11.0.1: 11.0.5
|
|
31
|
+
parse5@>=8 <8.1.0: 8.1.0
|
|
32
|
+
qs@>=6.7 <6.16.1: 6.17.1
|
|
33
|
+
runed@<0.38.0: 0.38.0
|
|
23
34
|
sharp@<0.35.5: 0.35.5
|
|
24
35
|
tinypool@<2.1.2: 2.2.0
|
|
25
|
-
'@qdrant/js-client-rest>undici': 7.30.0
|
|
26
36
|
xcode>uuid: 11.1.1
|
|
27
|
-
"@types/node": "{{versions.nodeTypes}}"
|
|
28
37
|
|
|
29
|
-
|
|
30
|
-
-
|
|
31
|
-
-
|
|
38
|
+
patchedDependencies:
|
|
39
|
+
daisyui@5.7.50: patches/daisyui-5.7.50.patch
|
|
40
|
+
deepmerge@4.3.1: patches/deepmerge-4.3.1.patch
|
|
41
|
+
|
|
42
|
+
allowBuilds:
|
|
43
|
+
core-js: false
|
|
44
|
+
esbuild: true
|
|
45
|
+
onnxruntime-node: true
|
|
46
|
+
protobufjs: true
|
|
47
|
+
vue-demi: true
|
|
32
48
|
|
|
33
49
|
{{#if useCatalogProtocol}}
|
|
34
50
|
catalog:
|
|
35
51
|
{{#each haiCatalogPackages}}
|
|
36
|
-
|
|
52
|
+
{{{yaml @key this}}}
|
|
37
53
|
{{/each}}
|
|
38
54
|
{{/if}}
|
|
@@ -5,20 +5,10 @@
|
|
|
5
5
|
*/
|
|
6
6
|
import type { BottomNavItem } from '@h-ai/ui'
|
|
7
7
|
import type { Snippet } from 'svelte'
|
|
8
|
-
{
|
|
9
|
-
import { browser } from '$app/environment'
|
|
10
|
-
{{else}}
|
|
11
|
-
{{#if features.crypto}}
|
|
12
|
-
import { browser } from '$app/environment'
|
|
13
|
-
{{/if}}
|
|
14
|
-
{{/if}}
|
|
8
|
+
import { browser } from '$app/env'
|
|
15
9
|
import { goto } from '$app/navigation'
|
|
16
|
-
import {
|
|
10
|
+
import { resolve } from '$app/paths'
|
|
17
11
|
import { page } from '$app/state'
|
|
18
|
-
{{#if hasI18n}}
|
|
19
|
-
import * as m from '$lib/paraglide/messages'
|
|
20
|
-
import { getLocale, setLocale } from '$lib/paraglide/runtime.js'
|
|
21
|
-
{{/if}}
|
|
22
12
|
{{#if features.crypto}}
|
|
23
13
|
import { crypto } from '@h-ai/crypto'
|
|
24
14
|
import { kit } from '@h-ai/kit'
|
|
@@ -28,12 +18,17 @@
|
|
|
28
18
|
{{/if}}
|
|
29
19
|
{{/if}}
|
|
30
20
|
{{#if hasI18n}}
|
|
31
|
-
import { AppBar, BottomNav, LanguageSwitch, setGlobalLocale } from '@h-ai/ui'
|
|
21
|
+
import { AppBar, BottomNav, LanguageSwitch, setGlobalLocale, ThemeSelector } from '@h-ai/ui'
|
|
32
22
|
{{else}}
|
|
33
|
-
import { AppBar, BottomNav } from '@h-ai/ui'
|
|
23
|
+
import { AppBar, BottomNav, ThemeSelector } from '@h-ai/ui'
|
|
34
24
|
{{/if}}
|
|
25
|
+
import { applyTheme, getSavedTheme } from '@h-ai/ui/theme'
|
|
35
26
|
{{#if features.crypto}}
|
|
36
27
|
import { untrack } from 'svelte'
|
|
28
|
+
{{/if}}
|
|
29
|
+
{{#if hasI18n}}
|
|
30
|
+
import * as m from '#lib/paraglide/messages.js'
|
|
31
|
+
import { getLocale, setLocale } from '#lib/paraglide/runtime.js'
|
|
37
32
|
{{/if}}
|
|
38
33
|
import '../app.css'
|
|
39
34
|
|
|
@@ -42,36 +37,82 @@
|
|
|
42
37
|
}
|
|
43
38
|
|
|
44
39
|
const { children }: Props = $props()
|
|
45
|
-
|
|
40
|
+
const initialTheme = browser
|
|
41
|
+
? getSavedTheme()
|
|
42
|
+
: 'light'
|
|
43
|
+
let currentTheme = $state(initialTheme)
|
|
46
44
|
if (browser)
|
|
47
|
-
|
|
45
|
+
applyTheme(initialTheme, false)
|
|
46
|
+
|
|
47
|
+
function handleThemeChange(theme: string) {
|
|
48
|
+
currentTheme = theme
|
|
49
|
+
applyTheme(theme)
|
|
50
|
+
}
|
|
51
|
+
{{#if features.crypto}}
|
|
52
|
+
if (browser) {
|
|
53
|
+
kit.client.installBrowserTransport(untrack(() => page.data.kitConfig), {
|
|
54
|
+
crypto,
|
|
55
|
+
basePath: resolve('/').replace(/\/$/, ''),
|
|
56
|
+
})
|
|
57
|
+
}
|
|
48
58
|
{{/if}}
|
|
49
59
|
{{#if features.iam}}
|
|
50
|
-
const authActions = kit.client.createAuthActions({ basePath: `${
|
|
60
|
+
const authActions = kit.client.createAuthActions({ basePath: `${resolve('/').replace(/\/$/, '')}/api/auth` })
|
|
51
61
|
$effect(() => authActions.bindPageExit({ enabled: page.data.iamPublicConfig?.session.endOnPageHide }))
|
|
52
62
|
{{/if}}
|
|
53
63
|
|
|
54
|
-
const navItems: (BottomNavItem & { path:
|
|
64
|
+
const navItems: (BottomNavItem & { path: ReturnType<typeof resolve> })[] = [
|
|
55
65
|
{{#if hasI18n}}
|
|
56
|
-
{
|
|
57
|
-
|
|
58
|
-
|
|
66
|
+
{
|
|
67
|
+
id: 'home',
|
|
68
|
+
path: resolve('/'),
|
|
69
|
+
label: m.nav_home(),
|
|
70
|
+
iconClass: 'icon-[tabler--home]',
|
|
71
|
+
},
|
|
72
|
+
{
|
|
73
|
+
id: 'discover',
|
|
74
|
+
path: resolve('discover'),
|
|
75
|
+
label: m.nav_discover(),
|
|
76
|
+
iconClass: 'icon-[tabler--compass]',
|
|
77
|
+
},
|
|
78
|
+
{
|
|
79
|
+
id: 'profile',
|
|
80
|
+
path: resolve('profile'),
|
|
81
|
+
label: m.nav_profile(),
|
|
82
|
+
iconClass: 'icon-[tabler--user]',
|
|
83
|
+
},
|
|
59
84
|
{{else}}
|
|
60
|
-
{
|
|
61
|
-
|
|
62
|
-
|
|
85
|
+
{
|
|
86
|
+
id: 'home',
|
|
87
|
+
path: resolve('/'),
|
|
88
|
+
label: '首页',
|
|
89
|
+
iconClass: 'icon-[tabler--home]',
|
|
90
|
+
},
|
|
91
|
+
{
|
|
92
|
+
id: 'discover',
|
|
93
|
+
path: resolve('discover'),
|
|
94
|
+
label: '发现',
|
|
95
|
+
iconClass: 'icon-[tabler--compass]',
|
|
96
|
+
},
|
|
97
|
+
{
|
|
98
|
+
id: 'profile',
|
|
99
|
+
path: resolve('profile'),
|
|
100
|
+
label: '我的',
|
|
101
|
+
iconClass: 'icon-[tabler--user]',
|
|
102
|
+
},
|
|
63
103
|
{{/if}}
|
|
64
104
|
]
|
|
65
105
|
|
|
66
|
-
const localPath = $derived(page.url.pathname.slice(
|
|
67
|
-
const activeNav = $derived(navItems.find(item => item.path ===
|
|
106
|
+
const localPath = $derived(page.url.pathname.slice(resolve('/').replace(/\/$/, '').length) || '/')
|
|
107
|
+
const activeNav = $derived(navItems.find(item => item.path === page.url.pathname)?.id)
|
|
68
108
|
// 所有页面共用页头页脚;仅业务页面显示底部导航。
|
|
69
109
|
const isAuthPage = $derived(localPath.startsWith('/auth'))
|
|
70
110
|
|
|
71
111
|
function handleNavigation(id: string) {
|
|
72
112
|
const item = navItems.find(item => item.id === id)
|
|
73
113
|
if (item)
|
|
74
|
-
|
|
114
|
+
// eslint-disable-next-line svelte/no-navigation-without-resolve -- path 仅来自上方 resolve 构造的导航表,不能二次添加挂载前缀。
|
|
115
|
+
void goto(item.path)
|
|
75
116
|
}
|
|
76
117
|
{{#if hasI18n}}
|
|
77
118
|
|
|
@@ -94,11 +135,14 @@
|
|
|
94
135
|
<div class='hai-mobile-viewport'>
|
|
95
136
|
<div class='hai-mobile-shell min-w-0'>
|
|
96
137
|
<AppBar title={page.data.appConfig.name} safeArea fixed={false}>
|
|
97
|
-
{{#if hasI18n}}
|
|
98
138
|
{#snippet trailing()}
|
|
99
|
-
<
|
|
100
|
-
|
|
139
|
+
<div class='flex items-center gap-1'>
|
|
140
|
+
{{#if hasI18n}}
|
|
141
|
+
<LanguageSwitch currentLanguage={getLocale()} onchange={handleLanguageChange} compact />
|
|
101
142
|
{{/if}}
|
|
143
|
+
<ThemeSelector {currentTheme} onchange={handleThemeChange} compact grouped={false} />
|
|
144
|
+
</div>
|
|
145
|
+
{/snippet}
|
|
102
146
|
</AppBar>
|
|
103
147
|
<main class='hai-mobile-main'>{@render children()}</main>
|
|
104
148
|
<footer class='border-t border-base-300 bg-base-100 p-2 text-center text-xs text-base-content/60'>
|
|
@@ -1,12 +1,15 @@
|
|
|
1
1
|
import type { CapacitorConfig } from '@capacitor/cli'
|
|
2
|
+
import { resolve } from 'node:path'
|
|
3
|
+
import process from 'node:process'
|
|
4
|
+
import { resolveNativeName } from './scripts/native-name.mjs'
|
|
2
5
|
|
|
3
6
|
const config: CapacitorConfig = {
|
|
4
7
|
appId: 'com.hai.{{projectName}}',
|
|
5
|
-
appName: '
|
|
8
|
+
appName: resolveNativeName(process.cwd(), resolve('config/_core.yml')),
|
|
6
9
|
webDir: 'dist',
|
|
7
10
|
server: {
|
|
8
11
|
androidScheme: 'https',
|
|
9
12
|
},
|
|
10
13
|
}
|
|
11
14
|
|
|
12
|
-
export default config
|
|
15
|
+
export default config
|
|
@@ -24,13 +24,13 @@
|
|
|
24
24
|
"status_runtime_web": "Browser preview",
|
|
25
25
|
"status_token_label": "Token storage",
|
|
26
26
|
"status_token_native": "Secure storage",
|
|
27
|
-
"status_token_memory": "Memory
|
|
27
|
+
"status_token_memory": "Memory access token + httpOnly cookie",
|
|
28
28
|
"tasks_title": "Today's tasks",
|
|
29
29
|
"tasks_sync": "Wire backend APIs",
|
|
30
30
|
"tasks_polish": "Polish mobile UX",
|
|
31
31
|
"tasks_release": "Prepare native packaging",
|
|
32
32
|
"profile_title": "App settings",
|
|
33
33
|
"profile_language": "Locale follows Paraglide",
|
|
34
|
-
"profile_theme": "Theme
|
|
34
|
+
"profile_theme": "Theme",
|
|
35
35
|
"profile_secure": "Sensitive tokens avoid localStorage"
|
|
36
36
|
}
|
|
@@ -24,13 +24,13 @@
|
|
|
24
24
|
"status_runtime_web": "ブラウザープレビュー",
|
|
25
25
|
"status_token_label": "トークン保存",
|
|
26
26
|
"status_token_native": "安全なストレージ",
|
|
27
|
-
"status_token_memory": "
|
|
27
|
+
"status_token_memory": "メモリー内access token + httpOnly Cookie",
|
|
28
28
|
"tasks_title": "本日のタスク",
|
|
29
29
|
"tasks_sync": "バックエンドAPIを接続",
|
|
30
30
|
"tasks_polish": "モバイルUXを改善",
|
|
31
31
|
"tasks_release": "ネイティブのパッケージ化を準備",
|
|
32
32
|
"profile_title": "アプリ設定",
|
|
33
33
|
"profile_language": "言語はParaglideに従います",
|
|
34
|
-
"profile_theme": "
|
|
34
|
+
"profile_theme": "テーマ",
|
|
35
35
|
"profile_secure": "機密トークンはlocalStorageに保存しません"
|
|
36
36
|
}
|
|
@@ -24,13 +24,13 @@
|
|
|
24
24
|
"status_runtime_web": "浏览器预览",
|
|
25
25
|
"status_token_label": "Token 存储",
|
|
26
26
|
"status_token_native": "安全存储",
|
|
27
|
-
"status_token_memory": "
|
|
27
|
+
"status_token_memory": "内存 access token + httpOnly Cookie",
|
|
28
28
|
"tasks_title": "今日任务",
|
|
29
29
|
"tasks_sync": "同步后端接口",
|
|
30
30
|
"tasks_polish": "打磨移动端体验",
|
|
31
31
|
"tasks_release": "准备原生打包",
|
|
32
32
|
"profile_title": "应用设置",
|
|
33
33
|
"profile_language": "语言跟随 Paraglide",
|
|
34
|
-
"profile_theme": "
|
|
34
|
+
"profile_theme": "主题",
|
|
35
35
|
"profile_secure": "敏感 Token 不落 localStorage"
|
|
36
36
|
}
|
|
@@ -48,9 +48,21 @@
|
|
|
48
48
|
let nativeTokenStorage = $state(false)
|
|
49
49
|
|
|
50
50
|
const navItems = $derived([
|
|
51
|
-
{
|
|
52
|
-
|
|
53
|
-
|
|
51
|
+
{
|
|
52
|
+
id: 'home',
|
|
53
|
+
label: m.nav_home(),
|
|
54
|
+
iconClass: 'icon-[tabler--layout-dashboard]',
|
|
55
|
+
},
|
|
56
|
+
{
|
|
57
|
+
id: 'tasks',
|
|
58
|
+
label: m.nav_tasks(),
|
|
59
|
+
iconClass: 'icon-[tabler--checkbox]',
|
|
60
|
+
},
|
|
61
|
+
{
|
|
62
|
+
id: 'profile',
|
|
63
|
+
label: m.nav_profile(),
|
|
64
|
+
iconClass: 'icon-[tabler--user-circle]',
|
|
65
|
+
},
|
|
54
66
|
])
|
|
55
67
|
|
|
56
68
|
async function bootstrap(): Promise<void> {
|
|
@@ -143,10 +155,10 @@
|
|
|
143
155
|
</footer>
|
|
144
156
|
{{#if features.iam}}
|
|
145
157
|
{#if authenticated && !booting && !bootError}
|
|
146
|
-
{{/if}}
|
|
147
158
|
<BottomNav items={navItems} active={router.path.slice(1)} onchange={handleTabChange} safeArea centered maxWidth='none' />
|
|
148
|
-
{{#if features.iam}}
|
|
149
159
|
{/if}
|
|
160
|
+
{{else}}
|
|
161
|
+
<BottomNav items={navItems} active={router.path.slice(1)} onchange={handleTabChange} safeArea centered maxWidth='none' />
|
|
150
162
|
{{/if}}
|
|
151
163
|
</div>
|
|
152
164
|
</div>
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* {{projectName}} — API 客户端初始化。
|
|
3
|
-
* Web
|
|
3
|
+
* Web 预览使用内存 access token + httpOnly refresh Cookie;原生端使用 Capacitor 安全存储。
|
|
4
4
|
* 原生存储失败会拒绝 Promise;登录/退出调用方须处理 auth.setTokens/clear 失败并释放界面 loading。
|
|
5
5
|
*/
|
|
6
6
|
import { apiClient } from '@h-ai/api-client'
|
|
@@ -56,7 +56,7 @@ export function resolveApiBase(): string {
|
|
|
56
56
|
}
|
|
57
57
|
|
|
58
58
|
/**
|
|
59
|
-
* 查询实际 Capacitor 平台,决定安全原生存储或 Web
|
|
59
|
+
* 查询实际 Capacitor 平台,决定安全原生存储或 Web Cookie 刷新通道。
|
|
60
60
|
* @returns 是否处于 Capacitor 原生平台;浏览器预览返回 false。
|
|
61
61
|
* @throws Error - 平台模块加载或检测失败时拒绝 Promise,不伪装为 Web 模式。
|
|
62
62
|
* @example 模块内部上下文
|
|
@@ -74,7 +74,7 @@ export async function usesNativeTokenStorage(): Promise<boolean> {
|
|
|
74
74
|
|
|
75
75
|
/**
|
|
76
76
|
* 按真实平台创建 TokenStorage;绑定 client 后通过 client.auth 变更身份。
|
|
77
|
-
* @returns
|
|
77
|
+
* @returns 原生安全存储或内存 access token + httpOnly refresh Cookie;其方法的读写故障继续拒绝 Promise。
|
|
78
78
|
* @throws Error - 平台检测或存储工厂失败时拒绝,不改用较弱的持久化方式。
|
|
79
79
|
* @example 模块内部上下文
|
|
80
80
|
* ```ts
|
|
@@ -86,7 +86,7 @@ async function createTokenStorage() {
|
|
|
86
86
|
if (await usesNativeTokenStorage())
|
|
87
87
|
return createCapacitorTokenStorage()
|
|
88
88
|
|
|
89
|
-
return apiClient.tokenStorage.
|
|
89
|
+
return apiClient.tokenStorage.httpOnlyCookie()
|
|
90
90
|
}
|
|
91
91
|
|
|
92
92
|
/**
|
|
@@ -137,6 +137,7 @@ export async function initApi(): Promise<void> {
|
|
|
137
137
|
* ```
|
|
138
138
|
*/
|
|
139
139
|
async function initialize(): Promise<void> {
|
|
140
|
+
const native = await usesNativeTokenStorage()
|
|
140
141
|
const storage = await createTokenStorage()
|
|
141
142
|
{{#if features.crypto}}
|
|
142
143
|
const transport = resolveTransport()
|
|
@@ -149,8 +150,14 @@ async function initialize(): Promise<void> {
|
|
|
149
150
|
}
|
|
150
151
|
const result = await apiClient.init({
|
|
151
152
|
baseUrl: resolveApiBase(),
|
|
153
|
+
clientName: 'hai-mobile-app',
|
|
154
|
+
headers: native
|
|
155
|
+
? { 'x-hai-token-transport': 'body' }
|
|
156
|
+
: {},
|
|
152
157
|
auth: { storage },
|
|
153
|
-
...(transport
|
|
158
|
+
...(transport
|
|
159
|
+
? { transport }
|
|
160
|
+
: {}),
|
|
154
161
|
})
|
|
155
162
|
if (!result.success)
|
|
156
163
|
throw new Error(result.error.message)
|
|
@@ -169,7 +176,14 @@ async function initialize(): Promise<void> {
|
|
|
169
176
|
throw error
|
|
170
177
|
}
|
|
171
178
|
{{else}}
|
|
172
|
-
const result = await apiClient.init({
|
|
179
|
+
const result = await apiClient.init({
|
|
180
|
+
baseUrl: resolveApiBase(),
|
|
181
|
+
clientName: 'hai-mobile-app',
|
|
182
|
+
headers: native
|
|
183
|
+
? { 'x-hai-token-transport': 'body' }
|
|
184
|
+
: {},
|
|
185
|
+
auth: { storage },
|
|
186
|
+
})
|
|
173
187
|
if (!result.success)
|
|
174
188
|
throw new Error(result.error.message)
|
|
175
189
|
initialized = true
|
|
@@ -7,7 +7,14 @@ declare const __APP_CORE_CONFIG__: Pick<CoreConfig, 'name' | 'version' | 'env' |
|
|
|
7
7
|
|
|
8
8
|
/** 构建包含公开默认值;预览或容器启动时的公开配置覆盖默认值,不重建静态资源。 */
|
|
9
9
|
const runtime = (globalThis as typeof globalThis & { __HAI_PUBLIC_CONFIG__?: { core?: Partial<typeof __APP_CORE_CONFIG__> } }).__HAI_PUBLIC_CONFIG__?.core
|
|
10
|
-
export const appConfig = {
|
|
10
|
+
export const appConfig = {
|
|
11
|
+
...__APP_CORE_CONFIG__,
|
|
12
|
+
...runtime,
|
|
13
|
+
logging: {
|
|
14
|
+
...__APP_CORE_CONFIG__.logging,
|
|
15
|
+
...runtime?.logging,
|
|
16
|
+
},
|
|
17
|
+
}
|
|
11
18
|
|
|
12
19
|
export function initClientCore(): void {
|
|
13
20
|
core.init({ logging: appConfig.logging })
|
|
@@ -46,12 +46,16 @@
|
|
|
46
46
|
<div>
|
|
47
47
|
<p class='text-base-content/50'>{m.status_runtime_label()}</p>
|
|
48
48
|
<Badge variant={nativeRuntime ? 'success' : 'warning'} size='sm'>
|
|
49
|
-
{nativeRuntime
|
|
49
|
+
{nativeRuntime
|
|
50
|
+
? m.status_runtime_native()
|
|
51
|
+
: m.status_runtime_web()}
|
|
50
52
|
</Badge>
|
|
51
53
|
</div>
|
|
52
54
|
<div class='col-span-2'>
|
|
53
55
|
<p class='text-base-content/50'>{m.status_token_label()}</p>
|
|
54
|
-
<p class='font-medium'>{nativeTokenStorage
|
|
56
|
+
<p class='font-medium'>{nativeTokenStorage
|
|
57
|
+
? m.status_token_native()
|
|
58
|
+
: m.status_token_memory()}</p>
|
|
55
59
|
</div>
|
|
56
60
|
</div>
|
|
57
61
|
</Card>
|
|
@@ -1,12 +1,24 @@
|
|
|
1
1
|
<script lang='ts'>
|
|
2
|
+
import { ThemeSelector } from '@h-ai/ui'
|
|
3
|
+
import { applyTheme, getSavedTheme } from '@h-ai/ui/theme'
|
|
2
4
|
import * as m from '../paraglide/messages.js'
|
|
5
|
+
|
|
6
|
+
let currentTheme = $state(getSavedTheme())
|
|
7
|
+
|
|
8
|
+
function handleThemeChange(theme: string) {
|
|
9
|
+
currentTheme = theme
|
|
10
|
+
applyTheme(theme)
|
|
11
|
+
}
|
|
3
12
|
</script>
|
|
4
13
|
|
|
5
14
|
<section class='space-y-4 p-4 pb-6'>
|
|
6
15
|
<Card title={m.profile_title()} shadow='sm'>
|
|
7
16
|
<div class='space-y-3 text-sm'>
|
|
8
17
|
<div class='bg-base-200 rounded-xl p-3'>{m.profile_language()}</div>
|
|
9
|
-
<div class='bg-base-200 rounded-xl p-3'>
|
|
18
|
+
<div class='flex flex-wrap items-center justify-between gap-3 bg-base-200 rounded-xl p-3' data-testid='profile-theme'>
|
|
19
|
+
<span>{m.profile_theme()}</span>
|
|
20
|
+
<ThemeSelector {currentTheme} onchange={handleThemeChange} compact grouped={false} />
|
|
21
|
+
</div>
|
|
10
22
|
<div class='bg-base-200 rounded-xl p-3'>{m.profile_secure()}</div>
|
|
11
23
|
</div>
|
|
12
24
|
</Card>
|
|
@@ -5,7 +5,11 @@
|
|
|
5
5
|
<section class='space-y-4 p-4 pb-6'>
|
|
6
6
|
<Card title={m.tasks_title()} shadow='sm'>
|
|
7
7
|
<div class='space-y-3'>
|
|
8
|
-
{#each [
|
|
8
|
+
{#each [
|
|
9
|
+
m.tasks_sync(),
|
|
10
|
+
m.tasks_polish(),
|
|
11
|
+
m.tasks_release(),
|
|
12
|
+
] as task (task)}
|
|
9
13
|
<div class='bg-base-200 rounded-xl flex items-center gap-3 p-3'>
|
|
10
14
|
<span class='icon-[tabler--circle-check] text-success text-xl'></span>
|
|
11
15
|
<span class='text-sm font-medium'>{task}</span>
|
|
@@ -9,28 +9,41 @@ const message = core.i18n.createMessageGetter({
|
|
|
9
9
|
'zh-CN': {
|
|
10
10
|
flag: 'HAI_BUILD_STATIC仅支持0或1;省略或0保持SSR,1启用website静态构建。',
|
|
11
11
|
base: 'PUBLIC_BASE_PATH须为空或以/开头的站内目录;不允许外部地址、末尾/、查询、片段或路径逃逸。',
|
|
12
|
-
modules: '静态website
|
|
12
|
+
modules: '静态website不能启用服务端业务模块。请移除服务端模块及其初始化后再构建,或继续使用默认SSR。',
|
|
13
13
|
routes: '静态website不能包含自定义API、表单actions或未预渲染页面;请移除动态入口或使用SSR。',
|
|
14
14
|
assets: 'static是公开资产目录,不能放入.env私有环境文件或符号链接;请移动私有内容后重新构建。',
|
|
15
15
|
},
|
|
16
16
|
'en-US': {
|
|
17
17
|
flag: 'HAI_BUILD_STATIC accepts only 0 or 1: omitted/0 keeps SSR, and 1 enables a static website build.',
|
|
18
18
|
base: 'PUBLIC_BASE_PATH must be empty or a site-local directory beginning with /. External URLs, trailing /, queries, fragments and path traversal are not allowed.',
|
|
19
|
-
modules: 'A static website cannot enable server-side business modules.
|
|
19
|
+
modules: 'A static website cannot enable server-side business modules. Remove server modules and their initialization before building, or keep the default SSR mode.',
|
|
20
20
|
routes: 'A static website cannot contain custom APIs, form actions or pages that were not prerendered. Remove dynamic routes or use SSR.',
|
|
21
21
|
assets: 'static is a public asset directory and cannot contain private .env files or symbolic links. Move private content before building.',
|
|
22
22
|
},
|
|
23
23
|
'ja-JP': {
|
|
24
24
|
flag: 'HAI_BUILD_STATICは0または1です。省略/0はSSR、1はwebsiteの静的構築を有効にします。',
|
|
25
25
|
base: 'PUBLIC_BASE_PATHは空、または/で始まるサイト内ディレクトリーです。外部URL、末尾の/、クエリー、フラグメント、パス逸脱は使えません。',
|
|
26
|
-
modules: '静的website
|
|
26
|
+
modules: '静的websiteではサーバー業務モジュールを有効にできません。サーバーモジュールと初期化処理を除去するか、既定のSSRを使用してください。',
|
|
27
27
|
routes: '静的websiteに独自API、form actions、事前描画されないページを含められません。動的ルートを削除するかSSRを使用してください。',
|
|
28
28
|
assets: 'staticは公開資産ディレクトリーです。非公開.envファイルやシンボリックリンクを置かず、非公開内容を移動してから構築してください。',
|
|
29
29
|
},
|
|
30
30
|
})
|
|
31
|
-
const serverFeatures = [
|
|
32
|
-
|
|
33
|
-
|
|
31
|
+
const serverFeatures = [
|
|
32
|
+
{{#each websiteServerFeatures}}
|
|
33
|
+
'{{this}}',
|
|
34
|
+
{{/each}}
|
|
35
|
+
]
|
|
36
|
+
const requestedLocale = [
|
|
37
|
+
process.env.HAI_CORE_DEFAULTLOCALE,
|
|
38
|
+
process.env.LC_ALL,
|
|
39
|
+
process.env.LC_MESSAGES,
|
|
40
|
+
process.env.LANG,
|
|
41
|
+
].find(value => value?.trim())?.split(/[_.-]/)[0]?.toLowerCase()
|
|
42
|
+
const locale = requestedLocale === 'en' || requestedLocale === 'c' || requestedLocale === 'posix'
|
|
43
|
+
? 'en-US'
|
|
44
|
+
: requestedLocale === 'ja'
|
|
45
|
+
? 'ja-JP'
|
|
46
|
+
: 'zh-CN'
|
|
34
47
|
|
|
35
48
|
/** 只读取显式构建值,不加载dotenv和服务端秘密。 */
|
|
36
49
|
export function resolveStaticWebsite() {
|