@engramx/mcp 0.1.0 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/LICENSE CHANGED
@@ -175,7 +175,7 @@
175
175
 
176
176
  END OF TERMS AND CONDITIONS
177
177
 
178
- Copyright 2025 EngramX contributors
178
+ Copyright 2025-2026 Vaughn Hew
179
179
 
180
180
  Licensed under the Apache License, Version 2.0 (the "License");
181
181
  you may not use this file except in compliance with the License.
package/dist/server.js CHANGED
@@ -9,7 +9,7 @@ import { EngramClient, ProfileManager, SessionManager } from '@engramx/client';
9
9
  import { registerTools } from './tools.js';
10
10
  import { registerProfileTools } from './profile-tools.js';
11
11
  import { registerResources } from './resources.js';
12
- // --- Environment variables (same names as agent-skill.ts) ---
12
+ // --- Environment variables ---
13
13
  const canisterId = process.env['ENGRAM_CANISTER_ID'] || process.env['VAULT_CANISTER_ID'];
14
14
  if (!canisterId) {
15
15
  console.error('Error: ENGRAM_CANISTER_ID environment variable is required.\n' +
@@ -35,9 +35,8 @@ const engram = new EngramClient({
35
35
  cacheMaxAge: 60_000,
36
36
  });
37
37
  // --- MCP Server ---
38
- const server = new McpServer({
39
- name: 'engramx',
40
- version: '0.1.0',
38
+ const server = new McpServer({ name: 'engramx', version: '0.1.0' }, {
39
+ instructions: 'engramx gives this agent persistent memory in a user-owned canister (an engram) plus an ic402 paid-services marketplace. Operator sessions are APPEND-ONLY: memory can be read and appended to, never overwritten or deleted. Memory flow: engram_list_memory_files (discover paths) -> engram_read_memory or engram_read_memory_batch (fetch content) -> engram_append_memory (add content; memory.append scope; config/ and secrets/ paths are owner-only). engram_memory_history shows prior versions of one file; engram_read_audit_log shows the engram-wide operation ledger. Free reads: engram_status and engram_list_services. engram_wallet_balance reports canister cycles (infrastructure fuel), NOT token money. MONEY: engram_submit_service_request SPENDS ckUSDC (settles a payment at the quoted service price into escrow at submit time) and engram_confirm_job irreversibly releases that escrow to the operator; call these only when the user intends to pay. engram_dispute_job blocks payout instead. engram_get_job_result is a free read.',
41
40
  });
42
41
  const profile = new ProfileManager(engram);
43
42
  const sessions = new SessionManager(engram);
@@ -1 +1 @@
1
- {"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"AAAA,gGAAgG;AAChG,yFAAyF;AAEzF,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AACpE,OAAO,EAAE,oBAAoB,EAAE,MAAM,2CAA2C,CAAC;AACjF,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AACjC,OAAO,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AACrC,OAAO,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC;AAClC,OAAO,EAAE,YAAY,EAAE,cAAc,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAC;AAC/E,OAAO,EAAE,aAAa,EAAE,MAAM,YAAY,CAAC;AAC3C,OAAO,EAAE,oBAAoB,EAAE,MAAM,oBAAoB,CAAC;AAC1D,OAAO,EAAE,iBAAiB,EAAE,MAAM,gBAAgB,CAAC;AAEnD,+DAA+D;AAE/D,MAAM,UAAU,GAAG,OAAO,CAAC,GAAG,CAAC,oBAAoB,CAAC,IAAI,OAAO,CAAC,GAAG,CAAC,mBAAmB,CAAC,CAAC;AACzF,IAAI,CAAC,UAAU,EAAE,CAAC;IAChB,OAAO,CAAC,KAAK,CACX,+DAA+D;QAC7D,2EAA2E;QAC3E,4EAA4E,CAC/E,CAAC;IACF,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC;AAED,MAAM,cAAc,GAClB,OAAO,CAAC,GAAG,CAAC,yBAAyB,CAAC;IACtC,OAAO,CAAC,GAAG,CAAC,0BAA0B,CAAC;IACvC,OAAO,CAAC,GAAG,CAAC,wBAAwB,CAAC;IACrC,IAAI,CAAC,OAAO,EAAE,EAAE,UAAU,EAAE,aAAa,CAAC,CAAC;AAE7C,IAAI,CAAC,UAAU,CAAC,cAAc,CAAC,EAAE,CAAC;IAChC,OAAO,CAAC,KAAK,CACX,mCAAmC,cAAc,KAAK;QACpD,kFAAkF,CACrF,CAAC;IACF,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC;AAED,MAAM,IAAI,GAAG,OAAO,CAAC,GAAG,CAAC,aAAa,CAAC,IAAI,iBAAiB,CAAC;AAE7D,iBAAiB;AAEjB,MAAM,MAAM,GAAG,IAAI,YAAY,CAAC;IAC9B,UAAU;IACV,cAAc;IACd,IAAI;IACJ,WAAW,EAAE,MAAM;CACpB,CAAC,CAAC;AAEH,qBAAqB;AAErB,MAAM,MAAM,GAAG,IAAI,SAAS,CAAC;IAC3B,IAAI,EAAE,SAAS;IACf,OAAO,EAAE,OAAO;CACjB,CAAC,CAAC;AAEH,MAAM,OAAO,GAAG,IAAI,cAAc,CAAC,MAAM,CAAC,CAAC;AAC3C,MAAM,QAAQ,GAAG,IAAI,cAAc,CAAC,MAAM,CAAC,CAAC;AAE5C,aAAa,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;AAC9B,oBAAoB,CAAC,MAAM,EAAE,OAAO,EAAE,QAAQ,CAAC,CAAC;AAChD,iBAAiB,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;AAElC,4BAA4B;AAE5B,MAAM,SAAS,GAAG,IAAI,oBAAoB,EAAE,CAAC;AAC7C,MAAM,MAAM,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC;AAEhC,qDAAqD;AACrD,OAAO,CAAC,KAAK,CAAC,yCAAyC,UAAU,WAAW,IAAI,GAAG,CAAC,CAAC"}
1
+ {"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"AAAA,gGAAgG;AAChG,yFAAyF;AAEzF,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AACpE,OAAO,EAAE,oBAAoB,EAAE,MAAM,2CAA2C,CAAC;AACjF,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AACjC,OAAO,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AACrC,OAAO,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC;AAClC,OAAO,EAAE,YAAY,EAAE,cAAc,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAC;AAC/E,OAAO,EAAE,aAAa,EAAE,MAAM,YAAY,CAAC;AAC3C,OAAO,EAAE,oBAAoB,EAAE,MAAM,oBAAoB,CAAC;AAC1D,OAAO,EAAE,iBAAiB,EAAE,MAAM,gBAAgB,CAAC;AAEnD,gCAAgC;AAEhC,MAAM,UAAU,GAAG,OAAO,CAAC,GAAG,CAAC,oBAAoB,CAAC,IAAI,OAAO,CAAC,GAAG,CAAC,mBAAmB,CAAC,CAAC;AACzF,IAAI,CAAC,UAAU,EAAE,CAAC;IAChB,OAAO,CAAC,KAAK,CACX,+DAA+D;QAC7D,2EAA2E;QAC3E,4EAA4E,CAC/E,CAAC;IACF,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC;AAED,MAAM,cAAc,GAClB,OAAO,CAAC,GAAG,CAAC,yBAAyB,CAAC;IACtC,OAAO,CAAC,GAAG,CAAC,0BAA0B,CAAC;IACvC,OAAO,CAAC,GAAG,CAAC,wBAAwB,CAAC;IACrC,IAAI,CAAC,OAAO,EAAE,EAAE,UAAU,EAAE,aAAa,CAAC,CAAC;AAE7C,IAAI,CAAC,UAAU,CAAC,cAAc,CAAC,EAAE,CAAC;IAChC,OAAO,CAAC,KAAK,CACX,mCAAmC,cAAc,KAAK;QACpD,kFAAkF,CACrF,CAAC;IACF,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC;AAED,MAAM,IAAI,GAAG,OAAO,CAAC,GAAG,CAAC,aAAa,CAAC,IAAI,iBAAiB,CAAC;AAE7D,iBAAiB;AAEjB,MAAM,MAAM,GAAG,IAAI,YAAY,CAAC;IAC9B,UAAU;IACV,cAAc;IACd,IAAI;IACJ,WAAW,EAAE,MAAM;CACpB,CAAC,CAAC;AAEH,qBAAqB;AAErB,MAAM,MAAM,GAAG,IAAI,SAAS,CAC1B,EAAE,IAAI,EAAE,SAAS,EAAE,OAAO,EAAE,OAAO,EAAE,EACrC;IACE,YAAY,EACV,qgCAAqgC;CACxgC,CACF,CAAC;AAEF,MAAM,OAAO,GAAG,IAAI,cAAc,CAAC,MAAM,CAAC,CAAC;AAC3C,MAAM,QAAQ,GAAG,IAAI,cAAc,CAAC,MAAM,CAAC,CAAC;AAE5C,aAAa,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;AAC9B,oBAAoB,CAAC,MAAM,EAAE,OAAO,EAAE,QAAQ,CAAC,CAAC;AAChD,iBAAiB,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;AAElC,4BAA4B;AAE5B,MAAM,SAAS,GAAG,IAAI,oBAAoB,EAAE,CAAC;AAC7C,MAAM,MAAM,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC;AAEhC,qDAAqD;AACrD,OAAO,CAAC,KAAK,CAAC,yCAAyC,UAAU,WAAW,IAAI,GAAG,CAAC,CAAC"}
package/dist/tools.js CHANGED
@@ -7,18 +7,22 @@ const MAX_PATH_LENGTH = 1024;
7
7
  const E8S_PER_ICP = 100_000_000;
8
8
  function validatePath(p) {
9
9
  if (!p || p.length === 0)
10
- return 'Path cannot be empty';
10
+ return 'Path cannot be empty (rejected client-side; no request was sent and nothing changed — supply a non-empty path and retry immediately)';
11
11
  if (p.length > MAX_PATH_LENGTH)
12
- return 'Path exceeds maximum length';
12
+ return `Path exceeds maximum length (${MAX_PATH_LENGTH} chars); rejected client-side — no request sent; shorten the path and retry immediately`;
13
13
  if (p.includes('\0'))
14
- return 'Path contains null byte';
14
+ return 'Path contains null byte (rejected client-side; no request sent — remove the null character and retry immediately)';
15
15
  if (p.includes('..'))
16
- return 'Path traversal sequences not allowed';
16
+ return 'Path traversal sequences not allowed (".." rejected client-side; no request sent — use a plain path without ".." and retry immediately)';
17
17
  return null;
18
18
  }
19
19
  export function registerTools(server, engram) {
20
20
  // 1. engram_read_memory
21
- server.tool('engram_read_memory', 'Read a memory file from the engram (e.g. "MEMORY.md", "memory/2026-02-11.md"). Returns content, version, and last modified timestamp.', { path: z.string().describe('File path in the engram') }, async ({ path }) => {
21
+ server.tool('engram_read_memory', 'Read ONE memory file by exact path (e.g. "MEMORY.md", "memory/2026-02-11.md") and return its current decrypted content as JSON {path, content, version, lastModifiedAt}. Use when the path is known; discover paths with engram_list_memory_files. For several files use engram_read_memory_batch; for prior versions use engram_memory_history. Read-only.', {
22
+ path: z
23
+ .string()
24
+ .describe('Exact memory file path, e.g. "MEMORY.md" or "identity/preferences.md". Non-empty, max 1024 bytes, no ".." traversal.'),
25
+ }, async ({ path }) => {
22
26
  const pathErr = validatePath(path);
23
27
  if (pathErr)
24
28
  return { content: [{ type: 'text', text: pathErr }], isError: true };
@@ -41,7 +45,10 @@ export function registerTools(server, engram) {
41
45
  catch (err) {
42
46
  return {
43
47
  content: [
44
- { type: 'text', text: `Error: ${err instanceof Error ? err.message : String(err)}` },
48
+ {
49
+ type: 'text',
50
+ text: `Error: ${err instanceof Error ? err.message : String(err)}\n[The canister message above is authoritative — follow its embedded next-action guidance. If it says a settlement/payment is pending confirmation, funds may be in flight: do NOT re-pay or resubmit.]`,
51
+ },
45
52
  ],
46
53
  isError: true,
47
54
  };
@@ -51,9 +58,13 @@ export function registerTools(server, engram) {
51
58
  // are append-only. Owner uses the dashboard at engramx.ai or the canister IDL
52
59
  // directly via Internet Identity.)
53
60
  // 2. engram_append_memory
54
- server.tool('engram_append_memory', 'Append content to a memory file. Creates the file if it does not exist. Cannot modify owner-protected paths.', {
55
- path: z.string().describe('File path'),
56
- content: z.string().describe('Content to append'),
61
+ server.tool('engram_append_memory', 'Append text to a memory file; the file is created if it does not exist. APPEND-ONLY: never overwrites or deletes, and this is the ONLY mutating memory tool on this surface (no write/delete/rollback exists here). Requires the memory.append scope (operator with canAppendMemory, or owner). Rejected: config/ and secrets/ paths (owner-only), owner-protected paths, and while guardian writes are paused. Returns JSON {path, version} with the new version number.', {
62
+ path: z
63
+ .string()
64
+ .describe('Target file path to append to; created if absent. Max 1024 bytes, no ".."; operators cannot use the config/ or secrets/ prefixes (owner-only).'),
65
+ content: z
66
+ .string()
67
+ .describe('Text to append. The client joins it to the existing file content with a newline and re-encrypts before storing.'),
57
68
  }, async ({ path, content }) => {
58
69
  const pathErr = validatePath(path);
59
70
  if (pathErr)
@@ -67,14 +78,17 @@ export function registerTools(server, engram) {
67
78
  catch (err) {
68
79
  return {
69
80
  content: [
70
- { type: 'text', text: `Error: ${err instanceof Error ? err.message : String(err)}` },
81
+ {
82
+ type: 'text',
83
+ text: `Error: ${err instanceof Error ? err.message : String(err)}\n[The canister message above is authoritative — follow its embedded next-action guidance. If it says a settlement/payment is pending confirmation, funds may be in flight: do NOT re-pay or resubmit.]`,
84
+ },
71
85
  ],
72
86
  isError: true,
73
87
  };
74
88
  }
75
89
  });
76
90
  // 3. engram_list_memory_files
77
- server.tool('engram_list_memory_files', 'List all memory files stored in the engram. Returns path, version, and last modified timestamp for each file.', async () => {
91
+ server.tool('engram_list_memory_files', 'List metadata for EVERY memory file: one {path, version, lastModifiedAt} entry per file, NO content. Call this first to discover paths, then fetch content with engram_read_memory or engram_read_memory_batch. Read-only.', async () => {
78
92
  try {
79
93
  const files = await engram.listMemoryFiles();
80
94
  return {
@@ -84,23 +98,36 @@ export function registerTools(server, engram) {
84
98
  catch (err) {
85
99
  return {
86
100
  content: [
87
- { type: 'text', text: `Error: ${err instanceof Error ? err.message : String(err)}` },
101
+ {
102
+ type: 'text',
103
+ text: `Error: ${err instanceof Error ? err.message : String(err)}\n[The canister message above is authoritative — follow its embedded next-action guidance. If it says a settlement/payment is pending confirmation, funds may be in flight: do NOT re-pay or resubmit.]`,
104
+ },
88
105
  ],
89
106
  isError: true,
90
107
  };
91
108
  }
92
109
  });
93
110
  // 5. engram_read_memory_batch
94
- server.tool('engram_read_memory_batch', 'Read multiple memory files in a single call. More efficient than multiple engram_read_memory calls.',
111
+ server.tool('engram_read_memory_batch', 'Read up to 50 memory files in one call. Returns a JSON array where each element is {path, content, version, lastModifiedAt} on success or {path, error} for that file; partial success is normal and a missing file never fails the whole batch. Prefer this over repeated engram_read_memory for 2+ known paths. Read-only.',
95
112
  // Cap matches the canister's MAX_BATCH_READ_PATHS (50) and tool-schemas.json maxItems —
96
113
  // a larger batch would pass zod here only to be rejected wholesale canister-side.
97
- { paths: z.array(z.string()).max(50).describe('Array of file paths to read (max 50)') }, async ({ paths }) => {
114
+ {
115
+ paths: z
116
+ .array(z.string())
117
+ .max(50)
118
+ .describe('Exact file paths to fetch (max 50; a larger batch is rejected wholesale). Discover paths with engram_list_memory_files.'),
119
+ }, async ({ paths }) => {
98
120
  try {
99
121
  for (const p of paths) {
100
122
  const pathErr = validatePath(p);
101
123
  if (pathErr)
102
124
  return {
103
- content: [{ type: 'text', text: `Invalid path "${p}": ${pathErr}` }],
125
+ content: [
126
+ {
127
+ type: 'text',
128
+ text: `Invalid path "${p}": ${pathErr}. Whole batch rejected client-side — no canister call was made and no path was read. Fix this path and resend the batch.`,
129
+ },
130
+ ],
104
131
  isError: true,
105
132
  };
106
133
  }
@@ -123,14 +150,17 @@ export function registerTools(server, engram) {
123
150
  catch (err) {
124
151
  return {
125
152
  content: [
126
- { type: 'text', text: `Error: ${err instanceof Error ? err.message : String(err)}` },
153
+ {
154
+ type: 'text',
155
+ text: `Error: ${err instanceof Error ? err.message : String(err)}\n[The canister message above is authoritative — follow its embedded next-action guidance. If it says a settlement/payment is pending confirmation, funds may be in flight: do NOT re-pay or resubmit.]`,
156
+ },
127
157
  ],
128
158
  isError: true,
129
159
  };
130
160
  }
131
161
  });
132
162
  // 6. engram_memory_history
133
- server.tool('engram_memory_history', 'Get the version history of a memory file, showing all modifications with timestamps and operation types.', { path: z.string().describe('File path') }, async ({ path }) => {
163
+ server.tool('engram_memory_history', 'Get the full version history of ONE memory file. Returns an array of {version, modifiedBy, modifiedAt, operation, contentSnapshot} where operation is Set|Append|Rollback and contentSnapshot is the decrypted content of that prior version (empty array if the path is unknown). Use engram_read_memory for just the current version; use engram_read_audit_log for the engram-wide operation ledger. Read-only.', { path: z.string().describe('Path of the memory file whose history to fetch.') }, async ({ path }) => {
134
164
  const pathErr = validatePath(path);
135
165
  if (pathErr)
136
166
  return { content: [{ type: 'text', text: pathErr }], isError: true };
@@ -143,14 +173,17 @@ export function registerTools(server, engram) {
143
173
  catch (err) {
144
174
  return {
145
175
  content: [
146
- { type: 'text', text: `Error: ${err instanceof Error ? err.message : String(err)}` },
176
+ {
177
+ type: 'text',
178
+ text: `Error: ${err instanceof Error ? err.message : String(err)}\n[The canister message above is authoritative — follow its embedded next-action guidance. If it says a settlement/payment is pending confirmation, funds may be in flight: do NOT re-pay or resubmit.]`,
179
+ },
147
180
  ],
148
181
  isError: true,
149
182
  };
150
183
  }
151
184
  });
152
185
  // 7. engram_wallet_balance
153
- server.tool('engram_wallet_balance', 'Check the engram canister cycles balance (canister fuel).', async () => {
186
+ server.tool('engram_wallet_balance', 'Get the engram canister CYCLES balance: infrastructure fuel, NOT a token or money balance (no ckUSDC/ICP amounts). Returns JSON {cyclesBalance} (bigint serialized as a string). Requires wallet.read (canReadWallet) or owner. For a broader health snapshot use engram_status.', async () => {
154
187
  try {
155
188
  const cycles = await engram.walletBalance();
156
189
  // Match HTTP MCP shape: {cyclesBalance: <number-or-string>}
@@ -167,7 +200,10 @@ export function registerTools(server, engram) {
167
200
  catch (err) {
168
201
  return {
169
202
  content: [
170
- { type: 'text', text: `Error: ${err instanceof Error ? err.message : String(err)}` },
203
+ {
204
+ type: 'text',
205
+ text: `Error: ${err instanceof Error ? err.message : String(err)}\n[The canister message above is authoritative — follow its embedded next-action guidance. If it says a settlement/payment is pending confirmation, funds may be in flight: do NOT re-pay or resubmit.]`,
206
+ },
171
207
  ],
172
208
  isError: true,
173
209
  };
@@ -180,7 +216,7 @@ export function registerTools(server, engram) {
180
216
  // `operatorTransfer` method and advertised a `wallet.spend` capability that
181
217
  // contradicts the operator invariant.)
182
218
  // 9. engram_status
183
- server.tool('engram_status', 'Get engram canister health and status: memory file count, operator count, cycles balance, version, and more.', async () => {
219
+ server.tool('engram_status', 'FREE health snapshot of the engram canister: version, memoryFileCount, auditLogSize, operatorCount, guardianCount, paymentsFrozen, writesPaused, backup and write counters, encryptionEnabled; owner and cyclesBalance are included only when the session is an authorized owner/operator/guardian (masked to null/0 otherwise). Check paymentsFrozen/writesPaused before paying or appending. For just the cycles number use engram_wallet_balance.', async () => {
184
220
  try {
185
221
  const status = await engram.status();
186
222
  return {
@@ -190,22 +226,28 @@ export function registerTools(server, engram) {
190
226
  catch (err) {
191
227
  return {
192
228
  content: [
193
- { type: 'text', text: `Error: ${err instanceof Error ? err.message : String(err)}` },
229
+ {
230
+ type: 'text',
231
+ text: `Error: ${err instanceof Error ? err.message : String(err)}\n[The canister message above is authoritative — follow its embedded next-action guidance. If it says a settlement/payment is pending confirmation, funds may be in flight: do NOT re-pay or resubmit.]`,
232
+ },
194
233
  ],
195
234
  isError: true,
196
235
  };
197
236
  }
198
237
  });
199
238
  // engram_read_audit_log
200
- server.tool('engram_read_audit_log', 'Read the engram audit log. Returns timestamped entries of all operations performed on the engram.', {
201
- fromIndex: z.number().optional().describe('Starting index (default: 0)'),
239
+ server.tool('engram_read_audit_log', 'Read the engram-wide chained audit log: who did what across memory writes, payments, services, and custody. Returns entries {id, timestamp, caller, callerRole, operation, details, success}. For content changes of ONE file use engram_memory_history instead. Requires an authenticated owner/operator/guardian session; returns [] if unauthorized.', {
240
+ fromIndex: z
241
+ .number()
242
+ .optional()
243
+ .describe('Entry index to start reading from (0 = oldest; default 0)'),
202
244
  limit: z
203
245
  .number()
204
246
  .min(1)
205
247
  .max(1000)
206
248
  .optional()
207
249
  .default(100)
208
- .describe('Max entries to return (default: 100)'),
250
+ .describe('Max entries to return (default 100, max 1000; the canister caps a single read at 500)'),
209
251
  }, async ({ fromIndex, limit }) => {
210
252
  try {
211
253
  const entries = await engram.readAuditLog(fromIndex ?? 0, limit);
@@ -216,14 +258,17 @@ export function registerTools(server, engram) {
216
258
  catch (err) {
217
259
  return {
218
260
  content: [
219
- { type: 'text', text: `Error: ${err instanceof Error ? err.message : String(err)}` },
261
+ {
262
+ type: 'text',
263
+ text: `Error: ${err instanceof Error ? err.message : String(err)}\n[The canister message above is authoritative — follow its embedded next-action guidance. If it says a settlement/payment is pending confirmation, funds may be in flight: do NOT re-pay or resubmit.]`,
264
+ },
220
265
  ],
221
266
  isError: true,
222
267
  };
223
268
  }
224
269
  });
225
270
  // === ic402 Service Marketplace ===
226
- server.tool('engram_list_services', 'List available paid services registered on this engram.', {}, async () => {
271
+ server.tool('engram_list_services', 'FREE discovery of ic402 paid services on this engram (enabled services only): read-only, spends nothing. Each entry includes {id, name, enabled}; pass the id as serviceId to engram_submit_service_request, which is the step that actually pays.', {}, async () => {
227
272
  try {
228
273
  const services = await engram.listServices();
229
274
  return { content: [{ type: 'text', text: jsonText(services) }] };
@@ -231,15 +276,22 @@ export function registerTools(server, engram) {
231
276
  catch (err) {
232
277
  return {
233
278
  content: [
234
- { type: 'text', text: `Error: ${err instanceof Error ? err.message : String(err)}` },
279
+ {
280
+ type: 'text',
281
+ text: `Error: ${err instanceof Error ? err.message : String(err)}\n[The canister message above is authoritative — follow its embedded next-action guidance. If it says a settlement/payment is pending confirmation, funds may be in flight: do NOT re-pay or resubmit.]`,
282
+ },
235
283
  ],
236
284
  isError: true,
237
285
  };
238
286
  }
239
287
  });
240
- server.tool('engram_submit_service_request', 'Submit a paid service request. Returns a job ID for polling.', {
241
- serviceId: z.string().describe('ID of the service to request'),
242
- params: z.string().describe('Request parameters (will be UTF-8 encoded)'),
288
+ server.tool('engram_submit_service_request', 'MOVES FUNDS: submit a paid request to an ic402 service (auto-pays via x402). Calling this settles a payment at submit time: the client auto-approves ckUSDC and the canister pulls the quoted service price (from the service record; see engram_list_services) into escrow, then creates a job. On success the returned {jobId} means payment SETTLED into escrow — poll it with engram_get_job_result to a terminal status; NEVER resubmit after success (resubmitting pays again). Returns {approvalPending} instead when the charge exceeds the owner spending policy (owner must approve first). If an error says settlement is pending confirmation, funds may be in flight — wait and reconcile, do NOT re-pay. Requires wallet.spend and payments not frozen; only call when the user intends to pay. How escrow is released depends on the service verification mode: BuyerConfirm jobs pay the operator only after engram_confirm_job; AutoSettle/HashMatch/ZkGroth16 jobs pay automatically once the operator delivers a valid result.', {
289
+ serviceId: z
290
+ .string()
291
+ .describe('id of an enabled service from engram_list_services; its pricing sets the amount charged'),
292
+ params: z
293
+ .string()
294
+ .describe('Service-specific input, UTF-8 encoded and passed to the service as opaque bytes (JSON by convention)'),
243
295
  }, async ({ serviceId, params }) => {
244
296
  try {
245
297
  // Auto-pay: builds the x402 payment (ICRC-2 approve + retry) so a paid request
@@ -250,15 +302,21 @@ export function registerTools(server, engram) {
250
302
  catch (err) {
251
303
  return {
252
304
  content: [
253
- { type: 'text', text: `Error: ${err instanceof Error ? err.message : String(err)}` },
305
+ {
306
+ type: 'text',
307
+ text: `Error: ${err instanceof Error ? err.message : String(err)}\n[The canister message above is authoritative — follow its embedded next-action guidance. If it says a settlement/payment is pending confirmation, funds may be in flight: do NOT re-pay or resubmit.]`,
308
+ },
254
309
  ],
255
310
  isError: true,
256
311
  };
257
312
  }
258
313
  });
259
- server.tool('engram_get_job_result', 'Poll a service job until it reaches a terminal status. Returns the full job object.', {
260
- jobId: z.string().describe('Job ID to poll'),
261
- maxAttempts: z.number().optional().describe('Max polling attempts (default 30)'),
314
+ server.tool('engram_get_job_result', 'Poll an ic402 service job every 2s until it reaches a terminal status (Settled, Verified, Refunded, Expired, or Disputed), then return the full job object {id, status, serviceId, amount, result}. Read-only, moves NO funds; errors if the job does not terminate within maxAttempts. Reading a result does not pay the operator: use engram_confirm_job to release payment or engram_dispute_job to reject.', {
315
+ jobId: z.string().describe('Job ID returned by engram_submit_service_request (e.g. "job-3")'),
316
+ maxAttempts: z
317
+ .number()
318
+ .optional()
319
+ .describe('Max 2-second poll cycles before giving up (default 30, about 60s total)'),
262
320
  }, async ({ jobId, maxAttempts }) => {
263
321
  try {
264
322
  const job = await engram.pollJobResult(jobId, maxAttempts ?? 30);
@@ -267,40 +325,67 @@ export function registerTools(server, engram) {
267
325
  catch (err) {
268
326
  return {
269
327
  content: [
270
- { type: 'text', text: `Error: ${err instanceof Error ? err.message : String(err)}` },
328
+ {
329
+ type: 'text',
330
+ text: `Error: ${err instanceof Error ? err.message : String(err)}\n[The canister message above is authoritative — follow its embedded next-action guidance. If it says a settlement/payment is pending confirmation, funds may be in flight: do NOT re-pay or resubmit.]`,
331
+ },
271
332
  ],
272
333
  isError: true,
273
334
  };
274
335
  }
275
336
  });
276
- server.tool('engram_dispute_job', 'Dispute a completed job (for BuyerConfirm verification method).', {
277
- jobId: z.string().describe('Job ID to dispute'),
278
- reason: z.string().describe('Reason for the dispute'),
337
+ server.tool('engram_dispute_job', 'Reject a completed BuyerConfirm job as the buyer who paid for it: marks the job Disputed and BLOCKS payout to the operator. No immediate refund; the owner resolves the dispute or escrow auto-refunds after timeout. Only valid while the job status is Submitted, and only for the same principal that submitted it. Unhappy-path counterpart of engram_confirm_job (which releases payment).', {
338
+ jobId: z
339
+ .string()
340
+ .describe('Job ID of the Submitted BuyerConfirm job to dispute (must be one this caller submitted)'),
341
+ reason: z.string().describe('Free-text explanation for the dispute; stored in the audit log'),
279
342
  }, async ({ jobId, reason }) => {
280
343
  try {
281
344
  await engram.disputeJob(jobId, reason);
282
- return { content: [{ type: 'text', text: `Disputed job ${jobId}` }] };
345
+ return {
346
+ content: [
347
+ {
348
+ type: 'text',
349
+ text: `Disputed job ${jobId} — job is now marked Disputed. No funds moved yet: this is NOT a refund. Resolution (refund or release) happens later via the owner resolveDispute or timeout. Next action: wait for resolution; do not re-dispute and do not pay again.`,
350
+ },
351
+ ],
352
+ };
283
353
  }
284
354
  catch (err) {
285
355
  return {
286
356
  content: [
287
- { type: 'text', text: `Error: ${err instanceof Error ? err.message : String(err)}` },
357
+ {
358
+ type: 'text',
359
+ text: `Error: ${err instanceof Error ? err.message : String(err)}\n[The canister message above is authoritative — follow its embedded next-action guidance. If it says a settlement/payment is pending confirmation, funds may be in flight: do NOT re-pay or resubmit.]`,
360
+ },
288
361
  ],
289
362
  isError: true,
290
363
  };
291
364
  }
292
365
  });
293
- server.tool('engram_confirm_job', 'Confirm a completed job result (for BuyerConfirm verification), releasing payment to the operator.', {
294
- jobId: z.string().describe('Job ID to confirm'),
366
+ server.tool('engram_confirm_job', 'MOVES FUNDS: accept a completed BuyerConfirm job, irreversibly RELEASING the escrowed payment to the operator. The amount/asset is whatever engram_submit_service_request escrowed at the quoted service price (ckUSDC from the engram pool). Only valid while the job status is Submitted, and only for the buyer principal that submitted it. Verify the result via engram_get_job_result first; if it is bad, use engram_dispute_job instead (blocks payout). Requires wallet.spend.', {
367
+ jobId: z
368
+ .string()
369
+ .describe('Job ID of the Submitted BuyerConfirm job to accept (must be one this caller submitted)'),
295
370
  }, async ({ jobId }) => {
296
371
  try {
297
372
  await engram.confirmJob(jobId);
298
- return { content: [{ type: 'text', text: `Confirmed job ${jobId}` }] };
373
+ return {
374
+ content: [
375
+ {
376
+ type: 'text',
377
+ text: `Confirmed job ${jobId} — payment RELEASED to the operator from escrow. Terminal: funds have moved and this cannot be undone. Do not confirm again and do not resubmit (a repeat confirm errors out and will not double-pay; a resubmit would create a NEW paid job).`,
378
+ },
379
+ ],
380
+ };
299
381
  }
300
382
  catch (err) {
301
383
  return {
302
384
  content: [
303
- { type: 'text', text: `Error: ${err instanceof Error ? err.message : String(err)}` },
385
+ {
386
+ type: 'text',
387
+ text: `Error: ${err instanceof Error ? err.message : String(err)}\n[The canister message above is authoritative — follow its embedded next-action guidance. If it says a settlement/payment is pending confirmation, funds may be in flight: do NOT re-pay or resubmit.]`,
388
+ },
304
389
  ],
305
390
  isError: true,
306
391
  };
package/dist/tools.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"tools.js","sourceRoot":"","sources":["../src/tools.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"tools.js","sourceRoot":"","sources":["../src/tools.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,8 +1,8 @@
1
1
  {
2
2
  "name": "@engramx/mcp",
3
- "version": "0.1.0",
3
+ "version": "0.2.0",
4
4
  "description": "MCP server for EngramX — persistent, decentralized agent memory",
5
- "license": "MIT",
5
+ "license": "Apache-2.0",
6
6
  "author": "EngramX <developer@engramx.ai>",
7
7
  "repository": {
8
8
  "type": "git",
@@ -26,7 +26,7 @@
26
26
  "@icp-sdk/core": "^5.4.0",
27
27
  "@modelcontextprotocol/sdk": "^1.29.0",
28
28
  "zod": "^4.4.3",
29
- "@engramx/client": "^0.1.0"
29
+ "@engramx/client": "^0.2.0"
30
30
  },
31
31
  "devDependencies": {
32
32
  "@types/node": "^25.9.2",
@@ -1,46 +0,0 @@
1
- /**
2
- * Canonical schema source for MCP tools — used by both surfaces.
3
- *
4
- * Stdio MCP imports `TOOL_SCHEMAS` and registers tools at runtime.
5
- *
6
- * HTTP MCP (canister) gets a generated Motoko file `src/engram/McpTools.mo`
7
- * from `scripts/gen-mcp-tools.mjs` reading `tool-schemas.json` (which this
8
- * file re-exports). Run as part of `compile-wasm.sh`.
9
- *
10
- * To add a tool:
11
- * 1. Add an entry to `tool-schemas.json` with surfaces ['stdio', 'http'] (or just one).
12
- * 2. For stdio: add a handler in `tools.ts` keyed by tool name.
13
- * 3. For HTTP MCP: add a `case (#X) { ... }` in `dispatchTool` (main.mo),
14
- * then run `node scripts/gen-mcp-tools.mjs` to refresh the catalog.
15
- */
16
- import { z } from 'zod';
17
- export type Surface = 'stdio' | 'http';
18
- export interface JsonSchemaProperty {
19
- type: 'string' | 'integer' | 'number' | 'boolean' | 'array' | 'object';
20
- description?: string;
21
- default?: unknown;
22
- items?: {
23
- type: string;
24
- };
25
- maxItems?: number;
26
- }
27
- export interface ToolSchema {
28
- name: string;
29
- description: string;
30
- inputSchema: {
31
- type: 'object';
32
- required?: string[];
33
- properties: Record<string, JsonSchemaProperty>;
34
- };
35
- requiredScope?: 'memory.read' | 'memory.append' | 'wallet.read' | 'wallet.spend';
36
- surfaces: Surface[];
37
- }
38
- export declare const TOOL_SCHEMAS: ToolSchema[];
39
- /** Convert a JSON Schema property shape to a Zod type for runtime validation. */
40
- export declare function jsonSchemaPropertyToZod(prop: JsonSchemaProperty, required: boolean): z.ZodTypeAny;
41
- /** Build a Zod shape (record of property → ZodType) from a tool's inputSchema. */
42
- export declare function buildZodShape(tool: ToolSchema): Record<string, z.ZodTypeAny>;
43
- /** Find a tool schema by name. Returns undefined if not found. */
44
- export declare function findToolSchema(name: string): ToolSchema | undefined;
45
- /** Tools available on a given surface. */
46
- export declare function toolsForSurface(surface: Surface): ToolSchema[];
@@ -1,70 +0,0 @@
1
- /**
2
- * Canonical schema source for MCP tools — used by both surfaces.
3
- *
4
- * Stdio MCP imports `TOOL_SCHEMAS` and registers tools at runtime.
5
- *
6
- * HTTP MCP (canister) gets a generated Motoko file `src/engram/McpTools.mo`
7
- * from `scripts/gen-mcp-tools.mjs` reading `tool-schemas.json` (which this
8
- * file re-exports). Run as part of `compile-wasm.sh`.
9
- *
10
- * To add a tool:
11
- * 1. Add an entry to `tool-schemas.json` with surfaces ['stdio', 'http'] (or just one).
12
- * 2. For stdio: add a handler in `tools.ts` keyed by tool name.
13
- * 3. For HTTP MCP: add a `case (#X) { ... }` in `dispatchTool` (main.mo),
14
- * then run `node scripts/gen-mcp-tools.mjs` to refresh the catalog.
15
- */
16
- import { z } from 'zod';
17
- import schemasJson from './tool-schemas.json' with { type: 'json' };
18
- export const TOOL_SCHEMAS = schemasJson.tools;
19
- // ---------------------------------------------------------------------------
20
- // Helpers
21
- // ---------------------------------------------------------------------------
22
- /** Convert a JSON Schema property shape to a Zod type for runtime validation. */
23
- export function jsonSchemaPropertyToZod(prop, required) {
24
- let zodType;
25
- switch (prop.type) {
26
- case 'string':
27
- zodType = z.string();
28
- break;
29
- case 'integer':
30
- case 'number':
31
- zodType = z.number();
32
- break;
33
- case 'boolean':
34
- zodType = z.boolean();
35
- break;
36
- case 'array':
37
- zodType = z.array(prop.items?.type === 'string' ? z.string() : z.any());
38
- break;
39
- case 'object':
40
- zodType = z.record(z.string(), z.any());
41
- break;
42
- default:
43
- zodType = z.any();
44
- }
45
- if (prop.description)
46
- zodType = zodType.describe(prop.description);
47
- if (prop.default !== undefined)
48
- zodType = zodType.default(prop.default);
49
- if (!required)
50
- zodType = zodType.optional();
51
- return zodType;
52
- }
53
- /** Build a Zod shape (record of property → ZodType) from a tool's inputSchema. */
54
- export function buildZodShape(tool) {
55
- const shape = {};
56
- const required = new Set(tool.inputSchema.required ?? []);
57
- for (const [name, prop] of Object.entries(tool.inputSchema.properties)) {
58
- shape[name] = jsonSchemaPropertyToZod(prop, required.has(name));
59
- }
60
- return shape;
61
- }
62
- /** Find a tool schema by name. Returns undefined if not found. */
63
- export function findToolSchema(name) {
64
- return TOOL_SCHEMAS.find((t) => t.name === name);
65
- }
66
- /** Tools available on a given surface. */
67
- export function toolsForSurface(surface) {
68
- return TOOL_SCHEMAS.filter((t) => t.surfaces.includes(surface));
69
- }
70
- //# sourceMappingURL=tool-schemas.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"tool-schemas.js","sourceRoot":"","sources":["../src/tool-schemas.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;GAcG;AAEH,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AACxB,OAAO,WAAW,MAAM,qBAAqB,CAAC,OAAO,IAAI,EAAE,MAAM,EAAE,CAAC;AAwBpE,MAAM,CAAC,MAAM,YAAY,GAAiB,WAAW,CAAC,KAAqB,CAAC;AAE5E,8EAA8E;AAC9E,UAAU;AACV,8EAA8E;AAE9E,iFAAiF;AACjF,MAAM,UAAU,uBAAuB,CAAC,IAAwB,EAAE,QAAiB;IACjF,IAAI,OAAqB,CAAC;IAC1B,QAAQ,IAAI,CAAC,IAAI,EAAE,CAAC;QAClB,KAAK,QAAQ;YACX,OAAO,GAAG,CAAC,CAAC,MAAM,EAAE,CAAC;YACrB,MAAM;QACR,KAAK,SAAS,CAAC;QACf,KAAK,QAAQ;YACX,OAAO,GAAG,CAAC,CAAC,MAAM,EAAE,CAAC;YACrB,MAAM;QACR,KAAK,SAAS;YACZ,OAAO,GAAG,CAAC,CAAC,OAAO,EAAE,CAAC;YACtB,MAAM;QACR,KAAK,OAAO;YACV,OAAO,GAAG,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,KAAK,EAAE,IAAI,KAAK,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,EAAE,CAAC,CAAC;YACxE,MAAM;QACR,KAAK,QAAQ;YACX,OAAO,GAAG,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,MAAM,EAAE,EAAE,CAAC,CAAC,GAAG,EAAE,CAAC,CAAC;YACxC,MAAM;QACR;YACE,OAAO,GAAG,CAAC,CAAC,GAAG,EAAE,CAAC;IACtB,CAAC;IACD,IAAI,IAAI,CAAC,WAAW;QAAE,OAAO,GAAG,OAAO,CAAC,QAAQ,CAAC,IAAI,CAAC,WAAW,CAAC,CAAC;IACnE,IAAI,IAAI,CAAC,OAAO,KAAK,SAAS;QAC5B,OAAO,GAAI,OAAsC,CAAC,OAAO,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;IAC1E,IAAI,CAAC,QAAQ;QAAE,OAAO,GAAG,OAAO,CAAC,QAAQ,EAAE,CAAC;IAC5C,OAAO,OAAO,CAAC;AACjB,CAAC;AAED,kFAAkF;AAClF,MAAM,UAAU,aAAa,CAAC,IAAgB;IAC5C,MAAM,KAAK,GAAiC,EAAE,CAAC;IAC/C,MAAM,QAAQ,GAAG,IAAI,GAAG,CAAC,IAAI,CAAC,WAAW,CAAC,QAAQ,IAAI,EAAE,CAAC,CAAC;IAC1D,KAAK,MAAM,CAAC,IAAI,EAAE,IAAI,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,IAAI,CAAC,WAAW,CAAC,UAAU,CAAC,EAAE,CAAC;QACvE,KAAK,CAAC,IAAI,CAAC,GAAG,uBAAuB,CAAC,IAAI,EAAE,QAAQ,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC;IAClE,CAAC;IACD,OAAO,KAAK,CAAC;AACf,CAAC;AAED,kEAAkE;AAClE,MAAM,UAAU,cAAc,CAAC,IAAY;IACzC,OAAO,YAAY,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,KAAK,IAAI,CAAC,CAAC;AACnD,CAAC;AAED,0CAA0C;AAC1C,MAAM,UAAU,eAAe,CAAC,OAAgB;IAC9C,OAAO,YAAY,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,QAAQ,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC,CAAC;AAClE,CAAC"}
@@ -1,136 +0,0 @@
1
- {
2
- "$comment": "Canonical MCP tool catalog. Single source of truth for stdio MCP and HTTP MCP. Stdio loads at runtime via tool-schemas.ts; HTTP MCP gets a generated Motoko file (src/engram/McpTools.mo) from scripts/gen-mcp-tools.mjs reading this JSON.",
3
- "tools": [
4
- {
5
- "name": "engram_read_memory",
6
- "description": "Read a memory file from the engram by path. Returns {path, content, version, lastModifiedAt}.",
7
- "inputSchema": {
8
- "type": "object",
9
- "required": ["path"],
10
- "properties": {
11
- "path": {
12
- "type": "string",
13
- "description": "Path within the engram (e.g. identity/preferences.md)"
14
- }
15
- }
16
- },
17
- "requiredScope": "memory.read",
18
- "surfaces": ["stdio", "http"]
19
- },
20
- {
21
- "name": "engram_append_memory",
22
- "description": "Append content to a memory file. Creates the file if it does not exist. Cannot write to owner-only protected paths.",
23
- "inputSchema": {
24
- "type": "object",
25
- "required": ["path", "content"],
26
- "properties": {
27
- "path": { "type": "string", "description": "File path" },
28
- "content": { "type": "string", "description": "Content to append" }
29
- }
30
- },
31
- "requiredScope": "memory.append",
32
- "surfaces": ["stdio", "http"]
33
- },
34
- {
35
- "name": "engram_list_memory_files",
36
- "description": "List all memory file paths in the engram with version and lastModifiedAt.",
37
- "inputSchema": { "type": "object", "properties": {} },
38
- "requiredScope": "memory.read",
39
- "surfaces": ["stdio", "http"]
40
- },
41
- {
42
- "name": "engram_read_memory_batch",
43
- "description": "Read multiple memory files in a single call. Returns content for each path or an error.",
44
- "inputSchema": {
45
- "type": "object",
46
- "required": ["paths"],
47
- "properties": {
48
- "paths": { "type": "array", "items": { "type": "string" }, "maxItems": 50 }
49
- }
50
- },
51
- "requiredScope": "memory.read",
52
- "surfaces": ["stdio", "http"]
53
- },
54
- {
55
- "name": "engram_memory_history",
56
- "description": "Get version history of a memory file. Returns each prior version with timestamp and modifying principal.",
57
- "inputSchema": {
58
- "type": "object",
59
- "required": ["path"],
60
- "properties": { "path": { "type": "string" } }
61
- },
62
- "requiredScope": "memory.read",
63
- "surfaces": ["stdio", "http"]
64
- },
65
- {
66
- "name": "engram_read_audit_log",
67
- "description": "Read the engram audit log entries.",
68
- "inputSchema": {
69
- "type": "object",
70
- "properties": {
71
- "fromIndex": { "type": "integer", "default": 0 },
72
- "limit": { "type": "integer", "default": 50 }
73
- }
74
- },
75
- "requiredScope": "memory.read",
76
- "surfaces": ["stdio", "http"]
77
- },
78
- {
79
- "name": "engram_status",
80
- "description": "Get engram operational status: version, file count, audit log size, frozen/paused state.",
81
- "inputSchema": { "type": "object", "properties": {} },
82
- "surfaces": ["stdio", "http"]
83
- },
84
- {
85
- "name": "engram_wallet_balance",
86
- "description": "Get the engram canister cycles balance (canister fuel).",
87
- "inputSchema": { "type": "object", "properties": {} },
88
- "requiredScope": "wallet.read",
89
- "surfaces": ["stdio", "http"]
90
- },
91
- {
92
- "name": "engram_list_services",
93
- "description": "List paid services this engram brokers via ic402.",
94
- "inputSchema": { "type": "object", "properties": {} },
95
- "surfaces": ["stdio", "http"]
96
- },
97
- {
98
- "name": "engram_get_job_result",
99
- "description": "Retrieve the result of a previously-submitted ic402 service job by job ID.",
100
- "inputSchema": {
101
- "type": "object",
102
- "required": ["jobId"],
103
- "properties": { "jobId": { "type": "string" } }
104
- },
105
- "requiredScope": "memory.read",
106
- "surfaces": ["stdio", "http"]
107
- },
108
- {
109
- "name": "engram_submit_service_request",
110
- "description": "Submit a paid request to an ic402 service registered on this engram.",
111
- "inputSchema": {
112
- "type": "object",
113
- "required": ["serviceId", "params"],
114
- "properties": {
115
- "serviceId": { "type": "string" },
116
- "params": { "type": "string", "description": "JSON-encoded service-specific parameters" }
117
- }
118
- },
119
- "requiredScope": "wallet.spend",
120
- "surfaces": ["stdio"]
121
- },
122
- {
123
- "name": "engram_dispute_job",
124
- "description": "Dispute a job result (operator role).",
125
- "inputSchema": {
126
- "type": "object",
127
- "required": ["jobId", "reason"],
128
- "properties": {
129
- "jobId": { "type": "string" },
130
- "reason": { "type": "string" }
131
- }
132
- },
133
- "surfaces": ["stdio"]
134
- }
135
- ]
136
- }