@h-ai/kit 1.0.0-beta.18 → 1.0.0-beta.19

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.
Files changed (43) hide show
  1. package/README.en.md +53 -33
  2. package/README.ja.md +53 -33
  3. package/README.md +54 -33
  4. package/dist/adapter/index.d.ts +8 -7
  5. package/dist/adapter/index.js.map +1 -1
  6. package/dist/browser.d.ts +9 -26
  7. package/dist/browser.js +4 -4
  8. package/dist/browser.js.map +1 -1
  9. package/dist/{chunk-JRQPMPQC.js → chunk-BCEBXG4X.js} +2 -2
  10. package/dist/chunk-BCEBXG4X.js.map +1 -0
  11. package/dist/{chunk-7EH47MTW.js → chunk-BVGXHIXR.js} +30 -9
  12. package/dist/chunk-BVGXHIXR.js.map +1 -0
  13. package/dist/{chunk-WCMEGLBL.js → chunk-GQZCU6PC.js} +11 -5
  14. package/dist/chunk-GQZCU6PC.js.map +1 -0
  15. package/dist/{chunk-5JW3VW4Q.js → chunk-JL2C5ZGQ.js} +38 -11
  16. package/dist/chunk-JL2C5ZGQ.js.map +1 -0
  17. package/dist/{chunk-6KS67QUS.js → chunk-WYGIKXHE.js} +20 -7
  18. package/dist/chunk-WYGIKXHE.js.map +1 -0
  19. package/dist/client/index.d.ts +6 -5
  20. package/dist/client/index.js +5 -5
  21. package/dist/client/index.js.map +1 -1
  22. package/dist/index.d.ts +18 -711
  23. package/dist/index.js +264 -149
  24. package/dist/index.js.map +1 -1
  25. package/dist/{kit-a2a-types-ikgvWS3T.d.ts → kit-a2a-types-CeDikRAX.d.ts} +3 -2
  26. package/dist/kit-config-CCksTmi5.d.ts +182 -0
  27. package/dist/kit-crypto-types-CqFENBqm.d.ts +47 -0
  28. package/dist/kit-types-BUDaKGB0.d.ts +2057 -0
  29. package/dist/modules/a2a/index.d.ts +9 -5
  30. package/dist/modules/a2a/index.js +1 -1
  31. package/dist/modules/crypto/index.d.ts +8 -105
  32. package/dist/modules/crypto/index.js +3 -149
  33. package/dist/modules/crypto/index.js.map +1 -1
  34. package/package.json +22 -22
  35. package/dist/chunk-5JW3VW4Q.js.map +0 -1
  36. package/dist/chunk-6KS67QUS.js.map +0 -1
  37. package/dist/chunk-7EH47MTW.js.map +0 -1
  38. package/dist/chunk-JRQPMPQC.js.map +0 -1
  39. package/dist/chunk-WCMEGLBL.js.map +0 -1
  40. package/dist/kit-client-auth-DeWmc-1u.d.ts +0 -406
  41. package/dist/kit-crypto-types-Brd0l8Hv.d.ts +0 -204
  42. package/dist/kit-i18n-CjwdGeKY.d.ts +0 -506
  43. package/dist/kit-types-CnfBC89D.d.ts +0 -832
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/modules/crypto/kit-transport-paths.ts"],"names":[],"mappings":"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","file":"chunk-JRQPMPQC.js","sourcesContent":["/**\n * @h-ai/kit — 传输加密路径匹配工具\n *\n * 统一定义哪些同源请求应纳入 transport 保护范围,供服务端 middleware\n * 与浏览器端 fetch 包装共同复用,避免两端判断漂移。\n * @module kit-transport-paths\n */\n\nimport { TRANSPORT_PROTOCOL } from '@h-ai/crypto'\n\n/**\n * 客户端与服务端共用的默认公开密钥交换路径。\n * @example 模块内部上下文\n * ```ts\n * const endpoint = new URL(DEFAULT_TRANSPORT_KEY_EXCHANGE_PATH, 'https://app.example.com')\n * void endpoint.pathname\n * ```\n */\nexport const DEFAULT_TRANSPORT_KEY_EXCHANGE_PATH = `/api${TRANSPORT_PROTOCOL.DEFAULT_KEY_EXCHANGE_PATH}`\n\nconst API_PREFIX = '/api/'\nconst ROOT_DATA_PATH = '/__data.json'\nconst DATA_SUFFIX = '/__data.json'\n\nfunction normalizePath(pathname: string): string {\n return pathname.startsWith('/') ? pathname : `/${pathname}`\n}\n\n/**\n * 初始化时校验宿主挂载目录,统一为无末尾斜杠的 URL pathname;请求阶段不重复解析。\n * @param value - 可信宿主的构建目录,域名根目录为空字符串。\n * @returns 已规范化的挂载目录。\n * @throws TypeError 目录包含转义分隔符、点段、查询、片段或控制字符。\n * @internal\n * @example 模块内部上下文\n * ```ts\n * const basePath = normalizeTransportBasePath('/console/')\n * const endpoint = `${basePath}/api/articles`\n * ```\n */\nexport function normalizeTransportBasePath(value = ''): string {\n const invalid = () => new TypeError('Transport basePath must be an absolute mount path without dot segments, query or fragment')\n if (value.includes('//') || /[\\\\?#\\p{Cc} ]/u.test(value) || /%(?:2f|5c|25)/i.test(value))\n throw invalid()\n const basePath = value.replace(/\\/$/, '')\n if (!basePath)\n return ''\n if (!basePath.startsWith('/'))\n throw invalid()\n try {\n const decoded = decodeURIComponent(basePath)\n if (/[\\\\?#\\p{Cc} ]/u.test(decoded) || decoded.split('/').some(segment => segment === '.' || segment === '..'))\n throw invalid()\n return new URL(basePath, 'http://kit.invalid').pathname\n }\n catch {\n throw invalid()\n }\n}\n\n/**\n * 判断路径是否为 SvelteKit 的页面数据端点。\n * @param pathname - URL pathname,不含 query 或 fragment。\n * @returns 是否是页面 __data.json 端点。\n * @example 模块内部上下文\n * ```ts\n * const isData = isSvelteKitDataPath('/articles/__data.json')\n * void isData\n * ```\n */\nexport function isSvelteKitDataPath(pathname: string): boolean {\n return pathname === ROOT_DATA_PATH || pathname.endsWith(DATA_SUFFIX)\n}\n\n/**\n * 判断路径是否属于 transport 保护范围。\n * @param pathname - 待判断的 URL pathname。\n * @param keyExchangePath - 公开密钥交换路径。\n * @param basePath - 已校验的宿主挂载目录;默认空字符串。\n * @returns 是否属于 API、密钥交换或 SvelteKit 数据端点。\n * @example 模块内部上下文\n * ```ts\n * const protectedPath = shouldHandleTransportPath('/api/articles')\n * void protectedPath\n * ```\n */\nexport function shouldHandleTransportPath(\n pathname: string,\n keyExchangePath: string = DEFAULT_TRANSPORT_KEY_EXCHANGE_PATH,\n basePath = '',\n): boolean {\n if (pathname === keyExchangePath)\n return true\n if (basePath && pathname !== basePath && !pathname.startsWith(`${basePath}/`))\n return false\n return pathname.startsWith(`${basePath}${API_PREFIX}`) || isSvelteKitDataPath(pathname)\n}\n\n/**\n * 判断路径是否应排除 transport。\n * @param pathname - 待判断的 URL pathname。\n * @param excludePaths - 按精确路径或子路径前缀排除的列表。\n * @param keyExchangePath - 始终排除加密载荷处理的密钥交换路径。\n * @returns 是否匹配交换端点、排除路径或其子路径。\n * @example 模块内部上下文\n * ```ts\n * const excluded = shouldExcludeTransportPath('/api/health', ['/api/health'], DEFAULT_TRANSPORT_KEY_EXCHANGE_PATH)\n * void excluded\n * ```\n */\nexport function shouldExcludeTransportPath(\n pathname: string,\n excludePaths: readonly string[],\n keyExchangePath: string,\n): boolean {\n if (pathname === keyExchangePath)\n return true\n\n return excludePaths.some((excludePath) => {\n const normalizedPath = normalizePath(excludePath)\n return pathname === normalizedPath || pathname.startsWith(`${normalizedPath}/`)\n })\n}\n\n/**\n * 从相对/绝对 URL 中提取 pathname。\n * @param urlOrPath - 绝对 URL 或相对路径。\n * @param origin - 解析相对路径的基准 origin。\n * @returns 解析后的 pathname;无效 URL 抛出 TypeError。\n * @example 模块内部上下文\n * ```ts\n * const path = resolveTransportPath('https://app.example.com/api/articles?page=1')\n * void path\n * ```\n */\nexport function resolveTransportPath(urlOrPath: string, origin = 'http://localhost'): string {\n return new URL(urlOrPath, origin).pathname\n}\n\n/**\n * 判断浏览器侧请求是否应走 transport。\n *\n * - 仅处理同源请求\n * - 仅保护宿主 basePath 下的 `/api/*` 与 SvelteKit `__data.json`\n * - 命中 `excludePaths` 时透传明文\n * @param url - 待判断的绝对或相对 URL。\n * @param options - 同源基准、密钥交换路径及排除列表。\n * @param options.origin - 当前应用 origin;跨域请求不进入包装。\n * @param options.keyExchangePath - 公开密钥交换路径。\n * @param options.excludePaths - 明文排除路径列表。\n * @param options.basePath - 已校验的宿主挂载目录;默认空字符串。\n * @returns 是否同源、属于保护范围且未被排除。\n * @example 模块内部上下文\n * ```ts\n * const protectedUrl = shouldUseTransportForUrl('/api/articles', { origin: 'https://app.example.com', excludePaths: ['/api/health'] })\n * void protectedUrl\n * ```\n */\nexport function shouldUseTransportForUrl(\n url: string | URL,\n options: {\n origin?: string\n keyExchangePath?: string\n excludePaths?: readonly string[]\n basePath?: string\n } = {},\n): boolean {\n const baseOrigin = options.origin ?? 'http://localhost'\n const requestUrl = url instanceof URL ? url : new URL(url, baseOrigin)\n\n if (options.origin && requestUrl.origin !== options.origin)\n return false\n\n const keyExchangePath = options.keyExchangePath ?? DEFAULT_TRANSPORT_KEY_EXCHANGE_PATH\n if (!shouldHandleTransportPath(requestUrl.pathname, keyExchangePath, options.basePath))\n return false\n\n return !shouldExcludeTransportPath(requestUrl.pathname, options.excludePaths ?? [], keyExchangePath)\n}\n"]}
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/crud/kit-crud.ts","../src/kit-config.ts"],"names":[],"mappings":"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","file":"chunk-WCMEGLBL.js","sourcesContent":["/**\n * @h-ai/kit — CRUD 操作定义\n *\n * 声明式 CRUD 资源定义工厂函数。\n * @module kit-crud\n */\n\nimport type {\n CrudFieldDef,\n CrudFieldOptions,\n CrudOperations,\n CrudResourceDef,\n CrudTableColumn,\n CrudText,\n} from './kit-crud-types.js'\n\n/**\n * 解析 CrudText 为字符串\n */\nfunction resolveText(text: CrudText): string {\n return typeof text === 'function' ? text() : text\n}\n\n/**\n * 按 order 排序字段\n */\nfunction sortFields(fields: CrudFieldDef[]): CrudFieldDef[] {\n return [...fields].sort((a, b) => (a.order ?? 0) - (b.order ?? 0))\n}\n\n/**\n * 解析选项列表\n */\nfunction resolveOptions(options: CrudFieldOptions | undefined): Array<{ label: string, value: string | number | boolean }> {\n if (!options)\n return []\n return typeof options === 'function' ? options() : options\n}\n\n/**\n * 定义 CRUD 资源\n *\n * 返回 CrudOperations 对象,包含字段过滤、列构建和 API 代理等能力。\n * 与 @h-ai/ui 的 CrudPage 组件配合使用。\n *\n * @param resource - 资源定义\n * @returns CRUD 操作对象\n * @example\n * ```ts\n * import { kit } from '@h-ai/kit'\n *\n * import type { CrudApiDef } from '@h-ai/kit'\n *\n * function articleResource(api: CrudApiDef<{ id: string, title: string }>) {\n * return kit.crud.define({ name: 'article', label: 'Articles', fields: [{ id: 'title', label: 'Title', type: 'string' }], api })\n * }\n * ```\n */\nexport function defineCrud<T = Record<string, unknown>>(\n resource: CrudResourceDef<T>,\n): CrudOperations<T> {\n const fields = resource.fields\n\n function getListFields(): CrudFieldDef[] {\n return sortFields(fields.filter(f => f.inList !== false))\n }\n\n function getFilterFields(): CrudFieldDef[] {\n return sortFields(fields.filter(f => f.filterable === true))\n }\n\n function getCreateFields(): CrudFieldDef[] {\n return sortFields(fields.filter(f => f.inCreate !== false))\n }\n\n function getEditFields(): CrudFieldDef[] {\n return sortFields(fields.filter(f => f.inEdit !== false))\n }\n\n function getDetailFields(): CrudFieldDef[] {\n return sortFields(fields.filter(f => f.inDetail !== false))\n }\n\n function toTableColumns(): CrudTableColumn[] {\n return getListFields().map(f => ({\n key: f.id,\n label: resolveText(f.label),\n width: f.width,\n align: f.align,\n render: f.render\n ? (item: Record<string, unknown>) => f.render!(item[f.id], item)\n : undefined,\n }))\n }\n\n function getDefaultValues(): Record<string, unknown> {\n const defaults: Record<string, unknown> = {}\n for (const f of fields) {\n if (f.defaultValue !== undefined) {\n defaults[f.id] = f.defaultValue\n }\n else if (f.type === 'boolean' || f.type === 'checkbox') {\n defaults[f.id] = false\n }\n else if (f.type === 'multi-select') {\n defaults[f.id] = []\n }\n else if (f.type === 'number') {\n defaults[f.id] = undefined\n }\n else {\n defaults[f.id] = ''\n }\n }\n return defaults\n }\n\n return {\n resource,\n getListFields,\n getFilterFields,\n getCreateFields,\n getEditFields,\n getDetailFields,\n toTableColumns,\n getDefaultValues,\n api: resource.api,\n }\n}\n\n// re-export 解析工具,供 UI 层使用\nexport { resolveOptions, resolveText }\n","/**\n * @h-ai/kit — 宿主配置\n *\n * 为 `config/_kit.yml` 提供监听、传输与请求策略的默认值和校验。\n * 服务端消费完整配置;浏览器仅接收显式投影的 transport 公共字段。\n * @module kit-config\n */\n\nimport type { KitConfig, KitConfigInput, KitServerConfig, KitServerConfigInput, KitTransportConfig, KitTransportConfigInput } from './kit-types.js'\nimport { RequestAccessConfigSchema, TrustedProxiesSchema } from '@h-ai/core'\nimport { TRANSPORT_PLAINTEXT_RANGE, TRANSPORT_PROTOCOL, TRANSPORT_TIME_LIMITS } from '@h-ai/crypto'\nimport { z } from 'zod'\n\nconst AbsolutePathSchema = z.custom<`/${string}`>(\n value => typeof value === 'string' && value.startsWith('/'),\n 'path must start with /',\n)\n\nconst KitTransportConfigInputSchema = z.union([\n z.literal(false),\n z.object({\n maxPlaintextBytes: z.union([z.number().int().min(TRANSPORT_PLAINTEXT_RANGE.min).max(TRANSPORT_PLAINTEXT_RANGE.max), z.literal('auto')]).transform(value => value === 'auto' ? undefined : value).optional().describe('普通业务双向明文上限;auto 为 1 MiB;大材料使用 routePlaintextBytes 单独声明').meta({ default: 'auto' }),\n maxFutureSkewSeconds: z.number().int().min(0).max(TRANSPORT_TIME_LIMITS.maxFutureSkewSeconds).optional().describe('允许客户端请求时间领先服务器的秒数').meta({ default: TRANSPORT_PROTOCOL.CLOCK_SKEW_MS / 1000 }),\n maxRequestAgeSeconds: z.number().int().min(TRANSPORT_TIME_LIMITS.minRequestAgeSeconds).max(TRANSPORT_TIME_LIMITS.maxRequestAgeSeconds).optional().describe('请求从签发起的有效秒数').meta({ default: TRANSPORT_PROTOCOL.REQUEST_WINDOW_MS / 1000 }),\n routePlaintextBytes: z.record(AbsolutePathSchema, z.number().int().min(TRANSPORT_PLAINTEXT_RANGE.min).max(TRANSPORT_PLAINTEXT_RANGE.max)).optional().describe('完整路径段到双向明文字节上限的映射;星号匹配单段,供附件和归档独立容量'),\n keyExchangePath: AbsolutePathSchema.default('/api/_hai/key-exchange'),\n excludePaths: z.array(AbsolutePathSchema).default([]),\n }),\n])\n\nconst ServerConfigInputSchema = z.object({\n host: z.string().min(1).default('127.0.0.1'),\n port: z.number().int().min(1).max(65535).default(3000),\n})\n\n/**\n * `config/_kit.yml` 对应的配置 Schema。\n * @example\n * ```ts\n * import { KitConfigSchema } from '@h-ai/kit'\n *\n * const config = KitConfigSchema.parse({ server: { port: 3000 }, transport: false })\n * void config\n * ```\n */\nexport const KitConfigSchema = z.object({\n server: ServerConfigInputSchema.optional(),\n transport: KitTransportConfigInputSchema.optional(),\n trustedProxies: TrustedProxiesSchema.default('auto'),\n access: RequestAccessConfigSchema.default(false),\n}).transform(({ server, transport, trustedProxies, access }) => ({\n server: resolveKitServerConfig(server ?? {}),\n transport: resolveKitTransportConfig(transport ?? false),\n trustedProxies,\n access,\n}))\n\n/**\n * 读取 `HOST` / `PORT` 环境变量覆盖(环境变量高于配置文件)。\n *\n * 浏览器端 `process` 不存在时安全回退为空;`PORT` 仅采纳 1-65535 的整数。\n */\nfunction readServerEnvOverride(): KitServerConfigInput {\n // eslint-disable-next-line node/prefer-global/process\n const env = typeof process !== 'undefined' ? process.env : undefined\n const override: { host?: string, port?: number } = {}\n const host = env?.HOST\n if (host)\n override.host = host\n const rawPort = env?.PORT\n if (rawPort) {\n const port = Number(rawPort)\n if (Number.isInteger(port) && port >= 1 && port <= 65535)\n override.port = port\n }\n return override\n}\n\n/**\n * 解析服务器监听配置并补齐默认值。\n *\n * 优先级:`HOST` / `PORT` 环境变量 > `config/_kit.yml` 的 `server` > 默认 `127.0.0.1:3000`。\n *\n * @param input - `config/_kit.yml` 中的 server 配置\n * @returns 完整 server 配置\n * @example 模块内部上下文\n * ```ts\n * const config = resolveKitServerConfig({ port: 4000 })\n * // HOST / PORT 环境变量优先于输入。\n * void config.port\n * ```\n */\nexport function resolveKitServerConfig(input: KitServerConfigInput = {}): KitServerConfig {\n return { ...ServerConfigInputSchema.parse(input), ...readServerEnvOverride() }\n}\n\n/**\n * 解析 transport 配置并补齐默认值。\n *\n * @param input - `config/_kit.yml` 中的 transport 配置\n * @returns 完整 transport 配置;`false` 表示关闭\n * @example\n * ```ts\n * import { resolveKitTransportConfig } from '@h-ai/kit'\n *\n * const transport = resolveKitTransportConfig({ excludePaths: ['/api/health'] })\n * if (transport) void transport.keyExchangePath\n * ```\n */\nexport function resolveKitTransportConfig(\n input: false | KitTransportConfigInput = false,\n): false | KitTransportConfig {\n return KitTransportConfigInputSchema.parse(input)\n}\n\n/**\n * 解析 `config/_kit.yml` 顶层配置并补齐默认值。\n *\n * 适合同一份配置同时供 SvelteKit 服务端 hook 与浏览器端 client 读取。\n * @param input - Kit 监听和公开 transport 输入;省略字段按 Schema 补默认值。\n * @returns 已补齐默认值的配置;不合法输入抛出 ZodError。\n * @example\n * ```ts\n * import { resolveKitConfig } from '@h-ai/kit'\n *\n * const config = resolveKitConfig({ transport: false })\n * void config.server.port\n * ```\n */\nexport function resolveKitConfig(input: KitConfigInput = {}): KitConfig {\n return KitConfigSchema.parse(input)\n}\n"]}
@@ -1,406 +0,0 @@
1
- import { IamCreateCaptchaInputSchema, IamPublicConfig, IamLoginInput, IamRegisterInput } from '@h-ai/api-contract';
2
- import { HaiResult } from '@h-ai/core';
3
- import { CryptoFunctions } from '@h-ai/crypto';
4
- import { PasswordCredentials, AuthRequestContext, AuthResult, OtpCredentials, LdapCredentials, ApiKeyCredentials, RegisterOptions } from '@h-ai/iam';
5
- import { k as KitPublicConfig } from './kit-types-CnfBC89D.js';
6
- import { z } from 'zod';
7
-
8
- /**
9
- * @h-ai/kit — Bearer 认证工具
10
- *
11
- * 提供服务端认证 Cookie 管理(login / logout)与浏览器端 Token 存储工具。
12
- * @module kit-auth
13
- */
14
-
15
- /**
16
- * 服务端认证写入/删除 Cookie 依赖;由当前请求提供并执行安全属性。
17
- * @example 模块内部上下文
18
- * ```ts
19
- * function signIn(cookies: CookieWriter, credentials: PasswordCredentials) {
20
- * return login(cookies, credentials) // 业务调用者检查 success 后消费身份。
21
- * }
22
- * ```
23
- */
24
- interface CookieWriter {
25
- set: (name: string, value: string, options: {
26
- path: string;
27
- httpOnly: boolean;
28
- sameSite: 'lax' | 'strict' | 'none';
29
- secure: boolean;
30
- maxAge?: number;
31
- }) => void;
32
- delete: (name: string, options: {
33
- path: string;
34
- }) => void;
35
- }
36
- /**
37
- * 浏览器 Token 存储器;使用页面内存或平台安全存储,禁止写入 Web Storage。
38
- * @example 模块内部上下文
39
- * ```ts
40
- * const store: BrowserTokenStore = getDefaultBrowserTokenStore()
41
- * store.clear() // 当前页面内存状态;不持有服务端会话真值。
42
- * ```
43
- */
44
- interface BrowserTokenStore {
45
- get: () => string | null;
46
- set: (token: string) => void;
47
- clear: () => void;
48
- }
49
- /**
50
- * 服务端登录(密码):内部调用 iam.auth.login,成功时自动写入 Token Cookie。
51
- *
52
- * @param cookies - SvelteKit cookies 对象
53
- * @param credentials - 密码凭证(identifier + password)
54
- * @param context - 宿主提供的可信登录元数据,不从凭据输入复制 IP。
55
- * @returns 认证结果(成功时 Cookie 已自动写入)
56
- * @example 模块内部上下文
57
- * ```ts
58
- * async function signIn(cookies: CookieWriter, credentials: PasswordCredentials) {
59
- * const result = await login(cookies, credentials)
60
- * if (!result.success) return result.error.message
61
- * return result.data
62
- * }
63
- * ```
64
- */
65
- declare function login(cookies: CookieWriter, credentials: PasswordCredentials, context?: AuthRequestContext): Promise<HaiResult<AuthResult>>;
66
- /**
67
- * 服务端登录(OTP 验证码):内部调用 iam.auth.loginWithOtp,成功时自动写入 Token Cookie。
68
- *
69
- * @param cookies - SvelteKit cookies 对象
70
- * @param credentials - OTP 凭证(identifier + code)
71
- * @param context - 宿主提供的可信登录元数据。
72
- * @returns 认证结果(成功时 Cookie 已自动写入)
73
- * @example 模块内部上下文
74
- * ```ts
75
- * async function signIn(cookies: CookieWriter, credentials: OtpCredentials) {
76
- * const result = await loginWithOtp(cookies, credentials)
77
- * if (!result.success) return result.error.message
78
- * return result.data
79
- * }
80
- * ```
81
- */
82
- declare function loginWithOtp(cookies: CookieWriter, credentials: OtpCredentials, context?: AuthRequestContext): Promise<HaiResult<AuthResult>>;
83
- /**
84
- * 服务端登录(LDAP):内部调用 iam.auth.loginWithLdap,成功时自动写入 Token Cookie。
85
- *
86
- * @param cookies - SvelteKit cookies 对象
87
- * @param credentials - LDAP 凭证(username + password)
88
- * @param context - 宿主提供的可信登录元数据。
89
- * @returns 认证结果(成功时 Cookie 已自动写入)
90
- * @example 模块内部上下文
91
- * ```ts
92
- * async function signIn(cookies: CookieWriter, credentials: LdapCredentials) {
93
- * const result = await loginWithLdap(cookies, credentials)
94
- * if (!result.success) return result.error.message
95
- * return result.data
96
- * }
97
- * ```
98
- */
99
- declare function loginWithLdap(cookies: CookieWriter, credentials: LdapCredentials, context?: AuthRequestContext): Promise<HaiResult<AuthResult>>;
100
- /**
101
- * 服务端登录(API Key):内部调用 iam.auth.loginWithApiKey,成功时自动写入 Token Cookie。
102
- *
103
- * @param cookies - SvelteKit cookies 对象
104
- * @param credentials - API Key 凭证(key)
105
- * @param context - 宿主提供的可信登录元数据。
106
- * @returns 认证结果(成功时 Cookie 已自动写入)
107
- * @example 模块内部上下文
108
- * ```ts
109
- * async function signIn(cookies: CookieWriter, credentials: ApiKeyCredentials) {
110
- * const result = await loginWithApiKey(cookies, credentials)
111
- * if (!result.success) return result.error.message
112
- * return result.data
113
- * }
114
- * ```
115
- */
116
- declare function loginWithApiKey(cookies: CookieWriter, credentials: ApiKeyCredentials, context?: AuthRequestContext): Promise<HaiResult<AuthResult>>;
117
- /**
118
- * 服务端注册并登录:内部调用 iam.auth.registerAndLogin,成功时自动写入 Token Cookie。
119
- *
120
- * @param cookies - SvelteKit cookies 对象
121
- * @param options - 注册选项(username、password、email 等)
122
- * @returns 认证结果(成功时 Cookie 已自动写入)
123
- * @example 模块内部上下文
124
- * ```ts
125
- * async function signIn(cookies: CookieWriter, credentials: RegisterOptions) {
126
- * const result = await registerAndLogin(cookies, credentials)
127
- * if (!result.success) return result.error.message
128
- * return result.data
129
- * }
130
- * ```
131
- */
132
- declare function registerAndLogin(cookies: CookieWriter, options: RegisterOptions, context?: AuthRequestContext): Promise<HaiResult<AuthResult>>;
133
- /**
134
- * 服务端登出:委托 iam.auth.logout 原子撤销凭据,并始终清除当前请求的 Token Cookie。
135
- * Cookie 清理只代表本地退出;服务端撤销失败仍返回失败,不能由调用端改成成功响应。
136
- *
137
- * @param cookies - SvelteKit cookies 对象
138
- * @param accessToken - 访问令牌(为 null/undefined 时仅清除 Cookie)
139
- * @returns 服务端撤销结果;无令牌时仅清理 Cookie 并成功,有令牌但未配置认证操作时失败。
140
- * @remarks 底层控制流异常仍以 Promise 拒绝传播;Cookie 清理不吞掉业务失败。
141
- * @example 模块内部上下文
142
- * ```ts
143
- * async function signOut(cookies: CookieWriter, accessToken: string) {
144
- * const result = await logout(cookies, accessToken)
145
- * if (!result.success) return result.error.code
146
- * return result.data
147
- * }
148
- * ```
149
- */
150
- declare function logout(cookies: CookieWriter, accessToken?: string | null): Promise<HaiResult<void>>;
151
- /**
152
- * 写入默认浏览器端 Access Token(仅页面内存,不持久化到 localStorage)。
153
- * @param token - 当前页面内存中使用的 access token,不写入 Web Storage。
154
- * @example
155
- * ```ts
156
- * import { kit } from '@h-ai/kit'
157
- *
158
- * kit.auth.setBrowserToken('example-only-token')
159
- * // 页面注销时同步清除浏览器内存令牌。
160
- * kit.auth.clearBrowserToken()
161
- * ```
162
- */
163
- declare function setBrowserToken(token: string): void;
164
- /**
165
- * 清除默认浏览器端 Access Token(仅页面内存)。
166
- * @example
167
- * ```ts
168
- * import { kit } from '@h-ai/kit'
169
- *
170
- * kit.auth.clearBrowserToken()
171
- * ```
172
- */
173
- declare function clearBrowserToken(): void;
174
-
175
- /**
176
- * @h-ai/kit — 统一客户端
177
- *
178
- * 将 CSRF Token 附加与可选传输加密封装为统一 `apiFetch`。
179
- * 应用层只需调用一次 `createKitClient()`,后续 API 调用即可复用同一套安全能力。
180
- * @module kit-client
181
- */
182
-
183
- /**
184
- * 传输加密客户端配置
185
- * @example
186
- * ```ts
187
- * import type { ClientTransportConfig } from '@h-ai/kit'
188
- * import { crypto } from '@h-ai/crypto'
189
- *
190
- * function configAfterInit(): ClientTransportConfig { return { crypto, excludePaths: ['/api/health'] } }
191
- * ```
192
- */
193
- interface ClientTransportConfig {
194
- /** 宿主构建挂载目录,默认空字符串;SvelteKit 使用 $app/paths.base。 */
195
- basePath?: string;
196
- /** 可选本地明文上限;缺省跟随服务端握手。 */
197
- maxPlaintextBytes?: number;
198
- /** @h-ai/crypto 服务实例 */
199
- crypto: CryptoFunctions;
200
- /** 密钥交换端点 URL(默认 `'/api/_hai/key-exchange'`) */
201
- keyExchangeUrl?: string;
202
- /** 排除路径(命中后强制走明文),需与服务端 transport.excludePaths 保持一致 */
203
- excludePaths?: readonly string[];
204
- }
205
- /**
206
- * Kit 客户端配置
207
- * @example
208
- * ```ts
209
- * import type { KitClientConfig } from '@h-ai/kit'
210
- *
211
- * const value: KitClientConfig = { auth: true }
212
- * void value
213
- * ```
214
- */
215
- interface KitClientConfig {
216
- /** 标准鉴别明确失效时原地登录原用户;成功才对被拒绝的请求重试一次。 */
217
- recoverSession?: () => Promise<boolean>;
218
- /** 会话终端分组,默认web;服务端按终端与全局配额共同限制。 */
219
- terminalType?: 'web' | 'app' | 'desktop' | 'api';
220
- /**
221
- * 传输加密配置。
222
- * - 不提供 / undefined:不启用传输加密,仅 CSRF
223
- * - 提供对象:启用传输加密
224
- */
225
- transport?: ClientTransportConfig;
226
- /** CSRF Cookie 名称(默认 `'hai_csrf'`) */
227
- csrfCookieName?: string;
228
- /** CSRF Header 名称(默认 `'X-CSRF-Token'`) */
229
- csrfHeaderName?: string;
230
- /**
231
- * 认证配置:自动从浏览器存储读取 Access Token 并注入请求头。
232
- * - `true`:使用默认页面内存存储(由 `kit.auth.setBrowserToken()` 写入,不读写 localStorage)
233
- * - `BrowserTokenStore`:使用自定义存储
234
- * - 不提供 / `false`:不自动注入
235
- */
236
- auth?: boolean | BrowserTokenStore;
237
- }
238
- /**
239
- * Kit 客户端实例
240
- * @example
241
- * ```ts
242
- * import type { KitClient } from '@h-ai/kit'
243
- *
244
- * async function read(client: KitClient) {
245
- * const response = await client.apiFetch('/api/health')
246
- * if (!response.ok) throw new Error('Request failed')
247
- * return response.json()
248
- * }
249
- * ```
250
- */
251
- interface KitClient {
252
- /** 统一 API fetch(写请求自动附加 CSRF,启用 transport 时自动加解密) */
253
- apiFetch: (input: RequestInfo | URL, init?: RequestInit, options?: {
254
- recoverSession?: boolean;
255
- reauthorize?: () => Promise<string | null | undefined>;
256
- }) => Promise<Response>;
257
- /** 传输加密是否就绪(未启用传输加密时始终为 true) */
258
- readonly ready: boolean;
259
- /**
260
- * 手动触发密钥交换(transport 启用时)。
261
- *
262
- * 注意:本方法是 Client 形态的合规例外,密钥协商失败时 `throw`(与 `@h-ai/api-client` 一致),
263
- * 调用方需自行 `try/catch`,不返回 `HaiResult`。
264
- */
265
- init: () => Promise<void>;
266
- /** 销毁密钥状态 */
267
- destroy: () => void;
268
- }
269
- /**
270
- * 在浏览器启动时安装同源 transport fetch 包装。
271
- *
272
- * 该包装作用于同源 `/api/*` 与 SvelteKit `__data.json` 请求,页面文档、
273
- * 静态资源以及 multipart/form-data 等上传请求保持原样。应用只需安装一次,
274
- * 后续 `fetch` / SvelteKit 内部 data fetch / `kit.client.create()` 明文发送路径
275
- * 都会共用这层传输加密能力。
276
- * @param transportConfig - 已初始化 crypto、同源密钥交换路径及排除路径;省略时不安装包装。
277
- * @example
278
- * ```ts
279
- * import { kit } from '@h-ai/kit'
280
- *
281
- * // 不传配置时不安装全局包装;启用时应传已初始化 crypto 与同源端点。
282
- * kit.client.installBrowserTransportFetch()
283
- * ```
284
- */
285
- declare function installBrowserTransportFetch(transportConfig?: ClientTransportConfig): void;
286
- /**
287
- * 用 `config/_kit.yml` 解析后的 {@link KitPublicConfig} 公共投影 一次性安装浏览器端传输加密。
288
- *
289
- * 行为:
290
- * - `config.transport === false` 时直接返回(不启用传输加密);
291
- * - 否则启动 {@link installBrowserTransportFetch},并预热 {@link CryptoFunctions} 模块。
292
- *
293
- * 应用层(SvelteKit `+layout.svelte` 或浏览器入口)只需调用此函数一次,
294
- * 之后宿主 basePath 下的同源 `/api/*` 与 `__data.json` 请求都会自动走传输加密。
295
- *
296
- * @param config 已解析的 kit 公共传输配置
297
- * @param deps 外部依赖
298
- * @param deps.crypto `@h-ai/crypto` 模块实例
299
- * @param deps.basePath 宿主构建挂载目录,默认空字符串;SvelteKit 使用 $app/paths.base。
300
- * @example
301
- * ```ts
302
- * import { kit } from '@h-ai/kit'
303
- *
304
- * import { crypto } from '@h-ai/crypto'
305
- *
306
- * function installAfterCryptoInit() {
307
- * kit.client.installBrowserTransport({ transport: { keyExchangePath: '/api/_hai/key-exchange', excludePaths: ['/api/health'] } }, { crypto })
308
- * }
309
- * ```
310
- */
311
- declare function installBrowserTransport(config: KitPublicConfig, deps: {
312
- crypto: CryptoFunctions;
313
- basePath?: string;
314
- }): void;
315
- /**
316
- * 创建 Kit 客户端
317
- *
318
- * 返回统一的 `apiFetch`,内部自动完成:
319
- * 1. CSRF Token 附加(写方法自动读取 Cookie + 设置 Header)
320
- * 2. 密钥交换(首次写请求时 lazy init,transport 启用时)
321
- * 3. 请求体加密(transport 启用时)
322
- * 4. 响应体解密(transport 启用时)
323
- *
324
- * @param config - 客户端配置
325
- * @returns KitClient 实例
326
- * @example
327
- * ```ts
328
- * import { kit } from '@h-ai/kit'
329
- *
330
- * const client = kit.client.create({ auth: true })
331
- * try {
332
- * await client.init() // Client API 使用 Promise 拒绝;不是 HaiResult。
333
- * const response = await client.apiFetch('/api/health')
334
- * if (!response.ok) throw new Error('Request failed')
335
- * } finally {
336
- * client.destroy()
337
- * }
338
- * ```
339
- */
340
- declare function createKitClient(config?: KitClientConfig): KitClient;
341
-
342
- /** 与标准 Kit 认证端点配套的表单动作;复用已有 CSRF/transport fetch。 */
343
-
344
- /**
345
- * 创建标准 Cookie 认证表单动作;复用可选 apiFetch 以保留 CSRF 和传输配置。
346
- * @param options - 可复用的 apiFetch 和标准认证端点 basePath。
347
- * @param options.apiFetch - 已装配 CSRF/transport 的 fetch;省略时使用默认 Kit 客户端。
348
- * @param options.basePath - 同源认证端点前缀,默认 /api/auth。
349
- * @returns 标准表单动作;业务和已认证的时间错误返回 HaiResult,网络/格式错误会拒绝 Promise。
350
- * @example
351
- * ```ts
352
- * import { kit } from '@h-ai/kit'
353
- *
354
- * const actions = kit.client.createAuthActions({ basePath: '/api/auth' })
355
- * void actions
356
- * ```
357
- */
358
- declare function createKitAuthActions(options?: {
359
- apiFetch?: KitClient['apiFetch'];
360
- basePath?: string;
361
- }): {
362
- bindPageExit(options?: {
363
- enabled?: boolean;
364
- }): () => void;
365
- createCaptcha(input: z.input<typeof IamCreateCaptchaInputSchema>): Promise<HaiResult<{
366
- id: string;
367
- challenge: {
368
- parameters: {
369
- algorithm: "PBKDF2/SHA-256";
370
- nonce: string;
371
- salt: string;
372
- cost: number;
373
- keyLength: number;
374
- keyPrefix: string;
375
- keySignature?: string | undefined;
376
- data?: Record<string, string | number | boolean | null> | undefined;
377
- };
378
- signature?: string | undefined;
379
- };
380
- }>>;
381
- publicConfig(): Promise<HaiResult<IamPublicConfig | null>>;
382
- login(input: IamLoginInput & {
383
- method?: "password" | "ldap" | "email" | "sms";
384
- code?: string;
385
- }): Promise<HaiResult<unknown>>;
386
- register: (input: IamRegisterInput) => Promise<HaiResult<unknown>>;
387
- sendOtp: (identifier: string, options?: {
388
- captcha?: string;
389
- }) => Promise<HaiResult<unknown>>;
390
- requestPasswordReset: (identifier: string, options?: {
391
- captcha?: string;
392
- }) => Promise<HaiResult<unknown>>;
393
- confirmPasswordReset: (token: string, newPassword: string) => Promise<HaiResult<unknown>>;
394
- renewPassword: (input: {
395
- identifier: string;
396
- password: string;
397
- newPassword: string;
398
- captcha?: string;
399
- }) => Promise<HaiResult<unknown>>;
400
- reauthenticate(password: string, operation: string): Promise<HaiResult<{
401
- ticket: string;
402
- expiresAt: number;
403
- }>>;
404
- };
405
-
406
- export { type ClientTransportConfig as C, type KitClient as K, createKitAuthActions as a, installBrowserTransportFetch as b, createKitClient as c, clearBrowserToken as d, type KitClientConfig as e, loginWithOtp as f, loginWithLdap as g, loginWithApiKey as h, installBrowserTransport as i, logout as j, login as l, registerAndLogin as r, setBrowserToken as s };
@@ -1,204 +0,0 @@
1
- import { TransportServerKeyRing, CryptoFunctions, TransportKeyStore } from '@h-ai/crypto';
2
- import { RequestEvent } from '@sveltejs/kit';
3
-
4
- /**
5
- * @h-ai/kit — Crypto 类型定义
6
- *
7
- * Crypto 模块集成相关类型
8
- * @module kit-crypto-types
9
- */
10
-
11
- /**
12
- * 辅助函数所需的异步加密依赖结构;实际服务需由应用适配,不等同于 @h-ai/crypto 的公开接口。
13
- * @example
14
- * ```ts
15
- * import type { CryptoServiceLike } from '@h-ai/kit'
16
- *
17
- * async function verify(crypto: CryptoServiceLike, body: string, secret: string, signature: string) {
18
- * const result = await crypto.hmac.verify(body, secret, signature, 'sha256')
19
- * return result.success && result.data === true
20
- * }
21
- * ```
22
- */
23
- interface CryptoServiceLike {
24
- hmac: {
25
- sign: (data: string, key: string, algorithm?: string) => Promise<{
26
- success: boolean;
27
- data?: string;
28
- error?: {
29
- code: number;
30
- message: string;
31
- };
32
- }>;
33
- verify: (data: string, key: string, signature: string, algorithm?: string) => Promise<{
34
- success: boolean;
35
- data?: boolean;
36
- error?: {
37
- code: number;
38
- message: string;
39
- };
40
- }>;
41
- };
42
- hash: {
43
- digest: (data: string, algorithm?: string) => Promise<{
44
- success: boolean;
45
- data?: string;
46
- error?: {
47
- code: number;
48
- message: string;
49
- };
50
- }>;
51
- timingSafeEqual: (a: string, b: string) => Promise<{
52
- success: boolean;
53
- data?: boolean;
54
- error?: {
55
- code: number;
56
- message: string;
57
- };
58
- }>;
59
- };
60
- aes: {
61
- encrypt: (data: string, key: string) => Promise<{
62
- success: boolean;
63
- data?: string;
64
- error?: {
65
- code: number;
66
- message: string;
67
- };
68
- }>;
69
- decrypt: (data: string, key: string) => Promise<{
70
- success: boolean;
71
- data?: string;
72
- error?: {
73
- code: number;
74
- message: string;
75
- };
76
- }>;
77
- };
78
- random: {
79
- bytes: (length: number) => Promise<{
80
- success: boolean;
81
- data?: Uint8Array;
82
- error?: {
83
- code: number;
84
- message: string;
85
- };
86
- }>;
87
- };
88
- }
89
- /**
90
- * Webhook 验证配置
91
- * @example
92
- * ```ts
93
- * import type { WebhookVerifyConfig } from '@h-ai/kit'
94
- *
95
- * function signatureHeader(config: WebhookVerifyConfig) { return config.event.request.headers.get(config.signatureHeader ?? 'X-Signature') }
96
- * ```
97
- */
98
- interface WebhookVerifyConfig {
99
- /** Crypto 服务实例 */
100
- crypto: CryptoServiceLike;
101
- /** 请求事件 */
102
- event: RequestEvent;
103
- /** 签名密钥 */
104
- secretKey: string;
105
- /** 签名头名称 */
106
- signatureHeader?: string;
107
- /** 算法 */
108
- algorithm?: 'sha256' | 'sha512';
109
- /** 编码 */
110
- encoding?: 'hex' | 'base64';
111
- }
112
- /**
113
- * CSRF 配置
114
- * @example
115
- * ```ts
116
- * import type { CryptoCsrfConfig } from '@h-ai/kit'
117
- *
118
- * function tokenSize(config: CryptoCsrfConfig) { return config.tokenLength ?? 32 }
119
- * ```
120
- */
121
- interface CryptoCsrfConfig {
122
- /** Crypto 服务实例 */
123
- crypto: CryptoServiceLike;
124
- /** Cookie 名称 */
125
- cookieName?: string;
126
- /** Header 名称 */
127
- headerName?: string;
128
- /** 表单字段名称 */
129
- formFieldName?: string;
130
- /** Token 长度 */
131
- tokenLength?: number;
132
- /** Cookie 选项 */
133
- cookieOptions?: {
134
- path?: string;
135
- httpOnly?: boolean;
136
- secure?: boolean;
137
- sameSite?: 'strict' | 'lax' | 'none';
138
- maxAge?: number;
139
- };
140
- }
141
- /**
142
- * 加密 Cookie 配置
143
- * @example
144
- * ```ts
145
- * import type { EncryptedCookieConfig } from '@h-ai/kit'
146
- *
147
- * function assertKey(config: EncryptedCookieConfig) {
148
- * if (!config.encryptionKey) throw new Error('Encryption key required')
149
- * }
150
- * ```
151
- */
152
- interface EncryptedCookieConfig {
153
- /** Crypto 服务实例 */
154
- crypto: CryptoServiceLike;
155
- /** 加密密钥 */
156
- encryptionKey: string;
157
- /** Cookie 选项 */
158
- cookieOptions?: {
159
- path?: string;
160
- httpOnly?: boolean;
161
- secure?: boolean;
162
- sameSite?: 'strict' | 'lax' | 'none';
163
- maxAge?: number;
164
- };
165
- }
166
-
167
- /**
168
- * 传输加密配置。
169
- *
170
- * kit 不再维护本地加解密实现;服务端管理器由 `crypto.transport.createServer()` 创建,
171
- * 协议常量与载荷类型统一来自 `@h-ai/crypto`。
172
- * @example
173
- * ```ts
174
- * import type { TransportEncryptionConfig } from '@h-ai/kit'
175
- *
176
- * function publicPaths(config: TransportEncryptionConfig) { return config.excludePaths ?? [] }
177
- * ```
178
- */
179
- interface TransportEncryptionConfig {
180
- /** 宿主构建挂载目录,默认空字符串;仅作用于 API/data 保护范围。 */
181
- basePath?: string;
182
- /** 双向业务明文 UTF-8 字节上限;默认 1 MiB,整数范围 1 KiB~64 MiB。 */
183
- maxPlaintextBytes?: number;
184
- /** 请求时间允许领先服务器的秒数,默认 30,整数范围 0~300。 */
185
- maxFutureSkewSeconds?: number;
186
- /** 请求从签发起的有效秒数,默认 300,整数范围 1~600。 */
187
- maxRequestAgeSeconds?: number;
188
- /** 路由明文容量;* 匹配一个完整路径段。 */
189
- routePlaintextBytes?: Readonly<Record<string, number>>;
190
- /** 受管服务端密钥环,仅从服务端 Secret 注入,不放公开 kit 配置。 */
191
- serverKeyRing: TransportServerKeyRing;
192
- /** 是否启用传输加密(默认 false) */
193
- enabled: boolean;
194
- /** @h-ai/crypto 服务实例 */
195
- crypto: CryptoFunctions;
196
- /** 密钥交换端点路径(默认 `/api/_hai/key-exchange`) */
197
- keyExchangePath?: string;
198
- /** 排除路径(不加密),支持精确匹配和前缀匹配 */
199
- excludePaths?: readonly string[];
200
- /** 显式客户端公钥存储;生产使用共享 Redis/reldb,内存仅供开发/测试。 */
201
- keyStore: TransportKeyStore;
202
- }
203
-
204
- export type { CryptoCsrfConfig as C, EncryptedCookieConfig as E, TransportEncryptionConfig as T, WebhookVerifyConfig as W, CryptoServiceLike as a };