@rubytech/create-realagent 1.0.608 → 1.0.610

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@rubytech/create-realagent",
3
- "version": "1.0.608",
3
+ "version": "1.0.610",
4
4
  "description": "Install Real Agent — Built for agents. By agents.",
5
5
  "bin": {
6
6
  "create-realagent": "./dist/index.js"
@@ -1 +1 @@
1
- {"version":3,"file":"resolve-person.d.ts","sourceRoot":"","sources":["../../src/lib/resolve-person.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,MAAM,WAAW,gBAAgB;IAC/B,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,WAAW,aAAa;IAC5B,WAAW,EAAE,MAAM,CAAC;IACpB,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACtC;AAED,wBAAgB,kBAAkB,CAChC,UAAU,EAAE,gBAAgB,EAC5B,SAAS,EAAE,MAAM,GAChB,aAAa,CAsBf"}
1
+ {"version":3,"file":"resolve-person.d.ts","sourceRoot":"","sources":["../../src/lib/resolve-person.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,MAAM,WAAW,gBAAgB;IAC/B,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,WAAW,aAAa;IAC5B,WAAW,EAAE,MAAM,CAAC;IACpB,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACtC;AAED,wBAAgB,kBAAkB,CAChC,UAAU,EAAE,gBAAgB,EAC5B,SAAS,EAAE,MAAM,GAChB,aAAa,CA2Bf"}
@@ -16,8 +16,14 @@ export function resolvePersonMatch(identifier, accountId) {
16
16
  const queryParams = { accountId };
17
17
  let matchClause;
18
18
  if (nodeId) {
19
- matchClause = `MATCH (p:Person) WHERE elementId(p) = $nodeId AND p.accountId = $accountId`;
20
- queryParams.nodeId = nodeId;
19
+ if (nodeId.includes(":")) {
20
+ matchClause = `MATCH (p:Person) WHERE elementId(p) = $nodeId AND p.accountId = $accountId`;
21
+ queryParams.nodeId = nodeId;
22
+ }
23
+ else {
24
+ matchClause = `MATCH (p:Person) WHERE id(p) = $nodeId AND p.accountId = $accountId`;
25
+ queryParams.nodeId = parseInt(nodeId, 10);
26
+ }
21
27
  }
22
28
  else if (email) {
23
29
  matchClause = `MATCH (p:Person {email: $email, accountId: $accountId})`;
@@ -1 +1 @@
1
- {"version":3,"file":"resolve-person.js","sourceRoot":"","sources":["../../src/lib/resolve-person.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAaH,MAAM,UAAU,kBAAkB,CAChC,UAA4B,EAC5B,SAAiB;IAEjB,MAAM,EAAE,MAAM,EAAE,KAAK,EAAE,SAAS,EAAE,GAAG,UAAU,CAAC;IAEhD,IAAI,CAAC,MAAM,IAAI,CAAC,KAAK,IAAI,CAAC,SAAS,EAAE,CAAC;QACpC,MAAM,IAAI,KAAK,CAAC,qDAAqD,CAAC,CAAC;IACzE,CAAC;IAED,MAAM,WAAW,GAA4B,EAAE,SAAS,EAAE,CAAC;IAE3D,IAAI,WAAmB,CAAC;IACxB,IAAI,MAAM,EAAE,CAAC;QACX,WAAW,GAAG,4EAA4E,CAAC;QAC3F,WAAW,CAAC,MAAM,GAAG,MAAM,CAAC;IAC9B,CAAC;SAAM,IAAI,KAAK,EAAE,CAAC;QACjB,WAAW,GAAG,yDAAyD,CAAC;QACxE,WAAW,CAAC,KAAK,GAAG,KAAK,CAAC,WAAW,EAAE,CAAC;IAC1C,CAAC;SAAM,CAAC;QACN,WAAW,GAAG,iEAAiE,CAAC;QAChF,WAAW,CAAC,SAAS,GAAG,SAAU,CAAC,IAAI,EAAE,CAAC;IAC5C,CAAC;IAED,OAAO,EAAE,WAAW,EAAE,WAAW,EAAE,CAAC;AACtC,CAAC"}
1
+ {"version":3,"file":"resolve-person.js","sourceRoot":"","sources":["../../src/lib/resolve-person.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAaH,MAAM,UAAU,kBAAkB,CAChC,UAA4B,EAC5B,SAAiB;IAEjB,MAAM,EAAE,MAAM,EAAE,KAAK,EAAE,SAAS,EAAE,GAAG,UAAU,CAAC;IAEhD,IAAI,CAAC,MAAM,IAAI,CAAC,KAAK,IAAI,CAAC,SAAS,EAAE,CAAC;QACpC,MAAM,IAAI,KAAK,CAAC,qDAAqD,CAAC,CAAC;IACzE,CAAC;IAED,MAAM,WAAW,GAA4B,EAAE,SAAS,EAAE,CAAC;IAE3D,IAAI,WAAmB,CAAC;IACxB,IAAI,MAAM,EAAE,CAAC;QACX,IAAI,MAAM,CAAC,QAAQ,CAAC,GAAG,CAAC,EAAE,CAAC;YACzB,WAAW,GAAG,4EAA4E,CAAC;YAC3F,WAAW,CAAC,MAAM,GAAG,MAAM,CAAC;QAC9B,CAAC;aAAM,CAAC;YACN,WAAW,GAAG,qEAAqE,CAAC;YACpF,WAAW,CAAC,MAAM,GAAG,QAAQ,CAAC,MAAM,EAAE,EAAE,CAAC,CAAC;QAC5C,CAAC;IACH,CAAC;SAAM,IAAI,KAAK,EAAE,CAAC;QACjB,WAAW,GAAG,yDAAyD,CAAC;QACxE,WAAW,CAAC,KAAK,GAAG,KAAK,CAAC,WAAW,EAAE,CAAC;IAC1C,CAAC;SAAM,CAAC;QACN,WAAW,GAAG,iEAAiE,CAAC;QAChF,WAAW,CAAC,SAAS,GAAG,SAAU,CAAC,IAAI,EAAE,CAAC;IAC5C,CAAC;IAED,OAAO,EAAE,WAAW,EAAE,WAAW,EAAE,CAAC;AACtC,CAAC"}
@@ -48,13 +48,13 @@ When using WebSearch directly (not via the researcher specialist), the same disc
48
48
 
49
49
  - Always Read a file before using Edit or overwriting with Write. Writing a new file does not require a prior Read.
50
50
  - Your working directory is `$ACCOUNT_DIR` — your entire filesystem scope. Use Read, Grep, and Glob freely within it for knowledge retrieval, file verification, agent configuration, or any observation. Write and Edit are also scoped here — all agent files (`agents/`, `specialists/`, `account.json`) live in this directory. Never write to `$PLATFORM_ROOT/` or paths outside `$ACCOUNT_DIR`.
51
- - MCP tool schemas are deferred. Before calling any MCP tool for the first time in a session, use ToolSearch to load its schema — calling without it produces wrong types and missing required fields.
51
+ - MCP tool schemas are deferred. Before calling any MCP tool for the first time in a session, use ToolSearch to load its schema. Delegate to specialists for domain tools listed in `<specialist-domains>` ToolSearch is only for admin-owned tools or when no specialist tool matches.
52
52
 
53
53
  ## Tool Routing
54
54
 
55
55
  Plugins provide domain-specific tools that query their own data stores directly. `memory-search` is a general-purpose semantic search across the entire knowledge graph — it finds nodes by vector similarity, which means results are ranked by semantic closeness to the query, not by domain relevance. A query containing the word "email" will surface product documentation *about* email features before it surfaces actual Email nodes whose content is unrelated to the query wording.
56
56
 
57
- When the user's intent maps to a specific plugin's domain, use that plugin's tools — not `memory-search`. The `<plugin-manifest>` groups tools by plugin and describes each plugin's purpose and retrieval paths. Match user intent to the plugin domain first; fall back to `memory-search` only when the query genuinely spans multiple domains or no dedicated tool exists.
57
+ When the user's intent maps to a specific plugin's domain, use that plugin's tools — not `memory-search`. The `<plugin-manifest>` groups tools by plugin and describes each plugin's purpose and retrieval paths. The `<specialist-domains>` block within it lists every specialist-owned tool by name. Match user intent to a tool in these registries first; fall back to `memory-search` only when the query genuinely spans multiple domains or no tool in the manifest matches the intent.
58
58
 
59
59
  For prioritisation requests — "who should I call first", "which tasks are most urgent", "rank these by risk" — use `memory-rank` instead of reasoning over raw `memory-search` results. It retrieves the same candidate pool and returns an ordered list with per-item reasoning already synthesised, keeping the response grounded in properties and relationships rather than owner-supplied prose. For informal prioritisation in the middle of a wider conversation, reasoning directly over `memory-search` results remains fine.
60
60
 
@@ -182,8 +182,11 @@ Tasks live in the graph — not in files. The tasks plugin manages them.
182
182
 
183
183
  At session start, read `agents/admin/AGENTS.md`. This file lists installed specialists and when to use each. If the file is absent or empty, handle all requests directly.
184
184
 
185
- - **Single-tool calls** handle directly. No delegation overhead for simple lookups.
186
- - **Multi-step sequences (3+ tool calls within one domain)** — delegate to the matching specialist using the Agent tool with `subagent_type: "specialists:{name}"`.
185
+ The `<specialist-domains>` block lists every specialist-owned tool with a description. This is your primary routing table. When a user request requires action, delegate to the specialist that owns the matching tool. ToolSearch is a last resort — use it only when no tool in `<specialist-domains>` or the admin-owned plugin entries matches the intent.
186
+
187
+ - **Single-tool call** — delegate to the specialist that owns the tool. The specialist has domain knowledge and will execute correctly.
188
+ - **Multi-step sequence** — delegate to the specialist.
189
+ - **No matching tool in the manifest** — only then use ToolSearch or memory-search.
187
190
  - After a specialist run, synthesise its results into the final response to the user.
188
191
  - Retain all task management. Specialists do not create, update, or complete tasks.
189
192
  - To install or remove specialists, load the specialist management skill via `plugin-read` (find its path in the manifest under `admin`). Keep `agents/admin/AGENTS.md` in sync.
@@ -6814,7 +6814,7 @@ async function buildPluginManifest(enabledPlugins) {
6814
6814
  specialistGroups.set(specialist, existing);
6815
6815
  }
6816
6816
  }
6817
- const specialistToolSummary = /* @__PURE__ */ new Map();
6817
+ const specialistToolDetails = /* @__PURE__ */ new Map();
6818
6818
  let specialistMcpCount = 0;
6819
6819
  for (let i = 0; i < specialistPlugins.length; i++) {
6820
6820
  const { dir, parsed } = specialistPlugins[i];
@@ -6822,25 +6822,28 @@ async function buildPluginManifest(enabledPlugins) {
6822
6822
  if (mcpTools.length > 0) {
6823
6823
  specialistMcpCount++;
6824
6824
  const hiddenSet = new Set(parsed.hidden);
6825
- const toolNames = mcpTools.filter((t) => !hiddenSet.has(t.name)).map((t) => t.name);
6826
- totalTools += toolNames.length;
6827
- if (toolNames.length > 0) {
6825
+ const visibleTools = mcpTools.filter((t) => !hiddenSet.has(t.name));
6826
+ totalTools += visibleTools.length;
6827
+ if (visibleTools.length > 0) {
6828
6828
  const desc = parsed.description ? parsed.description.split(/\.\s/)[0].replace(/\.$/, "") : "";
6829
- specialistToolSummary.set(
6830
- dir,
6831
- desc ? `${desc}: ${toolNames.join(", ")}` : toolNames.join(", ")
6832
- );
6829
+ specialistToolDetails.set(dir, { desc, tools: visibleTools });
6833
6830
  }
6834
6831
  }
6835
6832
  }
6836
6833
  if (specialistGroups.size > 0) {
6837
6834
  lines.push("\n<specialist-domains>");
6838
- lines.push("Specialist subagents own these domains. Domain knowledge is embedded in each specialist's system prompt. Delegate by matching user intent to the specialist. Single-tool calls within these domains can be handled directly via ToolSearch.");
6835
+ lines.push("Specialist subagents own these domains. Match user intent to a tool below, then delegate to the specialist or use ToolSearch to load the schema and call directly. Only fall back to memory-search when no tool here matches.");
6839
6836
  for (const [specialist, plugins] of specialistGroups) {
6840
- lines.push(`${specialist}: ${plugins.join(", ")}`);
6837
+ lines.push(`
6838
+ ${specialist}: ${plugins.join(", ")}`);
6841
6839
  for (const plugin of plugins) {
6842
- const summary = specialistToolSummary.get(plugin);
6843
- if (summary) lines.push(` ${plugin} \u2014 ${summary}`);
6840
+ const details = specialistToolDetails.get(plugin);
6841
+ if (details) {
6842
+ for (const tool of details.tools) {
6843
+ const toolDesc = tool.description ? tool.description.split(/\.\s/)[0].replace(/\.$/, "") : "";
6844
+ lines.push(toolDesc ? ` ${tool.name} \u2014 ${toolDesc}` : ` ${tool.name}`);
6845
+ }
6846
+ }
6844
6847
  }
6845
6848
  }
6846
6849
  lines.push("</specialist-domains>");
@@ -9783,7 +9786,7 @@ Current session key: ${sessionKey}` : systemPromptBase;
9783
9786
  if (gatewayResult.searchQuery) {
9784
9787
  gwParts.push(` <search-query>${xmlEsc(gatewayResult.searchQuery)}</search-query>`);
9785
9788
  }
9786
- if (gatewayResult.screening.promptInjectionRisk) {
9789
+ if (gatewayResult.screening.promptInjectionRisk && agentType !== "admin") {
9787
9790
  gwParts.push(` <screening verdict="${xmlEsc(gatewayResult.screening.verdict)}" promptInjection="true">${xmlEsc(gatewayResult.screening.reason)}</screening>`);
9788
9791
  }
9789
9792
  if (gatewayResult.language !== "en") {