@axiom-lattice/gateway 2.1.92 → 2.1.94
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/.turbo/turbo-build.log +10 -10
- package/CHANGELOG.md +22 -0
- package/dist/index.js +972 -385
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +876 -288
- package/dist/index.mjs.map +1 -1
- package/package.json +6 -6
- package/scripts/seed-lark-installation.ts +54 -0
- package/src/channels/lark/LarkChannelAdapter.ts +140 -18
- package/src/channels/lark/types.ts +0 -13
- package/src/channels/lark/verification.ts +1 -36
- package/src/controllers/__tests__/run.test.ts +115 -0
- package/src/controllers/__tests__/tasks.test.ts +215 -0
- package/src/controllers/agent_task.ts +7 -0
- package/src/controllers/assistant.ts +15 -2
- package/src/controllers/auth.ts +9 -0
- package/src/controllers/menu-items.ts +114 -0
- package/src/controllers/personal-assistant.ts +191 -0
- package/src/controllers/run.ts +47 -0
- package/src/controllers/tasks.ts +187 -0
- package/src/controllers/workspace.ts +12 -0
- package/src/index.ts +55 -20
- package/src/router/MessageRouter.ts +107 -41
- package/src/routes/index.ts +23 -0
- package/src/routes/menu-items.ts +10 -0
- package/src/services/agent_task_consumer.ts +2 -8
- package/src/channels/lark/__tests__/aggregator.test.ts +0 -23
- package/src/channels/lark/aggregator.ts +0 -16
- package/src/channels/lark/config.ts +0 -44
- package/src/channels/lark/runner.ts +0 -37
package/dist/index.js
CHANGED
|
@@ -56,8 +56,8 @@ async function createLarkSender(config, client) {
|
|
|
56
56
|
};
|
|
57
57
|
}
|
|
58
58
|
async function createDefaultLarkClient(config) {
|
|
59
|
-
const
|
|
60
|
-
return new
|
|
59
|
+
const Lark2 = await import("@larksuiteoapi/node-sdk");
|
|
60
|
+
return new Lark2.Client({
|
|
61
61
|
appId: config.appId,
|
|
62
62
|
appSecret: config.appSecret
|
|
63
63
|
});
|
|
@@ -303,7 +303,7 @@ async function handleTasksSend(request, reply) {
|
|
|
303
303
|
taskStore.set(taskId, record);
|
|
304
304
|
let agent;
|
|
305
305
|
try {
|
|
306
|
-
agent =
|
|
306
|
+
agent = import_core34.agentInstanceManager.getAgent({
|
|
307
307
|
assistant_id: assistantId,
|
|
308
308
|
thread_id: threadId,
|
|
309
309
|
tenant_id: tenantId,
|
|
@@ -395,7 +395,7 @@ async function handleTasksCancel(request, reply) {
|
|
|
395
395
|
return;
|
|
396
396
|
}
|
|
397
397
|
try {
|
|
398
|
-
const agent =
|
|
398
|
+
const agent = import_core34.agentInstanceManager.getAgent({
|
|
399
399
|
assistant_id: record.assistantId,
|
|
400
400
|
thread_id: record.threadId,
|
|
401
401
|
tenant_id: record.tenantId,
|
|
@@ -432,7 +432,7 @@ async function handleTasksStream(request, reply) {
|
|
|
432
432
|
}
|
|
433
433
|
let agent;
|
|
434
434
|
try {
|
|
435
|
-
agent =
|
|
435
|
+
agent = import_core34.agentInstanceManager.getAgent({
|
|
436
436
|
assistant_id: record.assistantId,
|
|
437
437
|
thread_id: record.threadId,
|
|
438
438
|
tenant_id: record.tenantId,
|
|
@@ -627,12 +627,12 @@ function registerA2ARoutes(app2) {
|
|
|
627
627
|
handleApiKeyRotate
|
|
628
628
|
);
|
|
629
629
|
}
|
|
630
|
-
var import_uuid9,
|
|
630
|
+
var import_uuid9, import_core34, import_protocols4, taskStore, _a2aKeyStore, _storeKeyMap;
|
|
631
631
|
var init_a2a = __esm({
|
|
632
632
|
"src/routes/a2a.ts"() {
|
|
633
633
|
"use strict";
|
|
634
634
|
import_uuid9 = require("uuid");
|
|
635
|
-
|
|
635
|
+
import_core34 = require("@axiom-lattice/core");
|
|
636
636
|
import_protocols4 = require("@axiom-lattice/protocols");
|
|
637
637
|
taskStore = /* @__PURE__ */ new Map();
|
|
638
638
|
_a2aKeyStore = null;
|
|
@@ -666,6 +666,11 @@ function getTenantId(request) {
|
|
|
666
666
|
}
|
|
667
667
|
return request.headers["x-tenant-id"] || "default";
|
|
668
668
|
}
|
|
669
|
+
function getUserId(request) {
|
|
670
|
+
const userId = request.user?.id;
|
|
671
|
+
if (userId) return userId;
|
|
672
|
+
return request.headers["x-user-id"] || void 0;
|
|
673
|
+
}
|
|
669
674
|
function convertAgentConfigToAssistant(config) {
|
|
670
675
|
return {
|
|
671
676
|
id: config.key,
|
|
@@ -698,12 +703,17 @@ async function getAssistantList(request, reply) {
|
|
|
698
703
|
assistantMap.set(assistant.id, assistant);
|
|
699
704
|
});
|
|
700
705
|
const allAssistants = Array.from(assistantMap.values());
|
|
706
|
+
const userId = getUserId(request);
|
|
707
|
+
const filtered = allAssistants.filter((a) => {
|
|
708
|
+
if (!a.ownerUserId) return true;
|
|
709
|
+
return a.ownerUserId === userId;
|
|
710
|
+
});
|
|
701
711
|
return {
|
|
702
712
|
success: true,
|
|
703
713
|
message: "Successfully retrieved assistant list",
|
|
704
714
|
data: {
|
|
705
|
-
records:
|
|
706
|
-
total:
|
|
715
|
+
records: filtered,
|
|
716
|
+
total: filtered.length
|
|
707
717
|
}
|
|
708
718
|
};
|
|
709
719
|
}
|
|
@@ -849,7 +859,7 @@ var getAgentGraph = async (request, reply) => {
|
|
|
849
859
|
var import_uuid = require("uuid");
|
|
850
860
|
var import_core3 = require("@axiom-lattice/core");
|
|
851
861
|
var import_protocols = require("@axiom-lattice/protocols");
|
|
852
|
-
function
|
|
862
|
+
function getUserId2(request) {
|
|
853
863
|
const authUser = request.user;
|
|
854
864
|
if (authUser?.id) return authUser.id;
|
|
855
865
|
return request.headers["x-user-id"] || void 0;
|
|
@@ -871,7 +881,7 @@ var createRun = async (request, reply) => {
|
|
|
871
881
|
const workspace_id = request.headers["x-workspace-id"];
|
|
872
882
|
const project_id = request.headers["x-project-id"];
|
|
873
883
|
const x_request_id = request.headers["x-request-id"] || (0, import_uuid.v4)();
|
|
874
|
-
const user_id =
|
|
884
|
+
const user_id = getUserId2(request);
|
|
875
885
|
const mergedConfig = user_id ? { ...custom_run_config, user_id } : custom_run_config;
|
|
876
886
|
if (!assistant_id) {
|
|
877
887
|
reply.status(400).send({
|
|
@@ -1025,6 +1035,33 @@ var abortRun = async (request, reply) => {
|
|
|
1025
1035
|
});
|
|
1026
1036
|
}
|
|
1027
1037
|
};
|
|
1038
|
+
var recoverRun = async (request, reply) => {
|
|
1039
|
+
try {
|
|
1040
|
+
const { assistantId, threadId } = request.params;
|
|
1041
|
+
const tenant_id = request.headers["x-tenant-id"];
|
|
1042
|
+
const workspace_id = request.headers["x-workspace-id"] || "default";
|
|
1043
|
+
const project_id = request.headers["x-project-id"] || "default";
|
|
1044
|
+
const agent = import_core3.agentInstanceManager.getAgent({
|
|
1045
|
+
assistant_id: assistantId,
|
|
1046
|
+
thread_id: threadId,
|
|
1047
|
+
tenant_id,
|
|
1048
|
+
workspace_id,
|
|
1049
|
+
project_id
|
|
1050
|
+
});
|
|
1051
|
+
await agent.resumeTask();
|
|
1052
|
+
const status = await agent.getRunStatus();
|
|
1053
|
+
reply.status(200).send({
|
|
1054
|
+
success: true,
|
|
1055
|
+
threadId,
|
|
1056
|
+
status
|
|
1057
|
+
});
|
|
1058
|
+
} catch (error) {
|
|
1059
|
+
reply.status(500).send({
|
|
1060
|
+
success: false,
|
|
1061
|
+
error: `Recover failed: ${error.message}`
|
|
1062
|
+
});
|
|
1063
|
+
}
|
|
1064
|
+
};
|
|
1028
1065
|
|
|
1029
1066
|
// src/controllers/memory.ts
|
|
1030
1067
|
var import_core4 = require("@axiom-lattice/core");
|
|
@@ -1197,6 +1234,8 @@ var triggerAgentTask = async (request, reply) => {
|
|
|
1197
1234
|
try {
|
|
1198
1235
|
const { assistant_id, thread_id, input, command } = request.body;
|
|
1199
1236
|
const tenant_id = request.headers["x-tenant-id"];
|
|
1237
|
+
const workspace_id = request.headers["x-workspace-id"];
|
|
1238
|
+
const project_id = request.headers["x-project-id"];
|
|
1200
1239
|
if (!assistant_id) {
|
|
1201
1240
|
reply.status(400).send({
|
|
1202
1241
|
success: false,
|
|
@@ -1217,7 +1256,12 @@ var triggerAgentTask = async (request, reply) => {
|
|
|
1217
1256
|
thread_id,
|
|
1218
1257
|
input,
|
|
1219
1258
|
command,
|
|
1220
|
-
"x-tenant-id": tenant_id
|
|
1259
|
+
"x-tenant-id": tenant_id,
|
|
1260
|
+
runConfig: {
|
|
1261
|
+
workspaceId: workspace_id,
|
|
1262
|
+
projectId: project_id,
|
|
1263
|
+
user_id: request.user?.id
|
|
1264
|
+
}
|
|
1221
1265
|
});
|
|
1222
1266
|
reply.status(200).send({
|
|
1223
1267
|
success: true
|
|
@@ -2805,6 +2849,268 @@ async function replyInboxTask(request, reply) {
|
|
|
2805
2849
|
}
|
|
2806
2850
|
}
|
|
2807
2851
|
|
|
2852
|
+
// src/controllers/personal-assistant.ts
|
|
2853
|
+
var import_core14 = require("@axiom-lattice/core");
|
|
2854
|
+
var import_crypto3 = require("crypto");
|
|
2855
|
+
function getWorkspaceId2(request) {
|
|
2856
|
+
return request.headers["x-workspace-id"] || "default";
|
|
2857
|
+
}
|
|
2858
|
+
function getTenantId7(request) {
|
|
2859
|
+
const userTenantId = request.user?.tenantId;
|
|
2860
|
+
if (userTenantId) return userTenantId;
|
|
2861
|
+
return request.headers["x-tenant-id"] || "default";
|
|
2862
|
+
}
|
|
2863
|
+
function getUserId3(request) {
|
|
2864
|
+
const userId = request.user?.id || request.headers["x-user-id"];
|
|
2865
|
+
if (!userId) throw new Error("User ID is required");
|
|
2866
|
+
return userId;
|
|
2867
|
+
}
|
|
2868
|
+
function getLinkStore() {
|
|
2869
|
+
return (0, import_core14.getStoreLattice)("default", "userTenantLink").store;
|
|
2870
|
+
}
|
|
2871
|
+
function getAssistantStore() {
|
|
2872
|
+
return (0, import_core14.getStoreLattice)("default", "assistant").store;
|
|
2873
|
+
}
|
|
2874
|
+
function getProjectStore() {
|
|
2875
|
+
return (0, import_core14.getStoreLattice)("default", "project").store;
|
|
2876
|
+
}
|
|
2877
|
+
async function getLinkMeta(userId, tenantId) {
|
|
2878
|
+
const link = await getLinkStore().getLink(userId, tenantId);
|
|
2879
|
+
return link?.metadata || {};
|
|
2880
|
+
}
|
|
2881
|
+
async function updateLinkMeta(userId, tenantId, meta) {
|
|
2882
|
+
await getLinkStore().updateLink(userId, tenantId, { metadata: meta });
|
|
2883
|
+
}
|
|
2884
|
+
async function createPersonalAssistant(request, reply) {
|
|
2885
|
+
const tenantId = getTenantId7(request);
|
|
2886
|
+
const userId = getUserId3(request);
|
|
2887
|
+
const { name, personality } = request.body;
|
|
2888
|
+
if (!name || !personality) {
|
|
2889
|
+
return reply.status(400).send({ success: false, message: "name and personality are required" });
|
|
2890
|
+
}
|
|
2891
|
+
const store = getAssistantStore();
|
|
2892
|
+
const existing = await store.getByOwner(tenantId, userId);
|
|
2893
|
+
if (existing) {
|
|
2894
|
+
return reply.status(409).send({ success: false, message: "You already have a personal assistant" });
|
|
2895
|
+
}
|
|
2896
|
+
const assistantId = (0, import_crypto3.randomUUID)();
|
|
2897
|
+
const projectStore = getProjectStore();
|
|
2898
|
+
const projectId = (0, import_crypto3.randomUUID)();
|
|
2899
|
+
const wsId = getWorkspaceId2(request);
|
|
2900
|
+
await projectStore.createProject(tenantId, wsId, projectId, {
|
|
2901
|
+
name: `${name}'s Space`,
|
|
2902
|
+
description: "Personal workspace for your assistant"
|
|
2903
|
+
});
|
|
2904
|
+
const config = import_core14.PersonalAssistantConfig.get();
|
|
2905
|
+
config.key = assistantId;
|
|
2906
|
+
import_core14.PersonalAssistantConfig.render(config, name, personality);
|
|
2907
|
+
const data = { name, graphDefinition: config, ownerUserId: userId };
|
|
2908
|
+
const assistant = await store.createAssistant(tenantId, assistantId, data);
|
|
2909
|
+
const meta = await getLinkMeta(userId, tenantId);
|
|
2910
|
+
meta.personalAssistantId = assistantId;
|
|
2911
|
+
meta.personalProjectId = projectId;
|
|
2912
|
+
meta.personalWorkspaceId = wsId;
|
|
2913
|
+
await updateLinkMeta(userId, tenantId, meta);
|
|
2914
|
+
return reply.status(201).send({
|
|
2915
|
+
success: true,
|
|
2916
|
+
message: "Personal assistant created",
|
|
2917
|
+
data: { id: assistant.id, name: assistant.name, projectId, workspaceId: wsId, createdAt: assistant.createdAt }
|
|
2918
|
+
});
|
|
2919
|
+
}
|
|
2920
|
+
async function getPersonalAssistant(request, reply) {
|
|
2921
|
+
const tenantId = getTenantId7(request);
|
|
2922
|
+
const userId = getUserId3(request);
|
|
2923
|
+
const store = getAssistantStore();
|
|
2924
|
+
const assistant = await store.getByOwner(tenantId, userId);
|
|
2925
|
+
if (!assistant) {
|
|
2926
|
+
return reply.status(404).send({ success: false, message: "No personal assistant found" });
|
|
2927
|
+
}
|
|
2928
|
+
const meta = await getLinkMeta(userId, tenantId);
|
|
2929
|
+
const projectId = meta.personalProjectId || "default";
|
|
2930
|
+
const workspaceId = meta.personalWorkspaceId || "default";
|
|
2931
|
+
return {
|
|
2932
|
+
success: true,
|
|
2933
|
+
message: "Personal assistant found",
|
|
2934
|
+
data: { id: assistant.id, name: assistant.name, projectId, workspaceId, createdAt: assistant.createdAt }
|
|
2935
|
+
};
|
|
2936
|
+
}
|
|
2937
|
+
async function deletePersonalAssistant(request, reply) {
|
|
2938
|
+
const tenantId = getTenantId7(request);
|
|
2939
|
+
const userId = getUserId3(request);
|
|
2940
|
+
const store = getAssistantStore();
|
|
2941
|
+
const assistant = await store.getByOwner(tenantId, userId);
|
|
2942
|
+
if (!assistant) {
|
|
2943
|
+
return reply.status(404).send({ success: false, message: "No personal assistant found" });
|
|
2944
|
+
}
|
|
2945
|
+
const deleted = await store.deleteAssistant(tenantId, assistant.id);
|
|
2946
|
+
if (!deleted) {
|
|
2947
|
+
return reply.status(500).send({ success: false, message: "Failed to delete personal assistant" });
|
|
2948
|
+
}
|
|
2949
|
+
const threadStore = (0, import_core14.getStoreLattice)("default", "thread").store;
|
|
2950
|
+
try {
|
|
2951
|
+
const threads = await threadStore.getThreadsByAssistantId(tenantId, assistant.id);
|
|
2952
|
+
for (const t of threads) {
|
|
2953
|
+
await threadStore.deleteThread(tenantId, t.id);
|
|
2954
|
+
}
|
|
2955
|
+
} catch {
|
|
2956
|
+
}
|
|
2957
|
+
const meta = await getLinkMeta(userId, tenantId);
|
|
2958
|
+
const projectId = meta.personalProjectId;
|
|
2959
|
+
const wsId = meta.personalWorkspaceId;
|
|
2960
|
+
if (projectId && wsId) {
|
|
2961
|
+
try {
|
|
2962
|
+
await getProjectStore().deleteProject(tenantId, projectId);
|
|
2963
|
+
} catch {
|
|
2964
|
+
}
|
|
2965
|
+
}
|
|
2966
|
+
delete meta.personalAssistantId;
|
|
2967
|
+
delete meta.personalProjectId;
|
|
2968
|
+
delete meta.personalWorkspaceId;
|
|
2969
|
+
await updateLinkMeta(userId, tenantId, meta);
|
|
2970
|
+
return { success: true, message: "Personal assistant deleted" };
|
|
2971
|
+
}
|
|
2972
|
+
|
|
2973
|
+
// src/controllers/tasks.ts
|
|
2974
|
+
var import_core15 = require("@axiom-lattice/core");
|
|
2975
|
+
function getTenantId8(request) {
|
|
2976
|
+
const userTenantId = request.user?.tenantId;
|
|
2977
|
+
if (userTenantId) return userTenantId;
|
|
2978
|
+
return request.headers["x-tenant-id"] || "default";
|
|
2979
|
+
}
|
|
2980
|
+
function getUserId4(request) {
|
|
2981
|
+
const userId = request.user?.id || request.headers["x-user-id"];
|
|
2982
|
+
if (!userId) throw new Error("User ID is required");
|
|
2983
|
+
return userId;
|
|
2984
|
+
}
|
|
2985
|
+
function getStore() {
|
|
2986
|
+
return (0, import_core15.getStoreLattice)("default", "task").store;
|
|
2987
|
+
}
|
|
2988
|
+
async function listTasks(request, reply) {
|
|
2989
|
+
try {
|
|
2990
|
+
const tenantId = getTenantId8(request);
|
|
2991
|
+
const userId = getUserId4(request);
|
|
2992
|
+
const query = request.query;
|
|
2993
|
+
const store = getStore();
|
|
2994
|
+
const tasks = await store.list({
|
|
2995
|
+
tenantId,
|
|
2996
|
+
ownerId: query.ownerId || userId,
|
|
2997
|
+
status: query.status,
|
|
2998
|
+
priority: query.priority,
|
|
2999
|
+
ownerType: query.ownerType,
|
|
3000
|
+
metadata: query.metadata ? JSON.parse(query.metadata) : void 0,
|
|
3001
|
+
limit: query.limit ? parseInt(query.limit) : void 0,
|
|
3002
|
+
offset: query.offset ? parseInt(query.offset) : void 0
|
|
3003
|
+
});
|
|
3004
|
+
return { success: true, data: tasks, count: tasks.length };
|
|
3005
|
+
} catch (error) {
|
|
3006
|
+
return { success: false, error: error.message };
|
|
3007
|
+
}
|
|
3008
|
+
}
|
|
3009
|
+
async function getTask(request, reply) {
|
|
3010
|
+
try {
|
|
3011
|
+
const tenantId = getTenantId8(request);
|
|
3012
|
+
const userId = getUserId4(request);
|
|
3013
|
+
const { id } = request.params;
|
|
3014
|
+
const store = getStore();
|
|
3015
|
+
const task = await store.getById(tenantId, id);
|
|
3016
|
+
if (!task) {
|
|
3017
|
+
return reply.status(404).send({ success: false, error: "Task not found" });
|
|
3018
|
+
}
|
|
3019
|
+
if (task.ownerType === "user" && task.ownerId !== userId) {
|
|
3020
|
+
return reply.status(403).send({ success: false, error: "Access denied" });
|
|
3021
|
+
}
|
|
3022
|
+
return { success: true, data: task };
|
|
3023
|
+
} catch (error) {
|
|
3024
|
+
return { success: false, error: error.message };
|
|
3025
|
+
}
|
|
3026
|
+
}
|
|
3027
|
+
async function createTask(request, reply) {
|
|
3028
|
+
try {
|
|
3029
|
+
const tenantId = getTenantId8(request);
|
|
3030
|
+
const userId = getUserId4(request);
|
|
3031
|
+
const body = request.body;
|
|
3032
|
+
if (!body.title) {
|
|
3033
|
+
return reply.status(400).send({ success: false, error: "title is required" });
|
|
3034
|
+
}
|
|
3035
|
+
const store = getStore();
|
|
3036
|
+
const task = await store.create({
|
|
3037
|
+
...body,
|
|
3038
|
+
tenantId,
|
|
3039
|
+
ownerType: body.ownerType || "user",
|
|
3040
|
+
ownerId: body.ownerId || userId
|
|
3041
|
+
});
|
|
3042
|
+
return reply.status(201).send({ success: true, data: task });
|
|
3043
|
+
} catch (error) {
|
|
3044
|
+
return reply.status(500).send({ success: false, error: error.message });
|
|
3045
|
+
}
|
|
3046
|
+
}
|
|
3047
|
+
async function updateTask(request, reply) {
|
|
3048
|
+
try {
|
|
3049
|
+
const tenantId = getTenantId8(request);
|
|
3050
|
+
const userId = getUserId4(request);
|
|
3051
|
+
const { id } = request.params;
|
|
3052
|
+
const store = getStore();
|
|
3053
|
+
const existing = await store.getById(tenantId, id);
|
|
3054
|
+
if (!existing) {
|
|
3055
|
+
return reply.status(404).send({ success: false, error: "Task not found" });
|
|
3056
|
+
}
|
|
3057
|
+
if (existing.ownerType === "user" && existing.ownerId !== userId) {
|
|
3058
|
+
return reply.status(403).send({ success: false, error: "Access denied" });
|
|
3059
|
+
}
|
|
3060
|
+
const task = await store.update(tenantId, id, request.body);
|
|
3061
|
+
if (!task) {
|
|
3062
|
+
return reply.status(404).send({ success: false, error: "Task not found" });
|
|
3063
|
+
}
|
|
3064
|
+
return { success: true, data: task };
|
|
3065
|
+
} catch (error) {
|
|
3066
|
+
return reply.status(500).send({ success: false, error: error.message });
|
|
3067
|
+
}
|
|
3068
|
+
}
|
|
3069
|
+
async function deleteTask(request, reply) {
|
|
3070
|
+
try {
|
|
3071
|
+
const tenantId = getTenantId8(request);
|
|
3072
|
+
const userId = getUserId4(request);
|
|
3073
|
+
const { id } = request.params;
|
|
3074
|
+
const store = getStore();
|
|
3075
|
+
const existing = await store.getById(tenantId, id);
|
|
3076
|
+
if (!existing) {
|
|
3077
|
+
return reply.status(404).send({ success: false, error: "Task not found" });
|
|
3078
|
+
}
|
|
3079
|
+
if (existing.ownerType === "user" && existing.ownerId !== userId) {
|
|
3080
|
+
return reply.status(403).send({ success: false, error: "Access denied" });
|
|
3081
|
+
}
|
|
3082
|
+
const deleted = await store.delete(tenantId, id);
|
|
3083
|
+
if (!deleted) {
|
|
3084
|
+
return reply.status(404).send({ success: false, error: "Task not found" });
|
|
3085
|
+
}
|
|
3086
|
+
return { success: true, message: "Task deleted" };
|
|
3087
|
+
} catch (error) {
|
|
3088
|
+
return reply.status(500).send({ success: false, error: error.message });
|
|
3089
|
+
}
|
|
3090
|
+
}
|
|
3091
|
+
async function completeTask(request, reply) {
|
|
3092
|
+
try {
|
|
3093
|
+
const tenantId = getTenantId8(request);
|
|
3094
|
+
const userId = getUserId4(request);
|
|
3095
|
+
const { id } = request.params;
|
|
3096
|
+
const store = getStore();
|
|
3097
|
+
const existing = await store.getById(tenantId, id);
|
|
3098
|
+
if (!existing) {
|
|
3099
|
+
return reply.status(404).send({ success: false, error: "Task not found" });
|
|
3100
|
+
}
|
|
3101
|
+
if (existing.ownerType === "user" && existing.ownerId !== userId) {
|
|
3102
|
+
return reply.status(403).send({ success: false, error: "Access denied" });
|
|
3103
|
+
}
|
|
3104
|
+
const task = await store.update(tenantId, id, { status: "completed" });
|
|
3105
|
+
if (!task) {
|
|
3106
|
+
return reply.status(404).send({ success: false, error: "Task not found" });
|
|
3107
|
+
}
|
|
3108
|
+
return { success: true, data: task };
|
|
3109
|
+
} catch (error) {
|
|
3110
|
+
return reply.status(500).send({ success: false, error: error.message });
|
|
3111
|
+
}
|
|
3112
|
+
}
|
|
3113
|
+
|
|
2808
3114
|
// src/schemas/data-query.ts
|
|
2809
3115
|
var dataQuerySchema = {
|
|
2810
3116
|
description: "Execute data query (semantic or SQL)",
|
|
@@ -3146,7 +3452,7 @@ var getHealthSchema = {
|
|
|
3146
3452
|
};
|
|
3147
3453
|
|
|
3148
3454
|
// src/controllers/thread_status.ts
|
|
3149
|
-
var
|
|
3455
|
+
var import_core16 = require("@axiom-lattice/core");
|
|
3150
3456
|
async function removePendingMessageHandler(request, reply) {
|
|
3151
3457
|
try {
|
|
3152
3458
|
const { assistant_id, thread_id, message_id } = request.params;
|
|
@@ -3159,7 +3465,7 @@ async function removePendingMessageHandler(request, reply) {
|
|
|
3159
3465
|
if (!assistant_id) {
|
|
3160
3466
|
return reply.code(400).send({ error: "Missing assistant_id parameter" });
|
|
3161
3467
|
}
|
|
3162
|
-
const agent =
|
|
3468
|
+
const agent = import_core16.agentInstanceManager.getAgent({
|
|
3163
3469
|
assistant_id,
|
|
3164
3470
|
thread_id,
|
|
3165
3471
|
tenant_id,
|
|
@@ -3193,7 +3499,7 @@ async function removePendingMessageHandler(request, reply) {
|
|
|
3193
3499
|
}
|
|
3194
3500
|
|
|
3195
3501
|
// src/services/sandbox_service.ts
|
|
3196
|
-
var
|
|
3502
|
+
var import_core17 = require("@axiom-lattice/core");
|
|
3197
3503
|
var ERROR_HTML = `<!DOCTYPE html>
|
|
3198
3504
|
<html lang="zh-CN">
|
|
3199
3505
|
<head>
|
|
@@ -3305,7 +3611,7 @@ var ERROR_HTML = `<!DOCTYPE html>
|
|
|
3305
3611
|
</html>`;
|
|
3306
3612
|
var SandboxService = class {
|
|
3307
3613
|
getFilesystemVmIsolation(tenantId, assistantId) {
|
|
3308
|
-
const agentLattice =
|
|
3614
|
+
const agentLattice = import_core17.agentLatticeManager.getAgentLatticeWithTenant(tenantId, assistantId);
|
|
3309
3615
|
if (!agentLattice) {
|
|
3310
3616
|
return null;
|
|
3311
3617
|
}
|
|
@@ -3319,9 +3625,9 @@ var SandboxService = class {
|
|
|
3319
3625
|
computeSandboxName(assistantId, threadId, vmIsolation, tenantId, workspaceId, projectId) {
|
|
3320
3626
|
switch (vmIsolation) {
|
|
3321
3627
|
case "agent":
|
|
3322
|
-
return (0,
|
|
3628
|
+
return (0, import_core17.normalizeSandboxName)(`${tenantId ?? "default"}-${assistantId}`);
|
|
3323
3629
|
case "project":
|
|
3324
|
-
return (0,
|
|
3630
|
+
return (0, import_core17.normalizeSandboxName)(
|
|
3325
3631
|
`${tenantId ?? "default"}-${workspaceId ?? "default"}-${projectId ?? "default"}`
|
|
3326
3632
|
);
|
|
3327
3633
|
case "global":
|
|
@@ -3369,15 +3675,15 @@ var SandboxService = class {
|
|
|
3369
3675
|
);
|
|
3370
3676
|
return rewritten;
|
|
3371
3677
|
}
|
|
3372
|
-
generateErrorHtml(assistantId, threadId, vmIsolation,
|
|
3373
|
-
const encodedError = encodeURIComponent(
|
|
3374
|
-
return ERROR_HTML.replace("{assistantId}", assistantId).replace("{threadId}", threadId).replace("{vmIsolation}", vmIsolation).replace("{errorMessage}",
|
|
3678
|
+
generateErrorHtml(assistantId, threadId, vmIsolation, errorMessage2) {
|
|
3679
|
+
const encodedError = encodeURIComponent(errorMessage2);
|
|
3680
|
+
return ERROR_HTML.replace("{assistantId}", assistantId).replace("{threadId}", threadId).replace("{vmIsolation}", vmIsolation).replace("{errorMessage}", errorMessage2);
|
|
3375
3681
|
}
|
|
3376
3682
|
};
|
|
3377
3683
|
var sandboxService = new SandboxService();
|
|
3378
3684
|
|
|
3379
3685
|
// src/controllers/sandbox.ts
|
|
3380
|
-
var
|
|
3686
|
+
var import_core18 = require("@axiom-lattice/core");
|
|
3381
3687
|
function getFilenameFromPath(path3) {
|
|
3382
3688
|
const segments = path3.replace(/\/+$/, "").split("/");
|
|
3383
3689
|
return segments[segments.length - 1] || "download";
|
|
@@ -3416,7 +3722,7 @@ function registerSandboxProxyRoutes(app2) {
|
|
|
3416
3722
|
}
|
|
3417
3723
|
const workspaceId = request.headers["x-workspace-id"];
|
|
3418
3724
|
const projectId = request.headers["x-project-id"];
|
|
3419
|
-
const sandboxManager = (0,
|
|
3725
|
+
const sandboxManager = (0, import_core18.getSandBoxManager)();
|
|
3420
3726
|
const sandbox = await sandboxManager.getSandboxFromConfig({
|
|
3421
3727
|
assistant_id: assistantId,
|
|
3422
3728
|
thread_id: threadId,
|
|
@@ -3464,7 +3770,7 @@ function registerSandboxProxyRoutes(app2) {
|
|
|
3464
3770
|
}
|
|
3465
3771
|
const workspaceId = request.headers["x-workspace-id"];
|
|
3466
3772
|
const projectId = request.headers["x-project-id"];
|
|
3467
|
-
const sandboxManager = (0,
|
|
3773
|
+
const sandboxManager = (0, import_core18.getSandBoxManager)();
|
|
3468
3774
|
const sandbox = await sandboxManager.getSandboxFromConfig({
|
|
3469
3775
|
assistant_id: assistantId,
|
|
3470
3776
|
thread_id: threadId,
|
|
@@ -3497,14 +3803,14 @@ function registerSandboxProxyRoutes(app2) {
|
|
|
3497
3803
|
// src/controllers/workspace.ts
|
|
3498
3804
|
var fs = __toESM(require("fs/promises"));
|
|
3499
3805
|
var path = __toESM(require("path"));
|
|
3500
|
-
var import_core17 = require("@axiom-lattice/core");
|
|
3501
|
-
var import_core18 = require("@axiom-lattice/core");
|
|
3502
3806
|
var import_core19 = require("@axiom-lattice/core");
|
|
3807
|
+
var import_core20 = require("@axiom-lattice/core");
|
|
3808
|
+
var import_core21 = require("@axiom-lattice/core");
|
|
3503
3809
|
var import_uuid2 = require("uuid");
|
|
3504
3810
|
var WorkspaceController = class {
|
|
3505
3811
|
constructor() {
|
|
3506
|
-
this.workspaceStore = (0,
|
|
3507
|
-
this.projectStore = (0,
|
|
3812
|
+
this.workspaceStore = (0, import_core19.getStoreLattice)("default", "workspace").store;
|
|
3813
|
+
this.projectStore = (0, import_core19.getStoreLattice)("default", "project").store;
|
|
3508
3814
|
}
|
|
3509
3815
|
getTenantId(request) {
|
|
3510
3816
|
const userTenantId = request.user?.tenantId;
|
|
@@ -3636,8 +3942,9 @@ var WorkspaceController = class {
|
|
|
3636
3942
|
if (!workspace) {
|
|
3637
3943
|
throw new Error("Workspace not found");
|
|
3638
3944
|
}
|
|
3945
|
+
console.log(`[getBackend] storageType=${workspace.storageType} filePath=${filePath}`);
|
|
3639
3946
|
if (workspace.storageType === "sandbox") {
|
|
3640
|
-
const sandboxManager = (0,
|
|
3947
|
+
const sandboxManager = (0, import_core21.getSandBoxManager)();
|
|
3641
3948
|
const volumeConfig = {
|
|
3642
3949
|
assistant_id: assistantId || "",
|
|
3643
3950
|
thread_id: "",
|
|
@@ -3645,20 +3952,25 @@ var WorkspaceController = class {
|
|
|
3645
3952
|
workspaceId,
|
|
3646
3953
|
projectId
|
|
3647
3954
|
};
|
|
3955
|
+
console.log(`[getBackend] trying volume backend for path=${filePath} assistant_id=${assistantId}`);
|
|
3648
3956
|
const volumeBackend = await sandboxManager.getVolumeBackendForPath(volumeConfig, filePath || "/project");
|
|
3649
3957
|
if (volumeBackend) {
|
|
3958
|
+
console.log(`[getBackend] using VolumeFilesystem`);
|
|
3650
3959
|
return { backend: volumeBackend, workspace };
|
|
3651
3960
|
}
|
|
3961
|
+
console.log(`[getBackend] volume not found, falling back to SandboxFilesystem`);
|
|
3652
3962
|
const sandbox = await sandboxManager.getSandboxFromConfig(volumeConfig);
|
|
3963
|
+
console.log(`[getBackend] sandbox acquired, name=${sandbox.name || "unknown"}`);
|
|
3653
3964
|
return {
|
|
3654
|
-
backend: new
|
|
3965
|
+
backend: new import_core20.SandboxFilesystem({
|
|
3655
3966
|
sandboxInstance: sandbox
|
|
3656
3967
|
}),
|
|
3657
3968
|
workspace
|
|
3658
3969
|
};
|
|
3659
3970
|
} else {
|
|
3971
|
+
console.log(`[getBackend] using FilesystemBackend rootDir=/lattice_store/tenants/${tenantId}/workspaces/${workspaceId}/${projectId}`);
|
|
3660
3972
|
return {
|
|
3661
|
-
backend: new
|
|
3973
|
+
backend: new import_core20.FilesystemBackend({
|
|
3662
3974
|
rootDir: `/lattice_store/tenants/${tenantId}/workspaces/${workspaceId}/${projectId}`,
|
|
3663
3975
|
virtualMode: true
|
|
3664
3976
|
}),
|
|
@@ -3736,7 +4048,7 @@ var WorkspaceController = class {
|
|
|
3736
4048
|
const { workspace } = await this.getBackend(tenantId, workspaceId, projectId, assistantId);
|
|
3737
4049
|
const resolvedPath = filePath;
|
|
3738
4050
|
if (workspace.storageType === "sandbox") {
|
|
3739
|
-
const sandboxManager = (0,
|
|
4051
|
+
const sandboxManager = (0, import_core21.getSandBoxManager)();
|
|
3740
4052
|
const volumeConfig = {
|
|
3741
4053
|
assistant_id: assistantId || "",
|
|
3742
4054
|
thread_id: "",
|
|
@@ -3786,7 +4098,7 @@ var WorkspaceController = class {
|
|
|
3786
4098
|
const { workspace } = await this.getBackend(tenantId, workspaceId, projectId, assistantId);
|
|
3787
4099
|
const resolvedPath = filePath;
|
|
3788
4100
|
if (workspace.storageType === "sandbox") {
|
|
3789
|
-
const sandboxManager = (0,
|
|
4101
|
+
const sandboxManager = (0, import_core21.getSandBoxManager)();
|
|
3790
4102
|
const volumeConfig = {
|
|
3791
4103
|
assistant_id: assistantId || "",
|
|
3792
4104
|
thread_id: "",
|
|
@@ -3873,8 +4185,11 @@ var WorkspaceController = class {
|
|
|
3873
4185
|
const { workspaceId, projectId } = request.params;
|
|
3874
4186
|
const path3 = request.query.path || "/";
|
|
3875
4187
|
const assistantId = request.query.assistantId;
|
|
4188
|
+
console.log(`[listPath] tenantId=${tenantId} workspaceId=${workspaceId} projectId=${projectId} path=${path3} assistantId=${assistantId}`);
|
|
3876
4189
|
const { backend } = await this.getBackend(tenantId, workspaceId, projectId, assistantId, path3);
|
|
4190
|
+
console.log(`[listPath] backend type=${backend.constructor.name} calling lsInfo(${path3})`);
|
|
3877
4191
|
const files = await backend.lsInfo(path3);
|
|
4192
|
+
console.log(`[listPath] result count=${files.length}`);
|
|
3878
4193
|
return { success: true, data: files };
|
|
3879
4194
|
}
|
|
3880
4195
|
async readFile(request) {
|
|
@@ -3920,7 +4235,7 @@ var WorkspaceController = class {
|
|
|
3920
4235
|
return reply.status(400).send({ success: false, error: "Invalid path parameter" });
|
|
3921
4236
|
}
|
|
3922
4237
|
if (workspace.storageType === "sandbox") {
|
|
3923
|
-
const sandboxManager = (0,
|
|
4238
|
+
const sandboxManager = (0, import_core21.getSandBoxManager)();
|
|
3924
4239
|
const volumeConfig = {
|
|
3925
4240
|
assistant_id: assistantId || "",
|
|
3926
4241
|
thread_id: "",
|
|
@@ -4028,9 +4343,9 @@ function registerWorkspaceRoutes(app2) {
|
|
|
4028
4343
|
}
|
|
4029
4344
|
|
|
4030
4345
|
// src/controllers/database-configs.ts
|
|
4031
|
-
var
|
|
4032
|
-
var
|
|
4033
|
-
function
|
|
4346
|
+
var import_core22 = require("@axiom-lattice/core");
|
|
4347
|
+
var import_crypto4 = require("crypto");
|
|
4348
|
+
function getTenantId9(request) {
|
|
4034
4349
|
const userTenantId = request.user?.tenantId;
|
|
4035
4350
|
if (userTenantId) {
|
|
4036
4351
|
return userTenantId;
|
|
@@ -4038,9 +4353,9 @@ function getTenantId7(request) {
|
|
|
4038
4353
|
return request.headers["x-tenant-id"] || "default";
|
|
4039
4354
|
}
|
|
4040
4355
|
async function getDatabaseConfigList(request, reply) {
|
|
4041
|
-
const tenantId =
|
|
4356
|
+
const tenantId = getTenantId9(request);
|
|
4042
4357
|
try {
|
|
4043
|
-
const storeLattice = (0,
|
|
4358
|
+
const storeLattice = (0, import_core22.getStoreLattice)("default", "database");
|
|
4044
4359
|
const store = storeLattice.store;
|
|
4045
4360
|
const configs = await store.getAllConfigs(tenantId);
|
|
4046
4361
|
console.log("Backend: getAllConfigs returned:", configs);
|
|
@@ -4068,10 +4383,10 @@ async function getDatabaseConfigList(request, reply) {
|
|
|
4068
4383
|
}
|
|
4069
4384
|
}
|
|
4070
4385
|
async function getDatabaseConfig(request, reply) {
|
|
4071
|
-
const tenantId =
|
|
4386
|
+
const tenantId = getTenantId9(request);
|
|
4072
4387
|
const { key } = request.params;
|
|
4073
4388
|
try {
|
|
4074
|
-
const storeLattice = (0,
|
|
4389
|
+
const storeLattice = (0, import_core22.getStoreLattice)("default", "database");
|
|
4075
4390
|
const store = storeLattice.store;
|
|
4076
4391
|
const config = await store.getConfigByKey(tenantId, key);
|
|
4077
4392
|
if (!config) {
|
|
@@ -4094,10 +4409,10 @@ async function getDatabaseConfig(request, reply) {
|
|
|
4094
4409
|
}
|
|
4095
4410
|
}
|
|
4096
4411
|
async function createDatabaseConfig(request, reply) {
|
|
4097
|
-
const tenantId =
|
|
4412
|
+
const tenantId = getTenantId9(request);
|
|
4098
4413
|
const body = request.body;
|
|
4099
4414
|
try {
|
|
4100
|
-
const storeLattice = (0,
|
|
4415
|
+
const storeLattice = (0, import_core22.getStoreLattice)("default", "database");
|
|
4101
4416
|
const store = storeLattice.store;
|
|
4102
4417
|
const existing = await store.getConfigByKey(tenantId, body.key);
|
|
4103
4418
|
if (existing) {
|
|
@@ -4107,10 +4422,10 @@ async function createDatabaseConfig(request, reply) {
|
|
|
4107
4422
|
message: "Database configuration with this key already exists"
|
|
4108
4423
|
};
|
|
4109
4424
|
}
|
|
4110
|
-
const id = body.id || (0,
|
|
4425
|
+
const id = body.id || (0, import_crypto4.randomUUID)();
|
|
4111
4426
|
const config = await store.createConfig(tenantId, id, body);
|
|
4112
4427
|
try {
|
|
4113
|
-
|
|
4428
|
+
import_core22.sqlDatabaseManager.registerDatabase(tenantId, config.key, config.config);
|
|
4114
4429
|
} catch (error) {
|
|
4115
4430
|
console.warn("Failed to auto-register database:", error);
|
|
4116
4431
|
}
|
|
@@ -4129,11 +4444,11 @@ async function createDatabaseConfig(request, reply) {
|
|
|
4129
4444
|
}
|
|
4130
4445
|
}
|
|
4131
4446
|
async function updateDatabaseConfig(request, reply) {
|
|
4132
|
-
const tenantId =
|
|
4447
|
+
const tenantId = getTenantId9(request);
|
|
4133
4448
|
const { key } = request.params;
|
|
4134
4449
|
const updates = request.body;
|
|
4135
4450
|
try {
|
|
4136
|
-
const storeLattice = (0,
|
|
4451
|
+
const storeLattice = (0, import_core22.getStoreLattice)("default", "database");
|
|
4137
4452
|
const store = storeLattice.store;
|
|
4138
4453
|
const existing = await store.getConfigByKey(tenantId, key);
|
|
4139
4454
|
if (!existing) {
|
|
@@ -4152,7 +4467,7 @@ async function updateDatabaseConfig(request, reply) {
|
|
|
4152
4467
|
}
|
|
4153
4468
|
if (updates.config) {
|
|
4154
4469
|
try {
|
|
4155
|
-
|
|
4470
|
+
import_core22.sqlDatabaseManager.registerDatabase(tenantId, updated.key, updated.config);
|
|
4156
4471
|
} catch (error) {
|
|
4157
4472
|
console.warn("Failed to re-register database:", error);
|
|
4158
4473
|
}
|
|
@@ -4171,10 +4486,10 @@ async function updateDatabaseConfig(request, reply) {
|
|
|
4171
4486
|
}
|
|
4172
4487
|
}
|
|
4173
4488
|
async function deleteDatabaseConfig(request, reply) {
|
|
4174
|
-
const tenantId =
|
|
4489
|
+
const tenantId = getTenantId9(request);
|
|
4175
4490
|
const { keyOrId } = request.params;
|
|
4176
4491
|
try {
|
|
4177
|
-
const storeLattice = (0,
|
|
4492
|
+
const storeLattice = (0, import_core22.getStoreLattice)("default", "database");
|
|
4178
4493
|
const store = storeLattice.store;
|
|
4179
4494
|
console.log("Delete request - keyOrId:", keyOrId);
|
|
4180
4495
|
let config = await store.getConfigByKey(tenantId, keyOrId);
|
|
@@ -4201,8 +4516,8 @@ async function deleteDatabaseConfig(request, reply) {
|
|
|
4201
4516
|
};
|
|
4202
4517
|
}
|
|
4203
4518
|
try {
|
|
4204
|
-
if (
|
|
4205
|
-
await
|
|
4519
|
+
if (import_core22.sqlDatabaseManager.hasDatabase(tenantId, configKey)) {
|
|
4520
|
+
await import_core22.sqlDatabaseManager.removeDatabase(tenantId, configKey);
|
|
4206
4521
|
}
|
|
4207
4522
|
} catch (error) {
|
|
4208
4523
|
console.warn("Failed to remove from SqlDatabaseManager:", error);
|
|
@@ -4220,10 +4535,10 @@ async function deleteDatabaseConfig(request, reply) {
|
|
|
4220
4535
|
}
|
|
4221
4536
|
}
|
|
4222
4537
|
async function testDatabaseConnection(request, reply) {
|
|
4223
|
-
const tenantId =
|
|
4538
|
+
const tenantId = getTenantId9(request);
|
|
4224
4539
|
const { key } = request.params;
|
|
4225
4540
|
try {
|
|
4226
|
-
const storeLattice = (0,
|
|
4541
|
+
const storeLattice = (0, import_core22.getStoreLattice)("default", "database");
|
|
4227
4542
|
const store = storeLattice.store;
|
|
4228
4543
|
const config = await store.getConfigByKey(tenantId, key);
|
|
4229
4544
|
if (!config) {
|
|
@@ -4234,16 +4549,16 @@ async function testDatabaseConnection(request, reply) {
|
|
|
4234
4549
|
};
|
|
4235
4550
|
}
|
|
4236
4551
|
const testKey = `__test_${key}_${Date.now()}`;
|
|
4237
|
-
|
|
4552
|
+
import_core22.sqlDatabaseManager.registerDatabase(tenantId, testKey, config.config);
|
|
4238
4553
|
const startTime = Date.now();
|
|
4239
|
-
const db = await
|
|
4554
|
+
const db = await import_core22.sqlDatabaseManager.getDatabase(tenantId, testKey);
|
|
4240
4555
|
try {
|
|
4241
4556
|
await db.connect();
|
|
4242
4557
|
await db.listTables();
|
|
4243
4558
|
const latency = Date.now() - startTime;
|
|
4244
4559
|
await new Promise((resolve) => setTimeout(resolve, 100));
|
|
4245
4560
|
await db.disconnect();
|
|
4246
|
-
await
|
|
4561
|
+
await import_core22.sqlDatabaseManager.removeDatabase(tenantId, testKey);
|
|
4247
4562
|
return {
|
|
4248
4563
|
success: true,
|
|
4249
4564
|
message: "Connection test successful",
|
|
@@ -4255,7 +4570,7 @@ async function testDatabaseConnection(request, reply) {
|
|
|
4255
4570
|
} catch (error) {
|
|
4256
4571
|
try {
|
|
4257
4572
|
await db.disconnect();
|
|
4258
|
-
await
|
|
4573
|
+
await import_core22.sqlDatabaseManager.removeDatabase(tenantId, testKey);
|
|
4259
4574
|
} catch {
|
|
4260
4575
|
}
|
|
4261
4576
|
return {
|
|
@@ -4307,9 +4622,9 @@ function registerDatabaseConfigRoutes(app2) {
|
|
|
4307
4622
|
}
|
|
4308
4623
|
|
|
4309
4624
|
// src/controllers/metrics-configs.ts
|
|
4310
|
-
var
|
|
4311
|
-
var
|
|
4312
|
-
function
|
|
4625
|
+
var import_core23 = require("@axiom-lattice/core");
|
|
4626
|
+
var import_crypto5 = require("crypto");
|
|
4627
|
+
function getTenantId10(request) {
|
|
4313
4628
|
const userTenantId = request.user?.tenantId;
|
|
4314
4629
|
if (userTenantId) {
|
|
4315
4630
|
return userTenantId;
|
|
@@ -4317,9 +4632,9 @@ function getTenantId8(request) {
|
|
|
4317
4632
|
return request.headers["x-tenant-id"] || "default";
|
|
4318
4633
|
}
|
|
4319
4634
|
async function getMetricsServerConfigList(request, reply) {
|
|
4320
|
-
const tenantId =
|
|
4635
|
+
const tenantId = getTenantId10(request);
|
|
4321
4636
|
try {
|
|
4322
|
-
const storeLattice = (0,
|
|
4637
|
+
const storeLattice = (0, import_core23.getStoreLattice)("default", "metrics");
|
|
4323
4638
|
const store = storeLattice.store;
|
|
4324
4639
|
const configs = await store.getAllConfigs(tenantId);
|
|
4325
4640
|
return {
|
|
@@ -4343,10 +4658,10 @@ async function getMetricsServerConfigList(request, reply) {
|
|
|
4343
4658
|
}
|
|
4344
4659
|
}
|
|
4345
4660
|
async function getMetricsServerConfig(request, reply) {
|
|
4346
|
-
const tenantId =
|
|
4661
|
+
const tenantId = getTenantId10(request);
|
|
4347
4662
|
const { key } = request.params;
|
|
4348
4663
|
try {
|
|
4349
|
-
const storeLattice = (0,
|
|
4664
|
+
const storeLattice = (0, import_core23.getStoreLattice)("default", "metrics");
|
|
4350
4665
|
const store = storeLattice.store;
|
|
4351
4666
|
const config = await store.getConfigByKey(tenantId, key);
|
|
4352
4667
|
if (!config) {
|
|
@@ -4369,10 +4684,10 @@ async function getMetricsServerConfig(request, reply) {
|
|
|
4369
4684
|
}
|
|
4370
4685
|
}
|
|
4371
4686
|
async function createMetricsServerConfig(request, reply) {
|
|
4372
|
-
const tenantId =
|
|
4687
|
+
const tenantId = getTenantId10(request);
|
|
4373
4688
|
const body = request.body;
|
|
4374
4689
|
try {
|
|
4375
|
-
const storeLattice = (0,
|
|
4690
|
+
const storeLattice = (0, import_core23.getStoreLattice)("default", "metrics");
|
|
4376
4691
|
const store = storeLattice.store;
|
|
4377
4692
|
const existing = await store.getConfigByKey(tenantId, body.key);
|
|
4378
4693
|
if (existing) {
|
|
@@ -4389,7 +4704,7 @@ async function createMetricsServerConfig(request, reply) {
|
|
|
4389
4704
|
message: "selectedDataSources is required for semantic metrics servers"
|
|
4390
4705
|
};
|
|
4391
4706
|
}
|
|
4392
|
-
const id = body.id || (0,
|
|
4707
|
+
const id = body.id || (0, import_crypto5.randomUUID)();
|
|
4393
4708
|
const configData = {
|
|
4394
4709
|
key: body.key,
|
|
4395
4710
|
name: body.name,
|
|
@@ -4401,7 +4716,7 @@ async function createMetricsServerConfig(request, reply) {
|
|
|
4401
4716
|
};
|
|
4402
4717
|
const config = await store.createConfig(tenantId, id, configData);
|
|
4403
4718
|
try {
|
|
4404
|
-
|
|
4719
|
+
import_core23.metricsServerManager.registerServer(tenantId, config.key, config.config);
|
|
4405
4720
|
} catch (error) {
|
|
4406
4721
|
console.warn("Failed to auto-register metrics server:", error);
|
|
4407
4722
|
}
|
|
@@ -4420,11 +4735,11 @@ async function createMetricsServerConfig(request, reply) {
|
|
|
4420
4735
|
}
|
|
4421
4736
|
}
|
|
4422
4737
|
async function updateMetricsServerConfig(request, reply) {
|
|
4423
|
-
const tenantId =
|
|
4738
|
+
const tenantId = getTenantId10(request);
|
|
4424
4739
|
const { key } = request.params;
|
|
4425
4740
|
const updates = request.body;
|
|
4426
4741
|
try {
|
|
4427
|
-
const storeLattice = (0,
|
|
4742
|
+
const storeLattice = (0, import_core23.getStoreLattice)("default", "metrics");
|
|
4428
4743
|
const store = storeLattice.store;
|
|
4429
4744
|
const existing = await store.getConfigByKey(tenantId, key);
|
|
4430
4745
|
if (!existing) {
|
|
@@ -4452,7 +4767,7 @@ async function updateMetricsServerConfig(request, reply) {
|
|
|
4452
4767
|
}
|
|
4453
4768
|
if (updates.config) {
|
|
4454
4769
|
try {
|
|
4455
|
-
|
|
4770
|
+
import_core23.metricsServerManager.registerServer(tenantId, updated.key, updated.config);
|
|
4456
4771
|
} catch (error) {
|
|
4457
4772
|
console.warn("Failed to re-register metrics server:", error);
|
|
4458
4773
|
}
|
|
@@ -4471,10 +4786,10 @@ async function updateMetricsServerConfig(request, reply) {
|
|
|
4471
4786
|
}
|
|
4472
4787
|
}
|
|
4473
4788
|
async function deleteMetricsServerConfig(request, reply) {
|
|
4474
|
-
const tenantId =
|
|
4789
|
+
const tenantId = getTenantId10(request);
|
|
4475
4790
|
const { keyOrId } = request.params;
|
|
4476
4791
|
try {
|
|
4477
|
-
const storeLattice = (0,
|
|
4792
|
+
const storeLattice = (0, import_core23.getStoreLattice)("default", "metrics");
|
|
4478
4793
|
const store = storeLattice.store;
|
|
4479
4794
|
let config = await store.getConfigByKey(tenantId, keyOrId);
|
|
4480
4795
|
let configKey = keyOrId;
|
|
@@ -4499,8 +4814,8 @@ async function deleteMetricsServerConfig(request, reply) {
|
|
|
4499
4814
|
};
|
|
4500
4815
|
}
|
|
4501
4816
|
try {
|
|
4502
|
-
if (
|
|
4503
|
-
|
|
4817
|
+
if (import_core23.metricsServerManager.hasServer(tenantId, configKey)) {
|
|
4818
|
+
import_core23.metricsServerManager.removeServer(tenantId, configKey);
|
|
4504
4819
|
}
|
|
4505
4820
|
} catch (error) {
|
|
4506
4821
|
console.warn("Failed to remove from MetricsServerManager:", error);
|
|
@@ -4518,10 +4833,10 @@ async function deleteMetricsServerConfig(request, reply) {
|
|
|
4518
4833
|
}
|
|
4519
4834
|
}
|
|
4520
4835
|
async function testMetricsServerConnection(request, reply) {
|
|
4521
|
-
const tenantId =
|
|
4836
|
+
const tenantId = getTenantId10(request);
|
|
4522
4837
|
const { key } = request.params;
|
|
4523
4838
|
try {
|
|
4524
|
-
const storeLattice = (0,
|
|
4839
|
+
const storeLattice = (0, import_core23.getStoreLattice)("default", "metrics");
|
|
4525
4840
|
const store = storeLattice.store;
|
|
4526
4841
|
const config = await store.getConfigByKey(tenantId, key);
|
|
4527
4842
|
if (!config) {
|
|
@@ -4532,11 +4847,11 @@ async function testMetricsServerConnection(request, reply) {
|
|
|
4532
4847
|
};
|
|
4533
4848
|
}
|
|
4534
4849
|
const testKey = `__test_${key}_${Date.now()}`;
|
|
4535
|
-
|
|
4850
|
+
import_core23.metricsServerManager.registerServer(tenantId, testKey, config.config);
|
|
4536
4851
|
try {
|
|
4537
|
-
const client = await
|
|
4852
|
+
const client = await import_core23.metricsServerManager.getClient(tenantId, testKey);
|
|
4538
4853
|
const result = await client.testConnection();
|
|
4539
|
-
|
|
4854
|
+
import_core23.metricsServerManager.removeServer(tenantId, testKey);
|
|
4540
4855
|
return {
|
|
4541
4856
|
success: true,
|
|
4542
4857
|
message: result.connected ? "Connection test successful" : "Connection test failed",
|
|
@@ -4544,7 +4859,7 @@ async function testMetricsServerConnection(request, reply) {
|
|
|
4544
4859
|
};
|
|
4545
4860
|
} catch (error) {
|
|
4546
4861
|
try {
|
|
4547
|
-
|
|
4862
|
+
import_core23.metricsServerManager.removeServer(tenantId, testKey);
|
|
4548
4863
|
} catch {
|
|
4549
4864
|
}
|
|
4550
4865
|
return {
|
|
@@ -4569,10 +4884,10 @@ async function testMetricsServerConnection(request, reply) {
|
|
|
4569
4884
|
}
|
|
4570
4885
|
}
|
|
4571
4886
|
async function listAvailableMetrics(request, reply) {
|
|
4572
|
-
const tenantId =
|
|
4887
|
+
const tenantId = getTenantId10(request);
|
|
4573
4888
|
const { key } = request.params;
|
|
4574
4889
|
try {
|
|
4575
|
-
const storeLattice = (0,
|
|
4890
|
+
const storeLattice = (0, import_core23.getStoreLattice)("default", "metrics");
|
|
4576
4891
|
const store = storeLattice.store;
|
|
4577
4892
|
const config = await store.getConfigByKey(tenantId, key);
|
|
4578
4893
|
if (!config) {
|
|
@@ -4582,10 +4897,10 @@ async function listAvailableMetrics(request, reply) {
|
|
|
4582
4897
|
message: "Metrics server configuration not found"
|
|
4583
4898
|
};
|
|
4584
4899
|
}
|
|
4585
|
-
if (!
|
|
4586
|
-
|
|
4900
|
+
if (!import_core23.metricsServerManager.hasServer(tenantId, key)) {
|
|
4901
|
+
import_core23.metricsServerManager.registerServer(tenantId, key, config.config);
|
|
4587
4902
|
}
|
|
4588
|
-
const client = await
|
|
4903
|
+
const client = await import_core23.metricsServerManager.getClient(tenantId, key);
|
|
4589
4904
|
const metrics = await client.listMetrics();
|
|
4590
4905
|
return {
|
|
4591
4906
|
success: true,
|
|
@@ -4607,11 +4922,11 @@ async function listAvailableMetrics(request, reply) {
|
|
|
4607
4922
|
}
|
|
4608
4923
|
}
|
|
4609
4924
|
async function queryMetricsData(request, reply) {
|
|
4610
|
-
const tenantId =
|
|
4925
|
+
const tenantId = getTenantId10(request);
|
|
4611
4926
|
const { key } = request.params;
|
|
4612
4927
|
const { metricName, startTime, endTime, step, labels } = request.body;
|
|
4613
4928
|
try {
|
|
4614
|
-
const storeLattice = (0,
|
|
4929
|
+
const storeLattice = (0, import_core23.getStoreLattice)("default", "metrics");
|
|
4615
4930
|
const store = storeLattice.store;
|
|
4616
4931
|
const config = await store.getConfigByKey(tenantId, key);
|
|
4617
4932
|
if (!config) {
|
|
@@ -4628,10 +4943,10 @@ async function queryMetricsData(request, reply) {
|
|
|
4628
4943
|
message: "metricName is required"
|
|
4629
4944
|
};
|
|
4630
4945
|
}
|
|
4631
|
-
if (!
|
|
4632
|
-
|
|
4946
|
+
if (!import_core23.metricsServerManager.hasServer(tenantId, key)) {
|
|
4947
|
+
import_core23.metricsServerManager.registerServer(tenantId, key, config.config);
|
|
4633
4948
|
}
|
|
4634
|
-
const client = await
|
|
4949
|
+
const client = await import_core23.metricsServerManager.getClient(tenantId, key);
|
|
4635
4950
|
const result = await client.queryMetricData(metricName, {
|
|
4636
4951
|
startTime,
|
|
4637
4952
|
endTime,
|
|
@@ -4655,10 +4970,10 @@ async function queryMetricsData(request, reply) {
|
|
|
4655
4970
|
}
|
|
4656
4971
|
}
|
|
4657
4972
|
async function getDataSources(request, reply) {
|
|
4658
|
-
const tenantId =
|
|
4973
|
+
const tenantId = getTenantId10(request);
|
|
4659
4974
|
const { key } = request.params;
|
|
4660
4975
|
try {
|
|
4661
|
-
const storeLattice = (0,
|
|
4976
|
+
const storeLattice = (0, import_core23.getStoreLattice)("default", "metrics");
|
|
4662
4977
|
const store = storeLattice.store;
|
|
4663
4978
|
const config = await store.getConfigByKey(tenantId, key);
|
|
4664
4979
|
if (!config) {
|
|
@@ -4676,7 +4991,7 @@ async function getDataSources(request, reply) {
|
|
|
4676
4991
|
};
|
|
4677
4992
|
}
|
|
4678
4993
|
const semanticConfig = config.config;
|
|
4679
|
-
const client = new
|
|
4994
|
+
const client = new import_core23.SemanticMetricsClient(semanticConfig);
|
|
4680
4995
|
const allDatasources = await client.getDataSources();
|
|
4681
4996
|
const selectedIds = semanticConfig.selectedDataSources || [];
|
|
4682
4997
|
const filteredDatasources = selectedIds.length > 0 ? allDatasources.filter((ds) => selectedIds.includes(String(ds.id))) : allDatasources;
|
|
@@ -4696,10 +5011,10 @@ async function getDataSources(request, reply) {
|
|
|
4696
5011
|
}
|
|
4697
5012
|
}
|
|
4698
5013
|
async function getDatasourceMetrics(request, reply) {
|
|
4699
|
-
const tenantId =
|
|
5014
|
+
const tenantId = getTenantId10(request);
|
|
4700
5015
|
const { key, datasourceId } = request.params;
|
|
4701
5016
|
try {
|
|
4702
|
-
const storeLattice = (0,
|
|
5017
|
+
const storeLattice = (0, import_core23.getStoreLattice)("default", "metrics");
|
|
4703
5018
|
const store = storeLattice.store;
|
|
4704
5019
|
const config = await store.getConfigByKey(tenantId, key);
|
|
4705
5020
|
if (!config) {
|
|
@@ -4717,7 +5032,7 @@ async function getDatasourceMetrics(request, reply) {
|
|
|
4717
5032
|
};
|
|
4718
5033
|
}
|
|
4719
5034
|
const semanticConfig = config.config;
|
|
4720
|
-
const client = new
|
|
5035
|
+
const client = new import_core23.SemanticMetricsClient(semanticConfig);
|
|
4721
5036
|
const metrics = await client.getDatasourceMetrics(datasourceId);
|
|
4722
5037
|
return {
|
|
4723
5038
|
success: true,
|
|
@@ -4733,11 +5048,11 @@ async function getDatasourceMetrics(request, reply) {
|
|
|
4733
5048
|
}
|
|
4734
5049
|
}
|
|
4735
5050
|
async function querySemanticMetrics(request, reply) {
|
|
4736
|
-
const tenantId =
|
|
5051
|
+
const tenantId = getTenantId10(request);
|
|
4737
5052
|
const { key } = request.params;
|
|
4738
5053
|
const body = request.body;
|
|
4739
5054
|
try {
|
|
4740
|
-
const storeLattice = (0,
|
|
5055
|
+
const storeLattice = (0, import_core23.getStoreLattice)("default", "metrics");
|
|
4741
5056
|
const store = storeLattice.store;
|
|
4742
5057
|
const config = await store.getConfigByKey(tenantId, key);
|
|
4743
5058
|
if (!config) {
|
|
@@ -4762,7 +5077,7 @@ async function querySemanticMetrics(request, reply) {
|
|
|
4762
5077
|
};
|
|
4763
5078
|
}
|
|
4764
5079
|
const semanticConfig = config.config;
|
|
4765
|
-
const client = new
|
|
5080
|
+
const client = new import_core23.SemanticMetricsClient(semanticConfig);
|
|
4766
5081
|
const result = await client.semanticQuery(body);
|
|
4767
5082
|
const columnNames = result.columns.map((col) => col.name);
|
|
4768
5083
|
const allDataPoints = [];
|
|
@@ -4822,7 +5137,7 @@ async function testSemanticDataSources(request, reply) {
|
|
|
4822
5137
|
password: body.password,
|
|
4823
5138
|
headers: body.headers
|
|
4824
5139
|
};
|
|
4825
|
-
const client = new
|
|
5140
|
+
const client = new import_core23.SemanticMetricsClient(testConfig);
|
|
4826
5141
|
const datasources = await client.getDataSources();
|
|
4827
5142
|
return {
|
|
4828
5143
|
success: true,
|
|
@@ -4858,7 +5173,7 @@ async function testDatasourceMetrics(request, reply) {
|
|
|
4858
5173
|
password: body.password,
|
|
4859
5174
|
headers: body.headers
|
|
4860
5175
|
};
|
|
4861
|
-
const client = new
|
|
5176
|
+
const client = new import_core23.SemanticMetricsClient(testConfig);
|
|
4862
5177
|
const metrics = await client.getDatasourceMetrics(datasourceId);
|
|
4863
5178
|
return {
|
|
4864
5179
|
success: true,
|
|
@@ -4890,9 +5205,9 @@ function registerMetricsServerConfigRoutes(app2) {
|
|
|
4890
5205
|
}
|
|
4891
5206
|
|
|
4892
5207
|
// src/controllers/mcp-configs.ts
|
|
4893
|
-
var
|
|
4894
|
-
var
|
|
4895
|
-
function
|
|
5208
|
+
var import_core24 = require("@axiom-lattice/core");
|
|
5209
|
+
var import_crypto6 = require("crypto");
|
|
5210
|
+
function getTenantId11(request) {
|
|
4896
5211
|
const userTenantId = request.user?.tenantId;
|
|
4897
5212
|
if (userTenantId) {
|
|
4898
5213
|
return userTenantId;
|
|
@@ -4900,9 +5215,9 @@ function getTenantId9(request) {
|
|
|
4900
5215
|
return request.headers["x-tenant-id"] || "default";
|
|
4901
5216
|
}
|
|
4902
5217
|
async function getMcpServerConfigList(request, reply) {
|
|
4903
|
-
const tenantId =
|
|
5218
|
+
const tenantId = getTenantId11(request);
|
|
4904
5219
|
try {
|
|
4905
|
-
const storeLattice = (0,
|
|
5220
|
+
const storeLattice = (0, import_core24.getStoreLattice)("default", "mcp");
|
|
4906
5221
|
const store = storeLattice.store;
|
|
4907
5222
|
const configs = await store.getAllConfigs(tenantId);
|
|
4908
5223
|
return {
|
|
@@ -4926,10 +5241,10 @@ async function getMcpServerConfigList(request, reply) {
|
|
|
4926
5241
|
}
|
|
4927
5242
|
}
|
|
4928
5243
|
async function getMcpServerConfig(request, reply) {
|
|
4929
|
-
const tenantId =
|
|
5244
|
+
const tenantId = getTenantId11(request);
|
|
4930
5245
|
const { key } = request.params;
|
|
4931
5246
|
try {
|
|
4932
|
-
const storeLattice = (0,
|
|
5247
|
+
const storeLattice = (0, import_core24.getStoreLattice)("default", "mcp");
|
|
4933
5248
|
const store = storeLattice.store;
|
|
4934
5249
|
const config = await store.getConfigByKey(tenantId, key);
|
|
4935
5250
|
if (!config) {
|
|
@@ -4952,10 +5267,10 @@ async function getMcpServerConfig(request, reply) {
|
|
|
4952
5267
|
}
|
|
4953
5268
|
}
|
|
4954
5269
|
async function createMcpServerConfig(request, reply) {
|
|
4955
|
-
const tenantId =
|
|
5270
|
+
const tenantId = getTenantId11(request);
|
|
4956
5271
|
const body = request.body;
|
|
4957
5272
|
try {
|
|
4958
|
-
const storeLattice = (0,
|
|
5273
|
+
const storeLattice = (0, import_core24.getStoreLattice)("default", "mcp");
|
|
4959
5274
|
const store = storeLattice.store;
|
|
4960
5275
|
const existing = await store.getConfigByKey(tenantId, body.key);
|
|
4961
5276
|
if (existing) {
|
|
@@ -4965,7 +5280,7 @@ async function createMcpServerConfig(request, reply) {
|
|
|
4965
5280
|
message: "MCP server configuration with this key already exists"
|
|
4966
5281
|
};
|
|
4967
5282
|
}
|
|
4968
|
-
const id = body.id || (0,
|
|
5283
|
+
const id = body.id || (0, import_crypto6.randomUUID)();
|
|
4969
5284
|
const config = await store.createConfig(tenantId, id, body);
|
|
4970
5285
|
try {
|
|
4971
5286
|
await connectAndRegisterTools(config);
|
|
@@ -4991,11 +5306,11 @@ async function createMcpServerConfig(request, reply) {
|
|
|
4991
5306
|
}
|
|
4992
5307
|
}
|
|
4993
5308
|
async function updateMcpServerConfig(request, reply) {
|
|
4994
|
-
const tenantId =
|
|
5309
|
+
const tenantId = getTenantId11(request);
|
|
4995
5310
|
const { key } = request.params;
|
|
4996
5311
|
const updates = request.body;
|
|
4997
5312
|
try {
|
|
4998
|
-
const storeLattice = (0,
|
|
5313
|
+
const storeLattice = (0, import_core24.getStoreLattice)("default", "mcp");
|
|
4999
5314
|
const store = storeLattice.store;
|
|
5000
5315
|
const existing = await store.getConfigByKey(tenantId, key);
|
|
5001
5316
|
if (!existing) {
|
|
@@ -5015,8 +5330,8 @@ async function updateMcpServerConfig(request, reply) {
|
|
|
5015
5330
|
}
|
|
5016
5331
|
if (shouldReconnect) {
|
|
5017
5332
|
try {
|
|
5018
|
-
if (
|
|
5019
|
-
await
|
|
5333
|
+
if (import_core24.mcpManager.hasServer(key)) {
|
|
5334
|
+
await import_core24.mcpManager.removeServer(key);
|
|
5020
5335
|
}
|
|
5021
5336
|
await connectAndRegisterTools(updated);
|
|
5022
5337
|
await store.updateConfig(tenantId, existing.id, { status: "connected" });
|
|
@@ -5041,10 +5356,10 @@ async function updateMcpServerConfig(request, reply) {
|
|
|
5041
5356
|
}
|
|
5042
5357
|
}
|
|
5043
5358
|
async function deleteMcpServerConfig(request, reply) {
|
|
5044
|
-
const tenantId =
|
|
5359
|
+
const tenantId = getTenantId11(request);
|
|
5045
5360
|
const { keyOrId } = request.params;
|
|
5046
5361
|
try {
|
|
5047
|
-
const storeLattice = (0,
|
|
5362
|
+
const storeLattice = (0, import_core24.getStoreLattice)("default", "mcp");
|
|
5048
5363
|
const store = storeLattice.store;
|
|
5049
5364
|
let config = await store.getConfigByKey(tenantId, keyOrId);
|
|
5050
5365
|
let configKey = keyOrId;
|
|
@@ -5062,8 +5377,8 @@ async function deleteMcpServerConfig(request, reply) {
|
|
|
5062
5377
|
};
|
|
5063
5378
|
}
|
|
5064
5379
|
try {
|
|
5065
|
-
if (
|
|
5066
|
-
await
|
|
5380
|
+
if (import_core24.mcpManager.hasServer(configKey)) {
|
|
5381
|
+
await import_core24.mcpManager.removeServer(configKey);
|
|
5067
5382
|
}
|
|
5068
5383
|
} catch (error) {
|
|
5069
5384
|
console.warn("Failed to remove from MCP manager:", error);
|
|
@@ -5088,10 +5403,10 @@ async function deleteMcpServerConfig(request, reply) {
|
|
|
5088
5403
|
}
|
|
5089
5404
|
}
|
|
5090
5405
|
async function testMcpServerConnection(request, reply) {
|
|
5091
|
-
const tenantId =
|
|
5406
|
+
const tenantId = getTenantId11(request);
|
|
5092
5407
|
const { key } = request.params;
|
|
5093
5408
|
try {
|
|
5094
|
-
const storeLattice = (0,
|
|
5409
|
+
const storeLattice = (0, import_core24.getStoreLattice)("default", "mcp");
|
|
5095
5410
|
const store = storeLattice.store;
|
|
5096
5411
|
const config = await store.getConfigByKey(tenantId, key);
|
|
5097
5412
|
if (!config) {
|
|
@@ -5105,11 +5420,11 @@ async function testMcpServerConnection(request, reply) {
|
|
|
5105
5420
|
try {
|
|
5106
5421
|
const testKey = `__test_${key}_${Date.now()}`;
|
|
5107
5422
|
const connection = convertToConnection(config.config);
|
|
5108
|
-
|
|
5109
|
-
await
|
|
5110
|
-
const tools = await
|
|
5423
|
+
import_core24.mcpManager.addServer(testKey, connection);
|
|
5424
|
+
await import_core24.mcpManager.connect();
|
|
5425
|
+
const tools = await import_core24.mcpManager.getAllTools();
|
|
5111
5426
|
const latency = Date.now() - startTime;
|
|
5112
|
-
await
|
|
5427
|
+
await import_core24.mcpManager.removeServer(testKey);
|
|
5113
5428
|
return {
|
|
5114
5429
|
success: true,
|
|
5115
5430
|
message: "Connection test successful",
|
|
@@ -5141,10 +5456,10 @@ async function testMcpServerConnection(request, reply) {
|
|
|
5141
5456
|
}
|
|
5142
5457
|
}
|
|
5143
5458
|
async function listMcpServerTools(request, reply) {
|
|
5144
|
-
const tenantId =
|
|
5459
|
+
const tenantId = getTenantId11(request);
|
|
5145
5460
|
const { key } = request.params;
|
|
5146
5461
|
try {
|
|
5147
|
-
const storeLattice = (0,
|
|
5462
|
+
const storeLattice = (0, import_core24.getStoreLattice)("default", "mcp");
|
|
5148
5463
|
const store = storeLattice.store;
|
|
5149
5464
|
const config = await store.getConfigByKey(tenantId, key);
|
|
5150
5465
|
if (!config) {
|
|
@@ -5154,10 +5469,10 @@ async function listMcpServerTools(request, reply) {
|
|
|
5154
5469
|
message: "MCP server configuration not found"
|
|
5155
5470
|
};
|
|
5156
5471
|
}
|
|
5157
|
-
if (!
|
|
5472
|
+
if (!import_core24.mcpManager.hasServer(key)) {
|
|
5158
5473
|
await connectAndRegisterTools(config);
|
|
5159
5474
|
}
|
|
5160
|
-
const tools = await
|
|
5475
|
+
const tools = await import_core24.mcpManager.getAllTools();
|
|
5161
5476
|
return {
|
|
5162
5477
|
success: true,
|
|
5163
5478
|
message: "Tools retrieved successfully",
|
|
@@ -5174,10 +5489,10 @@ async function listMcpServerTools(request, reply) {
|
|
|
5174
5489
|
}
|
|
5175
5490
|
}
|
|
5176
5491
|
async function connectMcpServer(request, reply) {
|
|
5177
|
-
const tenantId =
|
|
5492
|
+
const tenantId = getTenantId11(request);
|
|
5178
5493
|
const { key } = request.params;
|
|
5179
5494
|
try {
|
|
5180
|
-
const storeLattice = (0,
|
|
5495
|
+
const storeLattice = (0, import_core24.getStoreLattice)("default", "mcp");
|
|
5181
5496
|
const store = storeLattice.store;
|
|
5182
5497
|
const config = await store.getConfigByKey(tenantId, key);
|
|
5183
5498
|
if (!config) {
|
|
@@ -5198,7 +5513,7 @@ async function connectMcpServer(request, reply) {
|
|
|
5198
5513
|
};
|
|
5199
5514
|
} catch (error) {
|
|
5200
5515
|
console.error("Failed to connect MCP server:", error);
|
|
5201
|
-
const storeLattice = (0,
|
|
5516
|
+
const storeLattice = (0, import_core24.getStoreLattice)("default", "mcp");
|
|
5202
5517
|
const store = storeLattice.store;
|
|
5203
5518
|
const config = await store.getConfigByKey(tenantId, key);
|
|
5204
5519
|
if (config) {
|
|
@@ -5211,10 +5526,10 @@ async function connectMcpServer(request, reply) {
|
|
|
5211
5526
|
}
|
|
5212
5527
|
}
|
|
5213
5528
|
async function disconnectMcpServer(request, reply) {
|
|
5214
|
-
const tenantId =
|
|
5529
|
+
const tenantId = getTenantId11(request);
|
|
5215
5530
|
const { key } = request.params;
|
|
5216
5531
|
try {
|
|
5217
|
-
const storeLattice = (0,
|
|
5532
|
+
const storeLattice = (0, import_core24.getStoreLattice)("default", "mcp");
|
|
5218
5533
|
const store = storeLattice.store;
|
|
5219
5534
|
const config = await store.getConfigByKey(tenantId, key);
|
|
5220
5535
|
if (!config) {
|
|
@@ -5224,8 +5539,8 @@ async function disconnectMcpServer(request, reply) {
|
|
|
5224
5539
|
message: "MCP server configuration not found"
|
|
5225
5540
|
};
|
|
5226
5541
|
}
|
|
5227
|
-
if (
|
|
5228
|
-
await
|
|
5542
|
+
if (import_core24.mcpManager.hasServer(key)) {
|
|
5543
|
+
await import_core24.mcpManager.removeServer(key);
|
|
5229
5544
|
}
|
|
5230
5545
|
const updated = await store.updateConfig(tenantId, config.id, {
|
|
5231
5546
|
status: "disconnected"
|
|
@@ -5255,10 +5570,10 @@ async function testMcpServerTools(request, reply) {
|
|
|
5255
5570
|
}
|
|
5256
5571
|
const testKey = `__test_${Date.now()}`;
|
|
5257
5572
|
const connection = convertToConnection(body.config);
|
|
5258
|
-
|
|
5259
|
-
await
|
|
5260
|
-
const tools = await
|
|
5261
|
-
await
|
|
5573
|
+
import_core24.mcpManager.addServer(testKey, connection);
|
|
5574
|
+
await import_core24.mcpManager.connect();
|
|
5575
|
+
const tools = await import_core24.mcpManager.getAllTools();
|
|
5576
|
+
await import_core24.mcpManager.removeServer(testKey);
|
|
5262
5577
|
return {
|
|
5263
5578
|
success: true,
|
|
5264
5579
|
message: "Tools retrieved successfully",
|
|
@@ -5295,14 +5610,14 @@ function convertToConnection(config) {
|
|
|
5295
5610
|
}
|
|
5296
5611
|
async function connectAndRegisterTools(config) {
|
|
5297
5612
|
const connection = convertToConnection(config.config);
|
|
5298
|
-
|
|
5299
|
-
await
|
|
5300
|
-
const allTools = await
|
|
5613
|
+
import_core24.mcpManager.addServer(config.key, connection);
|
|
5614
|
+
await import_core24.mcpManager.connect();
|
|
5615
|
+
const allTools = await import_core24.mcpManager.getAllTools();
|
|
5301
5616
|
const selectedTools = allTools.filter(
|
|
5302
5617
|
(tool) => config.selectedTools.includes(tool.name)
|
|
5303
5618
|
);
|
|
5304
5619
|
for (const tool of selectedTools) {
|
|
5305
|
-
|
|
5620
|
+
import_core24.toolLatticeManager.registerExistingTool(tool.name, tool);
|
|
5306
5621
|
}
|
|
5307
5622
|
}
|
|
5308
5623
|
function registerMcpServerConfigRoutes(app2) {
|
|
@@ -5319,12 +5634,12 @@ function registerMcpServerConfigRoutes(app2) {
|
|
|
5319
5634
|
}
|
|
5320
5635
|
|
|
5321
5636
|
// src/controllers/eval.ts
|
|
5322
|
-
var
|
|
5637
|
+
var import_core26 = require("@axiom-lattice/core");
|
|
5323
5638
|
var import_uuid4 = require("uuid");
|
|
5324
5639
|
|
|
5325
5640
|
// src/services/eval-runner.ts
|
|
5326
5641
|
var import_events = require("events");
|
|
5327
|
-
var
|
|
5642
|
+
var import_core25 = require("@axiom-lattice/core");
|
|
5328
5643
|
var import_agent_eval = require("@axiom-lattice/agent-eval");
|
|
5329
5644
|
var import_uuid3 = require("uuid");
|
|
5330
5645
|
function mapLogs(logs) {
|
|
@@ -5386,7 +5701,7 @@ var EvalRunner = class {
|
|
|
5386
5701
|
if (hasModelKey) {
|
|
5387
5702
|
judgeModelConfig = { modelKey: judgeCfg.modelKey };
|
|
5388
5703
|
} else if (!hasCredentials) {
|
|
5389
|
-
const firstModel =
|
|
5704
|
+
const firstModel = import_core25.modelLatticeManager.getAllLattices()[0];
|
|
5390
5705
|
if (firstModel) {
|
|
5391
5706
|
judgeModelConfig = { modelKey: firstModel.key };
|
|
5392
5707
|
} else {
|
|
@@ -5497,13 +5812,13 @@ var EvalRunner = class {
|
|
|
5497
5812
|
return this.runs.has(runId);
|
|
5498
5813
|
}
|
|
5499
5814
|
getEvalStore() {
|
|
5500
|
-
return (0,
|
|
5815
|
+
return (0, import_core25.getStoreLattice)("default", "eval").store;
|
|
5501
5816
|
}
|
|
5502
5817
|
};
|
|
5503
5818
|
var evalRunner = new EvalRunner();
|
|
5504
5819
|
|
|
5505
5820
|
// src/controllers/eval.ts
|
|
5506
|
-
function
|
|
5821
|
+
function getTenantId12(request) {
|
|
5507
5822
|
const userTenantId = request.user?.tenantId;
|
|
5508
5823
|
if (userTenantId) {
|
|
5509
5824
|
return userTenantId;
|
|
@@ -5511,11 +5826,11 @@ function getTenantId10(request) {
|
|
|
5511
5826
|
return request.headers["x-tenant-id"] || "default";
|
|
5512
5827
|
}
|
|
5513
5828
|
function getEvalStore() {
|
|
5514
|
-
return (0,
|
|
5829
|
+
return (0, import_core26.getStoreLattice)("default", "eval").store;
|
|
5515
5830
|
}
|
|
5516
5831
|
async function createProject(request, reply) {
|
|
5517
5832
|
try {
|
|
5518
|
-
const tenantId =
|
|
5833
|
+
const tenantId = getTenantId12(request);
|
|
5519
5834
|
const store = getEvalStore();
|
|
5520
5835
|
const id = (0, import_uuid4.v4)();
|
|
5521
5836
|
const data = request.body;
|
|
@@ -5540,7 +5855,7 @@ async function createProject(request, reply) {
|
|
|
5540
5855
|
}
|
|
5541
5856
|
async function listProjects(request, reply) {
|
|
5542
5857
|
try {
|
|
5543
|
-
const tenantId =
|
|
5858
|
+
const tenantId = getTenantId12(request);
|
|
5544
5859
|
const store = getEvalStore();
|
|
5545
5860
|
let projects = await store.getProjectsByTenant(tenantId);
|
|
5546
5861
|
if (projects.length === 0) {
|
|
@@ -5574,7 +5889,7 @@ async function listProjects(request, reply) {
|
|
|
5574
5889
|
}
|
|
5575
5890
|
async function getProject(request, reply) {
|
|
5576
5891
|
try {
|
|
5577
|
-
const tenantId =
|
|
5892
|
+
const tenantId = getTenantId12(request);
|
|
5578
5893
|
const store = getEvalStore();
|
|
5579
5894
|
const { pid } = request.params;
|
|
5580
5895
|
const project = await store.getProjectById(tenantId, pid);
|
|
@@ -5594,7 +5909,7 @@ async function getProject(request, reply) {
|
|
|
5594
5909
|
}
|
|
5595
5910
|
async function updateProject(request, reply) {
|
|
5596
5911
|
try {
|
|
5597
|
-
const tenantId =
|
|
5912
|
+
const tenantId = getTenantId12(request);
|
|
5598
5913
|
const store = getEvalStore();
|
|
5599
5914
|
const { pid } = request.params;
|
|
5600
5915
|
const existing = await store.getProjectById(tenantId, pid);
|
|
@@ -5614,7 +5929,7 @@ async function updateProject(request, reply) {
|
|
|
5614
5929
|
}
|
|
5615
5930
|
async function deleteProject(request, reply) {
|
|
5616
5931
|
try {
|
|
5617
|
-
const tenantId =
|
|
5932
|
+
const tenantId = getTenantId12(request);
|
|
5618
5933
|
const store = getEvalStore();
|
|
5619
5934
|
const { pid } = request.params;
|
|
5620
5935
|
const existing = await store.getProjectById(tenantId, pid);
|
|
@@ -5633,7 +5948,7 @@ async function deleteProject(request, reply) {
|
|
|
5633
5948
|
}
|
|
5634
5949
|
async function createSuite(request, reply) {
|
|
5635
5950
|
try {
|
|
5636
|
-
const tenantId =
|
|
5951
|
+
const tenantId = getTenantId12(request);
|
|
5637
5952
|
const store = getEvalStore();
|
|
5638
5953
|
const { pid } = request.params;
|
|
5639
5954
|
const project = await store.getProjectById(tenantId, pid);
|
|
@@ -5655,7 +5970,7 @@ async function createSuite(request, reply) {
|
|
|
5655
5970
|
}
|
|
5656
5971
|
async function updateSuite(request, reply) {
|
|
5657
5972
|
try {
|
|
5658
|
-
const tenantId =
|
|
5973
|
+
const tenantId = getTenantId12(request);
|
|
5659
5974
|
const store = getEvalStore();
|
|
5660
5975
|
const { sid } = request.params;
|
|
5661
5976
|
const existing = await store.getSuiteById(tenantId, sid);
|
|
@@ -5675,7 +5990,7 @@ async function updateSuite(request, reply) {
|
|
|
5675
5990
|
}
|
|
5676
5991
|
async function deleteSuite(request, reply) {
|
|
5677
5992
|
try {
|
|
5678
|
-
const tenantId =
|
|
5993
|
+
const tenantId = getTenantId12(request);
|
|
5679
5994
|
const store = getEvalStore();
|
|
5680
5995
|
const { sid } = request.params;
|
|
5681
5996
|
const existing = await store.getSuiteById(tenantId, sid);
|
|
@@ -5694,7 +6009,7 @@ async function deleteSuite(request, reply) {
|
|
|
5694
6009
|
}
|
|
5695
6010
|
async function createCase(request, reply) {
|
|
5696
6011
|
try {
|
|
5697
|
-
const tenantId =
|
|
6012
|
+
const tenantId = getTenantId12(request);
|
|
5698
6013
|
const store = getEvalStore();
|
|
5699
6014
|
const { sid } = request.params;
|
|
5700
6015
|
const suite = await store.getSuiteById(tenantId, sid);
|
|
@@ -5723,7 +6038,7 @@ async function createCase(request, reply) {
|
|
|
5723
6038
|
}
|
|
5724
6039
|
async function listCasesForSuite(request, reply) {
|
|
5725
6040
|
try {
|
|
5726
|
-
const tenantId =
|
|
6041
|
+
const tenantId = getTenantId12(request);
|
|
5727
6042
|
const store = getEvalStore();
|
|
5728
6043
|
const { sid } = request.params;
|
|
5729
6044
|
const cases = await store.getCasesBySuite(tenantId, sid);
|
|
@@ -5739,7 +6054,7 @@ async function listCasesForSuite(request, reply) {
|
|
|
5739
6054
|
}
|
|
5740
6055
|
async function updateCase(request, reply) {
|
|
5741
6056
|
try {
|
|
5742
|
-
const tenantId =
|
|
6057
|
+
const tenantId = getTenantId12(request);
|
|
5743
6058
|
const store = getEvalStore();
|
|
5744
6059
|
const { cid } = request.params;
|
|
5745
6060
|
const existing = await store.getCaseById(tenantId, cid);
|
|
@@ -5759,7 +6074,7 @@ async function updateCase(request, reply) {
|
|
|
5759
6074
|
}
|
|
5760
6075
|
async function deleteCase(request, reply) {
|
|
5761
6076
|
try {
|
|
5762
|
-
const tenantId =
|
|
6077
|
+
const tenantId = getTenantId12(request);
|
|
5763
6078
|
const store = getEvalStore();
|
|
5764
6079
|
const { cid } = request.params;
|
|
5765
6080
|
const existing = await store.getCaseById(tenantId, cid);
|
|
@@ -5791,7 +6106,7 @@ function registerEvalRoutes(app2) {
|
|
|
5791
6106
|
app2.delete("/api/eval/projects/:pid/suites/:sid/cases/:cid", deleteCase);
|
|
5792
6107
|
app2.post("/api/eval/projects/:pid/runs", async (request, reply) => {
|
|
5793
6108
|
try {
|
|
5794
|
-
const tenantId =
|
|
6109
|
+
const tenantId = getTenantId12(request);
|
|
5795
6110
|
const { pid } = request.params;
|
|
5796
6111
|
const runId = await evalRunner.startRun(tenantId, pid);
|
|
5797
6112
|
reply.status(202).send({ success: true, message: "Run started", data: { run_id: runId } });
|
|
@@ -5803,7 +6118,7 @@ function registerEvalRoutes(app2) {
|
|
|
5803
6118
|
});
|
|
5804
6119
|
app2.get("/api/eval/runs", async (request, reply) => {
|
|
5805
6120
|
try {
|
|
5806
|
-
const tenantId =
|
|
6121
|
+
const tenantId = getTenantId12(request);
|
|
5807
6122
|
const query = request.query;
|
|
5808
6123
|
const runs = await getEvalStore().getRunsByTenant(tenantId, { projectId: query.project_id, status: query.status });
|
|
5809
6124
|
reply.send({ success: true, message: "Ok", data: { records: runs, total: runs.length } });
|
|
@@ -5813,7 +6128,7 @@ function registerEvalRoutes(app2) {
|
|
|
5813
6128
|
});
|
|
5814
6129
|
app2.get("/api/eval/runs/:rid", async (request, reply) => {
|
|
5815
6130
|
try {
|
|
5816
|
-
const tenantId =
|
|
6131
|
+
const tenantId = getTenantId12(request);
|
|
5817
6132
|
const { rid } = request.params;
|
|
5818
6133
|
const run = await getEvalStore().getRunById(tenantId, rid);
|
|
5819
6134
|
if (!run) return reply.status(404).send({ success: false, message: "Run not found" });
|
|
@@ -5835,7 +6150,7 @@ function registerEvalRoutes(app2) {
|
|
|
5835
6150
|
const emitter = evalRunner.getEventEmitter();
|
|
5836
6151
|
const eventKey = `run:${rid}`;
|
|
5837
6152
|
if (!evalRunner.isRunning(rid)) {
|
|
5838
|
-
const tenantId =
|
|
6153
|
+
const tenantId = getTenantId12(request);
|
|
5839
6154
|
const run = await getEvalStore().getRunById(tenantId, rid);
|
|
5840
6155
|
if (run) {
|
|
5841
6156
|
const eventType = run.status === "completed" ? "completed" : "error";
|
|
@@ -5874,7 +6189,7 @@ data: ${JSON.stringify(event.data)}
|
|
|
5874
6189
|
});
|
|
5875
6190
|
app2.delete("/api/eval/runs/:rid", async (request, reply) => {
|
|
5876
6191
|
try {
|
|
5877
|
-
const tenantId =
|
|
6192
|
+
const tenantId = getTenantId12(request);
|
|
5878
6193
|
const { rid } = request.params;
|
|
5879
6194
|
const deleted = await getEvalStore().deleteRun(tenantId, rid);
|
|
5880
6195
|
if (!deleted) return reply.status(404).send({ success: false, message: "Run not found" });
|
|
@@ -5885,7 +6200,7 @@ data: ${JSON.stringify(event.data)}
|
|
|
5885
6200
|
});
|
|
5886
6201
|
app2.get("/api/eval/reports/projects/:pid", async (request, reply) => {
|
|
5887
6202
|
try {
|
|
5888
|
-
const tenantId =
|
|
6203
|
+
const tenantId = getTenantId12(request);
|
|
5889
6204
|
const { pid } = request.params;
|
|
5890
6205
|
const report = await getEvalStore().getProjectReport(tenantId, pid);
|
|
5891
6206
|
if (!report) return reply.status(404).send({ success: false, message: "Project not found" });
|
|
@@ -5897,11 +6212,11 @@ data: ${JSON.stringify(event.data)}
|
|
|
5897
6212
|
}
|
|
5898
6213
|
|
|
5899
6214
|
// src/controllers/users.ts
|
|
5900
|
-
var
|
|
6215
|
+
var import_core27 = require("@axiom-lattice/core");
|
|
5901
6216
|
var import_uuid5 = require("uuid");
|
|
5902
6217
|
var UsersController = class {
|
|
5903
6218
|
constructor() {
|
|
5904
|
-
this.userStore = (0,
|
|
6219
|
+
this.userStore = (0, import_core27.getStoreLattice)("default", "user").store;
|
|
5905
6220
|
}
|
|
5906
6221
|
async listUsers(request, reply) {
|
|
5907
6222
|
const { email } = request.query;
|
|
@@ -5979,11 +6294,11 @@ function registerUserRoutes(app2) {
|
|
|
5979
6294
|
}
|
|
5980
6295
|
|
|
5981
6296
|
// src/controllers/tenants.ts
|
|
5982
|
-
var
|
|
6297
|
+
var import_core28 = require("@axiom-lattice/core");
|
|
5983
6298
|
var import_uuid6 = require("uuid");
|
|
5984
6299
|
var TenantsController = class {
|
|
5985
6300
|
constructor() {
|
|
5986
|
-
this.tenantStore = (0,
|
|
6301
|
+
this.tenantStore = (0, import_core28.getStoreLattice)("default", "tenant").store;
|
|
5987
6302
|
}
|
|
5988
6303
|
// ==================== Tenant CRUD ====================
|
|
5989
6304
|
async listTenants(request, reply) {
|
|
@@ -6047,7 +6362,7 @@ function registerTenantRoutes(app2) {
|
|
|
6047
6362
|
}
|
|
6048
6363
|
|
|
6049
6364
|
// src/controllers/auth.ts
|
|
6050
|
-
var
|
|
6365
|
+
var import_core29 = require("@axiom-lattice/core");
|
|
6051
6366
|
var import_uuid7 = require("uuid");
|
|
6052
6367
|
var defaultAuthConfig = {
|
|
6053
6368
|
autoApproveUsers: true,
|
|
@@ -6056,9 +6371,9 @@ var defaultAuthConfig = {
|
|
|
6056
6371
|
};
|
|
6057
6372
|
var AuthController = class {
|
|
6058
6373
|
constructor(config = {}) {
|
|
6059
|
-
this.userStore = (0,
|
|
6060
|
-
this.tenantStore = (0,
|
|
6061
|
-
this.userTenantLinkStore = (0,
|
|
6374
|
+
this.userStore = (0, import_core29.getStoreLattice)("default", "user").store;
|
|
6375
|
+
this.tenantStore = (0, import_core29.getStoreLattice)("default", "tenant").store;
|
|
6376
|
+
this.userTenantLinkStore = (0, import_core29.getStoreLattice)("default", "userTenantLink").store;
|
|
6062
6377
|
this.config = { ...defaultAuthConfig, ...config };
|
|
6063
6378
|
}
|
|
6064
6379
|
async register(request, reply) {
|
|
@@ -6212,6 +6527,8 @@ var AuthController = class {
|
|
|
6212
6527
|
});
|
|
6213
6528
|
}
|
|
6214
6529
|
const token = await this.generateToken(userId, tenantId);
|
|
6530
|
+
const link = await this.userTenantLinkStore.getLink(userId, tenantId);
|
|
6531
|
+
const linkMeta = link?.metadata || {};
|
|
6215
6532
|
return {
|
|
6216
6533
|
success: true,
|
|
6217
6534
|
data: {
|
|
@@ -6220,7 +6537,12 @@ var AuthController = class {
|
|
|
6220
6537
|
name: tenant.name,
|
|
6221
6538
|
status: tenant.status
|
|
6222
6539
|
},
|
|
6223
|
-
token
|
|
6540
|
+
token,
|
|
6541
|
+
personalAssistant: linkMeta.personalAssistantId ? {
|
|
6542
|
+
assistantId: linkMeta.personalAssistantId,
|
|
6543
|
+
projectId: linkMeta.personalProjectId || "default",
|
|
6544
|
+
workspaceId: linkMeta.personalWorkspaceId || "default"
|
|
6545
|
+
} : null
|
|
6224
6546
|
}
|
|
6225
6547
|
};
|
|
6226
6548
|
} catch (error) {
|
|
@@ -6466,82 +6788,6 @@ function normalizeChatType(chatType) {
|
|
|
6466
6788
|
return chatType === "p2p" ? "direct" : "group";
|
|
6467
6789
|
}
|
|
6468
6790
|
|
|
6469
|
-
// src/channels/lark/LarkChannelAdapter.ts
|
|
6470
|
-
var larkConfigSchema = import_zod.z.object({
|
|
6471
|
-
appId: import_zod.z.string(),
|
|
6472
|
-
appSecret: import_zod.z.string(),
|
|
6473
|
-
verificationToken: import_zod.z.string().optional(),
|
|
6474
|
-
encryptKey: import_zod.z.string().optional()
|
|
6475
|
-
});
|
|
6476
|
-
var larkChannelAdapter = {
|
|
6477
|
-
channel: "lark",
|
|
6478
|
-
configSchema: larkConfigSchema,
|
|
6479
|
-
async receive(rawPayload, installation) {
|
|
6480
|
-
const event = parseLarkMessageEvent(rawPayload);
|
|
6481
|
-
if (!event) return null;
|
|
6482
|
-
return {
|
|
6483
|
-
channel: "lark",
|
|
6484
|
-
channelInstallationId: installation.id,
|
|
6485
|
-
tenantId: installation.tenantId,
|
|
6486
|
-
sender: {
|
|
6487
|
-
id: event.openId,
|
|
6488
|
-
displayName: void 0
|
|
6489
|
-
},
|
|
6490
|
-
content: {
|
|
6491
|
-
text: event.text,
|
|
6492
|
-
metadata: {
|
|
6493
|
-
chatId: event.chatId,
|
|
6494
|
-
chatType: event.chatType,
|
|
6495
|
-
messageId: event.messageId
|
|
6496
|
-
}
|
|
6497
|
-
},
|
|
6498
|
-
conversation: {
|
|
6499
|
-
id: event.chatId,
|
|
6500
|
-
type: event.chatType
|
|
6501
|
-
},
|
|
6502
|
-
replyTarget: {
|
|
6503
|
-
adapterChannel: "lark",
|
|
6504
|
-
channelInstallationId: installation.id,
|
|
6505
|
-
rawTarget: {
|
|
6506
|
-
chatId: event.chatId,
|
|
6507
|
-
messageId: event.messageId,
|
|
6508
|
-
chatType: event.chatType
|
|
6509
|
-
}
|
|
6510
|
-
}
|
|
6511
|
-
};
|
|
6512
|
-
},
|
|
6513
|
-
async sendReply(replyTarget, message, installation) {
|
|
6514
|
-
const { createLarkSender: createLarkSender2 } = await Promise.resolve().then(() => (init_sender(), sender_exports));
|
|
6515
|
-
const sender = await createLarkSender2(installation.config);
|
|
6516
|
-
await sender.sendTextReply({
|
|
6517
|
-
chatId: replyTarget.rawTarget.chatId,
|
|
6518
|
-
text: message.text
|
|
6519
|
-
});
|
|
6520
|
-
}
|
|
6521
|
-
};
|
|
6522
|
-
|
|
6523
|
-
// src/channels/lark/verification.ts
|
|
6524
|
-
var import_crypto6 = __toESM(require("crypto"));
|
|
6525
|
-
function parseLarkRequestBody(body, encryptKey) {
|
|
6526
|
-
const parsed = body || {};
|
|
6527
|
-
if (encryptKey && typeof parsed.encrypt === "string") {
|
|
6528
|
-
return decryptLarkPayload(encryptKey, parsed.encrypt);
|
|
6529
|
-
}
|
|
6530
|
-
return parsed;
|
|
6531
|
-
}
|
|
6532
|
-
function decryptLarkPayload(encryptKey, encryptedPayload) {
|
|
6533
|
-
const key = import_crypto6.default.createHash("sha256").update(encryptKey).digest();
|
|
6534
|
-
const buffer = Buffer.from(encryptedPayload, "base64");
|
|
6535
|
-
const iv = buffer.subarray(0, 16);
|
|
6536
|
-
const ciphertext = buffer.subarray(16);
|
|
6537
|
-
const decipher = import_crypto6.default.createDecipheriv("aes-256-cbc", key, iv);
|
|
6538
|
-
const plaintext = Buffer.concat([
|
|
6539
|
-
decipher.update(ciphertext),
|
|
6540
|
-
decipher.final()
|
|
6541
|
-
]).toString("utf8");
|
|
6542
|
-
return JSON.parse(plaintext);
|
|
6543
|
-
}
|
|
6544
|
-
|
|
6545
6791
|
// src/logger/Logger.ts
|
|
6546
6792
|
var import_pino = __toESM(require("pino"));
|
|
6547
6793
|
var import_pino_pretty = require("pino-pretty");
|
|
@@ -6680,8 +6926,165 @@ var Logger = class _Logger {
|
|
|
6680
6926
|
}
|
|
6681
6927
|
};
|
|
6682
6928
|
|
|
6683
|
-
// src/channels/lark/
|
|
6929
|
+
// src/channels/lark/LarkChannelAdapter.ts
|
|
6930
|
+
var Lark = __toESM(require("@larksuiteoapi/node-sdk"));
|
|
6684
6931
|
var logger = new Logger({ serviceName: "lattice/gateway/lark" });
|
|
6932
|
+
var activeConnections = /* @__PURE__ */ new Map();
|
|
6933
|
+
function parseTextContent(content) {
|
|
6934
|
+
if (!content) return null;
|
|
6935
|
+
try {
|
|
6936
|
+
const parsed = JSON.parse(content);
|
|
6937
|
+
return typeof parsed.text === "string" ? parsed.text : null;
|
|
6938
|
+
} catch {
|
|
6939
|
+
return null;
|
|
6940
|
+
}
|
|
6941
|
+
}
|
|
6942
|
+
function normalizeChatType2(chatType) {
|
|
6943
|
+
return chatType === "p2p" ? "direct" : "group";
|
|
6944
|
+
}
|
|
6945
|
+
function wsEventToInbound(event, installationId, tenantId) {
|
|
6946
|
+
const messageId = event.message?.message_id;
|
|
6947
|
+
const chatId = event.message?.chat_id;
|
|
6948
|
+
const openId = event.sender?.sender_id?.open_id;
|
|
6949
|
+
if (!messageId || !chatId || !openId) return null;
|
|
6950
|
+
if (event.message?.message_type !== "text") return null;
|
|
6951
|
+
const text = parseTextContent(event.message.content);
|
|
6952
|
+
if (!text) return null;
|
|
6953
|
+
const chatType = normalizeChatType2(event.message.chat_type);
|
|
6954
|
+
return {
|
|
6955
|
+
channel: "lark",
|
|
6956
|
+
channelInstallationId: installationId,
|
|
6957
|
+
tenantId,
|
|
6958
|
+
sender: { id: openId, displayName: void 0 },
|
|
6959
|
+
content: { text, metadata: { chatId, chatType, messageId } },
|
|
6960
|
+
conversation: { id: chatId, type: chatType },
|
|
6961
|
+
replyTarget: {
|
|
6962
|
+
adapterChannel: "lark",
|
|
6963
|
+
channelInstallationId: installationId,
|
|
6964
|
+
rawTarget: { chatId, messageId, chatType }
|
|
6965
|
+
}
|
|
6966
|
+
};
|
|
6967
|
+
}
|
|
6968
|
+
var larkConfigSchema = import_zod.z.object({
|
|
6969
|
+
appId: import_zod.z.string(),
|
|
6970
|
+
appSecret: import_zod.z.string(),
|
|
6971
|
+
verificationToken: import_zod.z.string().optional(),
|
|
6972
|
+
encryptKey: import_zod.z.string().optional()
|
|
6973
|
+
});
|
|
6974
|
+
var larkChannelAdapter = {
|
|
6975
|
+
channel: "lark",
|
|
6976
|
+
configSchema: larkConfigSchema,
|
|
6977
|
+
async receive(rawPayload, installation) {
|
|
6978
|
+
const event = parseLarkMessageEvent(rawPayload);
|
|
6979
|
+
if (!event) return null;
|
|
6980
|
+
return {
|
|
6981
|
+
channel: "lark",
|
|
6982
|
+
channelInstallationId: installation.id,
|
|
6983
|
+
tenantId: installation.tenantId,
|
|
6984
|
+
sender: { id: event.openId, displayName: void 0 },
|
|
6985
|
+
content: {
|
|
6986
|
+
text: event.text,
|
|
6987
|
+
metadata: { chatId: event.chatId, chatType: event.chatType, messageId: event.messageId }
|
|
6988
|
+
},
|
|
6989
|
+
conversation: { id: event.chatId, type: event.chatType },
|
|
6990
|
+
replyTarget: {
|
|
6991
|
+
adapterChannel: "lark",
|
|
6992
|
+
channelInstallationId: installation.id,
|
|
6993
|
+
rawTarget: { chatId: event.chatId, messageId: event.messageId, chatType: event.chatType }
|
|
6994
|
+
}
|
|
6995
|
+
};
|
|
6996
|
+
},
|
|
6997
|
+
async sendReply(replyTarget, message, installation) {
|
|
6998
|
+
const { createLarkSender: createLarkSender2 } = await Promise.resolve().then(() => (init_sender(), sender_exports));
|
|
6999
|
+
const sender = await createLarkSender2(installation.config);
|
|
7000
|
+
await sender.sendTextReply({
|
|
7001
|
+
chatId: replyTarget.rawTarget.chatId,
|
|
7002
|
+
text: message.text
|
|
7003
|
+
});
|
|
7004
|
+
},
|
|
7005
|
+
resolveThreadId(message, binding) {
|
|
7006
|
+
const date = (/* @__PURE__ */ new Date()).toISOString().split("T")[0];
|
|
7007
|
+
const chatType = message.conversation?.type === "direct" ? "dm" : "group";
|
|
7008
|
+
const agentId = binding.agentId;
|
|
7009
|
+
if (chatType === "dm") {
|
|
7010
|
+
return `lark:dm:${message.sender.id}:${agentId}:${date}`;
|
|
7011
|
+
}
|
|
7012
|
+
return `lark:group:${message.conversation?.id ?? "unknown"}:${agentId}:${date}`;
|
|
7013
|
+
},
|
|
7014
|
+
async connect(installation, deps) {
|
|
7015
|
+
const { id: installationId, tenantId, config } = installation;
|
|
7016
|
+
if (!config.appId || !config.appSecret) {
|
|
7017
|
+
logger.warn("Lark installation missing credentials, skipping", { installationId });
|
|
7018
|
+
return;
|
|
7019
|
+
}
|
|
7020
|
+
if (activeConnections.has(installationId)) {
|
|
7021
|
+
logger.warn("Lark WS already connected for installation, skipping", { installationId });
|
|
7022
|
+
return;
|
|
7023
|
+
}
|
|
7024
|
+
logger.info("Lark WS client starting", { installationId, tenantId });
|
|
7025
|
+
const router = deps?.router;
|
|
7026
|
+
const eventDispatcher = new Lark.EventDispatcher({}).register({
|
|
7027
|
+
"im.message.receive_v1": async (data) => {
|
|
7028
|
+
try {
|
|
7029
|
+
const inbound = wsEventToInbound(data, installationId, tenantId);
|
|
7030
|
+
if (!inbound) return;
|
|
7031
|
+
logger.info("Lark WS message received", {
|
|
7032
|
+
installationId,
|
|
7033
|
+
senderId: inbound.sender.id,
|
|
7034
|
+
chatId: data.message?.chat_id
|
|
7035
|
+
});
|
|
7036
|
+
if (router) {
|
|
7037
|
+
const result = await router.dispatch(inbound);
|
|
7038
|
+
if (!result.success) {
|
|
7039
|
+
logger.warn("Lark WS dispatch failed", {
|
|
7040
|
+
installationId,
|
|
7041
|
+
error: result.error?.message
|
|
7042
|
+
});
|
|
7043
|
+
}
|
|
7044
|
+
}
|
|
7045
|
+
} catch (err) {
|
|
7046
|
+
logger.error("Lark WS event handler error", {
|
|
7047
|
+
installationId,
|
|
7048
|
+
error: err instanceof Error ? err.message : String(err)
|
|
7049
|
+
});
|
|
7050
|
+
}
|
|
7051
|
+
}
|
|
7052
|
+
});
|
|
7053
|
+
const client = new Lark.WSClient({
|
|
7054
|
+
appId: config.appId,
|
|
7055
|
+
appSecret: config.appSecret,
|
|
7056
|
+
loggerLevel: Lark.LoggerLevel.info
|
|
7057
|
+
});
|
|
7058
|
+
await client.start({ eventDispatcher });
|
|
7059
|
+
activeConnections.set(installationId, client);
|
|
7060
|
+
logger.info("Lark WS client connected", { installationId });
|
|
7061
|
+
}
|
|
7062
|
+
};
|
|
7063
|
+
|
|
7064
|
+
// src/channels/lark/verification.ts
|
|
7065
|
+
var import_crypto7 = __toESM(require("crypto"));
|
|
7066
|
+
function parseLarkRequestBody(body, encryptKey) {
|
|
7067
|
+
const parsed = body || {};
|
|
7068
|
+
if (encryptKey && typeof parsed.encrypt === "string") {
|
|
7069
|
+
return decryptLarkPayload(encryptKey, parsed.encrypt);
|
|
7070
|
+
}
|
|
7071
|
+
return parsed;
|
|
7072
|
+
}
|
|
7073
|
+
function decryptLarkPayload(encryptKey, encryptedPayload) {
|
|
7074
|
+
const key = import_crypto7.default.createHash("sha256").update(encryptKey).digest();
|
|
7075
|
+
const buffer = Buffer.from(encryptedPayload, "base64");
|
|
7076
|
+
const iv = buffer.subarray(0, 16);
|
|
7077
|
+
const ciphertext = buffer.subarray(16);
|
|
7078
|
+
const decipher = import_crypto7.default.createDecipheriv("aes-256-cbc", key, iv);
|
|
7079
|
+
const plaintext = Buffer.concat([
|
|
7080
|
+
decipher.update(ciphertext),
|
|
7081
|
+
decipher.final()
|
|
7082
|
+
]).toString("utf8");
|
|
7083
|
+
return JSON.parse(plaintext);
|
|
7084
|
+
}
|
|
7085
|
+
|
|
7086
|
+
// src/channels/lark/controller.ts
|
|
7087
|
+
var logger2 = new Logger({ serviceName: "lattice/gateway/lark" });
|
|
6685
7088
|
function createLarkEventHandler(deps) {
|
|
6686
7089
|
return async function handleLarkEvent(request, reply) {
|
|
6687
7090
|
const { installationId } = request.params;
|
|
@@ -6702,7 +7105,7 @@ function createLarkEventHandler(deps) {
|
|
|
6702
7105
|
return;
|
|
6703
7106
|
}
|
|
6704
7107
|
deps.router.dispatch(inboundMessage).catch((error) => {
|
|
6705
|
-
|
|
7108
|
+
logger2.error("Lark message dispatch error", {
|
|
6706
7109
|
error: error instanceof Error ? error.message : String(error)
|
|
6707
7110
|
});
|
|
6708
7111
|
});
|
|
@@ -6734,8 +7137,8 @@ function registerChannelRoutes(app2, dependencies) {
|
|
|
6734
7137
|
}
|
|
6735
7138
|
|
|
6736
7139
|
// src/controllers/channel-installations.ts
|
|
6737
|
-
var
|
|
6738
|
-
function
|
|
7140
|
+
var import_crypto8 = require("crypto");
|
|
7141
|
+
function getTenantId13(request) {
|
|
6739
7142
|
const userTenantId = request.user?.tenantId;
|
|
6740
7143
|
if (userTenantId) {
|
|
6741
7144
|
return userTenantId;
|
|
@@ -6743,8 +7146,8 @@ function getTenantId11(request) {
|
|
|
6743
7146
|
return request.headers["x-tenant-id"] || "default";
|
|
6744
7147
|
}
|
|
6745
7148
|
async function getInstallationStore() {
|
|
6746
|
-
const { getStoreLattice:
|
|
6747
|
-
const store =
|
|
7149
|
+
const { getStoreLattice: getStoreLattice18 } = await import("@axiom-lattice/core");
|
|
7150
|
+
const store = getStoreLattice18("default", "channelInstallation").store;
|
|
6748
7151
|
if (store) return store;
|
|
6749
7152
|
const { PostgreSQLChannelInstallationStore } = await import("@axiom-lattice/pg-stores");
|
|
6750
7153
|
const databaseUrl = process.env.DATABASE_URL;
|
|
@@ -6756,7 +7159,7 @@ async function getInstallationStore() {
|
|
|
6756
7159
|
});
|
|
6757
7160
|
}
|
|
6758
7161
|
async function getChannelInstallationList(request, reply) {
|
|
6759
|
-
const tenantId =
|
|
7162
|
+
const tenantId = getTenantId13(request);
|
|
6760
7163
|
const { channel } = request.query;
|
|
6761
7164
|
try {
|
|
6762
7165
|
const store = await getInstallationStore();
|
|
@@ -6782,7 +7185,7 @@ async function getChannelInstallationList(request, reply) {
|
|
|
6782
7185
|
}
|
|
6783
7186
|
}
|
|
6784
7187
|
async function getChannelInstallation(request, reply) {
|
|
6785
|
-
const tenantId =
|
|
7188
|
+
const tenantId = getTenantId13(request);
|
|
6786
7189
|
const { installationId } = request.params;
|
|
6787
7190
|
try {
|
|
6788
7191
|
const store = await getInstallationStore();
|
|
@@ -6815,7 +7218,7 @@ async function getChannelInstallation(request, reply) {
|
|
|
6815
7218
|
}
|
|
6816
7219
|
}
|
|
6817
7220
|
async function createChannelInstallation(request, reply) {
|
|
6818
|
-
const tenantId =
|
|
7221
|
+
const tenantId = getTenantId13(request);
|
|
6819
7222
|
const body = request.body;
|
|
6820
7223
|
try {
|
|
6821
7224
|
if (!body.channel) {
|
|
@@ -6850,7 +7253,7 @@ async function createChannelInstallation(request, reply) {
|
|
|
6850
7253
|
}
|
|
6851
7254
|
}
|
|
6852
7255
|
const store = await getInstallationStore();
|
|
6853
|
-
const installationId = body.id || (0,
|
|
7256
|
+
const installationId = body.id || (0, import_crypto8.randomUUID)();
|
|
6854
7257
|
const installation = await store.createInstallation(
|
|
6855
7258
|
tenantId,
|
|
6856
7259
|
installationId,
|
|
@@ -6878,7 +7281,7 @@ async function createChannelInstallation(request, reply) {
|
|
|
6878
7281
|
}
|
|
6879
7282
|
}
|
|
6880
7283
|
async function updateChannelInstallation(request, reply) {
|
|
6881
|
-
const tenantId =
|
|
7284
|
+
const tenantId = getTenantId13(request);
|
|
6882
7285
|
const { installationId } = request.params;
|
|
6883
7286
|
const body = request.body;
|
|
6884
7287
|
try {
|
|
@@ -6924,7 +7327,7 @@ async function updateChannelInstallation(request, reply) {
|
|
|
6924
7327
|
}
|
|
6925
7328
|
}
|
|
6926
7329
|
async function deleteChannelInstallation(request, reply) {
|
|
6927
|
-
const tenantId =
|
|
7330
|
+
const tenantId = getTenantId13(request);
|
|
6928
7331
|
const { installationId } = request.params;
|
|
6929
7332
|
try {
|
|
6930
7333
|
const store = await getInstallationStore();
|
|
@@ -6974,17 +7377,17 @@ function registerChannelInstallationRoutes(app2) {
|
|
|
6974
7377
|
}
|
|
6975
7378
|
|
|
6976
7379
|
// src/controllers/channel-bindings.ts
|
|
6977
|
-
var
|
|
6978
|
-
function
|
|
7380
|
+
var import_core30 = require("@axiom-lattice/core");
|
|
7381
|
+
function getTenantId14(request) {
|
|
6979
7382
|
const userTenantId = request.user?.tenantId;
|
|
6980
7383
|
if (userTenantId) return userTenantId;
|
|
6981
7384
|
return request.headers["x-tenant-id"] || "default";
|
|
6982
7385
|
}
|
|
6983
7386
|
async function getBindingList(request, _reply) {
|
|
6984
|
-
const tenantId =
|
|
7387
|
+
const tenantId = getTenantId14(request);
|
|
6985
7388
|
const { channel, agentId, channelInstallationId, limit, offset } = request.query;
|
|
6986
7389
|
try {
|
|
6987
|
-
const registry = (0,
|
|
7390
|
+
const registry = (0, import_core30.getBindingRegistry)();
|
|
6988
7391
|
const bindings = await registry.list({ channel, agentId, tenantId, channelInstallationId, limit, offset });
|
|
6989
7392
|
return { success: true, message: "Bindings retrieved", data: { records: bindings, total: bindings.length } };
|
|
6990
7393
|
} catch (error) {
|
|
@@ -6993,9 +7396,9 @@ async function getBindingList(request, _reply) {
|
|
|
6993
7396
|
}
|
|
6994
7397
|
}
|
|
6995
7398
|
async function getBinding(request, reply) {
|
|
6996
|
-
const tenantId =
|
|
7399
|
+
const tenantId = getTenantId14(request);
|
|
6997
7400
|
try {
|
|
6998
|
-
const registry = (0,
|
|
7401
|
+
const registry = (0, import_core30.getBindingRegistry)();
|
|
6999
7402
|
const bindings = await registry.list({ tenantId });
|
|
7000
7403
|
const binding = bindings.find((b) => b.id === request.params.id);
|
|
7001
7404
|
if (!binding || binding.tenantId !== tenantId) {
|
|
@@ -7009,9 +7412,9 @@ async function getBinding(request, reply) {
|
|
|
7009
7412
|
}
|
|
7010
7413
|
}
|
|
7011
7414
|
async function createBinding(request, reply) {
|
|
7012
|
-
const tenantId =
|
|
7415
|
+
const tenantId = getTenantId14(request);
|
|
7013
7416
|
try {
|
|
7014
|
-
const registry = (0,
|
|
7417
|
+
const registry = (0, import_core30.getBindingRegistry)();
|
|
7015
7418
|
const binding = await registry.create({ ...request.body, tenantId });
|
|
7016
7419
|
reply.status(201);
|
|
7017
7420
|
return { success: true, message: "Binding created", data: binding };
|
|
@@ -7023,8 +7426,8 @@ async function createBinding(request, reply) {
|
|
|
7023
7426
|
}
|
|
7024
7427
|
async function updateBinding(request, reply) {
|
|
7025
7428
|
try {
|
|
7026
|
-
const tenantId =
|
|
7027
|
-
const registry = (0,
|
|
7429
|
+
const tenantId = getTenantId14(request);
|
|
7430
|
+
const registry = (0, import_core30.getBindingRegistry)();
|
|
7028
7431
|
const bindings = await registry.list({ tenantId });
|
|
7029
7432
|
const existing = bindings.find((b) => b.id === request.params.id);
|
|
7030
7433
|
if (!existing || existing.tenantId !== tenantId) {
|
|
@@ -7041,8 +7444,8 @@ async function updateBinding(request, reply) {
|
|
|
7041
7444
|
}
|
|
7042
7445
|
async function deleteBinding(request, reply) {
|
|
7043
7446
|
try {
|
|
7044
|
-
const tenantId =
|
|
7045
|
-
const registry = (0,
|
|
7447
|
+
const tenantId = getTenantId14(request);
|
|
7448
|
+
const registry = (0, import_core30.getBindingRegistry)();
|
|
7046
7449
|
const bindings = await registry.list({ tenantId });
|
|
7047
7450
|
const existing = bindings.find((b) => b.id === request.params.id);
|
|
7048
7451
|
if (!existing || existing.tenantId !== tenantId) {
|
|
@@ -7058,10 +7461,10 @@ async function deleteBinding(request, reply) {
|
|
|
7058
7461
|
}
|
|
7059
7462
|
}
|
|
7060
7463
|
async function resolveBinding(request, _reply) {
|
|
7061
|
-
const tenantId =
|
|
7464
|
+
const tenantId = getTenantId14(request);
|
|
7062
7465
|
const { channel, senderId, channelInstallationId } = request.query;
|
|
7063
7466
|
try {
|
|
7064
|
-
const registry = (0,
|
|
7467
|
+
const registry = (0, import_core30.getBindingRegistry)();
|
|
7065
7468
|
const binding = await registry.resolve({ channel, senderId, channelInstallationId, tenantId });
|
|
7066
7469
|
if (!binding) {
|
|
7067
7470
|
return { success: false, message: "No binding found", data: null };
|
|
@@ -7083,6 +7486,105 @@ function registerChannelBindingRoutes(app2) {
|
|
|
7083
7486
|
app2.delete("/api/channel-bindings/:id", deleteBinding);
|
|
7084
7487
|
}
|
|
7085
7488
|
|
|
7489
|
+
// src/controllers/menu-items.ts
|
|
7490
|
+
var import_core31 = require("@axiom-lattice/core");
|
|
7491
|
+
function getTenantId15(request) {
|
|
7492
|
+
const userTenantId = request.user?.tenantId;
|
|
7493
|
+
if (userTenantId) return userTenantId;
|
|
7494
|
+
return request.headers["x-tenant-id"] || "default";
|
|
7495
|
+
}
|
|
7496
|
+
function errorMessage(err) {
|
|
7497
|
+
return err instanceof Error ? err.message : "Unexpected error";
|
|
7498
|
+
}
|
|
7499
|
+
async function getMenuItemList(request, _reply) {
|
|
7500
|
+
const tenantId = getTenantId15(request);
|
|
7501
|
+
try {
|
|
7502
|
+
const registry = (0, import_core31.getMenuRegistry)();
|
|
7503
|
+
const items = await registry.list({ tenantId, menuTarget: request.query.menuTarget });
|
|
7504
|
+
return { success: true, message: "Menu items retrieved", data: { records: items, total: items.length } };
|
|
7505
|
+
} catch (error) {
|
|
7506
|
+
const msg = errorMessage(error);
|
|
7507
|
+
console.error("Failed to get menu items:", msg);
|
|
7508
|
+
return { success: false, message: msg, data: { records: [], total: 0 } };
|
|
7509
|
+
}
|
|
7510
|
+
}
|
|
7511
|
+
async function getMenuItem(request, reply) {
|
|
7512
|
+
const tenantId = getTenantId15(request);
|
|
7513
|
+
try {
|
|
7514
|
+
const registry = (0, import_core31.getMenuRegistry)();
|
|
7515
|
+
const item = await registry.getById(request.params.id);
|
|
7516
|
+
if (!item || item.tenantId !== tenantId) {
|
|
7517
|
+
reply.status(404);
|
|
7518
|
+
return { success: false, message: "Menu item not found" };
|
|
7519
|
+
}
|
|
7520
|
+
return { success: true, message: "Menu item retrieved", data: item };
|
|
7521
|
+
} catch (error) {
|
|
7522
|
+
const msg = errorMessage(error);
|
|
7523
|
+
console.error("Failed to get menu item:", msg);
|
|
7524
|
+
reply.status(500);
|
|
7525
|
+
return { success: false, message: msg };
|
|
7526
|
+
}
|
|
7527
|
+
}
|
|
7528
|
+
async function createMenuItem(request, reply) {
|
|
7529
|
+
const tenantId = getTenantId15(request);
|
|
7530
|
+
try {
|
|
7531
|
+
const registry = (0, import_core31.getMenuRegistry)();
|
|
7532
|
+
const item = await registry.create({ ...request.body, tenantId });
|
|
7533
|
+
reply.status(201);
|
|
7534
|
+
return { success: true, message: "Menu item created", data: item };
|
|
7535
|
+
} catch (error) {
|
|
7536
|
+
const msg = errorMessage(error);
|
|
7537
|
+
console.error("Failed to create menu item:", msg);
|
|
7538
|
+
reply.status(500);
|
|
7539
|
+
return { success: false, message: msg };
|
|
7540
|
+
}
|
|
7541
|
+
}
|
|
7542
|
+
async function updateMenuItem(request, reply) {
|
|
7543
|
+
try {
|
|
7544
|
+
const tenantId = getTenantId15(request);
|
|
7545
|
+
const registry = (0, import_core31.getMenuRegistry)();
|
|
7546
|
+
const existing = await registry.getById(request.params.id);
|
|
7547
|
+
if (!existing || existing.tenantId !== tenantId) {
|
|
7548
|
+
reply.status(404);
|
|
7549
|
+
return { success: false, message: "Menu item not found" };
|
|
7550
|
+
}
|
|
7551
|
+
const item = await registry.update(request.params.id, request.body);
|
|
7552
|
+
return { success: true, message: "Menu item updated", data: item };
|
|
7553
|
+
} catch (error) {
|
|
7554
|
+
const msg = errorMessage(error);
|
|
7555
|
+
console.error("Failed to update menu item:", msg);
|
|
7556
|
+
reply.status(500);
|
|
7557
|
+
return { success: false, message: msg };
|
|
7558
|
+
}
|
|
7559
|
+
}
|
|
7560
|
+
async function deleteMenuItem(request, reply) {
|
|
7561
|
+
try {
|
|
7562
|
+
const tenantId = getTenantId15(request);
|
|
7563
|
+
const registry = (0, import_core31.getMenuRegistry)();
|
|
7564
|
+
const existing = await registry.getById(request.params.id);
|
|
7565
|
+
if (!existing || existing.tenantId !== tenantId) {
|
|
7566
|
+
reply.status(404);
|
|
7567
|
+
return { success: false, message: "Menu item not found" };
|
|
7568
|
+
}
|
|
7569
|
+
await registry.delete(request.params.id);
|
|
7570
|
+
return { success: true, message: "Menu item deleted" };
|
|
7571
|
+
} catch (error) {
|
|
7572
|
+
const msg = errorMessage(error);
|
|
7573
|
+
console.error("Failed to delete menu item:", msg);
|
|
7574
|
+
reply.status(500);
|
|
7575
|
+
return { success: false, message: msg };
|
|
7576
|
+
}
|
|
7577
|
+
}
|
|
7578
|
+
|
|
7579
|
+
// src/routes/menu-items.ts
|
|
7580
|
+
function registerMenuItemRoutes(app2) {
|
|
7581
|
+
app2.get("/api/menu-items", getMenuItemList);
|
|
7582
|
+
app2.post("/api/menu-items", createMenuItem);
|
|
7583
|
+
app2.get("/api/menu-items/:id", getMenuItem);
|
|
7584
|
+
app2.put("/api/menu-items/:id", updateMenuItem);
|
|
7585
|
+
app2.delete("/api/menu-items/:id", deleteMenuItem);
|
|
7586
|
+
}
|
|
7587
|
+
|
|
7086
7588
|
// src/routes/a2a-bridge.ts
|
|
7087
7589
|
var import_uuid8 = require("uuid");
|
|
7088
7590
|
var log = {
|
|
@@ -7263,6 +7765,7 @@ var registerLatticeRoutes = (app2, channelDeps) => {
|
|
|
7263
7765
|
app2.post("/api/runs", createRun);
|
|
7264
7766
|
app2.post("/api/resume_stream", resumeStream);
|
|
7265
7767
|
app2.post("/api/assistants/:assistantId/threads/:threadId/abort", abortRun);
|
|
7768
|
+
app2.post("/api/assistants/:assistantId/threads/:threadId/recover", recoverRun);
|
|
7266
7769
|
app2.get(
|
|
7267
7770
|
"/api/assistants/:assistantId/:thread_id/memory",
|
|
7268
7771
|
{ schema: getAllMemoryItemsSchema },
|
|
@@ -7298,6 +7801,15 @@ var registerLatticeRoutes = (app2, channelDeps) => {
|
|
|
7298
7801
|
app2.post("/api/assistants", createAssistant);
|
|
7299
7802
|
app2.put("/api/assistants/:id", updateAssistant);
|
|
7300
7803
|
app2.delete("/api/assistants/:id", deleteAssistant);
|
|
7804
|
+
app2.post("/api/personal-assistant", createPersonalAssistant);
|
|
7805
|
+
app2.get("/api/personal-assistant", getPersonalAssistant);
|
|
7806
|
+
app2.delete("/api/personal-assistant", deletePersonalAssistant);
|
|
7807
|
+
app2.get("/api/tasks", listTasks);
|
|
7808
|
+
app2.get("/api/tasks/:id", getTask);
|
|
7809
|
+
app2.post("/api/tasks", createTask);
|
|
7810
|
+
app2.put("/api/tasks/:id", updateTask);
|
|
7811
|
+
app2.delete("/api/tasks/:id", deleteTask);
|
|
7812
|
+
app2.patch("/api/tasks/:id/complete", completeTask);
|
|
7301
7813
|
app2.get(
|
|
7302
7814
|
"/api/assistants/:assistantId/graph",
|
|
7303
7815
|
{ schema: getAgentGraphSchema },
|
|
@@ -7396,6 +7908,7 @@ var registerLatticeRoutes = (app2, channelDeps) => {
|
|
|
7396
7908
|
});
|
|
7397
7909
|
registerChannelRoutes(app2, channelDeps);
|
|
7398
7910
|
registerChannelInstallationRoutes(app2);
|
|
7911
|
+
registerMenuItemRoutes(app2);
|
|
7399
7912
|
if (channelDeps) {
|
|
7400
7913
|
registerChannelBindingRoutes(app2);
|
|
7401
7914
|
}
|
|
@@ -7473,8 +7986,8 @@ var registerLatticeRoutes = (app2, channelDeps) => {
|
|
|
7473
7986
|
};
|
|
7474
7987
|
|
|
7475
7988
|
// src/router/MessageRouter.ts
|
|
7476
|
-
var
|
|
7477
|
-
var
|
|
7989
|
+
var import_core32 = require("@axiom-lattice/core");
|
|
7990
|
+
var import_crypto9 = require("crypto");
|
|
7478
7991
|
var BindingNotFoundError = class extends Error {
|
|
7479
7992
|
constructor(message) {
|
|
7480
7993
|
super(message);
|
|
@@ -7521,6 +8034,9 @@ var MessageRouter = class {
|
|
|
7521
8034
|
inboundMessage: message,
|
|
7522
8035
|
metadata: {}
|
|
7523
8036
|
};
|
|
8037
|
+
let binding = null;
|
|
8038
|
+
let threadId;
|
|
8039
|
+
let agentId;
|
|
7524
8040
|
try {
|
|
7525
8041
|
await this.runMiddlewares(ctx, async () => {
|
|
7526
8042
|
const tenantId = message.tenantId || (await this.installationStore.getInstallationById(message.channelInstallationId))?.tenantId;
|
|
@@ -7537,16 +8053,18 @@ var MessageRouter = class {
|
|
|
7537
8053
|
);
|
|
7538
8054
|
}
|
|
7539
8055
|
console.log({ event: "dispatch:start", channel: message.channel, senderId: message.sender.id, tenantId }, "Message dispatch started");
|
|
7540
|
-
|
|
8056
|
+
const adapter = this.adapterRegistry.get(message.channel);
|
|
8057
|
+
const hasAdapterThreadStrategy = !!adapter?.resolveThreadId;
|
|
8058
|
+
binding = await this.bindingRegistry.resolve({
|
|
7541
8059
|
channel: message.channel,
|
|
7542
8060
|
senderId: message.sender.id,
|
|
7543
8061
|
channelInstallationId: message.channelInstallationId,
|
|
7544
8062
|
tenantId
|
|
7545
8063
|
});
|
|
8064
|
+
const installation = await this.installationStore.getInstallationById(
|
|
8065
|
+
message.channelInstallationId
|
|
8066
|
+
);
|
|
7546
8067
|
if (!binding) {
|
|
7547
|
-
const installation = await this.installationStore.getInstallationById(
|
|
7548
|
-
message.channelInstallationId
|
|
7549
|
-
);
|
|
7550
8068
|
if (installation?.rejectWhenNoBinding) {
|
|
7551
8069
|
console.warn({
|
|
7552
8070
|
event: "dispatch:no_binding",
|
|
@@ -7579,7 +8097,7 @@ var MessageRouter = class {
|
|
|
7579
8097
|
createdAt: /* @__PURE__ */ new Date(),
|
|
7580
8098
|
updatedAt: /* @__PURE__ */ new Date()
|
|
7581
8099
|
};
|
|
7582
|
-
} else {
|
|
8100
|
+
} else if (!hasAdapterThreadStrategy) {
|
|
7583
8101
|
console.error({
|
|
7584
8102
|
event: "dispatch:no_fallback",
|
|
7585
8103
|
channel: message.channel,
|
|
@@ -7591,47 +8109,99 @@ var MessageRouter = class {
|
|
|
7591
8109
|
);
|
|
7592
8110
|
}
|
|
7593
8111
|
}
|
|
7594
|
-
ctx.binding = binding;
|
|
7595
|
-
|
|
7596
|
-
|
|
7597
|
-
|
|
7598
|
-
agentId: binding.agentId,
|
|
7599
|
-
threadId: binding.threadId,
|
|
7600
|
-
threadMode: binding.threadMode,
|
|
7601
|
-
workspaceId: binding.workspaceId,
|
|
7602
|
-
projectId: binding.projectId
|
|
7603
|
-
}, "Binding resolved");
|
|
7604
|
-
if (!binding.enabled) {
|
|
7605
|
-
console.warn({
|
|
7606
|
-
event: "dispatch:binding_disabled",
|
|
8112
|
+
ctx.binding = binding ?? void 0;
|
|
8113
|
+
if (binding) {
|
|
8114
|
+
console.log({
|
|
8115
|
+
event: "dispatch:binding",
|
|
7607
8116
|
bindingId: binding.id,
|
|
7608
8117
|
agentId: binding.agentId,
|
|
7609
|
-
|
|
7610
|
-
|
|
8118
|
+
threadId: binding.threadId,
|
|
8119
|
+
threadMode: binding.threadMode,
|
|
8120
|
+
workspaceId: binding.workspaceId,
|
|
8121
|
+
projectId: binding.projectId
|
|
8122
|
+
}, "Binding resolved");
|
|
8123
|
+
if (!binding.enabled) {
|
|
8124
|
+
console.warn({
|
|
8125
|
+
event: "dispatch:binding_disabled",
|
|
8126
|
+
bindingId: binding.id,
|
|
8127
|
+
agentId: binding.agentId,
|
|
8128
|
+
senderId: message.sender.id
|
|
8129
|
+
}, "Binding is disabled, rejecting message");
|
|
8130
|
+
throw new BindingNotFoundError(
|
|
8131
|
+
`Binding for sender "${message.sender.id}" is disabled`
|
|
8132
|
+
);
|
|
8133
|
+
}
|
|
8134
|
+
}
|
|
8135
|
+
agentId = binding?.agentId ?? installation?.fallbackAgentId;
|
|
8136
|
+
if (!agentId) {
|
|
7611
8137
|
throw new BindingNotFoundError(
|
|
7612
|
-
`
|
|
8138
|
+
`No agent configured for sender "${message.sender.id}"`
|
|
7613
8139
|
);
|
|
7614
8140
|
}
|
|
7615
|
-
|
|
8141
|
+
if (hasAdapterThreadStrategy) {
|
|
8142
|
+
const resolvedThreadId = await adapter.resolveThreadId(message, binding);
|
|
8143
|
+
threadId = resolvedThreadId;
|
|
8144
|
+
console.log({
|
|
8145
|
+
event: "dispatch:thread:adapter",
|
|
8146
|
+
threadId,
|
|
8147
|
+
channel: message.channel,
|
|
8148
|
+
adapterChannel: adapter.channel
|
|
8149
|
+
}, "Thread resolved by adapter strategy");
|
|
8150
|
+
const threadStore = (0, import_core32.getStoreLattice)("default", "thread").store;
|
|
8151
|
+
try {
|
|
8152
|
+
await threadStore.createThread(
|
|
8153
|
+
tenantId,
|
|
8154
|
+
agentId,
|
|
8155
|
+
threadId,
|
|
8156
|
+
{
|
|
8157
|
+
metadata: {
|
|
8158
|
+
channel: message.channel,
|
|
8159
|
+
channelInstallationId: message.channelInstallationId,
|
|
8160
|
+
senderId: message.sender.id,
|
|
8161
|
+
bindingId: binding?.id,
|
|
8162
|
+
...message.conversation ? {
|
|
8163
|
+
conversationId: message.conversation.id,
|
|
8164
|
+
conversationType: message.conversation.type
|
|
8165
|
+
} : {}
|
|
8166
|
+
}
|
|
8167
|
+
}
|
|
8168
|
+
);
|
|
8169
|
+
console.log({
|
|
8170
|
+
event: "dispatch:thread:adapter:created",
|
|
8171
|
+
threadId
|
|
8172
|
+
}, "Thread created by adapter strategy");
|
|
8173
|
+
} catch {
|
|
8174
|
+
console.log({
|
|
8175
|
+
event: "dispatch:thread:adapter:reuse",
|
|
8176
|
+
threadId
|
|
8177
|
+
}, "Thread already exists, reusing");
|
|
8178
|
+
}
|
|
8179
|
+
} else if (binding) {
|
|
8180
|
+
if (binding.threadMode === "per_conversation") {
|
|
8181
|
+
threadId = void 0;
|
|
8182
|
+
} else {
|
|
8183
|
+
threadId = binding.threadId;
|
|
8184
|
+
}
|
|
8185
|
+
}
|
|
7616
8186
|
if (!threadId) {
|
|
7617
|
-
const threadStore = (0,
|
|
7618
|
-
const newThreadId = (0,
|
|
8187
|
+
const threadStore = (0, import_core32.getStoreLattice)("default", "thread").store;
|
|
8188
|
+
const newThreadId = (0, import_crypto9.randomUUID)();
|
|
7619
8189
|
console.log({
|
|
7620
8190
|
event: "dispatch:thread:create",
|
|
7621
|
-
agentId
|
|
8191
|
+
agentId,
|
|
7622
8192
|
newThreadId,
|
|
7623
8193
|
tenantId
|
|
7624
8194
|
}, "Creating new thread for binding");
|
|
7625
8195
|
const newThread = await threadStore.createThread(
|
|
7626
8196
|
tenantId,
|
|
7627
|
-
|
|
8197
|
+
agentId,
|
|
7628
8198
|
newThreadId,
|
|
7629
8199
|
{
|
|
7630
8200
|
metadata: {
|
|
7631
8201
|
channel: message.channel,
|
|
7632
8202
|
channelInstallationId: message.channelInstallationId,
|
|
7633
8203
|
senderId: message.sender.id,
|
|
7634
|
-
bindingId:
|
|
8204
|
+
bindingId: binding?.id,
|
|
7635
8205
|
...message.conversation ? {
|
|
7636
8206
|
conversationId: message.conversation.id,
|
|
7637
8207
|
conversationType: message.conversation.type
|
|
@@ -7640,36 +8210,35 @@ var MessageRouter = class {
|
|
|
7640
8210
|
}
|
|
7641
8211
|
);
|
|
7642
8212
|
threadId = newThread.id;
|
|
7643
|
-
if (
|
|
7644
|
-
await this.bindingRegistry.update(
|
|
7645
|
-
|
|
7646
|
-
} else {
|
|
7647
|
-
|
|
8213
|
+
if (binding && binding.id !== "fallback") {
|
|
8214
|
+
await this.bindingRegistry.update(binding.id, { threadId });
|
|
8215
|
+
binding.threadId = threadId;
|
|
8216
|
+
} else if (binding) {
|
|
8217
|
+
binding.threadId = threadId;
|
|
7648
8218
|
}
|
|
7649
8219
|
}
|
|
7650
8220
|
console.log({
|
|
7651
8221
|
event: "dispatch:agent",
|
|
7652
|
-
agentId
|
|
8222
|
+
agentId,
|
|
7653
8223
|
threadId,
|
|
7654
|
-
threadMode: ctx.binding.threadMode,
|
|
7655
8224
|
senderId: message.sender.id,
|
|
7656
8225
|
contentLength: message.content.text.length
|
|
7657
8226
|
}, "Dispatching to agent");
|
|
7658
|
-
const agent =
|
|
8227
|
+
const agent = import_core32.agentInstanceManager.getAgent({
|
|
7659
8228
|
tenant_id: tenantId,
|
|
7660
|
-
assistant_id:
|
|
8229
|
+
assistant_id: agentId,
|
|
7661
8230
|
thread_id: threadId,
|
|
7662
|
-
workspace_id:
|
|
7663
|
-
project_id:
|
|
8231
|
+
workspace_id: binding?.workspaceId || "",
|
|
8232
|
+
project_id: binding?.projectId || ""
|
|
7664
8233
|
});
|
|
7665
8234
|
if (message.replyTarget) {
|
|
7666
8235
|
const replySubKey = `${threadId}:${message.replyTarget.adapterChannel}:reply`;
|
|
7667
|
-
const
|
|
7668
|
-
if (
|
|
7669
|
-
const
|
|
8236
|
+
const adapter2 = this.adapterRegistry.get(message.replyTarget.adapterChannel);
|
|
8237
|
+
if (adapter2) {
|
|
8238
|
+
const installation2 = await this.installationStore.getInstallationById(
|
|
7670
8239
|
message.channelInstallationId
|
|
7671
8240
|
);
|
|
7672
|
-
if (
|
|
8241
|
+
if (installation2) {
|
|
7673
8242
|
const existing = this._replySubs.get(replySubKey);
|
|
7674
8243
|
if (!existing || existing.count === 0) {
|
|
7675
8244
|
const timer = setTimeout(() => {
|
|
@@ -7709,7 +8278,7 @@ var MessageRouter = class {
|
|
|
7709
8278
|
channel: message.replyTarget.adapterChannel,
|
|
7710
8279
|
replyLength: replyText.length
|
|
7711
8280
|
}, "Sending channel reply");
|
|
7712
|
-
|
|
8281
|
+
adapter2.sendReply(message.replyTarget, { text: replyText }, installation2).then(() => {
|
|
7713
8282
|
console.log({
|
|
7714
8283
|
event: "dispatch:reply:sent",
|
|
7715
8284
|
threadId,
|
|
@@ -7747,7 +8316,7 @@ var MessageRouter = class {
|
|
|
7747
8316
|
});
|
|
7748
8317
|
console.log({
|
|
7749
8318
|
event: "dispatch:complete",
|
|
7750
|
-
agentId
|
|
8319
|
+
agentId,
|
|
7751
8320
|
threadId,
|
|
7752
8321
|
messageId: addResult?.messageId,
|
|
7753
8322
|
result: JSON.stringify(addResult)
|
|
@@ -7756,7 +8325,7 @@ var MessageRouter = class {
|
|
|
7756
8325
|
return {
|
|
7757
8326
|
success: true,
|
|
7758
8327
|
bindingId: ctx.binding?.id,
|
|
7759
|
-
threadId
|
|
8328
|
+
threadId,
|
|
7760
8329
|
result: ctx.result
|
|
7761
8330
|
};
|
|
7762
8331
|
} catch (error) {
|
|
@@ -7867,13 +8436,13 @@ function createRateLimitMiddleware(maxRequests = 10, windowMs = 60 * 1e3, maxEnt
|
|
|
7867
8436
|
}
|
|
7868
8437
|
|
|
7869
8438
|
// src/router/middlewares/auditLogger.ts
|
|
7870
|
-
var
|
|
8439
|
+
var logger3 = new Logger({ serviceName: "lattice/gateway/audit" });
|
|
7871
8440
|
function createAuditLoggerMiddleware() {
|
|
7872
8441
|
return async (ctx, next) => {
|
|
7873
8442
|
const start2 = Date.now();
|
|
7874
8443
|
try {
|
|
7875
8444
|
await next();
|
|
7876
|
-
|
|
8445
|
+
logger3.info("message routed", {
|
|
7877
8446
|
event: "message:routed",
|
|
7878
8447
|
channel: ctx.inboundMessage.channel,
|
|
7879
8448
|
senderId: ctx.inboundMessage.sender.id,
|
|
@@ -7883,7 +8452,7 @@ function createAuditLoggerMiddleware() {
|
|
|
7883
8452
|
status: "success"
|
|
7884
8453
|
});
|
|
7885
8454
|
} catch (error) {
|
|
7886
|
-
|
|
8455
|
+
logger3.error(
|
|
7887
8456
|
error instanceof Error ? error.message : String(error),
|
|
7888
8457
|
{
|
|
7889
8458
|
event: "message:error",
|
|
@@ -7899,7 +8468,7 @@ function createAuditLoggerMiddleware() {
|
|
|
7899
8468
|
}
|
|
7900
8469
|
|
|
7901
8470
|
// src/index.ts
|
|
7902
|
-
var
|
|
8471
|
+
var import_core35 = require("@axiom-lattice/core");
|
|
7903
8472
|
|
|
7904
8473
|
// src/swagger.ts
|
|
7905
8474
|
var import_swagger = __toESM(require("@fastify/swagger"));
|
|
@@ -7964,7 +8533,7 @@ var configureSwagger = async (app2, customSwaggerConfig, customSwaggerUiConfig)
|
|
|
7964
8533
|
};
|
|
7965
8534
|
|
|
7966
8535
|
// src/services/agent_task_consumer.ts
|
|
7967
|
-
var
|
|
8536
|
+
var import_core33 = require("@axiom-lattice/core");
|
|
7968
8537
|
var handleAgentTask = async (taskRequest, retryCount = 0) => {
|
|
7969
8538
|
const {
|
|
7970
8539
|
assistant_id,
|
|
@@ -7982,21 +8551,22 @@ var handleAgentTask = async (taskRequest, retryCount = 0) => {
|
|
|
7982
8551
|
console.log(
|
|
7983
8552
|
`\u5F00\u59CB\u5904\u7406\u4EFB\u52A1 [assistant_id: ${assistant_id}, thread_id: ${thread_id}]`
|
|
7984
8553
|
);
|
|
7985
|
-
const agent =
|
|
7986
|
-
await agent.addMessage({ input, command, custom_run_config: runConfig },
|
|
8554
|
+
const agent = import_core33.agentInstanceManager.getAgent({ assistant_id, thread_id, tenant_id, workspace_id: runConfig?.workspaceId, project_id: runConfig?.projectId, custom_run_config: runConfig });
|
|
8555
|
+
await agent.addMessage({ input, command, custom_run_config: runConfig }, import_core33.QueueMode.STEER);
|
|
7987
8556
|
if (callback_event) {
|
|
7988
8557
|
agent.subscribeOnce("message:completed", (evt) => {
|
|
7989
|
-
|
|
8558
|
+
import_core33.eventBus.publish(callback_event, {
|
|
7990
8559
|
success: true,
|
|
7991
|
-
state: evt.state
|
|
7992
|
-
config: { assistant_id, thread_id, tenant_id }
|
|
8560
|
+
state: evt.state
|
|
7993
8561
|
});
|
|
7994
8562
|
if (main_thread_id && main_tenant_id) {
|
|
7995
8563
|
try {
|
|
7996
|
-
const mainAgent =
|
|
8564
|
+
const mainAgent = import_core33.agentInstanceManager.getAgent({
|
|
7997
8565
|
assistant_id: main_assistant_id ?? assistant_id,
|
|
7998
8566
|
thread_id: main_thread_id,
|
|
7999
|
-
tenant_id: main_tenant_id
|
|
8567
|
+
tenant_id: main_tenant_id,
|
|
8568
|
+
workspace_id: runConfig?.workspaceId,
|
|
8569
|
+
project_id: runConfig?.projectId
|
|
8000
8570
|
});
|
|
8001
8571
|
if (mainAgent) {
|
|
8002
8572
|
const messages = evt.state?.values?.messages;
|
|
@@ -8021,10 +8591,9 @@ ${summary}`
|
|
|
8021
8591
|
}
|
|
8022
8592
|
});
|
|
8023
8593
|
agent.subscribeOnce("message:interrupted", (evt) => {
|
|
8024
|
-
|
|
8594
|
+
import_core33.eventBus.publish(callback_event, {
|
|
8025
8595
|
success: true,
|
|
8026
|
-
state: evt.state
|
|
8027
|
-
config: { assistant_id, thread_id, tenant_id }
|
|
8596
|
+
state: evt.state
|
|
8028
8597
|
});
|
|
8029
8598
|
});
|
|
8030
8599
|
}
|
|
@@ -8045,10 +8614,9 @@ ${summary}`
|
|
|
8045
8614
|
return handleAgentTask(taskRequest, nextRetryCount);
|
|
8046
8615
|
}
|
|
8047
8616
|
if (callback_event) {
|
|
8048
|
-
|
|
8617
|
+
import_core33.eventBus.publish(callback_event, {
|
|
8049
8618
|
success: false,
|
|
8050
|
-
error: error instanceof Error ? error.message : String(error)
|
|
8051
|
-
config: { assistant_id, thread_id, tenant_id }
|
|
8619
|
+
error: error instanceof Error ? error.message : String(error)
|
|
8052
8620
|
});
|
|
8053
8621
|
}
|
|
8054
8622
|
console.error(
|
|
@@ -8083,7 +8651,7 @@ var _AgentTaskConsumer = class _AgentTaskConsumer {
|
|
|
8083
8651
|
* 初始化事件监听和队列轮询
|
|
8084
8652
|
*/
|
|
8085
8653
|
initialize() {
|
|
8086
|
-
|
|
8654
|
+
import_core33.eventBus.subscribe(import_core33.AGENT_TASK_EVENT, this.trigger_agent_task.bind(this));
|
|
8087
8655
|
this.startPollingQueue();
|
|
8088
8656
|
console.log("Agent\u4EFB\u52A1\u6D88\u8D39\u8005\u5DF2\u542F\u52A8\u5E76\u76D1\u542C\u4EFB\u52A1\u4E8B\u4EF6\u548C\u961F\u5217");
|
|
8089
8657
|
}
|
|
@@ -8202,14 +8770,9 @@ var _AgentTaskConsumer = class _AgentTaskConsumer {
|
|
|
8202
8770
|
handleAgentTask(taskRequest).catch((error) => {
|
|
8203
8771
|
console.error("\u5904\u7406Agent\u4EFB\u52A1\u65F6\u53D1\u751F\u672A\u6355\u83B7\u7684\u9519\u8BEF:", error);
|
|
8204
8772
|
if (taskRequest.callback_event) {
|
|
8205
|
-
|
|
8773
|
+
import_core33.eventBus.publish(taskRequest.callback_event, {
|
|
8206
8774
|
success: false,
|
|
8207
|
-
error: error instanceof Error ? error.message : String(error)
|
|
8208
|
-
config: {
|
|
8209
|
-
assistant_id: taskRequest.assistant_id,
|
|
8210
|
-
thread_id: taskRequest.thread_id,
|
|
8211
|
-
tenant_id: taskRequest["x-tenant-id"]
|
|
8212
|
-
}
|
|
8775
|
+
error: error instanceof Error ? error.message : String(error)
|
|
8213
8776
|
});
|
|
8214
8777
|
}
|
|
8215
8778
|
});
|
|
@@ -8222,7 +8785,7 @@ _AgentTaskConsumer.agent_run_endpoint = "http://localhost:4001/api/runs";
|
|
|
8222
8785
|
var AgentTaskConsumer = _AgentTaskConsumer;
|
|
8223
8786
|
|
|
8224
8787
|
// src/index.ts
|
|
8225
|
-
var
|
|
8788
|
+
var import_core36 = require("@axiom-lattice/core");
|
|
8226
8789
|
var import_protocols5 = require("@axiom-lattice/protocols");
|
|
8227
8790
|
var import_meta = {};
|
|
8228
8791
|
process.on("unhandledRejection", (reason, promise) => {
|
|
@@ -8236,13 +8799,13 @@ var DEFAULT_LOGGER_CONFIG = {
|
|
|
8236
8799
|
loggerName: "lattice/gateway"
|
|
8237
8800
|
};
|
|
8238
8801
|
var loggerLattice = initializeLogger(DEFAULT_LOGGER_CONFIG);
|
|
8239
|
-
var
|
|
8802
|
+
var logger4 = loggerLattice.client;
|
|
8240
8803
|
function initializeLogger(config) {
|
|
8241
|
-
if (
|
|
8242
|
-
|
|
8804
|
+
if (import_core36.loggerLatticeManager.hasLattice("default")) {
|
|
8805
|
+
import_core36.loggerLatticeManager.removeLattice("default");
|
|
8243
8806
|
}
|
|
8244
|
-
(0,
|
|
8245
|
-
return (0,
|
|
8807
|
+
(0, import_core36.registerLoggerLattice)("default", config);
|
|
8808
|
+
return (0, import_core36.getLoggerLattice)("default");
|
|
8246
8809
|
}
|
|
8247
8810
|
var app = (0, import_fastify.default)({
|
|
8248
8811
|
logger: false,
|
|
@@ -8279,6 +8842,8 @@ app.addHook("preHandler", async (request, reply) => {
|
|
|
8279
8842
|
if (!authRequired) return;
|
|
8280
8843
|
if (request.method === "OPTIONS") return;
|
|
8281
8844
|
if (PUBLIC_ROUTES.some((r) => request.url === r)) return;
|
|
8845
|
+
const urlPath = request.url.split("?")[0];
|
|
8846
|
+
if (urlPath.includes("/viewfile") || urlPath.includes("/downloadfile")) return;
|
|
8282
8847
|
return reply.status(401).send({
|
|
8283
8848
|
success: false,
|
|
8284
8849
|
error: "Unauthorized - Missing or invalid token"
|
|
@@ -8335,7 +8900,7 @@ app.setErrorHandler((error, request, reply) => {
|
|
|
8335
8900
|
"x-request-id": getHeaderValue(request.headers["x-request-id"]),
|
|
8336
8901
|
"x-user-id": getHeaderValue(request.headers["x-user-id"])
|
|
8337
8902
|
};
|
|
8338
|
-
|
|
8903
|
+
logger4.error(
|
|
8339
8904
|
`\u8BF7\u6C42\u9519\u8BEF: ${request.method} ${request.url} error:${error.message}`,
|
|
8340
8905
|
{
|
|
8341
8906
|
...context,
|
|
@@ -8351,7 +8916,7 @@ app.setErrorHandler((error, request, reply) => {
|
|
|
8351
8916
|
});
|
|
8352
8917
|
function getConfiguredSandboxProvider() {
|
|
8353
8918
|
const sandboxProviderType = process.env.SANDBOX_PROVIDER_TYPE || "microsandbox-remote";
|
|
8354
|
-
return (0,
|
|
8919
|
+
return (0, import_core36.createSandboxProvider)({
|
|
8355
8920
|
type: sandboxProviderType,
|
|
8356
8921
|
remoteBaseURL: process.env.SANDBOX_BASE_URL,
|
|
8357
8922
|
microsandboxServiceBaseURL: process.env.MICROSANDBOX_SERVICE_BASE_URL,
|
|
@@ -8375,17 +8940,19 @@ var start = async (config) => {
|
|
|
8375
8940
|
file: config.loggerConfig.file || DEFAULT_LOGGER_CONFIG.file
|
|
8376
8941
|
};
|
|
8377
8942
|
loggerLattice = initializeLogger(loggerConfig);
|
|
8378
|
-
|
|
8943
|
+
logger4 = loggerLattice.client;
|
|
8379
8944
|
}
|
|
8380
8945
|
app.decorate("loggerLattice", loggerLattice);
|
|
8381
8946
|
let channelDeps;
|
|
8947
|
+
const adapterRegistry = new ChannelAdapterRegistry();
|
|
8948
|
+
adapterRegistry.register(larkChannelAdapter);
|
|
8382
8949
|
try {
|
|
8383
|
-
const { getStoreLattice:
|
|
8384
|
-
|
|
8385
|
-
|
|
8386
|
-
(
|
|
8387
|
-
|
|
8388
|
-
|
|
8950
|
+
const { getStoreLattice: getStore2 } = await import("@axiom-lattice/core");
|
|
8951
|
+
let bindingStore;
|
|
8952
|
+
let installationStore;
|
|
8953
|
+
bindingStore = getStore2("default", "channelBinding").store;
|
|
8954
|
+
installationStore = getStore2("default", "channelInstallation").store;
|
|
8955
|
+
(0, import_core35.setBindingRegistry)(bindingStore);
|
|
8389
8956
|
const router = new MessageRouter({
|
|
8390
8957
|
middlewares: [
|
|
8391
8958
|
createDeduplicationMiddleware(),
|
|
@@ -8398,27 +8965,49 @@ var start = async (config) => {
|
|
|
8398
8965
|
});
|
|
8399
8966
|
channelDeps = { router, installationStore };
|
|
8400
8967
|
try {
|
|
8401
|
-
const a2aKeyStore =
|
|
8968
|
+
const a2aKeyStore = getStore2("default", "a2aApiKey").store;
|
|
8402
8969
|
const a2a = await Promise.resolve().then(() => (init_a2a(), a2a_exports));
|
|
8403
8970
|
a2a.setA2AKeyStore(a2aKeyStore);
|
|
8404
8971
|
await a2a.refreshStoreKeyMap();
|
|
8405
|
-
|
|
8972
|
+
logger4.info("A2A key store initialized");
|
|
8406
8973
|
} catch {
|
|
8407
8974
|
}
|
|
8975
|
+
} catch (err) {
|
|
8976
|
+
logger4.warn("Channel infrastructure unavailable", {
|
|
8977
|
+
error: err instanceof Error ? err.message : String(err)
|
|
8978
|
+
});
|
|
8979
|
+
}
|
|
8980
|
+
try {
|
|
8981
|
+
const menuStore = (0, import_core36.getStoreLattice)("default", "menu").store;
|
|
8982
|
+
(0, import_core35.setMenuRegistry)(menuStore);
|
|
8983
|
+
logger4.info("Menu registry initialized");
|
|
8408
8984
|
} catch {
|
|
8409
8985
|
}
|
|
8410
8986
|
registerLatticeRoutes(app, channelDeps);
|
|
8411
|
-
if (!
|
|
8412
|
-
|
|
8413
|
-
|
|
8987
|
+
if (!import_core36.sandboxLatticeManager.hasLattice("default")) {
|
|
8988
|
+
import_core36.sandboxLatticeManager.registerLattice("default", getConfiguredSandboxProvider());
|
|
8989
|
+
logger4.info("Registered sandbox manager from env configuration");
|
|
8990
|
+
}
|
|
8991
|
+
if (channelDeps && process.env.CHANNELS_ENABLED !== "false") {
|
|
8992
|
+
const { connectAllChannels } = await import("@axiom-lattice/core");
|
|
8993
|
+
try {
|
|
8994
|
+
await connectAllChannels(
|
|
8995
|
+
(channel) => adapterRegistry.get(channel),
|
|
8996
|
+
{ deps: { router: channelDeps.router } }
|
|
8997
|
+
);
|
|
8998
|
+
} catch (err) {
|
|
8999
|
+
logger4.error("Failed to start channel connections", {
|
|
9000
|
+
error: err instanceof Error ? err.message : String(err)
|
|
9001
|
+
});
|
|
9002
|
+
}
|
|
8414
9003
|
}
|
|
8415
9004
|
const target_port = config?.port || Number(process.env.PORT) || 4001;
|
|
8416
9005
|
await app.listen({ port: target_port, host: "0.0.0.0" });
|
|
8417
|
-
|
|
9006
|
+
logger4.info(`Lattice Gateway is running on port: ${target_port}`);
|
|
8418
9007
|
try {
|
|
8419
|
-
|
|
9008
|
+
logger4.info("AgentLifecycleManager initialized");
|
|
8420
9009
|
} catch (error) {
|
|
8421
|
-
|
|
9010
|
+
logger4.warn("Failed to initialize AgentLifecycleManager", { error });
|
|
8422
9011
|
}
|
|
8423
9012
|
const queueServiceConfig = config?.queueServiceConfig;
|
|
8424
9013
|
if (queueServiceConfig) {
|
|
@@ -8428,15 +9017,13 @@ var start = async (config) => {
|
|
|
8428
9017
|
agentTaskConsumer.startPollingQueue();
|
|
8429
9018
|
}
|
|
8430
9019
|
}
|
|
8431
|
-
|
|
8432
|
-
|
|
8433
|
-
|
|
8434
|
-
|
|
8435
|
-
}
|
|
8436
|
-
logger3.error("Agent recovery failed", { error });
|
|
8437
|
-
}
|
|
9020
|
+
import_core36.agentInstanceManager.restore().then((stats) => {
|
|
9021
|
+
logger4.info(`Agent recovery complete: ${stats.restored} threads restored, ${stats.errors} errors`);
|
|
9022
|
+
}).catch((error) => {
|
|
9023
|
+
logger4.error("Agent recovery failed", { error });
|
|
9024
|
+
});
|
|
8438
9025
|
} catch (err) {
|
|
8439
|
-
|
|
9026
|
+
logger4.error("Server start failed", { error: err });
|
|
8440
9027
|
process.exit(1);
|
|
8441
9028
|
}
|
|
8442
9029
|
};
|