@h-ai/kit 0.1.0-alpha.13 → 0.1.0-alpha.16
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.md +96 -32
- package/dist/browser.d.ts +8 -6
- package/dist/browser.js +8 -6
- package/dist/browser.js.map +1 -1
- package/dist/chunk-BM7IP4W5.js +211 -0
- package/dist/chunk-BM7IP4W5.js.map +1 -0
- package/dist/chunk-EMSCTFJJ.js +256 -0
- package/dist/chunk-EMSCTFJJ.js.map +1 -0
- package/dist/{chunk-FRYJMRTP.js → chunk-KJUUEH7I.js} +30 -3
- package/dist/chunk-KJUUEH7I.js.map +1 -0
- package/dist/{chunk-BRZK7V5O.js → chunk-MI65L22O.js} +64 -89
- package/dist/chunk-MI65L22O.js.map +1 -0
- package/dist/client/index.d.ts +3 -3
- package/dist/client/index.js +20 -2
- package/dist/client/index.js.map +1 -1
- package/dist/{index-BotXLTck.d.ts → index-M00CsNUR.d.ts} +149 -10
- package/dist/index.d.ts +20 -81
- package/dist/index.js +244 -278
- package/dist/index.js.map +1 -1
- package/dist/{kit-types-BHlDNNpd.d.ts → kit-types-XUMggtk_.d.ts} +14 -5
- package/dist/modules/a2a/index.d.ts +2 -2
- package/dist/modules/crypto/index.d.ts +167 -52
- package/dist/modules/crypto/index.js +2 -3
- package/dist/modules/crypto/index.js.map +1 -1
- package/package.json +5 -4
- package/dist/chunk-BRZK7V5O.js.map +0 -1
- package/dist/chunk-FRYJMRTP.js.map +0 -1
- package/dist/chunk-GRYHRXVC.js +0 -274
- package/dist/chunk-GRYHRXVC.js.map +0 -1
- package/dist/chunk-XTZUGWBY.js +0 -137
- package/dist/chunk-XTZUGWBY.js.map +0 -1
- package/dist/kit-crypto-types-C-gEvx04.d.ts +0 -253
|
@@ -1,10 +1,171 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
3
|
-
export {
|
|
4
|
-
import {
|
|
5
|
-
import { M as Middleware } from '../../kit-types-BHlDNNpd.js';
|
|
1
|
+
import { RequestEvent, Cookies } from '@sveltejs/kit';
|
|
2
|
+
import { CryptoFunctions } from '@h-ai/crypto';
|
|
3
|
+
export { EncryptedPayload, TransportEncryptionManager, TransportKeyPair } from '@h-ai/crypto';
|
|
4
|
+
import { M as Middleware } from '../../kit-types-XUMggtk_.js';
|
|
6
5
|
import '@h-ai/iam';
|
|
7
6
|
|
|
7
|
+
/**
|
|
8
|
+
* @h-ai/kit — Crypto 类型定义
|
|
9
|
+
*
|
|
10
|
+
* Crypto 模块集成相关类型
|
|
11
|
+
* @module kit-crypto-types
|
|
12
|
+
*/
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* Crypto 服务接口(简化版,与 @h-ai/crypto 兼容)
|
|
16
|
+
*/
|
|
17
|
+
interface CryptoServiceLike {
|
|
18
|
+
hmac: {
|
|
19
|
+
sign: (data: string, key: string, algorithm?: string) => Promise<{
|
|
20
|
+
success: boolean;
|
|
21
|
+
data?: string;
|
|
22
|
+
error?: {
|
|
23
|
+
code: number;
|
|
24
|
+
message: string;
|
|
25
|
+
};
|
|
26
|
+
}>;
|
|
27
|
+
verify: (data: string, key: string, signature: string, algorithm?: string) => Promise<{
|
|
28
|
+
success: boolean;
|
|
29
|
+
data?: boolean;
|
|
30
|
+
error?: {
|
|
31
|
+
code: number;
|
|
32
|
+
message: string;
|
|
33
|
+
};
|
|
34
|
+
}>;
|
|
35
|
+
};
|
|
36
|
+
hash: {
|
|
37
|
+
digest: (data: string, algorithm?: string) => Promise<{
|
|
38
|
+
success: boolean;
|
|
39
|
+
data?: string;
|
|
40
|
+
error?: {
|
|
41
|
+
code: number;
|
|
42
|
+
message: string;
|
|
43
|
+
};
|
|
44
|
+
}>;
|
|
45
|
+
timingSafeEqual: (a: string, b: string) => Promise<{
|
|
46
|
+
success: boolean;
|
|
47
|
+
data?: boolean;
|
|
48
|
+
error?: {
|
|
49
|
+
code: number;
|
|
50
|
+
message: string;
|
|
51
|
+
};
|
|
52
|
+
}>;
|
|
53
|
+
};
|
|
54
|
+
aes: {
|
|
55
|
+
encrypt: (data: string, key: string) => Promise<{
|
|
56
|
+
success: boolean;
|
|
57
|
+
data?: string;
|
|
58
|
+
error?: {
|
|
59
|
+
code: number;
|
|
60
|
+
message: string;
|
|
61
|
+
};
|
|
62
|
+
}>;
|
|
63
|
+
decrypt: (data: string, key: string) => Promise<{
|
|
64
|
+
success: boolean;
|
|
65
|
+
data?: string;
|
|
66
|
+
error?: {
|
|
67
|
+
code: number;
|
|
68
|
+
message: string;
|
|
69
|
+
};
|
|
70
|
+
}>;
|
|
71
|
+
};
|
|
72
|
+
random: {
|
|
73
|
+
bytes: (length: number) => Promise<{
|
|
74
|
+
success: boolean;
|
|
75
|
+
data?: Uint8Array;
|
|
76
|
+
error?: {
|
|
77
|
+
code: number;
|
|
78
|
+
message: string;
|
|
79
|
+
};
|
|
80
|
+
}>;
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
/**
|
|
84
|
+
* Webhook 验证配置
|
|
85
|
+
*/
|
|
86
|
+
interface WebhookVerifyConfig {
|
|
87
|
+
/** Crypto 服务实例 */
|
|
88
|
+
crypto: CryptoServiceLike;
|
|
89
|
+
/** 请求事件 */
|
|
90
|
+
event: RequestEvent;
|
|
91
|
+
/** 签名密钥 */
|
|
92
|
+
secretKey: string;
|
|
93
|
+
/** 签名头名称 */
|
|
94
|
+
signatureHeader?: string;
|
|
95
|
+
/** 算法 */
|
|
96
|
+
algorithm?: 'sha256' | 'sha512';
|
|
97
|
+
/** 编码 */
|
|
98
|
+
encoding?: 'hex' | 'base64';
|
|
99
|
+
}
|
|
100
|
+
/**
|
|
101
|
+
* CSRF 配置
|
|
102
|
+
*/
|
|
103
|
+
interface CryptoCsrfConfig {
|
|
104
|
+
/** Crypto 服务实例 */
|
|
105
|
+
crypto: CryptoServiceLike;
|
|
106
|
+
/** Cookie 名称 */
|
|
107
|
+
cookieName?: string;
|
|
108
|
+
/** Header 名称 */
|
|
109
|
+
headerName?: string;
|
|
110
|
+
/** 表单字段名称 */
|
|
111
|
+
formFieldName?: string;
|
|
112
|
+
/** Token 长度 */
|
|
113
|
+
tokenLength?: number;
|
|
114
|
+
/** Cookie 选项 */
|
|
115
|
+
cookieOptions?: {
|
|
116
|
+
path?: string;
|
|
117
|
+
httpOnly?: boolean;
|
|
118
|
+
secure?: boolean;
|
|
119
|
+
sameSite?: 'strict' | 'lax' | 'none';
|
|
120
|
+
maxAge?: number;
|
|
121
|
+
};
|
|
122
|
+
}
|
|
123
|
+
/**
|
|
124
|
+
* 加密 Cookie 配置
|
|
125
|
+
*/
|
|
126
|
+
interface EncryptedCookieConfig {
|
|
127
|
+
/** Crypto 服务实例 */
|
|
128
|
+
crypto: CryptoServiceLike;
|
|
129
|
+
/** 加密密钥 */
|
|
130
|
+
encryptionKey: string;
|
|
131
|
+
/** Cookie 选项 */
|
|
132
|
+
cookieOptions?: {
|
|
133
|
+
path?: string;
|
|
134
|
+
httpOnly?: boolean;
|
|
135
|
+
secure?: boolean;
|
|
136
|
+
sameSite?: 'strict' | 'lax' | 'none';
|
|
137
|
+
maxAge?: number;
|
|
138
|
+
};
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
/**
|
|
142
|
+
* 传输加密配置。
|
|
143
|
+
*
|
|
144
|
+
* kit 不再维护本地加解密实现;服务端管理器由 `crypto.transport.createServer()` 创建,
|
|
145
|
+
* 协议常量与载荷类型统一来自 `@h-ai/crypto`。
|
|
146
|
+
*/
|
|
147
|
+
interface TransportEncryptionConfig {
|
|
148
|
+
/** 是否启用传输加密(默认 false) */
|
|
149
|
+
enabled: boolean;
|
|
150
|
+
/** @h-ai/crypto 服务实例 */
|
|
151
|
+
crypto: CryptoFunctions;
|
|
152
|
+
/** 密钥交换端点路径(默认 `/api/_hai/key-exchange`) */
|
|
153
|
+
keyExchangePath?: string;
|
|
154
|
+
/** 排除路径(不加密),支持精确匹配和前缀匹配 */
|
|
155
|
+
excludePaths?: string[];
|
|
156
|
+
/** 是否加密响应(默认 true) */
|
|
157
|
+
encryptResponse?: boolean;
|
|
158
|
+
/** 服务端可缓存的客户端公钥数量上限(默认 10000) */
|
|
159
|
+
maxClients?: number;
|
|
160
|
+
/**
|
|
161
|
+
* 是否强制要求传输加密(默认 true)
|
|
162
|
+
*
|
|
163
|
+
* - `true`:非排除路径上缺少 X-Client-Id 请求头时返回 400,防止绕过加密。
|
|
164
|
+
* - `false`:缺少 X-Client-Id 时透传明文,仅适用于渐进式迁移场景,不建议生产启用。
|
|
165
|
+
*/
|
|
166
|
+
requireEncryption?: boolean;
|
|
167
|
+
}
|
|
168
|
+
|
|
8
169
|
/**
|
|
9
170
|
* @h-ai/kit — Crypto Helpers
|
|
10
171
|
*
|
|
@@ -105,52 +266,6 @@ declare function createEncryptedCookie(config: EncryptedCookieConfig): {
|
|
|
105
266
|
delete(cookies: Cookies, name: string): void;
|
|
106
267
|
};
|
|
107
268
|
|
|
108
|
-
/**
|
|
109
|
-
* @h-ai/kit — 传输加密核心
|
|
110
|
-
*
|
|
111
|
-
* 基于非对称 + 对称的混合传输加密。
|
|
112
|
-
* @module kit-transport-encryption
|
|
113
|
-
*/
|
|
114
|
-
|
|
115
|
-
/**
|
|
116
|
-
* 创建传输加密管理器
|
|
117
|
-
*
|
|
118
|
-
* 启动时生成服务端非对称密钥对,通过 clientId → publicKey 的内存 Map 管理客户端密钥。
|
|
119
|
-
* 内置 LRU 淘汰机制,超过 maxClients 上限时自动移除最早注册的客户端。
|
|
120
|
-
*
|
|
121
|
-
* 注意:clientKeys 存储在进程内存中,多节点部署时各节点状态独立。
|
|
122
|
-
* 客户端密钥交换后的后续请求必须路由到同一节点(如使用 sticky session),
|
|
123
|
-
* 否则传输加密功能不可用。
|
|
124
|
-
*
|
|
125
|
-
* @param cryptoService - 传输加密服务实例(非对称 + 对称)
|
|
126
|
-
* @param maxClients - 最大客户端数量(默认 10000),超过时淘汰最早注册的
|
|
127
|
-
* @returns 成功返回传输加密管理器,密钥对生成失败时返回错误
|
|
128
|
-
*/
|
|
129
|
-
declare function createTransportEncryption(cryptoService: TransportCryptoServiceLike, maxClients?: number): HaiResult<TransportEncryptionManager>;
|
|
130
|
-
/**
|
|
131
|
-
* 创建密钥交换端点处理器
|
|
132
|
-
*
|
|
133
|
-
* 返回一个标准的 POST 处理函数,用于接收客户端公钥并返回服务端公钥与 clientId。
|
|
134
|
-
*
|
|
135
|
-
* @param manager - 传输加密管理器
|
|
136
|
-
* @returns POST 处理函数,可直接用于 SvelteKit +server.ts
|
|
137
|
-
*
|
|
138
|
-
* @example
|
|
139
|
-
* ```ts
|
|
140
|
-
* // src/routes/api/kit/key-exchange/+server.ts
|
|
141
|
-
* import { keyExchangeHandler } from '$lib/server/transport'
|
|
142
|
-
* export const POST = keyExchangeHandler
|
|
143
|
-
* ```
|
|
144
|
-
*/
|
|
145
|
-
declare function createKeyExchangeHandler(manager: TransportEncryptionManager): (request: Request) => Promise<Response>;
|
|
146
|
-
/**
|
|
147
|
-
* 校验加密载荷格式是否合法
|
|
148
|
-
*
|
|
149
|
-
* @param payload - 待校验对象
|
|
150
|
-
* @returns 是否为合法的 EncryptedPayload
|
|
151
|
-
*/
|
|
152
|
-
declare function isValidEncryptedPayload(payload: unknown): payload is EncryptedPayload;
|
|
153
|
-
|
|
154
269
|
/**
|
|
155
270
|
* @h-ai/kit — 传输加密中间件
|
|
156
271
|
*
|
|
@@ -177,4 +292,4 @@ declare function isValidEncryptedPayload(payload: unknown): payload is Encrypted
|
|
|
177
292
|
*/
|
|
178
293
|
declare function transportEncryptionMiddleware(config: TransportEncryptionConfig): Middleware;
|
|
179
294
|
|
|
180
|
-
export { CryptoCsrfConfig, CryptoServiceLike, EncryptedCookieConfig,
|
|
295
|
+
export { type CryptoCsrfConfig, type CryptoServiceLike, type EncryptedCookieConfig, type TransportEncryptionConfig, type WebhookVerifyConfig, createCsrfManager, createEncryptedCookie, signRequest, transportEncryptionMiddleware, verifyWebhookSignature };
|
|
@@ -1,6 +1,5 @@
|
|
|
1
|
-
export { transportEncryptionMiddleware } from '../../chunk-
|
|
2
|
-
import { kitM } from '../../chunk-
|
|
3
|
-
export { createKeyExchangeHandler, createTransportEncryption, isValidEncryptedPayload } from '../../chunk-BRZK7V5O.js';
|
|
1
|
+
export { transportEncryptionMiddleware } from '../../chunk-BM7IP4W5.js';
|
|
2
|
+
import { kitM } from '../../chunk-MI65L22O.js';
|
|
4
3
|
|
|
5
4
|
// src/modules/crypto/kit-crypto-helpers.ts
|
|
6
5
|
async function verifyWebhookSignature(config) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../src/modules/crypto/kit-crypto-helpers.ts"],"names":[],"mappings":"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","file":"index.js","sourcesContent":["/**\n * @h-ai/kit — Crypto Helpers\n *\n * 集成 @h-ai/crypto 的 SvelteKit 工具\n * @module kit-crypto-helpers\n */\n\nimport type { Cookies, RequestEvent } from '@sveltejs/kit'\nimport type {\n CryptoCsrfConfig,\n CryptoServiceLike,\n EncryptedCookieConfig,\n WebhookVerifyConfig,\n} from './kit-crypto-types.js'\nimport { kitM } from '../../kit-i18n.js'\n\n/**\n * 验证 Webhook 签名\n *\n * 从请求头取出签名,用 HMAC 对原始 Body 进行比较验证。\n *\n * @param config - 签名验证配置\n * @returns 签名是否合法\n *\n * @example\n * ```ts\n * const valid = await verifyWebhookSignature({\n * crypto, event, secretKey: 'wh_secret', signatureHeader: 'X-Signature',\n * })\n * if (!valid) return new Response('Invalid signature', { status: 401 })\n * ```\n */\nexport async function verifyWebhookSignature(config: WebhookVerifyConfig): Promise<boolean> {\n const {\n crypto,\n event,\n secretKey,\n signatureHeader = 'X-Signature',\n algorithm = 'sha256',\n } = config\n\n const signature = event.request.headers.get(signatureHeader)\n if (!signature) {\n return false\n }\n\n const body = await event.request.text()\n\n try {\n const result = await crypto.hmac.verify(body, secretKey, signature, algorithm)\n return result.success && result.data === true\n }\n catch {\n return false\n }\n}\n\n/**\n * 生成请求 HMAC 签名(用于调用外部服务)\n *\n * @param crypto - @h-ai/crypto 服务实例\n * @param body - 请求体字符串\n * @param secretKey - 共享密钥\n * @param algorithm - 哈希算法(默认 `'sha256'`)\n * @returns 签名字符串\n * @throws 签名失败时抛出 Error\n */\nexport async function signRequest(\n crypto: CryptoServiceLike,\n body: string,\n secretKey: string,\n algorithm = 'sha256',\n): Promise<string> {\n const result = await crypto.hmac.sign(body, secretKey, algorithm)\n if (!result.success) {\n throw new Error(result.error?.message || kitM('kit_signFailed'))\n }\n return result.data!\n}\n\n/**\n * 创建 CSRF Token 管理器\n *\n * 基于 `@h-ai/crypto` 随机字节 + 时间安全比较,\n * 提供 token 生成、验证和 SvelteKit handle 中间件。\n *\n * @param config - CSRF 配置(crypto 实例、Cookie 名、Header 名等)\n * @returns `{ generate, verify, createHandle }`\n *\n * @example\n * ```ts\n * const csrf = createCsrfManager({ crypto })\n * // 在 load 中生成\n * const token = await csrf.generate(cookies)\n * // 在 action 中验证\n * const ok = await csrf.verify(event)\n * ```\n */\nexport function createCsrfManager(config: CryptoCsrfConfig) {\n const {\n crypto,\n cookieName = 'csrf_token',\n headerName = 'X-CSRF-Token',\n formFieldName = '_csrf',\n tokenLength = 32,\n cookieOptions = {},\n } = config\n\n return {\n /**\n * 生成新的 CSRF Token 并设置 Cookie\n */\n async generate(cookies: Cookies): Promise<string> {\n const result = await crypto.random.bytes(tokenLength)\n if (!result.success) {\n throw new Error(kitM('kit_csrfTokenFailed'))\n }\n\n const token = Array.from(result.data!)\n .map(b => b.toString(16).padStart(2, '0'))\n .join('')\n\n cookies.set(cookieName, token, {\n path: '/',\n httpOnly: true,\n secure: true,\n sameSite: 'strict',\n ...cookieOptions,\n })\n\n return token\n },\n\n /**\n * 验证 CSRF Token\n */\n async verify(event: RequestEvent): Promise<boolean> {\n const cookieToken = event.cookies.get(cookieName)\n if (!cookieToken) {\n return false\n }\n\n // 从 header 或 form data 获取 token\n let requestToken = event.request.headers.get(headerName)\n\n if (!requestToken && event.request.method === 'POST') {\n try {\n const formData = await event.request.clone().formData()\n const fieldValue = formData.get(formFieldName)\n requestToken = typeof fieldValue === 'string' ? fieldValue : null\n }\n catch {\n // 不是 form data\n }\n }\n\n if (!requestToken) {\n return false\n }\n\n // 时间安全的比较\n const result = await crypto.hash.timingSafeEqual(cookieToken, requestToken)\n return result.success && result.data === true\n },\n\n /**\n * 创建 CSRF 验证中间件\n */\n createHandle() {\n return async ({ event, resolve }: { event: RequestEvent, resolve: (event: RequestEvent) => Promise<Response> }) => {\n // 跳过安全方法\n const safeMethods = ['GET', 'HEAD', 'OPTIONS']\n if (safeMethods.includes(event.request.method)) {\n return resolve(event)\n }\n\n const isValid = await this.verify(event)\n if (!isValid) {\n return new Response(kitM('kit_csrfVerifyFailed'), { status: 403 })\n }\n\n return resolve(event)\n }\n },\n }\n}\n\n/**\n * 创建加密 Cookie 管理器\n *\n * 使用 AES 对 Cookie 值进行加解密,防止客户端篡改。\n *\n * @param config - 加密 Cookie 配置(含加密密钥)\n * @returns `{ set, get, delete }`\n *\n * @example\n * ```ts\n * const enc = createEncryptedCookie({ crypto, encryptionKey: 'my-32byte-key' })\n * await enc.set(cookies, 'prefs', { theme: 'dark' })\n * const prefs = await enc.get(cookies, 'prefs')\n * ```\n */\nexport function createEncryptedCookie(config: EncryptedCookieConfig) {\n const { crypto, encryptionKey, cookieOptions = {} } = config\n\n return {\n /**\n * 设置加密 Cookie\n */\n async set(cookies: Cookies, name: string, value: unknown): Promise<void> {\n const json = JSON.stringify(value)\n const result = await crypto.aes.encrypt(json, encryptionKey)\n\n if (!result.success) {\n throw new Error(kitM('kit_encryptFailed'))\n }\n\n cookies.set(name, result.data!, {\n path: '/',\n httpOnly: true,\n secure: true,\n sameSite: 'lax',\n ...cookieOptions,\n })\n },\n\n /**\n * 获取并解密 Cookie\n */\n async get<T = unknown>(cookies: Cookies, name: string): Promise<T | null> {\n const encrypted = cookies.get(name)\n if (!encrypted) {\n return null\n }\n\n try {\n const result = await crypto.aes.decrypt(encrypted, encryptionKey)\n if (!result.success) {\n return null\n }\n\n return JSON.parse(result.data!) as T\n }\n catch {\n return null\n }\n },\n\n /**\n * 删除 Cookie\n */\n delete(cookies: Cookies, name: string): void {\n cookies.delete(name, { path: '/' })\n },\n }\n}\n"]}
|
|
1
|
+
{"version":3,"sources":["../../../src/modules/crypto/kit-crypto-helpers.ts"],"names":[],"mappings":"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","file":"index.js","sourcesContent":["/**\n * @h-ai/kit — Crypto Helpers\n *\n * 集成 @h-ai/crypto 的 SvelteKit 工具\n * @module kit-crypto-helpers\n */\n\nimport type { Cookies, RequestEvent } from '@sveltejs/kit'\nimport type {\n CryptoCsrfConfig,\n CryptoServiceLike,\n EncryptedCookieConfig,\n WebhookVerifyConfig,\n} from './kit-crypto-types.js'\nimport { kitM } from '../../kit-i18n.js'\n\n/**\n * 验证 Webhook 签名\n *\n * 从请求头取出签名,用 HMAC 对原始 Body 进行比较验证。\n *\n * @param config - 签名验证配置\n * @returns 签名是否合法\n *\n * @example\n * ```ts\n * const valid = await verifyWebhookSignature({\n * crypto, event, secretKey: 'wh_secret', signatureHeader: 'X-Signature',\n * })\n * if (!valid) return new Response('Invalid signature', { status: 401 })\n * ```\n */\nexport async function verifyWebhookSignature(config: WebhookVerifyConfig): Promise<boolean> {\n const {\n crypto,\n event,\n secretKey,\n signatureHeader = 'X-Signature',\n algorithm = 'sha256',\n } = config\n\n const signature = event.request.headers.get(signatureHeader)\n if (!signature) {\n return false\n }\n\n const body = await event.request.text()\n\n try {\n const result = await crypto.hmac.verify(body, secretKey, signature, algorithm)\n return result.success && result.data === true\n }\n catch {\n return false\n }\n}\n\n/**\n * 生成请求 HMAC 签名(用于调用外部服务)\n *\n * @param crypto - @h-ai/crypto 服务实例\n * @param body - 请求体字符串\n * @param secretKey - 共享密钥\n * @param algorithm - 哈希算法(默认 `'sha256'`)\n * @returns 签名字符串\n * @throws 签名失败时抛出 Error\n */\nexport async function signRequest(\n crypto: CryptoServiceLike,\n body: string,\n secretKey: string,\n algorithm = 'sha256',\n): Promise<string> {\n const result = await crypto.hmac.sign(body, secretKey, algorithm)\n if (!result.success) {\n throw new Error(result.error?.message || kitM('kit_signFailed'))\n }\n return result.data!\n}\n\n/**\n * 创建 CSRF Token 管理器\n *\n * 基于 `@h-ai/crypto` 随机字节 + 时间安全比较,\n * 提供 token 生成、验证和 SvelteKit handle 中间件。\n *\n * @param config - CSRF 配置(crypto 实例、Cookie 名、Header 名等)\n * @returns `{ generate, verify, createHandle }`\n *\n * @example\n * ```ts\n * const csrf = createCsrfManager({ crypto })\n * // 在 load 中生成\n * const token = await csrf.generate(cookies)\n * // 在 action 中验证\n * const ok = await csrf.verify(event)\n * ```\n */\nexport function createCsrfManager(config: CryptoCsrfConfig) {\n const {\n crypto,\n cookieName = 'csrf_token',\n headerName = 'X-CSRF-Token',\n formFieldName = '_csrf',\n tokenLength = 32,\n cookieOptions = {},\n } = config\n\n return {\n /**\n * 生成新的 CSRF Token 并设置 Cookie\n */\n async generate(cookies: Cookies): Promise<string> {\n const result = await crypto.random.bytes(tokenLength)\n if (!result.success) {\n throw new Error(kitM('kit_csrfTokenFailed'))\n }\n\n const token = Array.from(result.data!)\n .map(b => b.toString(16).padStart(2, '0'))\n .join('')\n\n cookies.set(cookieName, token, {\n path: '/',\n httpOnly: true,\n secure: true,\n sameSite: 'strict',\n ...cookieOptions,\n })\n\n return token\n },\n\n /**\n * 验证 CSRF Token\n */\n async verify(event: RequestEvent): Promise<boolean> {\n const cookieToken = event.cookies.get(cookieName)\n if (!cookieToken) {\n return false\n }\n\n // 从 header 或 form data 获取 token\n let requestToken = event.request.headers.get(headerName)\n\n if (!requestToken && event.request.method === 'POST') {\n try {\n const formData = await event.request.clone().formData()\n const fieldValue = formData.get(formFieldName)\n requestToken = typeof fieldValue === 'string' ? fieldValue : null\n }\n catch {\n // 不是 form data\n }\n }\n\n if (!requestToken) {\n return false\n }\n\n // 时间安全的比较\n const result = await crypto.hash.timingSafeEqual(cookieToken, requestToken)\n return result.success && result.data === true\n },\n\n /**\n * 创建 CSRF 验证中间件\n */\n createHandle() {\n return async ({ event, resolve }: { event: RequestEvent, resolve: (event: RequestEvent) => Promise<Response> }) => {\n // 跳过安全方法\n const safeMethods = ['GET', 'HEAD', 'OPTIONS']\n if (safeMethods.includes(event.request.method)) {\n return resolve(event)\n }\n\n const isValid = await this.verify(event)\n if (!isValid) {\n return new Response(kitM('kit_csrfVerifyFailed'), { status: 403 })\n }\n\n return resolve(event)\n }\n },\n }\n}\n\n/**\n * 创建加密 Cookie 管理器\n *\n * 使用 AES 对 Cookie 值进行加解密,防止客户端篡改。\n *\n * @param config - 加密 Cookie 配置(含加密密钥)\n * @returns `{ set, get, delete }`\n *\n * @example\n * ```ts\n * const enc = createEncryptedCookie({ crypto, encryptionKey: 'my-32byte-key' })\n * await enc.set(cookies, 'prefs', { theme: 'dark' })\n * const prefs = await enc.get(cookies, 'prefs')\n * ```\n */\nexport function createEncryptedCookie(config: EncryptedCookieConfig) {\n const { crypto, encryptionKey, cookieOptions = {} } = config\n\n return {\n /**\n * 设置加密 Cookie\n */\n async set(cookies: Cookies, name: string, value: unknown): Promise<void> {\n const json = JSON.stringify(value)\n const result = await crypto.aes.encrypt(json, encryptionKey)\n\n if (!result.success) {\n throw new Error(kitM('kit_encryptFailed'))\n }\n\n cookies.set(name, result.data!, {\n path: '/',\n httpOnly: true,\n secure: true,\n sameSite: 'lax',\n ...cookieOptions,\n })\n },\n\n /**\n * 获取并解密 Cookie\n */\n async get<T = unknown>(cookies: Cookies, name: string): Promise<T | null> {\n const encrypted = cookies.get(name)\n if (!encrypted) {\n return null\n }\n\n try {\n const result = await crypto.aes.decrypt(encrypted, encryptionKey)\n if (!result.success) {\n return null\n }\n\n return JSON.parse(result.data!) as T\n }\n catch {\n return null\n }\n },\n\n /**\n * 删除 Cookie\n */\n delete(cookies: Cookies, name: string): void {\n cookies.delete(name, { path: '/' })\n },\n }\n}\n"]}
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@h-ai/kit",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "0.1.0-alpha.
|
|
4
|
+
"version": "0.1.0-alpha.16",
|
|
5
5
|
"description": "Hai Framework SvelteKit integration module.",
|
|
6
6
|
"license": "Apache-2.0",
|
|
7
7
|
"exports": {
|
|
@@ -41,7 +41,7 @@
|
|
|
41
41
|
"access": "public"
|
|
42
42
|
},
|
|
43
43
|
"peerDependencies": {
|
|
44
|
-
"@sveltejs/adapter-node": "^5.
|
|
44
|
+
"@sveltejs/adapter-node": "^5.5.4",
|
|
45
45
|
"@sveltejs/adapter-static": "^3.0.0",
|
|
46
46
|
"@sveltejs/kit": "^2.53.4",
|
|
47
47
|
"svelte": "^5.53.6"
|
|
@@ -56,8 +56,9 @@
|
|
|
56
56
|
},
|
|
57
57
|
"dependencies": {
|
|
58
58
|
"zod": "^4.3.6",
|
|
59
|
-
"@h-ai/core": "0.1.0-alpha.
|
|
60
|
-
"@h-ai/
|
|
59
|
+
"@h-ai/core": "0.1.0-alpha.16",
|
|
60
|
+
"@h-ai/crypto": "0.1.0-alpha.16",
|
|
61
|
+
"@h-ai/iam": "0.1.0-alpha.16"
|
|
61
62
|
},
|
|
62
63
|
"devDependencies": {
|
|
63
64
|
"@sveltejs/kit": "^2.57.1",
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"sources":["../messages/en-US.json","../messages/zh-CN.json","../src/kit-i18n.ts","../src/modules/crypto/kit-transport-encryption.ts"],"names":[],"mappings":";;;;;AAAA,IAAA,aAAA,GAAA;AAAA,EACE,OAAA,EAAW,iDAAA;AAAA,EACX,gBAAA,EAAoB,cAAA;AAAA,EACpB,aAAA,EAAiB,4CAAA;AAAA,EACjB,qBAAA,EAAyB,wEAAA;AAAA,EACzB,mBAAA,EAAuB,+BAAA;AAAA,EACvB,oBAAA,EAAwB,gCAAA;AAAA,EACxB,wBAAA,EAA4B,oBAAA;AAAA,EAC5B,qBAAA,EAAyB,2CAAA;AAAA,EACzB,0BAAA,EAA8B,0BAAA;AAAA,EAC9B,mBAAA,EAAuB,8BAAA;AAAA,EACvB,iBAAA,EAAqB,mBAAA;AAAA,EACrB,gCAAA,EAAoC,4CAAA;AAAA,EACpC,8BAAA,EAAkC,sBAAA;AAAA,EAClC,0BAAA,EAA8B,6BAAA;AAAA,EAC9B,6BAAA,EAAiC,iCAAA;AAAA,EACjC,6BAAA,EAAiC,iCAAA;AAAA,EACjC,0BAAA,EAA8B,6BAAA;AAAA,EAC9B,2BAAA,EAA+B,2BAAA;AAAA,EAC/B,8BAAA,EAAkC,qBAAA;AAAA,EAClC,6BAAA,EAAiC,+EAAA;AAAA,EACjC,cAAA,EAAkB,wBAAA;AAAA,EAClB,gBAAA,EAAoB,yBAAA;AAAA,EACpB,gBAAA,EAAoB,eAAA;AAAA,EACpB,oBAAA,EAAwB,oBAAA;AAAA,EACxB,iBAAA,EAAqB,uBAAA;AAAA,EACrB,oBAAA,EAAwB,mBAAA;AAAA,EACxB,kBAAA,EAAsB,kBAAA;AAAA,EACtB,iBAAA,EAAqB,yBAAA;AAAA,EACrB,uBAAA,EAA2B,qCAAA;AAAA,EAC3B,cAAA,EAAkB;AACpB,CAAA;;;AC/BA,IAAA,aAAA,GAAA;AAAA,EACE,OAAA,EAAW,iDAAA;AAAA,EACX,gBAAA,EAAoB,oBAAA;AAAA,EACpB,aAAA,EAAiB,sEAAA;AAAA,EACjB,qBAAA,EAAyB,qGAAA;AAAA,EACzB,mBAAA,EAAuB,sCAAA;AAAA,EACvB,oBAAA,EAAwB,qCAAA;AAAA,EACxB,wBAAA,EAA4B,yBAAA;AAAA,EAC5B,qBAAA,EAAyB,0EAAA;AAAA,EACzB,0BAAA,EAA8B,kDAAA;AAAA,EAC9B,mBAAA,EAAuB,4CAAA;AAAA,EACvB,iBAAA,EAAqB,0BAAA;AAAA,EACrB,gCAAA,EAAoC,oEAAA;AAAA,EACpC,8BAAA,EAAkC,kDAAA;AAAA,EAClC,0BAAA,EAA8B,sCAAA;AAAA,EAC9B,6BAAA,EAAiC,kDAAA;AAAA,EACjC,6BAAA,EAAiC,kDAAA;AAAA,EACjC,0BAAA,EAA8B,sCAAA;AAAA,EAC9B,2BAAA,EAA+B,4CAAA;AAAA,EAC/B,8BAAA,EAAkC,sCAAA;AAAA,EAClC,6BAAA,EAAiC,iIAAA;AAAA,EACjC,cAAA,EAAkB,sCAAA;AAAA,EAClB,gBAAA,EAAoB,sCAAA;AAAA,EACpB,gBAAA,EAAoB,0BAAA;AAAA,EACpB,oBAAA,EAAwB,gCAAA;AAAA,EACxB,iBAAA,EAAqB,4CAAA;AAAA,EACrB,oBAAA,EAAwB,sCAAA;AAAA,EACxB,kBAAA,EAAsB,sCAAA;AAAA,EACtB,iBAAA,EAAqB,uCAAA;AAAA,EACrB,uBAAA,EAA2B,6CAAA;AAAA,EAC3B,cAAA,EAAkB;AACpB,CAAA;;;ACjBO,IAAM,IAAA,GACT,KAAK,IAAA,CAAK,mBAAA,CAAmC,EAAE,OAAA,EAAS,aAAA,EAAc,OAAA,EAAS,aAAA,EAAc;AAiB1F,SAAS,oBAAoB,MAAA,EAAsB;AACxD,EAAA,IAAA,CAAK,IAAA,CAAK,gBAAgB,MAAM,CAAA;AAClC;ACHO,SAAS,yBAAA,CACd,aAAA,EACA,UAAA,GAAa,GAAA,EAC0B;AAEvC,EAAA,MAAM,aAAA,GAAgB,aAAA,CAAc,UAAA,CAAW,eAAA,EAAgB;AAC/D,EAAA,IAAI,CAAC,aAAA,CAAc,OAAA,IAAW,CAAC,cAAc,IAAA,EAAM;AACjD,IAAA,OAAO,GAAA,CAAI,EAAE,IAAA,EAAM,qCAAA,EAAuC,SAAS,IAAA,CAAK,kCAAkC,GAAG,CAAA;AAAA,EAC/G;AACA,EAAA,MAAM,gBAAkC,aAAA,CAAc,IAAA;AAGtD,EAAA,MAAM,UAAA,uBAAiB,GAAA,EAAoB;AAC3C,EAAA,IAAI,eAAA,GAAkB,CAAA;AAEtB,EAAA,OAAO,EAAA,CAAG;AAAA,IACR,kBAAA,GAA6B;AAC3B,MAAA,OAAO,aAAA,CAAc,SAAA;AAAA,IACvB,CAAA;AAAA,IAEA,kBAAkB,eAAA,EAAiC;AACjD,MAAA,eAAA,EAAA;AACA,MAAA,MAAM,WAAW,CAAA,OAAA,EAAU,eAAe,CAAA,CAAA,EAAI,IAAA,CAAK,KAAK,CAAA,CAAA;AAGxD,MAAA,IAAI,UAAA,CAAW,QAAQ,UAAA,EAAY;AACjC,QAAA,MAAM,SAAA,GAAY,UAAA,CAAW,IAAA,EAAK,CAAE,MAAK,CAAE,KAAA;AAC3C,QAAA,IAAI,cAAc,MAAA,EAAW;AAC3B,UAAA,UAAA,CAAW,OAAO,SAAS,CAAA;AAAA,QAC7B;AAAA,MACF;AAEA,MAAA,UAAA,CAAW,GAAA,CAAI,UAAU,eAAe,CAAA;AACxC,MAAA,OAAO,QAAA;AAAA,IACT,CAAA;AAAA,IAEA,mBAAmB,QAAA,EAAsC;AACvD,MAAA,OAAO,UAAA,CAAW,IAAI,QAAQ,CAAA;AAAA,IAChC,CAAA;AAAA,IAEA,eAAA,CAAgB,UAAkB,IAAA,EAAgC;AAChE,MAAA,MAAM,eAAA,GAAkB,UAAA,CAAW,GAAA,CAAI,QAAQ,CAAA;AAC/C,MAAA,IAAI,CAAC,eAAA,EAAiB;AACpB,QAAA,MAAM,IAAI,KAAA,CAAM,IAAA,CAAK,gCAAgC,CAAC,CAAA;AAAA,MACxD;AAGA,MAAA,MAAM,YAAA,GAAe,aAAA,CAAc,SAAA,CAAU,WAAA,EAAY;AAGzD,MAAA,MAAM,SAAA,GAAY,aAAA,CAAc,SAAA,CAAU,aAAA,CAAc,MAAM,YAAY,CAAA;AAC1E,MAAA,IAAI,CAAC,SAAA,CAAU,OAAA,IAAW,CAAC,UAAU,IAAA,EAAM;AACzC,QAAA,MAAM,IAAI,KAAA,CAAM,IAAA,CAAK,4BAA4B,CAAC,CAAA;AAAA,MACpD;AAGA,MAAA,MAAM,YAAA,GAAe,aAAA,CAAc,UAAA,CAAW,OAAA,CAAQ,cAAc,eAAe,CAAA;AACnF,MAAA,IAAI,CAAC,YAAA,CAAa,OAAA,IAAW,CAAC,aAAa,IAAA,EAAM;AAC/C,QAAA,MAAM,IAAI,KAAA,CAAM,IAAA,CAAK,+BAA+B,CAAC,CAAA;AAAA,MACvD;AAEA,MAAA,OAAO;AAAA,QACL,cAAc,YAAA,CAAa,IAAA;AAAA,QAC3B,UAAA,EAAY,UAAU,IAAA,CAAK,UAAA;AAAA,QAC3B,EAAA,EAAI,UAAU,IAAA,CAAK;AAAA,OACrB;AAAA,IACF,CAAA;AAAA,IAEA,eAAe,OAAA,EAAmC;AAEhD,MAAA,MAAM,eAAe,aAAA,CAAc,UAAA,CAAW,QAAQ,OAAA,CAAQ,YAAA,EAAc,cAAc,UAAU,CAAA;AACpG,MAAA,IAAI,CAAC,YAAA,CAAa,OAAA,IAAW,CAAC,aAAa,IAAA,EAAM;AAC/C,QAAA,MAAM,IAAI,KAAA,CAAM,IAAA,CAAK,+BAA+B,CAAC,CAAA;AAAA,MACvD;AAGA,MAAA,MAAM,SAAA,GAAY,cAAc,SAAA,CAAU,aAAA,CAAc,QAAQ,UAAA,EAAY,YAAA,CAAa,IAAA,EAAM,OAAA,CAAQ,EAAE,CAAA;AACzG,MAAA,IAAI,CAAC,SAAA,CAAU,OAAA,IAAW,OAAO,SAAA,CAAU,SAAS,QAAA,EAAU;AAC5D,QAAA,MAAM,IAAI,KAAA,CAAM,IAAA,CAAK,4BAA4B,CAAC,CAAA;AAAA,MACpD;AAEA,MAAA,OAAO,SAAA,CAAU,IAAA;AAAA,IACnB;AAAA,GACD,CAAA;AACH;AAiBO,SAAS,yBACd,OAAA,EACyC;AACzC,EAAA,OAAO,OAAO,OAAA,KAAwC;AACpD,IAAA,IAAI;AACF,MAAA,MAAM,IAAA,GAAO,MAAM,OAAA,CAAQ,IAAA,EAAK;AAEhC,MAAA,IAAI,CAAC,IAAA,CAAK,eAAA,IAAmB,OAAO,IAAA,CAAK,oBAAoB,QAAA,EAAU;AACrE,QAAA,OAAO,IAAI,QAAA;AAAA,UACT,KAAK,SAAA,CAAU,EAAE,OAAO,IAAA,CAAK,6BAA6B,GAAG,CAAA;AAAA,UAC7D,EAAE,MAAA,EAAQ,GAAA,EAAK,SAAS,EAAE,cAAA,EAAgB,oBAAmB;AAAE,SACjE;AAAA,MACF;AAEA,MAAA,MAAM,QAAA,GAAW,OAAA,CAAQ,iBAAA,CAAkB,IAAA,CAAK,eAAe,CAAA;AAC/D,MAAA,MAAM,eAAA,GAAkB,QAAQ,kBAAA,EAAmB;AAEnD,MAAA,OAAO,IAAI,QAAA;AAAA,QACT,IAAA,CAAK,SAAA,CAAU,EAAE,eAAA,EAAiB,UAAU,CAAA;AAAA,QAC5C,EAAE,MAAA,EAAQ,GAAA,EAAK,SAAS,EAAE,cAAA,EAAgB,oBAAmB;AAAE,OACjE;AAAA,IACF,CAAA,CAAA,MACM;AACJ,MAAA,OAAO,IAAI,QAAA;AAAA,QACT,KAAK,SAAA,CAAU,EAAE,OAAO,IAAA,CAAK,gCAAgC,GAAG,CAAA;AAAA,QAChE,EAAE,MAAA,EAAQ,GAAA,EAAK,SAAS,EAAE,cAAA,EAAgB,oBAAmB;AAAE,OACjE;AAAA,IACF;AAAA,EACF,CAAA;AACF;AAQO,SAAS,wBAAwB,OAAA,EAA+C;AACrF,EAAA,IAAI,OAAO,OAAA,KAAY,QAAA,IAAY,OAAA,KAAY,IAAA;AAC7C,IAAA,OAAO,KAAA;AACT,EAAA,MAAM,CAAA,GAAI,OAAA;AACV,EAAA,OACE,OAAO,EAAE,YAAA,KAAiB,QAAA,IACvB,OAAO,CAAA,CAAE,UAAA,KAAe,QAAA,IACxB,OAAO,CAAA,CAAE,EAAA,KAAO,YAChB,CAAA,CAAE,YAAA,CAAa,SAAS,CAAA,IACxB,CAAA,CAAE,WAAW,MAAA,GAAS,CAAA,IACtB,CAAA,CAAE,EAAA,CAAG,MAAA,GAAS,CAAA;AAErB","file":"chunk-BRZK7V5O.js","sourcesContent":["{\n \"$schema\": \"https://inlang.com/schema/inlang-message-format\",\n \"kit_unauthorized\": \"Unauthorized\",\n \"kit_forbidden\": \"Forbidden: missing {permission} permission\",\n \"kit_authNotConfigured\": \"kit.auth is not configured: pass auth.operations in kit.createHandle()\",\n \"kit_csrfTokenFailed\": \"Failed to generate CSRF token\",\n \"kit_csrfVerifyFailed\": \"CSRF token verification failed\",\n \"kit_csrfValidationFailed\": \"Invalid CSRF token\",\n \"kit_rateLimitExceeded\": \"Too many requests, please try again later\",\n \"kit_unsupportedContentType\": \"Unsupported content type\",\n \"kit_parseBodyFailed\": \"Failed to parse request body\",\n \"kit_encryptFailed\": \"Encryption failed\",\n \"kit_transportKeyGenerationFailed\": \"Transport encryption key generation failed\",\n \"kit_transportClientKeyNotFound\": \"Client key not found\",\n \"kit_transportEncryptFailed\": \"Transport encryption failed\",\n \"kit_transportEncryptKeyFailed\": \"Symmetric key encryption failed\",\n \"kit_transportDecryptKeyFailed\": \"Symmetric key decryption failed\",\n \"kit_transportDecryptFailed\": \"Transport decryption failed\",\n \"kit_transportInvalidPayload\": \"Invalid encrypted payload\",\n \"kit_transportKeyExchangeFailed\": \"Key exchange failed\",\n \"kit_transportClientIdRequired\": \"Missing X-Client-Id header, key exchange is required for transport encryption\",\n \"kit_signFailed\": \"Request signing failed\",\n \"kit_authRequired\": \"Authentication required\",\n \"kit_accessDenied\": \"Access denied\",\n \"kit_resourceNotFound\": \"Resource not found\",\n \"kit_internalError\": \"Internal server error\",\n \"kit_validationFailed\": \"Validation failed\",\n \"kit_noGuardsPassed\": \"No guards passed\",\n \"kit_requiredRoles\": \"Required roles: {roles}\",\n \"kit_requiredPermissions\": \"Required permissions: {permissions}\",\n \"kit_idRequired\": \"ID is required\"\n}\n","{\n \"$schema\": \"https://inlang.com/schema/inlang-message-format\",\n \"kit_unauthorized\": \"未授权\",\n \"kit_forbidden\": \"权限不足:缺少 {permission} 权限\",\n \"kit_authNotConfigured\": \"kit.auth 未配置:请在 kit.createHandle() 中传入 auth.operations\",\n \"kit_csrfTokenFailed\": \"生成 CSRF Token 失败\",\n \"kit_csrfVerifyFailed\": \"CSRF Token 验证失败\",\n \"kit_csrfValidationFailed\": \"CSRF Token 无效\",\n \"kit_rateLimitExceeded\": \"请求过于频繁,请稍后再试\",\n \"kit_unsupportedContentType\": \"不支持的内容类型\",\n \"kit_parseBodyFailed\": \"请求体解析失败\",\n \"kit_encryptFailed\": \"加密失败\",\n \"kit_transportKeyGenerationFailed\": \"传输加密密钥对生成失败\",\n \"kit_transportClientKeyNotFound\": \"客户端密钥未找到\",\n \"kit_transportEncryptFailed\": \"传输加密失败\",\n \"kit_transportEncryptKeyFailed\": \"对称密钥加密失败\",\n \"kit_transportDecryptKeyFailed\": \"对称密钥解密失败\",\n \"kit_transportDecryptFailed\": \"传输解密失败\",\n \"kit_transportInvalidPayload\": \"无效的加密载荷\",\n \"kit_transportKeyExchangeFailed\": \"密钥交换失败\",\n \"kit_transportClientIdRequired\": \"缺少 X-Client-Id 请求头,传输加密必须先完成密钥交换\",\n \"kit_signFailed\": \"请求签名失败\",\n \"kit_authRequired\": \"需要身份认证\",\n \"kit_accessDenied\": \"拒绝访问\",\n \"kit_resourceNotFound\": \"资源未找到\",\n \"kit_internalError\": \"内部服务器错误\",\n \"kit_validationFailed\": \"数据验证失败\",\n \"kit_noGuardsPassed\": \"没有守卫通过\",\n \"kit_requiredRoles\": \"需要角色:{roles}\",\n \"kit_requiredPermissions\": \"需要权限:{permissions}\",\n \"kit_idRequired\": \"ID 不能为空\"\n}\n","/**\n * @h-ai/kit — i18n 工具\n *\n * Kit 模块的国际化消息工具,从 @h-ai/core 调用 i18n API。\n * @module kit-i18n\n */\n\nimport { core } from '@h-ai/core'\nimport messagesEnUS from '../messages/en-US.json'\nimport messagesZhCN from '../messages/zh-CN.json'\n\ntype KitMessageKey = keyof typeof messagesZhCN\n\n/** 获取 Kit 模块的 i18n 消息 */\nexport const kitM\n = core.i18n.createMessageGetter<KitMessageKey>({ 'zh-CN': messagesZhCN, 'en-US': messagesEnUS })\n\n/**\n * 统一设置所有 hai 模块的默认语言\n *\n * 通过 @h-ai/core 的集中式 locale 管理器,一次调用即可同步所有模块。\n * 各模块的 createMessageGetter 会读取全局 locale。\n *\n * @example\n * ```ts\n * import { kit } from '@h-ai/kit'\n *\n * // 在 i18n handle 中\n * const locale = event.cookies.get('PARAGLIDE_LOCALE') ?? 'zh-CN'\n * kit.i18n.setLocale(locale)\n * ```\n */\nexport function setAllModulesLocale(locale: string): void {\n core.i18n.setGlobalLocale(locale)\n}\n","/**\n * @h-ai/kit — 传输加密核心\n *\n * 基于非对称 + 对称的混合传输加密。\n * @module kit-transport-encryption\n */\n\nimport type { HaiResult } from '@h-ai/core'\nimport type {\n EncryptedPayload,\n TransportCryptoServiceLike,\n TransportEncryptionManager,\n TransportKeyPair,\n} from './kit-crypto-types.js'\nimport { err, ok } from '@h-ai/core'\nimport { kitM } from '../../kit-i18n.js'\n\n/**\n * 创建传输加密管理器\n *\n * 启动时生成服务端非对称密钥对,通过 clientId → publicKey 的内存 Map 管理客户端密钥。\n * 内置 LRU 淘汰机制,超过 maxClients 上限时自动移除最早注册的客户端。\n *\n * 注意:clientKeys 存储在进程内存中,多节点部署时各节点状态独立。\n * 客户端密钥交换后的后续请求必须路由到同一节点(如使用 sticky session),\n * 否则传输加密功能不可用。\n *\n * @param cryptoService - 传输加密服务实例(非对称 + 对称)\n * @param maxClients - 最大客户端数量(默认 10000),超过时淘汰最早注册的\n * @returns 成功返回传输加密管理器,密钥对生成失败时返回错误\n */\nexport function createTransportEncryption(\n cryptoService: TransportCryptoServiceLike,\n maxClients = 10000,\n): HaiResult<TransportEncryptionManager> {\n // 生成服务端密钥对\n const keyPairResult = cryptoService.asymmetric.generateKeyPair()\n if (!keyPairResult.success || !keyPairResult.data) {\n return err({ code: 'KIT_TRANSPORT_KEY_GENERATION_FAILED', message: kitM('kit_transportKeyGenerationFailed') })\n }\n const serverKeyPair: TransportKeyPair = keyPairResult.data\n\n // 客户端公钥存储:clientId → publicKey(Map 保持插入顺序,用于 LRU 淘汰)\n const clientKeys = new Map<string, string>()\n let clientIdCounter = 0\n\n return ok({\n getServerPublicKey(): string {\n return serverKeyPair.publicKey\n },\n\n registerClientKey(clientPublicKey: string): string {\n clientIdCounter++\n const clientId = `client_${clientIdCounter}_${Date.now()}`\n\n // LRU 淘汰:超过上限时移除最早注册的客户端\n if (clientKeys.size >= maxClients) {\n const oldestKey = clientKeys.keys().next().value\n if (oldestKey !== undefined) {\n clientKeys.delete(oldestKey)\n }\n }\n\n clientKeys.set(clientId, clientPublicKey)\n return clientId\n },\n\n getClientPublicKey(clientId: string): string | undefined {\n return clientKeys.get(clientId)\n },\n\n encryptResponse(clientId: string, data: string): EncryptedPayload {\n const clientPublicKey = clientKeys.get(clientId)\n if (!clientPublicKey) {\n throw new Error(kitM('kit_transportClientKeyNotFound'))\n }\n\n // 1. 生成随机对称密钥\n const symmetricKey = cryptoService.symmetric.generateKey()\n\n // 2. 对称加密内容\n const encResult = cryptoService.symmetric.encryptWithIV(data, symmetricKey)\n if (!encResult.success || !encResult.data) {\n throw new Error(kitM('kit_transportEncryptFailed'))\n }\n\n // 3. 非对称加密对称密钥(使用客户端公钥)\n const keyEncResult = cryptoService.asymmetric.encrypt(symmetricKey, clientPublicKey)\n if (!keyEncResult.success || !keyEncResult.data) {\n throw new Error(kitM('kit_transportEncryptKeyFailed'))\n }\n\n return {\n encryptedKey: keyEncResult.data,\n ciphertext: encResult.data.ciphertext,\n iv: encResult.data.iv,\n }\n },\n\n decryptRequest(payload: EncryptedPayload): string {\n // 1. 非对称解密对称密钥(使用服务端私钥)\n const keyDecResult = cryptoService.asymmetric.decrypt(payload.encryptedKey, serverKeyPair.privateKey)\n if (!keyDecResult.success || !keyDecResult.data) {\n throw new Error(kitM('kit_transportDecryptKeyFailed'))\n }\n\n // 2. 对称解密内容\n const decResult = cryptoService.symmetric.decryptWithIV(payload.ciphertext, keyDecResult.data, payload.iv)\n if (!decResult.success || typeof decResult.data !== 'string') {\n throw new Error(kitM('kit_transportDecryptFailed'))\n }\n\n return decResult.data\n },\n })\n}\n\n/**\n * 创建密钥交换端点处理器\n *\n * 返回一个标准的 POST 处理函数,用于接收客户端公钥并返回服务端公钥与 clientId。\n *\n * @param manager - 传输加密管理器\n * @returns POST 处理函数,可直接用于 SvelteKit +server.ts\n *\n * @example\n * ```ts\n * // src/routes/api/kit/key-exchange/+server.ts\n * import { keyExchangeHandler } from '$lib/server/transport'\n * export const POST = keyExchangeHandler\n * ```\n */\nexport function createKeyExchangeHandler(\n manager: TransportEncryptionManager,\n): (request: Request) => Promise<Response> {\n return async (request: Request): Promise<Response> => {\n try {\n const body = await request.json() as { clientPublicKey?: string }\n\n if (!body.clientPublicKey || typeof body.clientPublicKey !== 'string') {\n return new Response(\n JSON.stringify({ error: kitM('kit_transportInvalidPayload') }),\n { status: 400, headers: { 'Content-Type': 'application/json' } },\n )\n }\n\n const clientId = manager.registerClientKey(body.clientPublicKey)\n const serverPublicKey = manager.getServerPublicKey()\n\n return new Response(\n JSON.stringify({ serverPublicKey, clientId }),\n { status: 200, headers: { 'Content-Type': 'application/json' } },\n )\n }\n catch {\n return new Response(\n JSON.stringify({ error: kitM('kit_transportKeyExchangeFailed') }),\n { status: 500, headers: { 'Content-Type': 'application/json' } },\n )\n }\n }\n}\n\n/**\n * 校验加密载荷格式是否合法\n *\n * @param payload - 待校验对象\n * @returns 是否为合法的 EncryptedPayload\n */\nexport function isValidEncryptedPayload(payload: unknown): payload is EncryptedPayload {\n if (typeof payload !== 'object' || payload === null)\n return false\n const p = payload as Record<string, unknown>\n return (\n typeof p.encryptedKey === 'string'\n && typeof p.ciphertext === 'string'\n && typeof p.iv === 'string'\n && p.encryptedKey.length > 0\n && p.ciphertext.length > 0\n && p.iv.length > 0\n )\n}\n"]}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/crud/kit-crud.ts"],"names":[],"mappings":"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","file":"chunk-FRYJMRTP.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 *\n * @example\n * ```ts\n * const userCrud = defineCrud({\n * name: 'user',\n * label: () => m.users_title(),\n * fields: [\n * { id: 'username', label: '用户名', type: 'string', validation: { required: true } },\n * { id: 'email', label: '邮箱', type: 'email' },\n * ],\n * api: { list, get, create, update, remove },\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"]}
|
package/dist/chunk-GRYHRXVC.js
DELETED
|
@@ -1,274 +0,0 @@
|
|
|
1
|
-
import { kitM, isValidEncryptedPayload } from './chunk-BRZK7V5O.js';
|
|
2
|
-
import process from 'process';
|
|
3
|
-
|
|
4
|
-
var DEFAULT_TOKEN_COOKIE_NAME = "hai_access_token";
|
|
5
|
-
var authState = {
|
|
6
|
-
cookieName: DEFAULT_TOKEN_COOKIE_NAME,
|
|
7
|
-
operations: null
|
|
8
|
-
};
|
|
9
|
-
function configureAuth(config) {
|
|
10
|
-
if (config.cookieName)
|
|
11
|
-
authState.cookieName = config.cookieName;
|
|
12
|
-
if (config.operations)
|
|
13
|
-
authState.operations = config.operations;
|
|
14
|
-
}
|
|
15
|
-
var defaultBrowserTokenStore = createTokenStore();
|
|
16
|
-
function getBearerTokenFromRequest(request) {
|
|
17
|
-
const authorization = request.headers.get("authorization");
|
|
18
|
-
if (!authorization)
|
|
19
|
-
return null;
|
|
20
|
-
const [scheme, token] = authorization.split(" ");
|
|
21
|
-
if (!scheme || !token)
|
|
22
|
-
return null;
|
|
23
|
-
if (scheme.toLowerCase() !== "bearer")
|
|
24
|
-
return null;
|
|
25
|
-
const trimmed = token.trim();
|
|
26
|
-
return trimmed.length > 0 ? trimmed : null;
|
|
27
|
-
}
|
|
28
|
-
function getAccessToken(request, cookies) {
|
|
29
|
-
return getBearerTokenFromRequest(request) ?? cookies?.get(authState.cookieName) ?? null;
|
|
30
|
-
}
|
|
31
|
-
function setToken(cookies, token, maxAge) {
|
|
32
|
-
cookies.set(authState.cookieName, token, {
|
|
33
|
-
path: "/",
|
|
34
|
-
httpOnly: true,
|
|
35
|
-
sameSite: "lax",
|
|
36
|
-
secure: process.env.NODE_ENV === "production",
|
|
37
|
-
maxAge
|
|
38
|
-
});
|
|
39
|
-
}
|
|
40
|
-
function clearToken(cookies) {
|
|
41
|
-
cookies.delete(authState.cookieName, { path: "/" });
|
|
42
|
-
}
|
|
43
|
-
function getAuthOperations() {
|
|
44
|
-
if (!authState.operations) {
|
|
45
|
-
throw new Error(kitM("kit_authNotConfigured"));
|
|
46
|
-
}
|
|
47
|
-
return typeof authState.operations === "function" ? authState.operations() : authState.operations;
|
|
48
|
-
}
|
|
49
|
-
async function executeLogin(cookies, authPromise) {
|
|
50
|
-
const result = await authPromise;
|
|
51
|
-
if (result.success) {
|
|
52
|
-
setToken(cookies, result.data.tokens.accessToken, result.data.tokens.expiresIn);
|
|
53
|
-
}
|
|
54
|
-
return result;
|
|
55
|
-
}
|
|
56
|
-
async function login(cookies, credentials) {
|
|
57
|
-
return executeLogin(cookies, getAuthOperations().login(credentials));
|
|
58
|
-
}
|
|
59
|
-
async function loginWithOtp(cookies, credentials) {
|
|
60
|
-
return executeLogin(cookies, getAuthOperations().loginWithOtp(credentials));
|
|
61
|
-
}
|
|
62
|
-
async function loginWithLdap(cookies, credentials) {
|
|
63
|
-
return executeLogin(cookies, getAuthOperations().loginWithLdap(credentials));
|
|
64
|
-
}
|
|
65
|
-
async function loginWithApiKey(cookies, credentials) {
|
|
66
|
-
return executeLogin(cookies, getAuthOperations().loginWithApiKey(credentials));
|
|
67
|
-
}
|
|
68
|
-
async function registerAndLogin(cookies, options) {
|
|
69
|
-
return executeLogin(cookies, getAuthOperations().registerAndLogin(options));
|
|
70
|
-
}
|
|
71
|
-
async function logout(cookies, accessToken) {
|
|
72
|
-
if (accessToken) {
|
|
73
|
-
await getAuthOperations().logout(accessToken);
|
|
74
|
-
}
|
|
75
|
-
clearToken(cookies);
|
|
76
|
-
}
|
|
77
|
-
function createTokenStore(key = DEFAULT_TOKEN_COOKIE_NAME) {
|
|
78
|
-
return {
|
|
79
|
-
get() {
|
|
80
|
-
if (typeof window === "undefined") {
|
|
81
|
-
return null;
|
|
82
|
-
}
|
|
83
|
-
return window.localStorage.getItem(key);
|
|
84
|
-
},
|
|
85
|
-
set(token) {
|
|
86
|
-
if (typeof window === "undefined") {
|
|
87
|
-
return;
|
|
88
|
-
}
|
|
89
|
-
window.localStorage.setItem(key, token);
|
|
90
|
-
},
|
|
91
|
-
clear() {
|
|
92
|
-
if (typeof window === "undefined") {
|
|
93
|
-
return;
|
|
94
|
-
}
|
|
95
|
-
window.localStorage.removeItem(key);
|
|
96
|
-
}
|
|
97
|
-
};
|
|
98
|
-
}
|
|
99
|
-
function setBrowserToken(token) {
|
|
100
|
-
defaultBrowserTokenStore.set(token);
|
|
101
|
-
}
|
|
102
|
-
function clearBrowserToken() {
|
|
103
|
-
defaultBrowserTokenStore.clear();
|
|
104
|
-
}
|
|
105
|
-
function createHandleFetch(tokenStore = createTokenStore()) {
|
|
106
|
-
return async ({ event, request, fetch: fetch2 }) => {
|
|
107
|
-
const requestUrl = new URL(request.url);
|
|
108
|
-
if (requestUrl.origin !== event.url.origin)
|
|
109
|
-
return fetch2(request);
|
|
110
|
-
const token = tokenStore.get();
|
|
111
|
-
if (!token)
|
|
112
|
-
return fetch2(request);
|
|
113
|
-
const headers = new Headers(request.headers);
|
|
114
|
-
headers.set("Authorization", `Bearer ${token}`);
|
|
115
|
-
return fetch2(new Request(request, { headers }));
|
|
116
|
-
};
|
|
117
|
-
}
|
|
118
|
-
|
|
119
|
-
// src/client/kit-client.ts
|
|
120
|
-
function getCookie(name) {
|
|
121
|
-
if (typeof document === "undefined")
|
|
122
|
-
return void 0;
|
|
123
|
-
const match = document.cookie.match(new RegExp(`(?:^|;\\s*)${name}=([^;]*)`));
|
|
124
|
-
return match?.[1];
|
|
125
|
-
}
|
|
126
|
-
function createKitClient(config = {}) {
|
|
127
|
-
const {
|
|
128
|
-
transport: transportConfig,
|
|
129
|
-
csrfCookieName = "hai_csrf",
|
|
130
|
-
csrfHeaderName = "X-CSRF-Token",
|
|
131
|
-
auth: authConfig
|
|
132
|
-
} = config;
|
|
133
|
-
const authStore = authConfig ? authConfig === true ? createTokenStore() : authConfig : null;
|
|
134
|
-
let transportReady = false;
|
|
135
|
-
let clientKeyPair = null;
|
|
136
|
-
let serverPublicKey = null;
|
|
137
|
-
let clientId = null;
|
|
138
|
-
let initPromise = null;
|
|
139
|
-
async function doKeyExchange() {
|
|
140
|
-
if (!transportConfig)
|
|
141
|
-
return;
|
|
142
|
-
const { crypto: cryptoService, keyExchangeUrl = "/api/kit/key-exchange" } = transportConfig;
|
|
143
|
-
const keyPairResult = cryptoService.asymmetric.generateKeyPair();
|
|
144
|
-
if (!keyPairResult.success || !keyPairResult.data) {
|
|
145
|
-
throw new Error("Failed to generate client key pair");
|
|
146
|
-
}
|
|
147
|
-
clientKeyPair = keyPairResult.data;
|
|
148
|
-
const response = await fetch(keyExchangeUrl, {
|
|
149
|
-
method: "POST",
|
|
150
|
-
headers: { "Content-Type": "application/json" },
|
|
151
|
-
body: JSON.stringify({ clientPublicKey: clientKeyPair.publicKey })
|
|
152
|
-
});
|
|
153
|
-
if (!response.ok) {
|
|
154
|
-
throw new Error(`Key exchange failed: ${response.status}`);
|
|
155
|
-
}
|
|
156
|
-
const data = await response.json();
|
|
157
|
-
if (!data.serverPublicKey || !data.clientId) {
|
|
158
|
-
throw new Error("Invalid key exchange response");
|
|
159
|
-
}
|
|
160
|
-
serverPublicKey = data.serverPublicKey;
|
|
161
|
-
clientId = data.clientId;
|
|
162
|
-
transportReady = true;
|
|
163
|
-
}
|
|
164
|
-
async function ensureTransportReady() {
|
|
165
|
-
if (transportReady)
|
|
166
|
-
return;
|
|
167
|
-
if (!initPromise) {
|
|
168
|
-
initPromise = doKeyExchange().finally(() => {
|
|
169
|
-
initPromise = null;
|
|
170
|
-
});
|
|
171
|
-
}
|
|
172
|
-
await initPromise;
|
|
173
|
-
}
|
|
174
|
-
function encryptBody(bodyText) {
|
|
175
|
-
if (!transportConfig || !serverPublicKey)
|
|
176
|
-
return bodyText;
|
|
177
|
-
const { crypto: cryptoService } = transportConfig;
|
|
178
|
-
const symmetricKey = cryptoService.symmetric.generateKey();
|
|
179
|
-
const encResult = cryptoService.symmetric.encryptWithIV(bodyText, symmetricKey);
|
|
180
|
-
if (!encResult.success || !encResult.data) {
|
|
181
|
-
throw new Error("Request body encryption failed");
|
|
182
|
-
}
|
|
183
|
-
const keyEncResult = cryptoService.asymmetric.encrypt(symmetricKey, serverPublicKey);
|
|
184
|
-
if (!keyEncResult.success || !keyEncResult.data) {
|
|
185
|
-
throw new Error("Symmetric key encryption failed");
|
|
186
|
-
}
|
|
187
|
-
const payload = {
|
|
188
|
-
encryptedKey: keyEncResult.data,
|
|
189
|
-
ciphertext: encResult.data.ciphertext,
|
|
190
|
-
iv: encResult.data.iv
|
|
191
|
-
};
|
|
192
|
-
return JSON.stringify(payload);
|
|
193
|
-
}
|
|
194
|
-
async function decryptResponse(response) {
|
|
195
|
-
if (!clientKeyPair || !transportConfig)
|
|
196
|
-
return response;
|
|
197
|
-
const encryptedBody = await response.json();
|
|
198
|
-
if (!isValidEncryptedPayload(encryptedBody))
|
|
199
|
-
return response;
|
|
200
|
-
const { crypto: cryptoService } = transportConfig;
|
|
201
|
-
const keyDecResult = cryptoService.asymmetric.decrypt(encryptedBody.encryptedKey, clientKeyPair.privateKey);
|
|
202
|
-
if (!keyDecResult.success || !keyDecResult.data) {
|
|
203
|
-
throw new Error("Response key decryption failed");
|
|
204
|
-
}
|
|
205
|
-
const decResult = cryptoService.symmetric.decryptWithIV(encryptedBody.ciphertext, keyDecResult.data, encryptedBody.iv);
|
|
206
|
-
if (!decResult.success || typeof decResult.data !== "string") {
|
|
207
|
-
throw new Error("Response body decryption failed");
|
|
208
|
-
}
|
|
209
|
-
return new Response(decResult.data, {
|
|
210
|
-
status: response.status,
|
|
211
|
-
statusText: response.statusText,
|
|
212
|
-
headers: response.headers
|
|
213
|
-
});
|
|
214
|
-
}
|
|
215
|
-
async function apiFetch(url, init = {}) {
|
|
216
|
-
const method = (init.method ?? "GET").toUpperCase();
|
|
217
|
-
const isWriteMethod = !["GET", "HEAD", "OPTIONS"].includes(method);
|
|
218
|
-
const headers = new Headers(init.headers);
|
|
219
|
-
if (authStore) {
|
|
220
|
-
const token = authStore.get();
|
|
221
|
-
if (token) {
|
|
222
|
-
headers.set("Authorization", `Bearer ${token}`);
|
|
223
|
-
}
|
|
224
|
-
}
|
|
225
|
-
if (isWriteMethod) {
|
|
226
|
-
const csrfToken = getCookie(csrfCookieName);
|
|
227
|
-
if (csrfToken) {
|
|
228
|
-
headers.set(csrfHeaderName, csrfToken);
|
|
229
|
-
}
|
|
230
|
-
}
|
|
231
|
-
if (transportConfig) {
|
|
232
|
-
await ensureTransportReady();
|
|
233
|
-
if (clientId) {
|
|
234
|
-
headers.set("X-Client-Id", clientId);
|
|
235
|
-
}
|
|
236
|
-
if (init.body !== void 0 && init.body !== null) {
|
|
237
|
-
const bodyText = typeof init.body === "string" ? init.body : JSON.stringify(init.body);
|
|
238
|
-
const encrypted = encryptBody(bodyText);
|
|
239
|
-
headers.set("Content-Type", "application/json");
|
|
240
|
-
let response2 = await fetch(url, { ...init, headers, body: encrypted });
|
|
241
|
-
if (response2.headers.get("X-Encrypted") === "true") {
|
|
242
|
-
response2 = await decryptResponse(response2);
|
|
243
|
-
}
|
|
244
|
-
return response2;
|
|
245
|
-
}
|
|
246
|
-
}
|
|
247
|
-
let response = await fetch(url, { ...init, headers });
|
|
248
|
-
if (transportConfig && response.headers.get("X-Encrypted") === "true") {
|
|
249
|
-
response = await decryptResponse(response);
|
|
250
|
-
}
|
|
251
|
-
return response;
|
|
252
|
-
}
|
|
253
|
-
return {
|
|
254
|
-
apiFetch,
|
|
255
|
-
get ready() {
|
|
256
|
-
return !transportConfig || transportReady;
|
|
257
|
-
},
|
|
258
|
-
async init() {
|
|
259
|
-
if (transportConfig)
|
|
260
|
-
await ensureTransportReady();
|
|
261
|
-
},
|
|
262
|
-
destroy() {
|
|
263
|
-
clientKeyPair = null;
|
|
264
|
-
serverPublicKey = null;
|
|
265
|
-
clientId = null;
|
|
266
|
-
transportReady = false;
|
|
267
|
-
initPromise = null;
|
|
268
|
-
}
|
|
269
|
-
};
|
|
270
|
-
}
|
|
271
|
-
|
|
272
|
-
export { clearBrowserToken, configureAuth, createHandleFetch, createKitClient, createTokenStore, getAccessToken, login, loginWithApiKey, loginWithLdap, loginWithOtp, logout, registerAndLogin, setBrowserToken };
|
|
273
|
-
//# sourceMappingURL=chunk-GRYHRXVC.js.map
|
|
274
|
-
//# sourceMappingURL=chunk-GRYHRXVC.js.map
|