@theronap/agnoclast-mcp 0.9.222 → 0.9.223

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.
Files changed (2) hide show
  1. package/lib/server.mjs +43 -1
  2. package/package.json +1 -1
package/lib/server.mjs CHANGED
@@ -4860,7 +4860,7 @@ function renderNudge(payload) {
4860
4860
  shape: z.enum(['message', 'event', 'document', 'record']).describe('message = emails, chats, replies · event = ticket changes, alerts, CRM updates · document = notes, transcripts, reports · record = rows, metrics, anything else'),
4861
4861
  purpose: z.enum(['communication', 'work', 'reference', 'metrics']).describe('sets defaults only'),
4862
4862
  sample: z.record(z.string(), z.any()).optional().describe('ONE real item, exactly as the system will send it (a JSON object)'),
4863
- mapping: z.record(z.string(), z.any()).optional().describe('which field plays which role, as dot paths into one item: { id, time, title, body, group, url, people: [..] }. Omit to have it suggested from the sample'),
4863
+ mapping: z.record(z.string(), z.any()).optional().describe('which field plays which role, as dot paths into one item: { id, time, title, body, group, url, people: [..] } — plus, for items with deadlines, due, work_from (when to start) and done: then each item keeps one obligation that the source updates and closes. Omit to have it suggested from the sample'),
4864
4864
  mode: z.enum(['channel', 'ingest']).optional().describe('channel (default) = every item files onto one page as it arrives · ingest = each item waits in the pile to be sorted'),
4865
4865
  ...homeArgs,
4866
4866
  dry_run: z.boolean().optional().describe('true = show the mapping, the sample preview and the home (or the candidate pages) and create NOTHING. Do this first'),
@@ -4891,6 +4891,48 @@ function renderNudge(payload) {
4891
4891
  },
4892
4892
  )
4893
4893
 
4894
+ server.registerTool(
4895
+ 'set_custom_source_mapping',
4896
+ {
4897
+ title: 'Change a custom source\'s field mapping',
4898
+ description: 'Change which field of a custom source\'s pushed items plays which role — for a sender that learned to send more after it was set up. Pass the WHOLE mapping (read the current one with list_custom_sources first): { id, time, title, body, group, url, people: [..], due, work_from, done }. DEADLINES (2026-10-08): map `due` (when the item must be done) and, if the item says so, `work_from` (when work should start) and `done` (a field that is truthy once it is). Then each item with a deadline keeps ONE obligation for you on the source\'s home page — created on the next push, kept current on every push after, and discharged by the source itself when the item reports done; a machine proposal for the same work is folded into it. Nothing already late is created. The `id` field cannot change here: it decides what counts as the same item, and changing it would re-file everything as new — set up a new source instead.',
4899
+ inputSchema: {
4900
+ source: z.string().describe('the source — its id or its name, as list_custom_sources shows'),
4901
+ mapping: z.record(z.string(), z.any()).describe('the whole mapping, role → dot path into one item'),
4902
+ },
4903
+ },
4904
+ async (a) => {
4905
+ let list
4906
+ try {
4907
+ const res = await fetchCortex(`${BASE}/api/custom-connectors`, { headers: { Authorization: `Bearer ${TOKEN}` } })
4908
+ if (!res.ok) return cannot('Could not read your custom sources', res)
4909
+ list = (await res.json()).connectors
4910
+ } catch (e) {
4911
+ return toolError(`Could not read your custom sources: ${e.message}`)
4912
+ }
4913
+ const picked = pickSource(list, a.source)
4914
+ if (!picked.ok) return toolError(picked.message)
4915
+ const src = picked.source
4916
+ let res
4917
+ try {
4918
+ res = await fetchCortex(`${BASE}/api/custom-connectors/${encodeURIComponent(src.id)}/mapping`, {
4919
+ method: 'PUT',
4920
+ headers: { Authorization: `Bearer ${TOKEN}`, 'Content-Type': 'application/json' },
4921
+ body: JSON.stringify({ mapping: a.mapping }),
4922
+ })
4923
+ } catch (e) {
4924
+ return toolError(`Not changed: ${e.message}`)
4925
+ }
4926
+ if (!res.ok) return cannot('Not changed', res)
4927
+ const j = await res.json()
4928
+ const roles = Object.entries(j.mapping ?? {}).map(([k, v]) => `${k} ← ${Array.isArray(v) ? v.join(', ') : v}`).join(' · ')
4929
+ const keeps = j.mapping?.due
4930
+ ? '\nItems with a deadline now keep an obligation each — created on the next push, closed when the item reports done.'
4931
+ : ''
4932
+ return { content: [{ type: 'text', text: `${src.name} mapping: ${roles}${keeps}` }] }
4933
+ },
4934
+ )
4935
+
4894
4936
  server.registerTool(
4895
4937
  'set_custom_source_home',
4896
4938
  {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@theronap/agnoclast-mcp",
3
- "version": "0.9.222",
3
+ "version": "0.9.223",
4
4
  "description": "Connect your AI assistant to Cortex — your org's projects, activity, gaps, and directives, scoped to you.",
5
5
  "type": "module",
6
6
  "bin": {