@h-ai/serv 0.1.0-alpha.15
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/LICENSE +202 -0
- package/README.md +515 -0
- package/dist/chunk-27PCPE37.js +17 -0
- package/dist/chunk-27PCPE37.js.map +1 -0
- package/dist/chunk-4QBF4PUG.js +128 -0
- package/dist/chunk-4QBF4PUG.js.map +1 -0
- package/dist/chunk-YQV2OMQK.js +16 -0
- package/dist/chunk-YQV2OMQK.js.map +1 -0
- package/dist/features/ai.d.ts +361 -0
- package/dist/features/ai.js +206 -0
- package/dist/features/ai.js.map +1 -0
- package/dist/features/iam.d.ts +774 -0
- package/dist/features/iam.js +145 -0
- package/dist/features/iam.js.map +1 -0
- package/dist/features/storage.d.ts +163 -0
- package/dist/features/storage.js +94 -0
- package/dist/features/storage.js.map +1 -0
- package/dist/index.d.ts +646 -0
- package/dist/index.js +809 -0
- package/dist/index.js.map +1 -0
- package/dist/serv-context-CwewduFi.d.ts +155 -0
- package/package.json +82 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../messages/en-US.json","../messages/zh-CN.json","../src/serv-i18n.ts","../src/pipelines/serv-pipeline-helper.ts","../src/pipelines/serv-pipeline-require-auth.ts"],"names":["err","HaiCommonError"],"mappings":"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","file":"chunk-4QBF4PUG.js","sourcesContent":["{\n \"$schema\": \"https://inlang.com/schema/inlang-message-format\",\n \"serv_validationFailed\": \"Validation failed\",\n \"serv_validationRequired\": \"This field is required\",\n \"serv_validationInvalid\": \"Invalid input format\",\n \"serv_validationInvalidType\": \"Invalid field type\",\n \"serv_validationStringMin\": \"Enter at least {min} characters\",\n \"serv_validationStringMax\": \"Enter at most {max} characters\",\n \"serv_validationNumberMin\": \"Value must be at least {min}\",\n \"serv_validationNumberMax\": \"Value must be at most {max}\",\n \"serv_validationArrayMin\": \"Select at least {min} item(s)\",\n \"serv_validationArrayMax\": \"Select at most {max} item(s)\",\n \"serv_validationTooSmall\": \"Value must be at least {min}\",\n \"serv_validationTooBig\": \"Value must be at most {max}\",\n \"serv_validationEmail\": \"Enter a valid email address\",\n \"serv_validationUrl\": \"Enter a valid URL\",\n \"serv_validationUuid\": \"Enter a valid UUID\",\n \"serv_validationEnum\": \"Select a valid option\",\n \"serv_errorUnauthorized\": \"Unauthorized\",\n \"serv_errorForbidden\": \"Forbidden\",\n \"serv_errorInternal\": \"Internal server error\",\n \"serv_storageKeyRequired\": \"Storage key must not be empty\",\n \"serv_storageKeyTooLong\": \"Storage key must not exceed {max} characters\",\n \"serv_storageKeyIllegalChars\": \"Storage key contains illegal characters\",\n \"serv_storageKeyDotSegments\": \"Storage key must not contain . or .. path segments\",\n \"serv_iamCannotDeleteCurrentUser\": \"Cannot delete the current logged-in user\",\n \"serv_transportInvalidPayload\": \"Invalid encrypted transport payload\",\n \"serv_transportUnknownClient\": \"Unknown encryption client; key exchange required\",\n \"serv_transportClientIdRequired\": \"Missing X-Client-Id header; key exchange required\",\n \"serv_transportClientKeyNotFound\": \"Client not registered or session expired; complete key exchange again\",\n \"serv_transportDecryptFailed\": \"Failed to decrypt request\",\n \"serv_transportEncryptFailed\": \"Failed to encrypt response\",\n \"serv_transportKeyExchangeFailed\": \"Key exchange failed\"\n}\n","{\n \"$schema\": \"https://inlang.com/schema/inlang-message-format\",\n \"serv_validationFailed\": \"数据验证失败\",\n \"serv_validationRequired\": \"此字段必填\",\n \"serv_validationInvalid\": \"输入格式无效\",\n \"serv_validationInvalidType\": \"字段类型不正确\",\n \"serv_validationStringMin\": \"至少输入 {min} 个字符\",\n \"serv_validationStringMax\": \"最多输入 {max} 个字符\",\n \"serv_validationNumberMin\": \"数值不能小于 {min}\",\n \"serv_validationNumberMax\": \"数值不能大于 {max}\",\n \"serv_validationArrayMin\": \"至少选择 {min} 项\",\n \"serv_validationArrayMax\": \"最多选择 {max} 项\",\n \"serv_validationTooSmall\": \"不能小于 {min}\",\n \"serv_validationTooBig\": \"不能大于 {max}\",\n \"serv_validationEmail\": \"请输入有效的邮箱地址\",\n \"serv_validationUrl\": \"请输入有效的网址\",\n \"serv_validationUuid\": \"请输入有效的 UUID\",\n \"serv_validationEnum\": \"请选择有效选项\",\n \"serv_errorUnauthorized\": \"未登录或登录已失效\",\n \"serv_errorForbidden\": \"无权执行该操作\",\n \"serv_errorInternal\": \"服务器内部错误\",\n \"serv_storageKeyRequired\": \"存储 key 不能为空\",\n \"serv_storageKeyTooLong\": \"存储 key 不能超过 {max} 个字符\",\n \"serv_storageKeyIllegalChars\": \"存储 key 包含非法字符\",\n \"serv_storageKeyDotSegments\": \"存储 key 不能包含 . 或 .. 路径段\",\n \"serv_iamCannotDeleteCurrentUser\": \"不能删除当前登录用户\",\n \"serv_transportInvalidPayload\": \"传输层加密载荷格式无效\",\n \"serv_transportUnknownClient\": \"未识别的加密客户端,请先完成密钥协商\",\n \"serv_transportClientIdRequired\": \"缺少 X-Client-Id 请求头,请先完成密钥协商\",\n \"serv_transportClientKeyNotFound\": \"客户端未注册或会话已过期,请重新完成密钥协商\",\n \"serv_transportDecryptFailed\": \"请求解密失败\",\n \"serv_transportEncryptFailed\": \"响应加密失败\",\n \"serv_transportKeyExchangeFailed\": \"密钥协商失败\"\n}\n","/**\n * @h-ai/serv — i18n 工具\n *\n * Serv 模块的国际化消息工具,从 @h-ai/core 调用 i18n API。\n * 与 kit-i18n 结构对齐,便于跨包统一维护。\n * @module serv-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 ServMessageKey = keyof typeof messagesZhCN\n\nconst SUPPORTED_SERV_LOCALES = ['zh-CN', 'en-US'] as const\nconst DEFAULT_SERV_LOCALE = 'zh-CN'\n\n/**\n * 规范化 serv 请求 locale。\n *\n * 支持:\n * - 完整 locale:`zh-CN` / `en-US`\n * - 简写:`zh` / `en`\n * - `Accept-Language` 风格值:`en-US,en;q=0.9`\n *\n * 未识别时回退到默认 `zh-CN`。\n */\nexport function normalizeServLocale(locale: string | undefined): string {\n const candidate = locale?.split(',')[0]?.trim()\n if (!candidate)\n return DEFAULT_SERV_LOCALE\n\n const exact = SUPPORTED_SERV_LOCALES.find(item => item.toLowerCase() === candidate.toLowerCase())\n if (exact)\n return exact\n\n const baseLanguage = candidate.split('-')[0]?.toLowerCase()\n if (baseLanguage === 'en')\n return 'en-US'\n if (baseLanguage === 'zh')\n return 'zh-CN'\n\n return DEFAULT_SERV_LOCALE\n}\n\n/**\n * 获取 Serv 模块的 i18n 消息。\n *\n * 单次调用可通过 `options.locale` 指定该次调用使用的语言,\n * 用于在请求处理过程中根据 `Accept-Language` 头本地化错误消息,\n * 而不污染全局 locale(多并发请求安全)。\n *\n * @example\n * ```ts\n * // 使用全局 locale\n * servM('serv_validationRequired')\n *\n * // 使用请求自身的 locale\n * servM('serv_validationStringMin', { locale: 'en-US', params: { min: 3 } })\n * ```\n */\nexport const servM\n = core.i18n.createMessageGetter<ServMessageKey>({ 'zh-CN': messagesZhCN, 'en-US': messagesEnUS })\n\nexport type { ServMessageKey }\n","/**\n * @h-ai/serv — Pipeline 公共 helper\n *\n * 放置不属于 Hono middleware / oRPC wrapper 默认实现本身、\n * 但会被多个 pipeline 复用的公共工具。\n * @module pipelines/serv-pipeline-helper\n */\n\nimport type { ServProcedureHandler } from './serv-pipeline-types.js'\nimport { err, HaiCommonError } from '@h-ai/core'\nimport { servM } from '../serv-i18n.js'\n\n/** 构造 `HaiResult` 失败分支同构的 HTTP 错误定义。 */\nexport interface ServErrorBodyDef {\n readonly code: string | number\n readonly httpStatus: number\n readonly system: string\n readonly module: string\n}\n\n/**\n * 构造与 `HaiResult` 失败分支同构的 HTTP 响应体。\n *\n * - 字段顺序与 `haiResultSchema()` 输出一致,便于客户端统一解析。\n * - 仅暴露最小信息(code/message/httpStatus),避免泄漏内部细节。\n */\nexport function buildHaiErrorBody(def: ServErrorBodyDef, message: string) {\n return {\n success: false as const,\n error: {\n code: def.code,\n message,\n httpStatus: def.httpStatus,\n system: def.system,\n module: def.module,\n },\n }\n}\n\n/**\n * 捕获未处理异常并转换为 HaiResult。\n *\n * 虽然它不是 middleware / 鉴权 wrapper,但属于所有 procedure pipeline\n * 都可能复用的“公共包装能力”,因此与 `buildHaiErrorBody()` 一起放在 helper 中。\n *\n * @param handler - 被包装的 procedure handler\n * @returns 带异常保护的新 handler\n *\n * @example\n * ```ts\n * const safeHandler = serv.mapHaiError(myHandler)\n * ```\n */\nexport function mapHaiError<TInput, TOutput>(handler: ServProcedureHandler<TInput, TOutput>): ServProcedureHandler<TInput, TOutput> {\n return async (options) => {\n try {\n return await handler(options)\n }\n catch (error) {\n // 所有未捕获异常统一在这里收口,避免直接把异常冒泡到 HTTP 层。\n return err(HaiCommonError.INTERNAL_ERROR, servM('serv_errorInternal', { locale: options.context.locale }), error)\n }\n }\n}\n","/**\n * @h-ai/serv — requireAuth 默认实现\n * @module pipelines/serv-pipeline-require-auth\n */\n\nimport type { ServProcedureHandler } from './serv-pipeline-types.js'\nimport { err, HaiCommonError } from '@h-ai/core'\nimport { servM } from '../serv-i18n.js'\nimport { mapHaiError } from './serv-pipeline-helper.js'\n\n/**\n * 需要已验证会话的 procedure 包装器。\n *\n * `context.session` 由 `buildAuthContextFactory(verifyToken)`(或 `serv.createApp({ iam })` 自动启用)填充。\n * token 不存在或无效(verifyToken 失败)时 `session` 均为 `undefined`,统一返回 401 UNAUTHORIZED。\n * 内置调用 `mapHaiError`,无需外层再次封装。\n *\n * @param handler - 被包装的 procedure handler\n * @returns 带认证检查的新 handler\n *\n * @example\n * ```ts\n * const protectedHandler = serv.requireAuth(myHandler)\n * ```\n */\nexport function requireAuth<TInput, TOutput>(handler: ServProcedureHandler<TInput, TOutput>): ServProcedureHandler<TInput, TOutput> {\n return mapHaiError(async (options) => {\n // 关键点:只认 `context.session`,不认“请求头里似乎带了 access token”。\n // session 只能来自 createContext/verifyToken 的成功校验结果,避免把未验证 token 当成已登录。\n if (!options.context.session)\n return err(HaiCommonError.UNAUTHORIZED, servM('serv_errorUnauthorized', { locale: options.context.locale }))\n return handler(options)\n })\n}\n"]}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { requireAuth, servM } from './chunk-4QBF4PUG.js';
|
|
2
|
+
import { err, HaiCommonError } from '@h-ai/core';
|
|
3
|
+
|
|
4
|
+
var WILDCARD_PERMISSION = "*";
|
|
5
|
+
function requirePermission(permission, handler) {
|
|
6
|
+
return requireAuth(async (options) => {
|
|
7
|
+
const permissions = options.context.session?.permissions ?? [];
|
|
8
|
+
if (!permissions.includes(permission) && !permissions.includes(WILDCARD_PERMISSION))
|
|
9
|
+
return err(HaiCommonError.FORBIDDEN, servM("serv_errorForbidden", { locale: options.context.locale }));
|
|
10
|
+
return handler(options);
|
|
11
|
+
});
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
export { WILDCARD_PERMISSION, requirePermission };
|
|
15
|
+
//# sourceMappingURL=chunk-YQV2OMQK.js.map
|
|
16
|
+
//# sourceMappingURL=chunk-YQV2OMQK.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/pipelines/serv-pipeline-require-permission.ts"],"names":[],"mappings":";;;AAcO,IAAM,mBAAA,GAAsB;AAiB5B,SAAS,iBAAA,CACd,YACA,OAAA,EACuC;AACvC,EAAA,OAAO,WAAA,CAAY,OAAO,OAAA,KAAY;AAEpC,IAAA,MAAM,WAAA,GAAc,OAAA,CAAQ,OAAA,CAAQ,OAAA,EAAS,eAAe,EAAC;AAC7D,IAAA,IAAI,CAAC,YAAY,QAAA,CAAS,UAAU,KAAK,CAAC,WAAA,CAAY,SAAS,mBAAmB,CAAA;AAChF,MAAA,OAAO,GAAA,CAAI,cAAA,CAAe,SAAA,EAAW,KAAA,CAAM,qBAAA,EAAuB,EAAE,MAAA,EAAQ,OAAA,CAAQ,OAAA,CAAQ,MAAA,EAAQ,CAAC,CAAA;AACvG,IAAA,OAAO,QAAQ,OAAO,CAAA;AAAA,EACxB,CAAC,CAAA;AACH","file":"chunk-YQV2OMQK.js","sourcesContent":["/**\n * @h-ai/serv — requirePermission 默认实现\n * @module pipelines/serv-pipeline-require-permission\n */\n\nimport type { ServProcedureHandler } from './serv-pipeline-types.js'\nimport { err, HaiCommonError } from '@h-ai/core'\nimport { servM } from '../serv-i18n.js'\nimport { requireAuth } from './serv-pipeline-require-auth.js'\n\n/**\n * 通配符权限:拥有此权限的用户自动通过所有 {@link requirePermission} 检查。\n * 用于超级管理员场景。**禁止**普通用户被分配此权限。\n */\nexport const WILDCARD_PERMISSION = '*'\n\n/**\n * 需要指定权限的 procedure 包装器。\n *\n * 内置调用 `requireAuth`,在验证 Token 后进一步匹配 `session.permissions`。\n * 拥有 {@link WILDCARD_PERMISSION}(`'*'`)的用户自动通过所有权限检查。\n *\n * @param permission - 所需权限字符串(如 `'iam.users.read'`)\n * @param handler - 被包装的 procedure handler\n * @returns 带权限检查的新 handler\n *\n * @example\n * ```ts\n * const adminHandler = serv.requirePermission('iam.users.write', myHandler)\n * ```\n */\nexport function requirePermission<TInput, TOutput>(\n permission: string,\n handler: ServProcedureHandler<TInput, TOutput>,\n): ServProcedureHandler<TInput, TOutput> {\n return requireAuth(async (options) => {\n // 先认证,再鉴权;未登录请求在 requireAuth 中已经被挡住。\n const permissions = options.context.session?.permissions ?? []\n if (!permissions.includes(permission) && !permissions.includes(WILDCARD_PERMISSION))\n return err(HaiCommonError.FORBIDDEN, servM('serv_errorForbidden', { locale: options.context.locale }))\n return handler(options)\n })\n}\n"]}
|
|
@@ -0,0 +1,361 @@
|
|
|
1
|
+
import * as _orpc_contract from '@orpc/contract';
|
|
2
|
+
import * as zod_v4_core from 'zod/v4/core';
|
|
3
|
+
import * as zod from 'zod';
|
|
4
|
+
import * as _orpc_server from '@orpc/server';
|
|
5
|
+
import { AIFunctions } from '@h-ai/ai';
|
|
6
|
+
import { S as ServContext } from '../serv-context-CwewduFi.js';
|
|
7
|
+
import '@h-ai/core';
|
|
8
|
+
|
|
9
|
+
/** AI 默认 procedures 依赖。 */
|
|
10
|
+
interface AiProcedureDeps {
|
|
11
|
+
readonly ai: AIFunctions;
|
|
12
|
+
}
|
|
13
|
+
/** 创建 AI 默认 procedures。 */
|
|
14
|
+
declare function createAiProcedures(deps: AiProcedureDeps): {
|
|
15
|
+
chats: {
|
|
16
|
+
createCompletion: _orpc_server.Procedure<_orpc_server.MergedInitialContext<ServContext & Record<never, never>, ServContext & Record<never, never>, ServContext>, ServContext, zod.ZodObject<{
|
|
17
|
+
model: zod.ZodOptional<zod.ZodString>;
|
|
18
|
+
messages: zod.ZodArray<zod.ZodObject<{
|
|
19
|
+
role: zod.ZodEnum<{
|
|
20
|
+
system: "system";
|
|
21
|
+
user: "user";
|
|
22
|
+
assistant: "assistant";
|
|
23
|
+
tool: "tool";
|
|
24
|
+
}>;
|
|
25
|
+
content: zod.ZodOptional<zod.ZodUnion<readonly [zod.ZodString, zod.ZodArray<zod.ZodUnion<readonly [zod.ZodObject<{
|
|
26
|
+
type: zod.ZodLiteral<"text">;
|
|
27
|
+
text: zod.ZodString;
|
|
28
|
+
}, zod_v4_core.$strip>, zod.ZodObject<{
|
|
29
|
+
type: zod.ZodLiteral<"image_url">;
|
|
30
|
+
image_url: zod.ZodObject<{
|
|
31
|
+
url: zod.ZodString;
|
|
32
|
+
detail: zod.ZodOptional<zod.ZodEnum<{
|
|
33
|
+
auto: "auto";
|
|
34
|
+
low: "low";
|
|
35
|
+
high: "high";
|
|
36
|
+
}>>;
|
|
37
|
+
}, zod_v4_core.$strip>;
|
|
38
|
+
}, zod_v4_core.$strip>]>>]>>;
|
|
39
|
+
name: zod.ZodOptional<zod.ZodString>;
|
|
40
|
+
tool_calls: zod.ZodOptional<zod.ZodArray<zod.ZodObject<{
|
|
41
|
+
id: zod.ZodString;
|
|
42
|
+
type: zod.ZodLiteral<"function">;
|
|
43
|
+
function: zod.ZodObject<{
|
|
44
|
+
name: zod.ZodString;
|
|
45
|
+
arguments: zod.ZodString;
|
|
46
|
+
}, zod_v4_core.$strip>;
|
|
47
|
+
}, zod_v4_core.$strip>>>;
|
|
48
|
+
tool_call_id: zod.ZodOptional<zod.ZodString>;
|
|
49
|
+
}, zod_v4_core.$strip>>;
|
|
50
|
+
temperature: zod.ZodOptional<zod.ZodNumber>;
|
|
51
|
+
top_p: zod.ZodOptional<zod.ZodNumber>;
|
|
52
|
+
max_tokens: zod.ZodOptional<zod.ZodNumber>;
|
|
53
|
+
stream: zod.ZodOptional<zod.ZodBoolean>;
|
|
54
|
+
tools: zod.ZodOptional<zod.ZodArray<zod.ZodObject<{
|
|
55
|
+
type: zod.ZodLiteral<"function">;
|
|
56
|
+
function: zod.ZodObject<{
|
|
57
|
+
name: zod.ZodString;
|
|
58
|
+
description: zod.ZodOptional<zod.ZodString>;
|
|
59
|
+
parameters: zod.ZodOptional<zod.ZodObject<{
|
|
60
|
+
type: zod.ZodLiteral<"object">;
|
|
61
|
+
properties: zod.ZodOptional<zod.ZodRecord<zod.ZodString, zod.ZodObject<{
|
|
62
|
+
type: zod.ZodString;
|
|
63
|
+
description: zod.ZodOptional<zod.ZodString>;
|
|
64
|
+
enum: zod.ZodOptional<zod.ZodArray<zod.ZodString>>;
|
|
65
|
+
}, zod_v4_core.$strip>>>;
|
|
66
|
+
required: zod.ZodOptional<zod.ZodArray<zod.ZodString>>;
|
|
67
|
+
}, zod_v4_core.$strip>>;
|
|
68
|
+
}, zod_v4_core.$strip>;
|
|
69
|
+
}, zod_v4_core.$strip>>>;
|
|
70
|
+
tool_choice: zod.ZodOptional<zod.ZodUnion<readonly [zod.ZodLiteral<"auto">, zod.ZodLiteral<"none">, zod.ZodObject<{
|
|
71
|
+
type: zod.ZodLiteral<"function">;
|
|
72
|
+
function: zod.ZodObject<{
|
|
73
|
+
name: zod.ZodString;
|
|
74
|
+
}, zod_v4_core.$strip>;
|
|
75
|
+
}, zod_v4_core.$strip>]>>;
|
|
76
|
+
}, zod_v4_core.$strip>, zod.ZodDiscriminatedUnion<[zod.ZodObject<{
|
|
77
|
+
success: zod.ZodLiteral<true>;
|
|
78
|
+
data: zod.ZodObject<{
|
|
79
|
+
id: zod.ZodString;
|
|
80
|
+
object: zod.ZodLiteral<"chat.completion">;
|
|
81
|
+
created: zod.ZodNumber;
|
|
82
|
+
model: zod.ZodString;
|
|
83
|
+
choices: zod.ZodArray<zod.ZodObject<{
|
|
84
|
+
index: zod.ZodNumber;
|
|
85
|
+
message: zod.ZodObject<{
|
|
86
|
+
role: zod.ZodLiteral<"assistant">;
|
|
87
|
+
content: zod.ZodOptional<zod.ZodNullable<zod.ZodString>>;
|
|
88
|
+
tool_calls: zod.ZodOptional<zod.ZodArray<zod.ZodObject<{
|
|
89
|
+
id: zod.ZodString;
|
|
90
|
+
type: zod.ZodLiteral<"function">;
|
|
91
|
+
function: zod.ZodObject<{
|
|
92
|
+
name: zod.ZodString;
|
|
93
|
+
arguments: zod.ZodString;
|
|
94
|
+
}, zod_v4_core.$strip>;
|
|
95
|
+
}, zod_v4_core.$strip>>>;
|
|
96
|
+
}, zod_v4_core.$strip>;
|
|
97
|
+
finish_reason: zod.ZodEnum<{
|
|
98
|
+
length: "length";
|
|
99
|
+
tool_calls: "tool_calls";
|
|
100
|
+
stop: "stop";
|
|
101
|
+
content_filter: "content_filter";
|
|
102
|
+
}>;
|
|
103
|
+
}, zod_v4_core.$strip>>;
|
|
104
|
+
usage: zod.ZodObject<{
|
|
105
|
+
prompt_tokens: zod.ZodNumber;
|
|
106
|
+
completion_tokens: zod.ZodNumber;
|
|
107
|
+
total_tokens: zod.ZodNumber;
|
|
108
|
+
}, zod_v4_core.$strip>;
|
|
109
|
+
}, zod_v4_core.$strip>;
|
|
110
|
+
}, zod_v4_core.$strip>, zod.ZodObject<{
|
|
111
|
+
success: zod.ZodLiteral<false>;
|
|
112
|
+
error: zod.ZodObject<{
|
|
113
|
+
code: zod.ZodUnion<readonly [zod.ZodString, zod.ZodNumber]>;
|
|
114
|
+
message: zod.ZodString;
|
|
115
|
+
httpStatus: zod.ZodOptional<zod.ZodNumber>;
|
|
116
|
+
system: zod.ZodOptional<zod.ZodString>;
|
|
117
|
+
module: zod.ZodOptional<zod.ZodString>;
|
|
118
|
+
cause: zod.ZodOptional<zod.ZodUnknown>;
|
|
119
|
+
suggestion: zod.ZodOptional<zod.ZodString>;
|
|
120
|
+
ext: zod.ZodOptional<zod.ZodRecord<zod.ZodString, zod.ZodUnknown>>;
|
|
121
|
+
}, zod_v4_core.$strip>;
|
|
122
|
+
}, zod_v4_core.$strip>], "success">, _orpc_contract.MergedErrorMap<Record<never, never>, Record<never, never>>, Record<never, never>>;
|
|
123
|
+
sendMessage: _orpc_server.Procedure<_orpc_server.MergedInitialContext<ServContext & Record<never, never>, ServContext & Record<never, never>, ServContext>, ServContext, zod.ZodObject<{
|
|
124
|
+
message: zod.ZodString;
|
|
125
|
+
systemPrompt: zod.ZodOptional<zod.ZodString>;
|
|
126
|
+
model: zod.ZodOptional<zod.ZodString>;
|
|
127
|
+
temperature: zod.ZodOptional<zod.ZodNumber>;
|
|
128
|
+
}, zod_v4_core.$strip>, zod.ZodDiscriminatedUnion<[zod.ZodObject<{
|
|
129
|
+
success: zod.ZodLiteral<true>;
|
|
130
|
+
data: zod.ZodObject<{
|
|
131
|
+
content: zod.ZodString;
|
|
132
|
+
model: zod.ZodString;
|
|
133
|
+
usage: zod.ZodOptional<zod.ZodObject<{
|
|
134
|
+
prompt_tokens: zod.ZodNumber;
|
|
135
|
+
completion_tokens: zod.ZodNumber;
|
|
136
|
+
total_tokens: zod.ZodNumber;
|
|
137
|
+
}, zod_v4_core.$strip>>;
|
|
138
|
+
}, zod_v4_core.$strip>;
|
|
139
|
+
}, zod_v4_core.$strip>, zod.ZodObject<{
|
|
140
|
+
success: zod.ZodLiteral<false>;
|
|
141
|
+
error: zod.ZodObject<{
|
|
142
|
+
code: zod.ZodUnion<readonly [zod.ZodString, zod.ZodNumber]>;
|
|
143
|
+
message: zod.ZodString;
|
|
144
|
+
httpStatus: zod.ZodOptional<zod.ZodNumber>;
|
|
145
|
+
system: zod.ZodOptional<zod.ZodString>;
|
|
146
|
+
module: zod.ZodOptional<zod.ZodString>;
|
|
147
|
+
cause: zod.ZodOptional<zod.ZodUnknown>;
|
|
148
|
+
suggestion: zod.ZodOptional<zod.ZodString>;
|
|
149
|
+
ext: zod.ZodOptional<zod.ZodRecord<zod.ZodString, zod.ZodUnknown>>;
|
|
150
|
+
}, zod_v4_core.$strip>;
|
|
151
|
+
}, zod_v4_core.$strip>], "success">, _orpc_contract.MergedErrorMap<Record<never, never>, Record<never, never>>, Record<never, never>>;
|
|
152
|
+
listHistory: _orpc_server.Procedure<_orpc_server.MergedInitialContext<ServContext & Record<never, never>, ServContext & Record<never, never>, ServContext>, ServContext, zod.ZodObject<{
|
|
153
|
+
objectId: zod.ZodString;
|
|
154
|
+
sessionId: zod.ZodString;
|
|
155
|
+
limit: zod.ZodOptional<zod.ZodNumber>;
|
|
156
|
+
order: zod.ZodOptional<zod.ZodEnum<{
|
|
157
|
+
asc: "asc";
|
|
158
|
+
desc: "desc";
|
|
159
|
+
}>>;
|
|
160
|
+
}, zod_v4_core.$strip>, zod.ZodDiscriminatedUnion<[zod.ZodObject<{
|
|
161
|
+
success: zod.ZodLiteral<true>;
|
|
162
|
+
data: zod.ZodObject<{
|
|
163
|
+
items: zod.ZodArray<zod.ZodObject<{
|
|
164
|
+
id: zod.ZodString;
|
|
165
|
+
objectId: zod.ZodString;
|
|
166
|
+
sessionId: zod.ZodString;
|
|
167
|
+
request: zod.ZodObject<{
|
|
168
|
+
model: zod.ZodString;
|
|
169
|
+
messages: zod.ZodArray<zod.ZodObject<{
|
|
170
|
+
role: zod.ZodEnum<{
|
|
171
|
+
system: "system";
|
|
172
|
+
user: "user";
|
|
173
|
+
assistant: "assistant";
|
|
174
|
+
tool: "tool";
|
|
175
|
+
}>;
|
|
176
|
+
content: zod.ZodOptional<zod.ZodUnion<readonly [zod.ZodString, zod.ZodArray<zod.ZodUnion<readonly [zod.ZodObject<{
|
|
177
|
+
type: zod.ZodLiteral<"text">;
|
|
178
|
+
text: zod.ZodString;
|
|
179
|
+
}, zod_v4_core.$strip>, zod.ZodObject<{
|
|
180
|
+
type: zod.ZodLiteral<"image_url">;
|
|
181
|
+
image_url: zod.ZodObject<{
|
|
182
|
+
url: zod.ZodString;
|
|
183
|
+
detail: zod.ZodOptional<zod.ZodEnum<{
|
|
184
|
+
auto: "auto";
|
|
185
|
+
low: "low";
|
|
186
|
+
high: "high";
|
|
187
|
+
}>>;
|
|
188
|
+
}, zod_v4_core.$strip>;
|
|
189
|
+
}, zod_v4_core.$strip>]>>]>>;
|
|
190
|
+
name: zod.ZodOptional<zod.ZodString>;
|
|
191
|
+
tool_calls: zod.ZodOptional<zod.ZodArray<zod.ZodObject<{
|
|
192
|
+
id: zod.ZodString;
|
|
193
|
+
type: zod.ZodLiteral<"function">;
|
|
194
|
+
function: zod.ZodObject<{
|
|
195
|
+
name: zod.ZodString;
|
|
196
|
+
arguments: zod.ZodString;
|
|
197
|
+
}, zod_v4_core.$strip>;
|
|
198
|
+
}, zod_v4_core.$strip>>>;
|
|
199
|
+
tool_call_id: zod.ZodOptional<zod.ZodString>;
|
|
200
|
+
}, zod_v4_core.$strip>>;
|
|
201
|
+
}, zod_v4_core.$strip>;
|
|
202
|
+
response: zod.ZodObject<{
|
|
203
|
+
content: zod.ZodString;
|
|
204
|
+
toolCalls: zod.ZodOptional<zod.ZodArray<zod.ZodObject<{
|
|
205
|
+
id: zod.ZodString;
|
|
206
|
+
type: zod.ZodLiteral<"function">;
|
|
207
|
+
function: zod.ZodObject<{
|
|
208
|
+
name: zod.ZodString;
|
|
209
|
+
arguments: zod.ZodString;
|
|
210
|
+
}, zod_v4_core.$strip>;
|
|
211
|
+
}, zod_v4_core.$strip>>>;
|
|
212
|
+
finishReason: zod.ZodString;
|
|
213
|
+
usage: zod.ZodObject<{
|
|
214
|
+
prompt_tokens: zod.ZodNumber;
|
|
215
|
+
completion_tokens: zod.ZodNumber;
|
|
216
|
+
total_tokens: zod.ZodNumber;
|
|
217
|
+
}, zod_v4_core.$strip>;
|
|
218
|
+
}, zod_v4_core.$strip>;
|
|
219
|
+
createdAt: zod.ZodNumber;
|
|
220
|
+
duration: zod.ZodNumber;
|
|
221
|
+
}, zod_v4_core.$strip>>;
|
|
222
|
+
}, zod_v4_core.$strip>;
|
|
223
|
+
}, zod_v4_core.$strip>, zod.ZodObject<{
|
|
224
|
+
success: zod.ZodLiteral<false>;
|
|
225
|
+
error: zod.ZodObject<{
|
|
226
|
+
code: zod.ZodUnion<readonly [zod.ZodString, zod.ZodNumber]>;
|
|
227
|
+
message: zod.ZodString;
|
|
228
|
+
httpStatus: zod.ZodOptional<zod.ZodNumber>;
|
|
229
|
+
system: zod.ZodOptional<zod.ZodString>;
|
|
230
|
+
module: zod.ZodOptional<zod.ZodString>;
|
|
231
|
+
cause: zod.ZodOptional<zod.ZodUnknown>;
|
|
232
|
+
suggestion: zod.ZodOptional<zod.ZodString>;
|
|
233
|
+
ext: zod.ZodOptional<zod.ZodRecord<zod.ZodString, zod.ZodUnknown>>;
|
|
234
|
+
}, zod_v4_core.$strip>;
|
|
235
|
+
}, zod_v4_core.$strip>], "success">, _orpc_contract.MergedErrorMap<Record<never, never>, Record<never, never>>, Record<never, never>>;
|
|
236
|
+
};
|
|
237
|
+
memories: {
|
|
238
|
+
recall: _orpc_server.Procedure<_orpc_server.MergedInitialContext<ServContext & Record<never, never>, ServContext & Record<never, never>, ServContext>, ServContext, zod.ZodObject<{
|
|
239
|
+
query: zod.ZodString;
|
|
240
|
+
topK: zod.ZodOptional<zod.ZodNumber>;
|
|
241
|
+
types: zod.ZodOptional<zod.ZodArray<zod.ZodEnum<{
|
|
242
|
+
fact: "fact";
|
|
243
|
+
preference: "preference";
|
|
244
|
+
event: "event";
|
|
245
|
+
entity: "entity";
|
|
246
|
+
instruction: "instruction";
|
|
247
|
+
}>>>;
|
|
248
|
+
minImportance: zod.ZodOptional<zod.ZodNumber>;
|
|
249
|
+
objectId: zod.ZodOptional<zod.ZodString>;
|
|
250
|
+
}, zod_v4_core.$strip>, zod.ZodDiscriminatedUnion<[zod.ZodObject<{
|
|
251
|
+
success: zod.ZodLiteral<true>;
|
|
252
|
+
data: zod.ZodObject<{
|
|
253
|
+
items: zod.ZodArray<zod.ZodObject<{
|
|
254
|
+
id: zod.ZodString;
|
|
255
|
+
content: zod.ZodString;
|
|
256
|
+
type: zod.ZodEnum<{
|
|
257
|
+
fact: "fact";
|
|
258
|
+
preference: "preference";
|
|
259
|
+
event: "event";
|
|
260
|
+
entity: "entity";
|
|
261
|
+
instruction: "instruction";
|
|
262
|
+
}>;
|
|
263
|
+
importance: zod.ZodNumber;
|
|
264
|
+
objectId: zod.ZodOptional<zod.ZodString>;
|
|
265
|
+
metadata: zod.ZodOptional<zod.ZodRecord<zod.ZodString, zod.ZodUnknown>>;
|
|
266
|
+
createdAt: zod.ZodNumber;
|
|
267
|
+
lastAccessedAt: zod.ZodNumber;
|
|
268
|
+
accessCount: zod.ZodNumber;
|
|
269
|
+
}, zod_v4_core.$strip>>;
|
|
270
|
+
}, zod_v4_core.$strip>;
|
|
271
|
+
}, zod_v4_core.$strip>, zod.ZodObject<{
|
|
272
|
+
success: zod.ZodLiteral<false>;
|
|
273
|
+
error: zod.ZodObject<{
|
|
274
|
+
code: zod.ZodUnion<readonly [zod.ZodString, zod.ZodNumber]>;
|
|
275
|
+
message: zod.ZodString;
|
|
276
|
+
httpStatus: zod.ZodOptional<zod.ZodNumber>;
|
|
277
|
+
system: zod.ZodOptional<zod.ZodString>;
|
|
278
|
+
module: zod.ZodOptional<zod.ZodString>;
|
|
279
|
+
cause: zod.ZodOptional<zod.ZodUnknown>;
|
|
280
|
+
suggestion: zod.ZodOptional<zod.ZodString>;
|
|
281
|
+
ext: zod.ZodOptional<zod.ZodRecord<zod.ZodString, zod.ZodUnknown>>;
|
|
282
|
+
}, zod_v4_core.$strip>;
|
|
283
|
+
}, zod_v4_core.$strip>], "success">, _orpc_contract.MergedErrorMap<Record<never, never>, Record<never, never>>, Record<never, never>>;
|
|
284
|
+
list: _orpc_server.Procedure<_orpc_server.MergedInitialContext<ServContext & Record<never, never>, ServContext & Record<never, never>, ServContext>, ServContext, zod.ZodObject<{
|
|
285
|
+
types: zod.ZodOptional<zod.ZodArray<zod.ZodEnum<{
|
|
286
|
+
fact: "fact";
|
|
287
|
+
preference: "preference";
|
|
288
|
+
event: "event";
|
|
289
|
+
entity: "entity";
|
|
290
|
+
instruction: "instruction";
|
|
291
|
+
}>>>;
|
|
292
|
+
objectId: zod.ZodOptional<zod.ZodString>;
|
|
293
|
+
offset: zod.ZodOptional<zod.ZodNumber>;
|
|
294
|
+
limit: zod.ZodOptional<zod.ZodNumber>;
|
|
295
|
+
}, zod_v4_core.$strip>, zod.ZodDiscriminatedUnion<[zod.ZodObject<{
|
|
296
|
+
success: zod.ZodLiteral<true>;
|
|
297
|
+
data: zod.ZodObject<{
|
|
298
|
+
items: zod.ZodArray<zod.ZodObject<{
|
|
299
|
+
id: zod.ZodString;
|
|
300
|
+
content: zod.ZodString;
|
|
301
|
+
type: zod.ZodEnum<{
|
|
302
|
+
fact: "fact";
|
|
303
|
+
preference: "preference";
|
|
304
|
+
event: "event";
|
|
305
|
+
entity: "entity";
|
|
306
|
+
instruction: "instruction";
|
|
307
|
+
}>;
|
|
308
|
+
importance: zod.ZodNumber;
|
|
309
|
+
objectId: zod.ZodOptional<zod.ZodString>;
|
|
310
|
+
metadata: zod.ZodOptional<zod.ZodRecord<zod.ZodString, zod.ZodUnknown>>;
|
|
311
|
+
createdAt: zod.ZodNumber;
|
|
312
|
+
lastAccessedAt: zod.ZodNumber;
|
|
313
|
+
accessCount: zod.ZodNumber;
|
|
314
|
+
}, zod_v4_core.$strip>>;
|
|
315
|
+
total: zod.ZodNumber;
|
|
316
|
+
}, zod_v4_core.$strip>;
|
|
317
|
+
}, zod_v4_core.$strip>, zod.ZodObject<{
|
|
318
|
+
success: zod.ZodLiteral<false>;
|
|
319
|
+
error: zod.ZodObject<{
|
|
320
|
+
code: zod.ZodUnion<readonly [zod.ZodString, zod.ZodNumber]>;
|
|
321
|
+
message: zod.ZodString;
|
|
322
|
+
httpStatus: zod.ZodOptional<zod.ZodNumber>;
|
|
323
|
+
system: zod.ZodOptional<zod.ZodString>;
|
|
324
|
+
module: zod.ZodOptional<zod.ZodString>;
|
|
325
|
+
cause: zod.ZodOptional<zod.ZodUnknown>;
|
|
326
|
+
suggestion: zod.ZodOptional<zod.ZodString>;
|
|
327
|
+
ext: zod.ZodOptional<zod.ZodRecord<zod.ZodString, zod.ZodUnknown>>;
|
|
328
|
+
}, zod_v4_core.$strip>;
|
|
329
|
+
}, zod_v4_core.$strip>], "success">, _orpc_contract.MergedErrorMap<Record<never, never>, Record<never, never>>, Record<never, never>>;
|
|
330
|
+
};
|
|
331
|
+
sessions: {
|
|
332
|
+
list: _orpc_server.Procedure<_orpc_server.MergedInitialContext<ServContext & Record<never, never>, ServContext & Record<never, never>, ServContext>, ServContext, zod.ZodObject<{
|
|
333
|
+
objectId: zod.ZodString;
|
|
334
|
+
}, zod_v4_core.$strip>, zod.ZodDiscriminatedUnion<[zod.ZodObject<{
|
|
335
|
+
success: zod.ZodLiteral<true>;
|
|
336
|
+
data: zod.ZodObject<{
|
|
337
|
+
items: zod.ZodArray<zod.ZodObject<{
|
|
338
|
+
objectId: zod.ZodString;
|
|
339
|
+
sessionId: zod.ZodString;
|
|
340
|
+
createdAt: zod.ZodNumber;
|
|
341
|
+
updatedAt: zod.ZodNumber;
|
|
342
|
+
metadata: zod.ZodOptional<zod.ZodRecord<zod.ZodString, zod.ZodUnknown>>;
|
|
343
|
+
}, zod_v4_core.$strip>>;
|
|
344
|
+
}, zod_v4_core.$strip>;
|
|
345
|
+
}, zod_v4_core.$strip>, zod.ZodObject<{
|
|
346
|
+
success: zod.ZodLiteral<false>;
|
|
347
|
+
error: zod.ZodObject<{
|
|
348
|
+
code: zod.ZodUnion<readonly [zod.ZodString, zod.ZodNumber]>;
|
|
349
|
+
message: zod.ZodString;
|
|
350
|
+
httpStatus: zod.ZodOptional<zod.ZodNumber>;
|
|
351
|
+
system: zod.ZodOptional<zod.ZodString>;
|
|
352
|
+
module: zod.ZodOptional<zod.ZodString>;
|
|
353
|
+
cause: zod.ZodOptional<zod.ZodUnknown>;
|
|
354
|
+
suggestion: zod.ZodOptional<zod.ZodString>;
|
|
355
|
+
ext: zod.ZodOptional<zod.ZodRecord<zod.ZodString, zod.ZodUnknown>>;
|
|
356
|
+
}, zod_v4_core.$strip>;
|
|
357
|
+
}, zod_v4_core.$strip>], "success">, _orpc_contract.MergedErrorMap<Record<never, never>, Record<never, never>>, Record<never, never>>;
|
|
358
|
+
};
|
|
359
|
+
};
|
|
360
|
+
|
|
361
|
+
export { type AiProcedureDeps, createAiProcedures };
|
|
@@ -0,0 +1,206 @@
|
|
|
1
|
+
import { wrapItemsResult } from '../chunk-27PCPE37.js';
|
|
2
|
+
import { requireAuth } from '../chunk-4QBF4PUG.js';
|
|
3
|
+
import { apiContract } from '@h-ai/api-contract';
|
|
4
|
+
import { ok } from '@h-ai/core';
|
|
5
|
+
import { implement } from '@orpc/server';
|
|
6
|
+
|
|
7
|
+
var aiContract = apiContract.ai;
|
|
8
|
+
function createAiProcedures(deps) {
|
|
9
|
+
const p = implement(aiContract).$context();
|
|
10
|
+
return p.router({
|
|
11
|
+
chats: {
|
|
12
|
+
createCompletion: p.chats.createCompletion.handler(requireAuth(async ({ input }) => {
|
|
13
|
+
return mapChatCompletionResult(await deps.ai.llm.chat(toChatCompletionRequest(input)));
|
|
14
|
+
})),
|
|
15
|
+
sendMessage: p.chats.sendMessage.handler(requireAuth(async ({ input }) => {
|
|
16
|
+
return sendMessage(deps, input);
|
|
17
|
+
})),
|
|
18
|
+
listHistory: p.chats.listHistory.handler(requireAuth(async ({ input }) => {
|
|
19
|
+
const { objectId, sessionId, limit, order } = input;
|
|
20
|
+
return mapChatRecordsResult(await deps.ai.llm.getHistory({ objectId, sessionId }, { limit, order }));
|
|
21
|
+
}))
|
|
22
|
+
},
|
|
23
|
+
memories: {
|
|
24
|
+
recall: p.memories.recall.handler(requireAuth(async ({ input }) => {
|
|
25
|
+
const { query, ...options } = input;
|
|
26
|
+
return wrapItemsResult(await deps.ai.memory.recall(query, options));
|
|
27
|
+
})),
|
|
28
|
+
list: p.memories.list.handler(requireAuth(async ({ input }) => {
|
|
29
|
+
return deps.ai.memory.listPage(input);
|
|
30
|
+
}))
|
|
31
|
+
},
|
|
32
|
+
sessions: {
|
|
33
|
+
list: p.sessions.list.handler(requireAuth(async ({ input }) => {
|
|
34
|
+
return wrapItemsResult(await deps.ai.llm.listSessions(input.objectId));
|
|
35
|
+
}))
|
|
36
|
+
}
|
|
37
|
+
});
|
|
38
|
+
}
|
|
39
|
+
function toChatCompletionRequest(input) {
|
|
40
|
+
return {
|
|
41
|
+
messages: input.messages.map(toChatMessage),
|
|
42
|
+
model: input.model,
|
|
43
|
+
temperature: input.temperature,
|
|
44
|
+
top_p: input.top_p,
|
|
45
|
+
max_tokens: input.max_tokens
|
|
46
|
+
};
|
|
47
|
+
}
|
|
48
|
+
function toChatMessage(message) {
|
|
49
|
+
if (message.role === "system") {
|
|
50
|
+
return { role: "system", content: toMessageText(message.content) };
|
|
51
|
+
}
|
|
52
|
+
if (message.role === "user") {
|
|
53
|
+
return { role: "user", content: message.content ?? "" };
|
|
54
|
+
}
|
|
55
|
+
if (message.role === "tool") {
|
|
56
|
+
return { role: "tool", content: toMessageText(message.content), tool_call_id: message.tool_call_id ?? "" };
|
|
57
|
+
}
|
|
58
|
+
return {
|
|
59
|
+
role: "assistant",
|
|
60
|
+
content: toAssistantContent(message.content),
|
|
61
|
+
tool_calls: message.tool_calls
|
|
62
|
+
};
|
|
63
|
+
}
|
|
64
|
+
function toMessageText(content) {
|
|
65
|
+
if (typeof content === "string") {
|
|
66
|
+
return content;
|
|
67
|
+
}
|
|
68
|
+
return content?.map((part) => part.type === "text" ? part.text : part.image_url.url).join("\n") ?? "";
|
|
69
|
+
}
|
|
70
|
+
function toAssistantContent(content) {
|
|
71
|
+
if (typeof content === "string") {
|
|
72
|
+
return content;
|
|
73
|
+
}
|
|
74
|
+
return content ? toMessageText(content) : null;
|
|
75
|
+
}
|
|
76
|
+
function mapChatCompletionResult(result) {
|
|
77
|
+
if (!result.success) {
|
|
78
|
+
return result;
|
|
79
|
+
}
|
|
80
|
+
return ok({
|
|
81
|
+
id: result.data.id,
|
|
82
|
+
object: "chat.completion",
|
|
83
|
+
created: result.data.created,
|
|
84
|
+
model: result.data.model,
|
|
85
|
+
choices: result.data.choices.map((choice) => ({
|
|
86
|
+
index: choice.index,
|
|
87
|
+
message: {
|
|
88
|
+
role: "assistant",
|
|
89
|
+
content: choice.message.content ?? null,
|
|
90
|
+
tool_calls: mapFunctionToolCalls(choice.message.tool_calls)
|
|
91
|
+
},
|
|
92
|
+
finish_reason: toApiFinishReason(choice.finish_reason)
|
|
93
|
+
})),
|
|
94
|
+
usage: {
|
|
95
|
+
prompt_tokens: result.data.usage?.prompt_tokens ?? 0,
|
|
96
|
+
completion_tokens: result.data.usage?.completion_tokens ?? 0,
|
|
97
|
+
total_tokens: result.data.usage?.total_tokens ?? 0
|
|
98
|
+
}
|
|
99
|
+
});
|
|
100
|
+
}
|
|
101
|
+
function toApiFinishReason(reason) {
|
|
102
|
+
if (reason === "length" || reason === "tool_calls" || reason === "content_filter") {
|
|
103
|
+
return reason;
|
|
104
|
+
}
|
|
105
|
+
return "stop";
|
|
106
|
+
}
|
|
107
|
+
function mapChatRecordsResult(result) {
|
|
108
|
+
if (!result.success) {
|
|
109
|
+
return result;
|
|
110
|
+
}
|
|
111
|
+
return ok({ items: result.data.map(toApiChatRecord) });
|
|
112
|
+
}
|
|
113
|
+
function toApiChatRecord(record) {
|
|
114
|
+
return {
|
|
115
|
+
id: record.id,
|
|
116
|
+
objectId: record.objectId,
|
|
117
|
+
sessionId: record.sessionId,
|
|
118
|
+
request: {
|
|
119
|
+
model: record.request.model,
|
|
120
|
+
messages: record.request.messages.map(toApiChatMessage)
|
|
121
|
+
},
|
|
122
|
+
response: {
|
|
123
|
+
content: record.response.content,
|
|
124
|
+
toolCalls: mapFunctionToolCalls(record.response.toolCalls),
|
|
125
|
+
finishReason: record.response.finishReason,
|
|
126
|
+
usage: {
|
|
127
|
+
prompt_tokens: record.response.usage.prompt_tokens,
|
|
128
|
+
completion_tokens: record.response.usage.completion_tokens,
|
|
129
|
+
total_tokens: record.response.usage.total_tokens
|
|
130
|
+
}
|
|
131
|
+
},
|
|
132
|
+
createdAt: record.createdAt,
|
|
133
|
+
duration: record.duration
|
|
134
|
+
};
|
|
135
|
+
}
|
|
136
|
+
function toApiChatMessage(message) {
|
|
137
|
+
if (message.role === "tool") {
|
|
138
|
+
return { role: "tool", content: toContentText(message.content), tool_call_id: message.tool_call_id };
|
|
139
|
+
}
|
|
140
|
+
if (message.role === "assistant") {
|
|
141
|
+
return {
|
|
142
|
+
role: "assistant",
|
|
143
|
+
content: toContentText(message.content),
|
|
144
|
+
tool_calls: mapFunctionToolCalls(message.tool_calls)
|
|
145
|
+
};
|
|
146
|
+
}
|
|
147
|
+
if (message.role === "user") {
|
|
148
|
+
return { role: "user", content: toContentText(message.content) };
|
|
149
|
+
}
|
|
150
|
+
return { role: "system", content: toContentText(message.content) };
|
|
151
|
+
}
|
|
152
|
+
function toContentText(content) {
|
|
153
|
+
if (typeof content === "string") {
|
|
154
|
+
return content;
|
|
155
|
+
}
|
|
156
|
+
if (!Array.isArray(content)) {
|
|
157
|
+
return "";
|
|
158
|
+
}
|
|
159
|
+
return content.map((part) => {
|
|
160
|
+
if (typeof part !== "object" || part === null) {
|
|
161
|
+
return "";
|
|
162
|
+
}
|
|
163
|
+
const record = part;
|
|
164
|
+
if (typeof record.text === "string") {
|
|
165
|
+
return record.text;
|
|
166
|
+
}
|
|
167
|
+
if (typeof record.image_url === "object" && record.image_url !== null) {
|
|
168
|
+
const image = record.image_url;
|
|
169
|
+
return typeof image.url === "string" ? image.url : "";
|
|
170
|
+
}
|
|
171
|
+
return "";
|
|
172
|
+
}).filter(Boolean).join("\n");
|
|
173
|
+
}
|
|
174
|
+
function mapFunctionToolCalls(toolCalls) {
|
|
175
|
+
return toolCalls?.flatMap((toolCall) => {
|
|
176
|
+
if (toolCall.type !== "function" || !("function" in toolCall)) {
|
|
177
|
+
return [];
|
|
178
|
+
}
|
|
179
|
+
return [{
|
|
180
|
+
id: toolCall.id,
|
|
181
|
+
type: "function",
|
|
182
|
+
function: {
|
|
183
|
+
name: toolCall.function.name,
|
|
184
|
+
arguments: toolCall.function.arguments
|
|
185
|
+
}
|
|
186
|
+
}];
|
|
187
|
+
});
|
|
188
|
+
}
|
|
189
|
+
async function sendMessage(deps, input) {
|
|
190
|
+
const result = await deps.ai.llm.ask(input.message, {
|
|
191
|
+
systemPrompt: input.systemPrompt,
|
|
192
|
+
model: input.model,
|
|
193
|
+
temperature: input.temperature
|
|
194
|
+
});
|
|
195
|
+
if (!result.success) {
|
|
196
|
+
return result;
|
|
197
|
+
}
|
|
198
|
+
return ok({
|
|
199
|
+
content: result.data,
|
|
200
|
+
model: input.model ?? deps.ai.config?.llm.model ?? "default"
|
|
201
|
+
});
|
|
202
|
+
}
|
|
203
|
+
|
|
204
|
+
export { createAiProcedures };
|
|
205
|
+
//# sourceMappingURL=ai.js.map
|
|
206
|
+
//# sourceMappingURL=ai.js.map
|