plugin-agent-orchestrator 1.0.27 → 1.0.28

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.
@@ -12,13 +12,13 @@ module.exports = {
12
12
  "antd": "5.24.2",
13
13
  "@ant-design/icons": "5.6.1",
14
14
  "ahooks": "3.7.8",
15
- "@nocobase/client-v2": "2.1.6",
16
- "@nocobase/client": "2.1.6",
17
- "@nocobase/server": "2.1.6",
18
- "@nocobase/database": "2.1.6",
15
+ "@nocobase/client-v2": "2.1.8",
16
+ "@nocobase/client": "2.1.8",
17
+ "@nocobase/server": "2.1.8",
18
+ "@nocobase/database": "2.1.8",
19
19
  "@langchain/langgraph": "0.2.74",
20
20
  "@langchain/core": "0.3.80",
21
- "@nocobase/ai": "2.1.6",
22
- "@nocobase/actions": "2.1.6",
23
- "@nocobase/plugin-ai": "2.1.6"
21
+ "@nocobase/ai": "2.1.8",
22
+ "@nocobase/actions": "2.1.8",
23
+ "@nocobase/plugin-ai": "2.1.8"
24
24
  };
@@ -42,11 +42,13 @@ class McpController {
42
42
  const skills = await this.plugin.db.getRepository("skillDefinitions").find({
43
43
  filter: { enabled: true }
44
44
  });
45
- const tools = await Promise.all(skills.map(async (skill) => ({
46
- name: skill.get("name").toLowerCase().replace(/[^a-z0-9_]/g, "_").replace(/_+/g, "_"),
47
- description: typeof this.plugin.getSkillDescriptionForAI === "function" ? await this.plugin.getSkillDescriptionForAI(skill) : skill.get("description"),
48
- inputSchema: (0, import_json_fields.parseJsonText)(skill.get("inputSchema"), null)
49
- })));
45
+ const tools = await Promise.all(
46
+ skills.map(async (skill) => ({
47
+ name: skill.get("name").toLowerCase().replace(/[^a-z0-9_]/g, "_").replace(/_+/g, "_"),
48
+ description: typeof this.plugin.getSkillDescriptionForAI === "function" ? await this.plugin.getSkillDescriptionForAI(skill) : skill.get("description"),
49
+ inputSchema: (0, import_json_fields.parseJsonText)(skill.get("inputSchema"), null)
50
+ }))
51
+ );
50
52
  ctx.body = {
51
53
  tools
52
54
  };
@@ -86,6 +88,15 @@ Files generated:
86
88
  ` + result.files.map((f) => {
87
89
  return `- [${f.name}](${f.downloadUrl})`;
88
90
  }).join("\n");
91
+ const manifest = result.files.map((f) => ({
92
+ name: f.name,
93
+ downloadUrl: f.downloadUrl,
94
+ mimetype: f.mimetype ?? f.mimeType ?? null,
95
+ size: f.size ?? null,
96
+ execId: result.execId ?? null
97
+ }));
98
+ textContent += `
99
+ <!--skillhub:files ${JSON.stringify(manifest)}-->`;
89
100
  }
90
101
  ctx.body = {
91
102
  content: [
package/package.json CHANGED
@@ -4,7 +4,7 @@
4
4
  "displayName.zh-CN": "代理协调器",
5
5
  "displayName.vi-VN": "Điều phối Agent",
6
6
  "description": "Hierarchical Multi-Agent orchestration for NocoBase AI Employees. Enables Leader agents to delegate tasks to Sub-Agent employees without modifying core plugin-ai.",
7
- "version": "1.0.27",
7
+ "version": "1.0.28",
8
8
  "license": "Apache-2.0",
9
9
  "main": "dist/server/index.js",
10
10
  "keywords": [
@@ -13,13 +13,20 @@ export class McpController {
13
13
  filter: { enabled: true },
14
14
  });
15
15
 
16
- const tools = await Promise.all(skills.map(async (skill: any) => ({
17
- name: skill.get('name').toLowerCase().replace(/[^a-z0-9_]/g, '_').replace(/_+/g, '_'),
18
- description: typeof this.plugin.getSkillDescriptionForAI === 'function'
19
- ? await this.plugin.getSkillDescriptionForAI(skill)
20
- : skill.get('description'),
16
+ const tools = await Promise.all(
17
+ skills.map(async (skill: any) => ({
18
+ name: skill
19
+ .get('name')
20
+ .toLowerCase()
21
+ .replace(/[^a-z0-9_]/g, '_')
22
+ .replace(/_+/g, '_'),
23
+ description:
24
+ typeof this.plugin.getSkillDescriptionForAI === 'function'
25
+ ? await this.plugin.getSkillDescriptionForAI(skill)
26
+ : skill.get('description'),
21
27
  inputSchema: parseJsonText(skill.get('inputSchema'), null),
22
- })));
28
+ })),
29
+ );
23
30
 
24
31
  ctx.body = {
25
32
  tools,
@@ -44,8 +51,13 @@ export class McpController {
44
51
  filter: { enabled: true },
45
52
  });
46
53
 
47
- const skill = skills.find((s: any) =>
48
- s.get('name').toLowerCase().replace(/[^a-z0-9_]/g, '_').replace(/_+/g, '_') === name
54
+ const skill = skills.find(
55
+ (s: any) =>
56
+ s
57
+ .get('name')
58
+ .toLowerCase()
59
+ .replace(/[^a-z0-9_]/g, '_')
60
+ .replace(/_+/g, '_') === name,
49
61
  );
50
62
 
51
63
  if (!skill) {
@@ -54,15 +66,30 @@ export class McpController {
54
66
 
55
67
  try {
56
68
  const result = await this.plugin.executeSkill(skill, args || {}, ctx);
57
-
69
+
58
70
  let textContent = `Executed successfully.`;
59
71
  if (result.stdout) textContent += `\nOutput:\n${result.stdout}`;
60
72
  if (result.stderr) textContent += `\nErrors:\n${result.stderr}`;
61
-
73
+
62
74
  if (result.files?.length) {
63
- textContent += `\nFiles generated:\n` + result.files.map((f: any) => {
64
- return `- [${f.name}](${f.downloadUrl})`;
65
- }).join('\n');
75
+ textContent +=
76
+ `\nFiles generated:\n` +
77
+ result.files
78
+ .map((f: any) => {
79
+ return `- [${f.name}](${f.downloadUrl})`;
80
+ })
81
+ .join('\n');
82
+
83
+ // Embed a trustworthy file manifest so the chat file-preview plugin can resolve the
84
+ // real download URL by filename, instead of guessing it from LLM-rewritten links.
85
+ const manifest = result.files.map((f: any) => ({
86
+ name: f.name,
87
+ downloadUrl: f.downloadUrl,
88
+ mimetype: f.mimetype ?? f.mimeType ?? null,
89
+ size: f.size ?? null,
90
+ execId: result.execId ?? null,
91
+ }));
92
+ textContent += `\n<!--skillhub:files ${JSON.stringify(manifest)}-->`;
66
93
  }
67
94
 
68
95
  ctx.body = {
@@ -70,7 +97,7 @@ export class McpController {
70
97
  {
71
98
  type: 'text',
72
99
  text: textContent,
73
- }
100
+ },
74
101
  ],
75
102
  isError: result.status !== 'succeeded',
76
103
  };