yaml-flow 8.5.2 → 8.5.3

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.
@@ -1,10 +1,10 @@
1
1
  {
2
- "generatedAt": "2026-05-28T18:29:20.093Z",
2
+ "generatedAt": "2026-05-29T06:34:54.124Z",
3
3
  "algorithm": "sha256",
4
4
  "files": {
5
5
  "browser/board-livecards-localstorage.js": {
6
- "sha256": "sha256-ukHGdsDK8ytpOVMNh82v3OUUtYThohkEWbgGlROvO6s=",
7
- "bytes": 144037
6
+ "sha256": "sha256-PrytBTTr3LONwR2KFY9Yd3F536oNOQDPS6RiQT5KwHg=",
7
+ "bytes": 144225
8
8
  },
9
9
  "browser/live-cards.schema.json": {
10
10
  "sha256": "sha256-F5nfqDzZ5L3p0lLTMxGt4YtMa2sVzdNPh8sbQ8OiXHE=",
@@ -25,5 +25,5 @@ ${new Date().toISOString()}
25
25
  `).filter(Boolean).map(a=>JSON.parse(a)):[]}return{append(r){let a={id:et(),payload:r};return D.mkdirSync(Q.dirname(e),{recursive:!0}),D.appendFileSync(e,JSON.stringify(a)+`
26
26
  `,"utf-8"),a},readAll(){return t()},readAfter(r){let a=t();if(!r)return{entries:a,newCursor:a.length>0?a[a.length-1].id:null};let n=a.findIndex(o=>o.id===r),s=n===-1?a:a.slice(n+1);return{entries:s,newCursor:s.length>0?s[s.length-1].id:r}},clear(){D.existsSync(e)&&D.truncateSync(e,0)}}}function Xo(e){if(e==null||typeof e!="object")return JSON.stringify(e);if(Array.isArray(e))return`[${e.map(Xo).join(",")}]`;let t=e;return`{${Object.keys(t).sort().map(r=>`${JSON.stringify(r)}:${Xo(t[r])}`).join(",")}}`}function q0(e){return ed("sha256").update(Xo(e)).digest("hex")}function D0(e){let t=Q.join(e,"board-journal.jsonl");return{readAllEntries(){if(!D.existsSync(t))return[];let r=D.readFileSync(t,"utf-8").trim();return r?r.split(`
27
27
  `).filter(Boolean).map(a=>JSON.parse(a)):[]},appendEntry(r){D.appendFileSync(t,JSON.stringify(r)+`
28
- `,"utf-8")},generateId(){return et()}}}function M0(e){return{tryAcquire(){try{if(!D.existsSync(e)){D.mkdirSync(Q.dirname(e),{recursive:!0});try{D.writeFileSync(e,"{}",{flag:"wx"})}catch{}}return(0,td.lockSync)(e,{retries:0})}catch{return null}}}}var F0={$schema:"http://json-schema.org/draft-07/schema#",$id:"https://nsreehari.github.io/boards/live-cards.schema.json",definitions:{bind_ref:{description:"A card data path reference, e.g. 'card_data.raw_quotes' or 'requires.upstream'",type:"string",pattern:"^(card_data|requires|fetched_sources|computed_values)(\\.|$)"},bind_or_literal:{description:"A literal value or a bind reference object",oneOf:[{type:"string"},{type:"number"},{type:"boolean"},{type:"array"},{type:"object",properties:{bind:{$ref:"#/definitions/bind_ref"}},required:["bind"]}]},compute_expr:{description:"A declarative JSON compute expression",type:"object",required:["fn"],properties:{fn:{type:"string",description:"Function name from the built-in vocabulary",enum:["sum","avg","min","max","count","first","last","add","sub","mul","div","round","abs","mod","gt","gte","lt","lte","eq","neq","if","and","or","not","concat","upper","lower","template","filter","pluck","map","sort","slice","flat","unique","group","get","default","now","diff_days","format_date"]},input:{description:"card_data.path, literal, array of inputs, or nested compute_expr",oneOf:[{type:"string"},{type:"number"},{type:"boolean"},{type:"array"},{$ref:"#/definitions/compute_expr"}]},field:{type:"string",description:"For pluck/sum/group \u2014 the object key to extract"},where:{$ref:"#/definitions/compute_expr",description:"For filter \u2014 predicate expression ($ = current item)"},cond:{$ref:"#/definitions/compute_expr",description:"For if \u2014 condition expression"},then:{description:"For if \u2014 value when cond is truthy"},else:{description:"For if \u2014 value when cond is falsy"},format:{type:"string",description:"For format_date \u2014 date format string"}}},meta:{type:"object",properties:{title:{type:"string"},tags:{type:"array",items:{type:"string"}}}},requires:{type:"array",items:{type:"string"},description:"IDs of upstream nodes this node depends on"},provides:{type:"array",items:{type:"object",required:["bindTo","ref"],properties:{bindTo:{type:"string",description:"Token name published downstream"},ref:{type:"string",description:"Path to read value from (card_data.*, requires.*, fetched_sources.*, computed_values.*)"}}},description:"Explicit bindings exposing computed or card_data values downstream as named tokens"},compute_step:{description:"A single ordered compute step: reads card_data.*/requires.*/computed_values.*, writes to computed_values[bindTo]",type:"object",required:["bindTo","expr"],properties:{bindTo:{type:"string",description:"Key in computed_values to write result"},expr:{type:"string",description:"JSONata expression evaluated against { card_data, requires, fetched_sources, computed_values }"}}},source_def:{description:"One source entry. The engine requires 'bindTo' (compute namespace key) and 'outputFile' (delivery signal path). bindTo and outputFile must be unique across all source_defs in a card. Every other property is yours \u2014 add whatever your task-executor needs: kind, url, headers, mailbox, channel, model, query, etc. The full object is passed verbatim as the --in JSON to the executor.",type:"object",required:["bindTo","outputFile"],additionalProperties:!0,properties:{bindTo:{type:"string",description:"Key under fetched_sources.* available in compute expressions"},outputFile:{type:"string",description:"Board-relative path the executor writes its JSON result to. Presence of this file signals delivery."},projections:{type:"object",description:"Named data projections from card_data or requires, evaluated before the executor is called. Each key is a ref name; each value is a JSONata expression rooted at card_data or requires. The resolved values are passed to the executor as _projections. fetched_sources, computed_values, and source_defs are not accessible here \u2014 sources run before those exist.",additionalProperties:{type:"string"}},optionalForCompletionGating:{type:"boolean",default:!1,description:"When true this source does not gate card completion. Default false when absent, so source_defs are completion-gating by default."},timeout:{type:"integer",minimum:0,default:12e4,description:"Executor/script timeout in ms. Default: 120 000 (2 min)."},script:{type:"string",description:"Legacy direct-run: shell command executed when no .task-executor is registered. stdout is captured as the result."}}},render_element:{type:"object",required:["kind"],properties:{id:{type:"string",description:"Optional element ID for targeted updates"},kind:{enum:["metric","table","editable-table","chart","form","filter","list","notes","todo","alert","narrative","badge","text","markdown","ref","custom","actions"]},label:{type:"string",description:"Heading above this element"},className:{type:"string",description:"Bootstrap grid class, e.g. 'col-12 col-md-6'"},visible:{type:"string",description:"card_data/requires/fetched_sources/computed_values path \u2014 element shown only if truthy"},data:{type:"object",properties:{bind:{$ref:"#/definitions/bind_ref",description:"card_data/requires/fetched_sources/computed_values path to read data from"},writeTo:{$ref:"#/definitions/bind_ref",description:"card_data path for user input (form, filter, todo, notes)"},columns:{type:"array",items:{type:"string"},description:"table: visible columns"},maxRows:{type:"integer",description:"table/list: max rows to display"},sortable:{type:"boolean",default:!0,description:"table: enable click-to-sort"},placeholder:{type:"string",description:"Empty-state message"},chartType:{enum:["bar","line","pie","doughnut"]},chartOptions:{type:"object",description:"Chart.js options passthrough"},fields:{type:"object",description:"JSON Schema for form/filter fields"},thresholds:{type:"object",properties:{green:{type:"string"},amber:{type:"string"}}},colorMap:{type:"object",description:"badge: value \u2192 Bootstrap color"},style:{enum:["heading","muted","default"],description:"text: display style"},upload:{type:"boolean",default:!0,description:"file-upload: show drop zone (false = read-only file list)"},accept:{type:"array",items:{type:"string"},description:"file-upload: allowed extensions"},multiple:{type:"boolean",default:!0,description:"file-upload: allow multiple files"},fileAttach:{type:"boolean",default:!1,description:"chat: enable inline file attachments"},fileAccept:{type:"array",items:{type:"string"},description:"chat: allowed attachment extensions"},buttons:{type:"array",description:"actions: button definitions",items:{type:"object",required:["id","label"],properties:{id:{type:"string"},label:{type:"string"},style:{type:"string",description:"Bootstrap button variant, e.g. 'success', 'outline-danger'"},size:{type:"string",default:"sm"},disabled:{oneOf:[{type:"boolean"},{type:"string",description:"card_data/requires/fetched_sources/computed_values path \u2014 truthy = disabled"}]}}}}}}}},view:{type:"object",required:["elements"],properties:{elements:{type:"array",minItems:1,items:{$ref:"#/definitions/render_element"}},layout:{type:"object",properties:{board:{type:"object",properties:{col:{type:"integer",minimum:1,maximum:12},order:{type:"integer"}}},canvas:{type:"object",properties:{x:{type:"number"},y:{type:"number"},w:{type:"number"},h:{type:"number"}}}}},features:{type:"object",properties:{chat:{type:"boolean",default:!1},notes:{type:"boolean",default:!1},refresh:{type:"boolean",default:!0}}}}}},title:"LiveCard",description:"A unified card node. Behavior depends on which sections are present (source_defs, compute, view, etc.)",type:"object",required:["id"],additionalProperties:!1,properties:{id:{type:"string"},requires:{$ref:"#/definitions/requires"},provides:{$ref:"#/definitions/provides"},meta:{$ref:"#/definitions/meta"},view:{$ref:"#/definitions/view"},card_data:{type:"object",description:"Authored card data and runtime metadata. Includes uploaded-file metadata maintained by host handlers and inference evaluation results.",properties:{files:{type:"array",description:"Optional uploaded-file metadata maintained by host handlers. Stored name is normalized and serial-prefixed (for example 001-my_file.pdf).",items:{type:"object",required:["name","stored_name"],properties:{name:{type:"string",minLength:1},stored_name:{type:"string",minLength:5,maxLength:32,pattern:"^[0-9]{3,}-[a-z0-9._-]+$"},size:{oneOf:[{type:"integer",minimum:0},{type:"null"}]},mime_type:{type:"string"},path:{type:"string",pattern:"^[^\\s]+/files/[0-9]{3,}-[a-z0-9._-]+$"},uploaded_at:{type:"string",format:"date-time"},chat:{type:"boolean",description:"Whether this file entry is associated with a chat interaction"}},additionalProperties:!1}}},additionalProperties:!0},source_defs:{type:"array",description:"Source entries. Each entry is passed verbatim to the board's .task-executor (registered via init --task-executor) as the --in JSON file. The executor fetches/generates the data and writes JSON to --out. If no executor is registered, the built-in executor runs the entry's 'cli' command directly. Sources gate completion by default. Set optionalForCompletionGating: true for enrichment-only source_defs that should not block task-completed.",items:{$ref:"#/definitions/source_def"}},compute:{type:"array",description:"Ordered array of compute steps. Each reads card_data.*/requires.*/fetched_sources.*/computed_values.* and writes to ephemeral computed_values[bindTo].",items:{$ref:"#/definitions/compute_step"}}}},V0=dv(n0()),z0=On(import.meta.url),U0=z0("./jsonata-sync.cjs"),wn=null,Fl=/\b(card_data|requires|fetched_sources|computed_values|source_defs)\b/g,L0=/^\s*(card_data|requires|fetched_sources|computed_values|source_defs)(\.|$)/;function H0(e){let t=new Set,r;for(Fl.lastIndex=0;(r=Fl.exec(e))!==null;)t.add(r[1]);return t}function gd(e){let t=L0.exec(e);return t?t[1]:null}function Vl(e,t,r,a){try{U0(e)}catch(s){let o=s instanceof Error?s.message:String(s);a.push(`${t}: invalid JSONata expression (${o})`);return}let n=H0(e);for(let s of n)r.has(s)||a.push(`${t}: disallowed namespace "${s}" in expression`)}function Yo(e,t,r){if(Array.isArray(e)){e.forEach((n,s)=>{Yo(n,`${t}/${s}`,r)});return}if(typeof e=="string"){let n=gd(e);if(!n)return;new Set(["card_data","requires","computed_values"]).has(n)||r.push(`${t}: disallowed namespace "${n}" in view reference`);return}if(!e||typeof e!="object")return;let a=e;for(let[n,s]of Object.entries(a))Yo(s,`${t}/${n}`,r)}function K0(){if(wn)return wn;let e=new V0.default({allErrors:!0});return(0,rd.default)(e),wn=e.compile(F0),wn}function G0(e){let t=K0(),r=t(e),a=(t.errors??[]).map(n=>`${n.instancePath||"/"}: ${n.message??"unknown error"}`);if(e&&typeof e=="object"&&!Array.isArray(e)){let n=e.source_defs;if(Array.isArray(n)){let s=new Set,o=new Set;n.forEach((u,i)=>{if(!u||typeof u!="object"||Array.isArray(u))return;let c=u;typeof c.bindTo=="string"&&c.bindTo&&(s.has(c.bindTo)&&a.push(`/source_defs/${i}/bindTo: bindTo "${c.bindTo}" must be unique across all source_defs`),s.add(c.bindTo)),typeof c.outputFile=="string"&&c.outputFile&&(o.has(c.outputFile)&&a.push(`/source_defs/${i}/outputFile: outputFile "${c.outputFile}" must be unique across all source_defs`),o.add(c.outputFile))})}}return!r||a.length>0?{ok:!1,errors:a}:{ok:!0,errors:[]}}function B0(e){let t=[];if(!e||typeof e!="object"||Array.isArray(e))return{ok:!0,errors:[]};let r=e,a=r.compute;Array.isArray(a)&&a.forEach((c,l)=>{if(!c||typeof c!="object"||Array.isArray(c))return;let d=c.expr;typeof d!="string"||d.trim().length===0||Vl(d,`/compute/${l}/expr`,new Set(["card_data","requires","fetched_sources","computed_values"]),t)});let n=new Set(["card_data","requires","fetched_sources","computed_values"]),s=r.provides;Array.isArray(s)&&s.forEach((c,l)=>{if(!c||typeof c!="object"||Array.isArray(c))return;let d=c.ref;if(typeof d!="string"||d.trim().length===0)return;let w=gd(d);w===null?t.push(`/provides/${l}/ref: path "${d}" must start with a valid namespace (${[...n].join(", ")})`):n.has(w)||t.push(`/provides/${l}/ref: disallowed namespace "${w}" in path "${d}" (valid: ${[...n].join(", ")})`)});let o=r.view;o&&typeof o=="object"&&!Array.isArray(o)&&Yo(o,"/view",t);let u=new Set(["card_data","requires"]),i=r.source_defs;return Array.isArray(i)&&i.forEach((c,l)=>{if(!c||typeof c!="object"||Array.isArray(c))return;let d=c.projections;if(!(!d||typeof d!="object"||Array.isArray(d)))for(let[w,$]of Object.entries(d))typeof $!="string"||$.trim().length===0||Vl($,`/source_defs/${l}/projections/${w}`,u,t)}),{ok:t.length===0,errors:t}}function J0(e){let t=G0(e);if(!t.ok)return t;let r=B0(e);return r.ok?{ok:!0,errors:[]}:{ok:!1,errors:r.errors}}var Ar={RUNNING:"running",COMPLETED:"completed",FAILED:"failed",INACTIVATED:"inactivated"};function bt(e){return e?Array.isArray(e.provides)?e.provides:[]:[]}function $a(e){return e?Array.isArray(e.requires)?e.requires:[]:[]}function W0(e){return e.tasks??{}}function zl(e){return e?e.status===Ar.FAILED||e.status===Ar.INACTIVATED:!1}function X0(e,t){return e.refreshStrategy??t?.refreshStrategy??"data-changed"}function Y0(e){return e.maxExecutions}function Q0(e,t){let r=new Set;for(let[a,n]of Object.entries(t))if(n.status===Ar.COMPLETED){let s=e.tasks[a];s&&bt(s).forEach(o=>r.add(o))}return Array.from(r)}function Z0(e,t){let r={};return e.forEach(a=>{let n=t[a];n&&bt(n).forEach(s=>{r[s]||(r[s]=[]),r[s].push(a)})}),r}function e_(e,t,r){let a=e.tasks[t]??In(),n={};if(r){let o=r.tasks[t],u=$a(o);for(let i of u)for(let[c,l]of Object.entries(r.tasks))if(bt(l).includes(i)){let d=e.tasks[c];d?.lastDataHash&&(n[i]=d.lastDataHash);break}}let s={...a,status:"running",startedAt:new Date().toISOString(),lastUpdated:new Date().toISOString(),progress:0,error:void 0,startConsumedHashes:n};return{...e,tasks:{...e.tasks,[t]:s},lastUpdated:new Date().toISOString()}}function t_(e,t,r,a,n,s){let o=e.tasks[r]??In(),u=t.tasks[r];if(!u)throw new Error(`Task "${r}" not found in graph`);let i;a&&u.on&&u.on[a]?i=u.on[a]:i=bt(u);let c=o.startConsumedHashes?{...o.startConsumedHashes}:{...o.lastConsumedHashes};if(!o.startConsumedHashes){let w=u.requires??[];for(let $ of w)for(let[h,v]of Object.entries(t.tasks))if(bt(v).includes($)){let m=e.tasks[h];m?.lastDataHash&&(c[$]=m.lastDataHash);break}}let l={...o,status:"completed",completedAt:new Date().toISOString(),lastUpdated:new Date().toISOString(),executionCount:o.executionCount+1,lastEpoch:o.executionCount+1,lastDataHash:n,data:s,lastConsumedHashes:c,error:void 0},d=[...new Set([...e.availableOutputs,...i])];return{...e,tasks:{...e.tasks,[r]:l},availableOutputs:d,lastUpdated:new Date().toISOString()}}function r_(e,t,r,a){let n=e.tasks[r]??In(),s=t.tasks[r];if(s?.retry){let i=n.retryCount+1;if(i<=s.retry.max_attempts){let c={...n,status:"not-started",retryCount:i,lastUpdated:new Date().toISOString(),error:a};return{...e,tasks:{...e.tasks,[r]:c},lastUpdated:new Date().toISOString()}}}let o={...n,status:"failed",failedAt:new Date().toISOString(),lastUpdated:new Date().toISOString(),error:a,executionCount:n.executionCount+1},u=e.availableOutputs;if(s?.on_failure&&s.on_failure.length>0&&(u=[...new Set([...e.availableOutputs,...s.on_failure])]),s?.circuit_breaker&&o.executionCount>=s.circuit_breaker.max_executions){let i=s.circuit_breaker.on_break;u=[...new Set([...u,...i])]}return{...e,tasks:{...e.tasks,[r]:o},availableOutputs:u,lastUpdated:new Date().toISOString()}}function a_(e,t,r,a){let n=e.tasks[t]??In(),s={...n,progress:typeof a=="number"?a:n.progress,messages:[...n.messages??[],...r?[{message:r,timestamp:new Date().toISOString(),status:n.status}]:[]],lastUpdated:new Date().toISOString()};return{...e,tasks:{...e.tasks,[t]:s},lastUpdated:new Date().toISOString()}}function n_(e,t){let r=e.tasks[t];if(!r)return e;let a={...r,status:"not-started",startedAt:void 0,completedAt:void 0,failedAt:void 0,error:void 0,data:void 0,progress:null,lastUpdated:new Date().toISOString()};return{...e,tasks:{...e.tasks,[t]:a},lastUpdated:new Date().toISOString()}}function In(){return{status:"not-started",executionCount:0,retryCount:0,lastEpoch:0,messages:[],progress:null}}function vd(e,t){let r=`live-${Date.now()}`,a={};for(let s of Object.keys(e.tasks))a[s]=_d();let n={status:"running",tasks:a,availableOutputs:[],stuckDetection:{is_stuck:!1,stuck_description:null,outputs_unresolvable:[],tasks_blocked:[]},lastUpdated:new Date().toISOString(),executionId:r,executionConfig:{executionMode:e.settings.execution_mode??"eligibility-mode",conflictStrategy:e.settings.conflict_strategy??"alphabetical",completionStrategy:e.settings.completion}};return{config:e,state:n}}function s_(e,t){let{config:r,state:a}=e;if("executionId"in t&&t.executionId&&t.executionId!==a.executionId)return e;switch(t.type){case"task-started":return{config:r,state:e_(a,t.taskName,r)};case"task-completed":return{config:r,state:t_(a,r,t.taskName,t.result,t.dataHash,t.data)};case"task-failed":return{config:r,state:r_(a,r,t.taskName,t.error)};case"task-progress":return{config:r,state:a_(a,t.taskName,t.message,t.progress)};case"task-restart":return{config:r,state:n_(a,t.taskName)};case"inject-tokens":return{config:r,state:{...a,availableOutputs:[...new Set([...a.availableOutputs,...t.tokens])],lastUpdated:new Date().toISOString()}};case"agent-action":return{config:r,state:p_(a,t.action)};case"task-upsert":return i_(e,t.taskName,t.taskConfig);case"task-removal":return u_(e,t.taskName);case"node-requires-add":return c_(e,t.nodeName,t.tokens);case"node-requires-remove":return l_(e,t.nodeName,t.tokens);case"node-provides-add":return d_(e,t.nodeName,t.tokens);case"node-provides-remove":return f_(e,t.nodeName,t.tokens);default:return e}}function o_(e,t){return t.reduce((r,a)=>s_(r,a),e)}function i_(e,t,r){let a=!!e.config.tasks[t];return{config:{...e.config,tasks:{...e.config.tasks,[t]:r}},state:{...e.state,tasks:{...e.state.tasks,[t]:a?e.state.tasks[t]:_d()},lastUpdated:new Date().toISOString()}}}function u_(e,t){if(!e.config.tasks[t])return e;let{[t]:r,...a}=e.config.tasks,{[t]:n,...s}=e.state.tasks;return{config:{...e.config,tasks:a},state:{...e.state,tasks:s,lastUpdated:new Date().toISOString()}}}function c_(e,t,r){let a=e.config.tasks[t];if(!a)return e;let n=$a(a),s=r.filter(o=>!n.includes(o));return s.length===0?e:{config:{...e.config,tasks:{...e.config.tasks,[t]:{...a,requires:[...n,...s]}}},state:e.state}}function l_(e,t,r){let a=e.config.tasks[t];if(!a)return e;let n=$a(a),s=n.filter(o=>!r.includes(o));return s.length===n.length?e:{config:{...e.config,tasks:{...e.config.tasks,[t]:{...a,requires:s}}},state:e.state}}function d_(e,t,r){let a=e.config.tasks[t];if(!a)return e;let n=bt(a),s=r.filter(o=>!n.includes(o));return s.length===0?e:{config:{...e.config,tasks:{...e.config.tasks,[t]:{...a,provides:[...n,...s]}}},state:e.state}}function f_(e,t,r){let a=e.config.tasks[t];if(!a)return e;let n=bt(a),s=n.filter(o=>!r.includes(o));return s.length===n.length?e:{config:{...e.config,tasks:{...e.config.tasks,[t]:{...a,provides:s}}},state:e.state}}function Qo(e){return{version:1,config:e.config,state:e.state,snapshotAt:new Date().toISOString()}}function Ko(e){if(!e||typeof e!="object")throw new Error("Invalid snapshot: expected an object");let t=e;if(!t.config||typeof t.config!="object")throw new Error('Invalid snapshot: missing or invalid "config"');if(!t.state||typeof t.state!="object")throw new Error('Invalid snapshot: missing or invalid "state"');let r=t.config,a=t.state;if(!r.settings||typeof r.settings!="object")throw new Error("Invalid snapshot: config.settings missing");if(!r.tasks||typeof r.tasks!="object")throw new Error("Invalid snapshot: config.tasks missing");if(!a.tasks||typeof a.tasks!="object")throw new Error("Invalid snapshot: state.tasks missing");if(!Array.isArray(a.availableOutputs))throw new Error("Invalid snapshot: state.availableOutputs must be an array");return{config:r,state:a}}function _d(){return{status:"not-started",executionCount:0,retryCount:0,lastEpoch:0,messages:[],progress:null}}function p_(e,t){let r=new Date().toISOString();switch(t){case"stop":return{...e,status:"stopped",lastUpdated:r};case"pause":return{...e,status:"paused",lastUpdated:r};case"resume":return{...e,status:"running",lastUpdated:r};default:return e}}function Zo(e){let{config:t,state:r}=e,a=W0(t);if(Object.keys(a).length===0)return{eligible:[],pending:[],unresolved:[],blocked:[],conflicts:{}};let n=h_(a),s=Q0(t,r.tasks),o=new Set([...s,...r.availableOutputs]),u=[],i=[],c=[],l=[];for(let[w,$]of Object.entries(a)){let h=r.tasks[w],v=X0($,t.settings),m=v!=="once";if(h?.status===Ar.RUNNING||zl(h))continue;let f=Y0($);if(f!==void 0&&h&&h.executionCount>=f||$.circuit_breaker&&h&&h.executionCount>=$.circuit_breaker.max_executions||!m&&h?.status===Ar.COMPLETED)continue;if(m&&h?.status===Ar.COMPLETED){let g=$a($),p=!1;switch(v){case"data-changed":{g.length>0&&g.some(E=>{for(let[j,x]of Object.entries(a))if(bt(x).includes(E)){let C=r.tasks[j];if(!C)continue;let q=h.lastConsumedHashes?.[E];return C.lastDataHash==null?C.executionCount>h.lastEpoch:C.lastDataHash!==q}return!1})||(p=!0);break}case"epoch-changed":{g.length>0&&g.some(E=>{for(let[j,x]of Object.entries(a))if(bt(x).includes(E)){let C=r.tasks[j];if(C&&C.executionCount>h.lastEpoch)return!0}return!1})||(p=!0);break}case"time-based":{let E=$.refreshInterval??0;if(E<=0){p=!0;break}let j=h.completedAt;if(!j){p=!0;break}(Date.now()-Date.parse(j))/1e3<E&&(p=!0);break}case"manual":p=!0;break}if(p)continue}let k=$a($);if(k.length===0){u.push(w);continue}let y=[],S=[],_=[];for(let g of k){if(o.has(g))continue;let p=n[g]||[];p.length===0?y.push(g):p.every(E=>zl(r.tasks[E]))?_.push({token:g,failedProducer:p[0]}):S.push(g)}y.length>0?c.push({taskName:w,missingTokens:y}):_.length>0?l.push({taskName:w,failedTokens:_.map(g=>g.token),failedProducers:[...new Set(_.map(g=>g.failedProducer))]}):S.length>0?i.push({taskName:w,waitingOn:S}):u.push(w)}let d={};if(u.length>1){let w=Z0(u,a);for(let[$,h]of Object.entries(w))h.length>1&&(d[$]=h)}return{eligible:u,pending:i,unresolved:c,blocked:l,conflicts:d}}function h_(e){let t={};for(let[r,a]of Object.entries(e)){for(let n of bt(a))t[n]||(t[n]=[]),t[n].push(r);if(a.on)for(let n of Object.values(a.on))for(let s of n)t[s]||(t[s]=[]),t[s].includes(r)||t[s].push(r);if(a.on_failure)for(let n of a.on_failure)t[n]||(t[n]=[]),t[n].includes(r)||t[n].push(r)}return t}var Ul=class{buffer=[];append(e){this.buffer.push(e)}drain(){let e=this.buffer;return this.buffer=[],e}get size(){return this.buffer.length}};function Go(e){let t=ei(e);return m_(t)}function ei(e){if(e==null||typeof e!="object")return JSON.stringify(e);if(Array.isArray(e))return"["+e.map(ei).join(",")+"]";let t=e;return"{"+Object.keys(t).sort().map(r=>JSON.stringify(r)+":"+ei(t[r])).join(",")+"}"}function m_(e){let t=0xcbf29ce484222325n,r=0x100000001b3n,a=0xffffffffffffffffn;for(let n=0;n<e.length;n++)t^=BigInt(e.charCodeAt(n)),t=t*r&a;return t.toString(16).padStart(16,"0")}function y_(e){if(typeof Buffer<"u")return Buffer.from(e,"utf8").toString("base64url");if(typeof btoa=="function"){let t=new TextEncoder().encode(e),r="";for(let a of t)r+=String.fromCharCode(a);return btoa(r).replace(/\+/g,"-").replace(/\//g,"_").replace(/=+$/g,"")}throw new Error("No base64 encoder available in this runtime")}function g_(e){if(typeof Buffer<"u")return Buffer.from(e,"base64url").toString("utf8");if(typeof atob=="function"){let t=e.replace(/-/g,"+").replace(/_/g,"/"),r=t+"=".repeat((4-t.length%4)%4),a=atob(r),n=new Uint8Array(a.length);for(let s=0;s<a.length;s++)n[s]=a.charCodeAt(s);return new TextDecoder().decode(n)}throw new Error("No base64 decoder available in this runtime")}function Ll(e){let t=JSON.stringify({t:e,n:Date.now().toString(36)+Math.random().toString(36).slice(2,6)});return y_(t)}function v_(e){try{let t=JSON.parse(g_(e));return typeof t?.t=="string"?{taskName:t.t}:null}catch{return null}}function __(e,t,r){let{handlers:a,onNodeRemoved:n,onDrain:s}=t,o=new Ul,u="state"in e&&"config"in e?e:vd(e),i=!1,c=new Set,l=new Map(Object.entries(a)),d=new Ul,w=!1,$=!1;function h(){if(!i){if(w){$=!0;return}w=!0;try{do $=!1,v();while($)}finally{w=!1}}}function v(){let y=d.drain(),S=o.drain(),_=[...y,...S];if(_.length>0&&(u=o_(u,_),n)){for(let p of _)if(p.type==="task-removal")try{n(p.taskName)}catch(E){console.warn("[reactive] onNodeRemoved failed:",E instanceof Error?E.message:String(E))}}let g=Zo(u);_.length>0&&s?.(_,u,g);for(let p of g.eligible)k(p);for(let p of _)if(p.type==="task-progress"){let{taskName:E,update:j}=p;if(!u.config.tasks[E])continue;let x=u.state.tasks[E];if(!x||x.status!=="running")continue;let C=Ll(E),q=f(E,C,j).catch(F=>{i||(d.append({type:"task-failed",taskName:E,error:F.message??String(F),timestamp:new Date().toISOString()}),h())}).finally(()=>{c.delete(q)});c.add(q)}}function m(y){let S=u.config.tasks[y].requires??[],_=new Map;for(let[p,E]of Object.entries(u.config.tasks))for(let j of E.provides??[])_.set(j,p);let g={};for(let p of S){let E=_.get(p);E?g[p]=u.state.tasks[E]?.data:g[p]=void 0}return g}async function f(y,S,_){let g=u.config.tasks[y],p=g.taskHandlers??[],E=m(y);for(let j of p){let x=l.get(j);if(!x)throw new Error(`Handler '${j}' not found in registry (task '${y}')`);let C={nodeId:y,state:E,taskState:u.state.tasks[y],config:g,callbackToken:S,update:_};if(await x(C)==="task-initiate-failure")throw new Error(`Handler '${j}' returned task-initiate-failure (task '${y}')`)}}function k(y){let S=u.config.tasks[y]?.taskHandlers;if(!S||S.length===0)return;d.append({type:"task-started",taskName:y,timestamp:new Date().toISOString()}),h();let _=Ll(y),g=f(y,_).catch(p=>{i||(d.append({type:"task-failed",taskName:y,error:p.message??String(p),timestamp:new Date().toISOString()}),h())}).finally(()=>{c.delete(g)});c.add(g)}return{push(y){i||(y.type==="task-completed"&&y.data&&!y.dataHash&&(y={...y,dataHash:Go(y.data)}),o.append(y),h())},pushAll(y){if(!i){for(let S of y)S.type==="task-completed"&&S.data&&!S.dataHash?o.append({...S,dataHash:Go(S.data)}):o.append(S);h()}},resolveCallback(y,S,_){if(i)return;let g=v_(y);if(!g)return;let{taskName:p}=g;if(u.config.tasks[p]){if(_&&_.length>0)o.append({type:"task-failed",taskName:p,error:_.join("; "),timestamp:new Date().toISOString()});else{let E=S&&Object.keys(S).length>0?Go(S):void 0;o.append({type:"task-completed",taskName:p,data:S,dataHash:E,timestamp:new Date().toISOString()})}h()}},addNode(y,S){i||(o.append({type:"task-upsert",taskName:y,taskConfig:S,timestamp:new Date().toISOString()}),h())},removeNode(y){i||(o.append({type:"task-removal",taskName:y,timestamp:new Date().toISOString()}),h())},addRequires(y,S){i||(o.append({type:"node-requires-add",nodeName:y,tokens:S,timestamp:new Date().toISOString()}),h())},removeRequires(y,S){i||(o.append({type:"node-requires-remove",nodeName:y,tokens:S,timestamp:new Date().toISOString()}),h())},addProvides(y,S){i||(o.append({type:"node-provides-add",nodeName:y,tokens:S,timestamp:new Date().toISOString()}),h())},removeProvides(y,S){i||(o.append({type:"node-provides-remove",nodeName:y,tokens:S,timestamp:new Date().toISOString()}),h())},registerHandler(y,S){l.set(y,S)},unregisterHandler(y){l.delete(y)},retrigger(y){i||u.config.tasks[y]&&(o.append({type:"task-restart",taskName:y,timestamp:new Date().toISOString()}),h())},retriggerAll(y){if(!i){for(let S of y)u.config.tasks[S]&&o.append({type:"task-restart",taskName:S,timestamp:new Date().toISOString()});h()}},snapshot(){return Qo(u)},getState(){return u},getSchedule(){return Zo(u)},async waitForHandlers(){c.size>0&&await Promise.allSettled([...c])},async dispose(y){y?.wait&&c.size>0&&await Promise.allSettled([...c]),i=!0}}}var $_=On(import.meta.url),Cn=$_("./jsonata-sync.cjs"),$d=Cn;function Hl(e,t){if(!t||!e)return;let r=t.split("."),a=e;for(let n=0;n<r.length;n++){if(a==null)return;a=a[r[n]]}return a}function wd(e,t,r){let a=t.split("."),n=e;for(let s=0;s<a.length-1;s++)(n[a[s]]==null||typeof n[a[s]]!="object")&&(n[a[s]]={}),n=n[a[s]];n[a[a.length-1]]=r}async function w_(e,t){if(!e?.compute?.length)return e;e.card_data||(e.card_data={}),e.computed_values={},e._sourcesData=t?.sourcesData??{};let r=e.requires??{},a={card_data:e.card_data,requires:r,expects_data:r,fetched_sources:e._sourcesData,data:e.computed_values,computed_values:e.computed_values};for(let n of e.compute)try{let s=await Cn(n.expr).evaluate(a);wd(e.computed_values,n.bindTo,s),a.computed_values=e.computed_values}catch{}return e}function b_(e,t){if(!e?.compute?.length)return{ok:!0,node:e};e.card_data||(e.card_data={}),e.computed_values={},e._sourcesData=t?.sourcesData??{};let r=e.requires??{},a={card_data:e.card_data,requires:r,expects_data:r,fetched_sources:e._sourcesData,data:e.computed_values,computed_values:e.computed_values},n=[];for(let s of e.compute)try{let o=$d(s.expr).evaluate(a);wd(e.computed_values,s.bindTo,o),a.computed_values=e.computed_values}catch(o){let u=o instanceof Error?o.message:String(o);n.push({bindTo:s.bindTo,error:u})}return n.length>0?{ok:!0,node:e,errors:n}:{ok:!0,node:e}}async function S_(e,t,r){let a={...r??{},card_data:t.card_data??{},requires:t.requires??{},fetched_sources:t._sourcesData??{},computed_values:t.computed_values??{}};return Cn(e).evaluate(a)}function k_(e,t){return t.startsWith("fetched_sources.")?Hl(e._sourcesData??{},t.slice(16)):Hl(e,t)}var Kl=new Set(["metric","table","editable-table","chart","form","filter","list","notes","todo","alert","narrative","badge","text","markdown","ref","custom","actions"]),E_=new Set(["id","meta","requires","provides","view","card_data","compute","source_defs"]);function P_(e){let t=[];if(!e||typeof e!="object"||Array.isArray(e))return{ok:!1,errors:["Node must be a non-null object"]};let r=e;(typeof r.id!="string"||!r.id)&&t.push("id: required, must be a non-empty string");for(let a of Object.keys(r))E_.has(a)||t.push(`Unknown top-level key: "${a}"`);if((r.card_data==null||typeof r.card_data!="object"||Array.isArray(r.card_data))&&t.push("card_data: required, must be an object"),r.meta!=null)if(typeof r.meta!="object"||Array.isArray(r.meta))t.push("meta: must be an object");else{let a=r.meta;a.title!=null&&typeof a.title!="string"&&t.push("meta.title: must be a string"),a.tags!=null&&!Array.isArray(a.tags)&&t.push("meta.tags: must be an array")}if(r.requires!=null&&!Array.isArray(r.requires)&&t.push("requires: must be an array of strings"),r.provides!=null&&(Array.isArray(r.provides)?r.provides.forEach((a,n)=>{if(!a||typeof a!="object"||Array.isArray(a))t.push(`provides[${n}]: must be an object with bindTo and ref`);else{let s=a;(typeof s.bindTo!="string"||!s.bindTo)&&t.push(`provides[${n}]: missing required "bindTo" string`),(typeof s.ref!="string"||!s.ref)&&t.push(`provides[${n}]: missing required "ref" string`)}}):t.push("provides: must be an array of { bindTo, ref } bindings")),r.compute!=null&&(Array.isArray(r.compute)?r.compute.forEach((a,n)=>{if(!a||typeof a!="object"||Array.isArray(a))t.push(`compute[${n}]: must be a compute step object`);else{let s=a;(typeof s.bindTo!="string"||!s.bindTo)&&t.push(`compute[${n}]: missing required "bindTo" property`),(typeof s.expr!="string"||!s.expr)&&t.push(`compute[${n}]: missing required "expr" string (JSONata expression)`)}}):t.push("compute: must be an array of compute steps")),r.source_defs!=null)if(!Array.isArray(r.source_defs))t.push("source_defs: must be an array");else{let a=new Set,n=new Set;r.source_defs.forEach((s,o)=>{if(!s||typeof s!="object"||Array.isArray(s))t.push(`source_defs[${o}]: must be an object`);else{let u=s;typeof u.bindTo!="string"||!u.bindTo?t.push(`source_defs[${o}]: missing required "bindTo" property`):(a.has(u.bindTo)&&t.push(`source_defs[${o}]: bindTo "${u.bindTo}" is not unique across source_defs`),a.add(u.bindTo)),typeof u.outputFile!="string"||!u.outputFile?t.push(`source_defs[${o}]: missing required "outputFile" property`):(n.has(u.outputFile)&&t.push(`source_defs[${o}]: outputFile "${u.outputFile}" is not unique across source_defs`),n.add(u.outputFile)),u.optionalForCompletionGating!=null&&typeof u.optionalForCompletionGating!="boolean"&&t.push(`source_defs[${o}]: optionalForCompletionGating must be a boolean`)}})}if(r.view!=null)if(typeof r.view!="object"||Array.isArray(r.view))t.push("view: must be an object");else{let a=r.view;!Array.isArray(a.elements)||a.elements.length===0?t.push("view.elements: required, must be a non-empty array"):a.elements.forEach((n,s)=>{if(!n||typeof n!="object"){t.push(`view.elements[${s}]: must be an object`);return}!n.kind||typeof n.kind!="string"?t.push(`view.elements[${s}].kind: required, must be a string`):Kl.has(n.kind)||t.push(`view.elements[${s}].kind: unknown kind "${n.kind}". Valid: ${[...Kl].join(", ")}`),n.data!=null&&(typeof n.data!="object"||Array.isArray(n.data))&&t.push(`view.elements[${s}].data: must be an object`)}),a.layout!=null&&(typeof a.layout!="object"||Array.isArray(a.layout))&&t.push("view.layout: must be an object"),a.features!=null&&(typeof a.features!="object"||Array.isArray(a.features))&&t.push("view.features: must be an object")}return{ok:t.length===0,errors:t}}async function j_(e,t){if(!e||e.length===0)return[];let r={card_data:t.card_data??{},requires:t.requires??{}};return Promise.all(e.map(async a=>{let n={};if(a.projections&&typeof a.projections=="object"&&!Array.isArray(a.projections)){for(let[s,o]of Object.entries(a.projections))if(typeof o=="string"&&o.trim().length>0)try{n[s]=await Cn(o).evaluate(r)}catch{n[s]=void 0}}return{...a,_projections:n}}))}function O_(e,t){if(!e||e.length===0)return[];let r={card_data:t.card_data??{},requires:t.requires??{}};return e.map(a=>{let n={};if(a.projections&&typeof a.projections=="object"&&!Array.isArray(a.projections)){for(let[s,o]of Object.entries(a.projections))if(typeof o=="string"&&o.trim().length>0)try{n[s]=$d(o).evaluate(r)}catch{n[s]=void 0}}return{...a,_projections:n}})}var qr={run:w_,runSync:b_,eval:S_,resolve:k_,validate:P_,enrichSources:j_,enrichSourcesSync:O_};function N_(e){return JSON.stringify(e)}function T_(e){let t;try{t=JSON.parse(e)}catch{throw new Error(`parseExecutionRef: invalid JSON \u2014 ${e}`)}if(typeof t!="object"||t===null||typeof t.howToRun!="string"||typeof t.whatToRun!="string")throw new Error(`parseExecutionRef: missing required fields howToRun/whatToRun \u2014 ${e}`);return t}function bd(e,t){function r(){return e.readIndex()??{}}function a(n,s,o){let u=String(s||"").split(".").filter(Boolean);if(u.length===0)return o&&typeof o=="object"&&!Array.isArray(o)?o:{value:o};let i={...n},c=i;for(let l=0;l<u.length-1;l++){let d=u[l],w=c[d],$=w&&typeof w=="object"&&!Array.isArray(w)?{...w}:{};c[d]=$,c=$}return c[u[u.length-1]]=o,i}return{readCard(n){let s=r()[n];return!s||!e.cardExists(s.key)?null:e.readCard(s.key)},readCardKey(n){return r()[n]?.key??null},readAllCards(){let n=[];for(let[s,o]of Object.entries(r())){if(!e.cardExists(o.key))continue;let u=e.readCard(o.key);u?n.push(u):t?.(`[card-store] could not read card "${s}" at key "${o.key}"`)}return n},readChecksumIndex(){let n={};for(let[s,o]of Object.entries(r()))n[s]=o.checksum;return n},changedSince(n){let s=r(),o=[];for(let[u,i]of Object.entries(s))n[u]!==i.checksum&&o.push(u);for(let u of Object.keys(n))s[u]||o.push(u);return o},validateUpsert(n,s){let o=r(),u=o[n],i=Object.entries(o).find(([,c])=>c.key===s);return u&&u.key!==s?{ok:!1,error:`Card id "${n}" is already mapped to key "${u.key}", cannot remap to "${s}"`}:i&&i[0]!==n?{ok:!1,error:`Key "${s}" is already mapped to card id "${i[0]}", cannot remap to "${n}"`}:{ok:!0}},writeCard(n,s,o){let u=r(),i=o??u[n]?.key??e.defaultCardKey(n),c=e.writeCard(i,s);u[n]={key:i,checksum:c,updatedAt:new Date().toISOString()},e.writeIndex(u)},patchCard(n,s,o){let u=r(),i=u[n];if(!i||!e.cardExists(i.key))throw new Error(`card "${n}" not found`);let c=e.readCard(i.key);if(!c||typeof c!="object"||Array.isArray(c))throw new Error(`card "${n}" is not patchable`);let l=a(c,s,o),d=e.writeCard(i.key,l);u[n]={key:i.key,checksum:d,updatedAt:new Date().toISOString()},e.writeIndex(u)},removeCard(n){let s=r(),o=s[n];o&&(e.removeCard(o.key),delete s[n],e.writeIndex(s))},readIndex(){return r()}}}function Bo(e,t){return{readSourceData(r,a){let n=e.read(`${r}/${a}`);if(n==null)return null;let s=n.trim();if(!s)return null;try{return JSON.parse(s)}catch{return s}},ingestSourceDataStaged(r,a,n,s){let o=t(n);e.write(`${r}/.staged/${s}/${a}`,o)},commitSourceData(r,a,n){let s=`${r}/.staged/${n}/${a}`,o=e.read(s);return o==null?!1:(e.write(`${r}/${a}`,o),e.remove(s),!0)},hasSource(r,a){return e.exists(`${r}/${a}`)},listSources(r){return e.listKeys(`${r}/`).filter(a=>!a.includes("/.staged/")).map(a=>a.slice(`${r}/`.length))}}}function x_(e){function t(r){let a=e.readAllEntries();if(!r)return a;let n=a.findIndex(s=>s.id===r);return n===-1?a:a.slice(n+1)}return{readEntriesAfterCursor(r){let a=t(r);return a.length===0?{events:[],newCursor:r}:{events:a.map(n=>n.event),newCursor:a[a.length-1].id}},pendingCount(r){return t(r).length},appendEvent(r){e.appendEntry({id:e.generateId(),event:r})}}}function R_(e,t){return{appendEntries(r,a){if(!r||a.length===0)return;let n=e.read(r)??[];e.write(r,[...n,...a])},dispatchEntriesForJournalId(r,a){if(!r)return;let n=e.read(r);if(!(!n||n.length===0)){for(let s of n)try{a(s)}catch(o){let u=o instanceof Error?o.message:String(o);try{t(s,u)}catch{}}e.delete(r)}}}}var Sd="v1",wa="board/graph",kd="board/lastJournalProcessedId";function Gl(e){return`cards/${e}/runtime`}function I_(e){return{readRuntime(t){return e.read(Gl(t))??{_sources:{}}},writeRuntime(t,r){e.write(Gl(t),r)}}}function C_(e,t){let r={...e};for(let a of t.deleteKeys)delete r[a];return{...r,...t.shallowMerge}}function A_(e){return{readSnapshot(t){return e.readValues(t)},commitSnapshot(t,r){if(r.schemaVersion!==Sd)throw new Error(`Unsupported snapshot schema version: ${r.schemaVersion}`);let a=e.readValues(t);if(a.version!==r.expectedVersion)return{ok:!1,reason:"version-mismatch",currentVersion:a.version};let n=C_(a.values,r);return{ok:!0,newVersion:e.writeValues(t,n,r.deleteKeys)}}}}function ii(e){function t(r){let a=e.read(r);return a==null?null:typeof a=="string"?a:JSON.stringify(a)}return{readTaskExecutorRef(){let r=t("task-executor");if(r?.trim())return T_(r.trim())},writeTaskExecutorRef(r){e.write("task-executor",N_(r))},readChatHandlerFlow(){return e.read("chat-handler-flow")},writeChatHandlerFlow(r){e.write("chat-handler-flow",r)},readCardStoreRef(){return t("card-store-ref")},writeCardStoreRef(r){e.write("card-store-ref",r)},readOutputsStoreRef(){return t("outputs-store-ref")},writeOutputsStoreRef(r){e.write("outputs-store-ref",r)},readScratchStoreRef(){return t("scratch-store-ref")},writeScratchStoreRef(r){e.write("scratch-store-ref",r)},readArchiveStoreRef(){return t("archive-store-ref")},writeArchiveStoreRef(r){e.write("archive-store-ref",r)},readChatStoreRef(){return t("chat-store-ref")},writeChatStoreRef(r){e.write("chat-store-ref",r)},readArtifactsStoreRef(){return t("artifacts-store-ref")},writeArtifactsStoreRef(r){e.write("artifacts-store-ref",r)}}}function q_(e){return{writeComputedValues(t,r){e.write(`cards/${t}/computed_values`,r)},readComputedValues(t){return e.read(`cards/${t}/computed_values`)},readAllComputedValues(){let t={};for(let r of e.listKeys("cards/")){let a=r.match(/^cards\/([^/]+)\/computed_values$/);a&&(t[a[1]]=e.read(r))}return t},writeDataObjects(t){for(let[r,a]of Object.entries(t))r&&e.write(`data-objects/${r}`,a)},readDataObject(t){return e.read(`data-objects/${t}`)},readAllDataObjects(){let t={};for(let r of e.listKeys("data-objects/"))t[r.slice(13)]=e.read(r);return t},writeStatusSnapshot(t){e.write("status",t)},readStatusSnapshot(){return e.read("status")}}}function Bl(e){return e?{lastRequestedToken:e.lastRequestedToken,lastCompletedToken:e.lastCompletedToken,lastCompletionStatus:e.lastCompletionStatus??(e.lastCompletedToken?"success":"not-started"),queueRequestedToken:e.queueRequestedToken}:{lastCompletionStatus:"not-started"}}function D_(e){return e?.lastRequestedToken?e.lastCompletedToken!==e.lastRequestedToken:!1}function Jl(e,t){return e?.lastRequestedToken?D_(e)?"in-flight":!e.lastCompletedToken||e.lastCompletedToken<t?"dispatch":"idle":"dispatch"}function M_(e,t){return{...e,lastCompletedToken:t,lastCompletionStatus:"success"}}function Wl(e,t){return{...e,lastCompletedToken:t,lastCompletionStatus:"failure"}}function Jo(e,t){let r=t.state.tasks,a=t.config.tasks,n=Object.keys(r),s=Zo(t),o={completed:0,failed:0,in_progress:0,pending:0,blocked:0,unresolved:0},u=new Map;for(let h of s.pending)u.set(h.taskName,h.waitingOn);for(let h of s.unresolved)u.set(h.taskName,h.missingTokens);for(let h of s.blocked)u.set(h.taskName,h.failedTokens);let i=new Map;for(let[h,v]of Object.entries(a))for(let m of v.requires??[]){let f=i.get(m)??[];f.push(h),i.set(m,f)}let c=n.sort().map(h=>{let v=r[h],m=a[h]??{requires:[],provides:[]};v.status==="completed"?o.completed+=1:v.status==="failed"?o.failed+=1:v.status==="in-progress"&&(o.in_progress+=1);let f=m.requires??[],k=m.provides??[],y=Object.keys(v.data??{}).sort(),S=f.filter(x=>t.state.availableOutputs.includes(x)),_=f.filter(x=>!t.state.availableOutputs.includes(x)),g=u.get(h)??_,p=new Set;for(let x of k)for(let C of i.get(x)??[])C!==h&&p.add(C);let E=v.failedAt,j=v.error?{message:v.error,code:"TASK_FAILED",at:E,source:"task-runtime"}:void 0;return{name:h,status:v.status,error:j,requires:f,requires_satisfied:S,requires_missing:_,provides_declared:k,provides_runtime:y,blocked_by:g,unblocks:Array.from(p).sort(),runtime:{attempt_count:v.executionCount??0,restart_count:v.retryCount??0,in_progress_since:v.status==="in-progress"?v.startedAt??null:null,last_transition_at:v.lastUpdated??null,last_completed_at:v.completedAt??null,last_restarted_at:v.startedAt??null,status_age_ms:v.lastUpdated?0:null}}});o.pending=s.pending.length,o.blocked=s.blocked.length,o.unresolved=s.unresolved.length;let l=c.map(h=>({name:h.name,fanOut:h.unblocks.length})).sort((h,v)=>v.fanOut-h.fanOut||h.name.localeCompare(v.name)),d=l.length>0?l[0]:{name:null,fanOut:0},w=new Set;for(let h of Object.values(a))for(let v of h.requires??[])w.add(v);let $=0;for(let[h,v]of Object.entries(a)){let m=(v.requires??[]).length===0,f=(v.provides??[]).some(k=>(i.get(k)??[]).some(y=>y!==h));m&&!f&&($+=1)}return{schema_version:"v1",meta:{board:{path:e}},summary:{card_count:n.length,completed:o.completed,eligible:s.eligible.length,pending:o.pending,blocked:o.blocked,unresolved:o.unresolved,failed:o.failed,in_progress:o.in_progress,orphan_cards:$,topology:{edge_count:Array.from(w).length,max_fan_out_card:d.name,max_fan_out:d.fanOut}},cards:c}}function F_(){return new Date().toISOString()}function V_(e,t,r,a,n,s,o){return async u=>{let i=[],c=r.cardStore.readCard(u.nodeId);if(!c)return"task-initiate-failure";let l=c.id,d=c.card_data??{},w=c.source_defs??[],$=w.filter(M=>M.optionalForCompletionGating!==!0),h=r.cardRuntimeStore.readRuntime(l),v=!1,m=()=>{v&&(r.cardRuntimeStore.writeRuntime(l,h),v=!1)},f=M=>Bl(h._sources[M]),k=(M,U)=>{h._sources[M]=Bl(U),v=!0},y=u.taskState?.executionCount??0;if(h._lastExecutionCount!==y&&(h._sources={},h._lastExecutionCount=y,v=!0),u.update){let M=u.update,U=M.outputFile;if(U){let J=f(U);if(M.failure){let te=M.rqt??J.lastRequestedToken??J.queueRequestedToken;te&&k(U,Wl(J,te))}else{let te=M.rqt;if(!J.lastCompletedToken||te>J.lastCompletedToken){let W=typeof M.deliveryToken=="string"?M.deliveryToken:void 0,T=!1;W&&(T=r.fetchedSourcesStore.commitSourceData(l,U,W)),T?k(U,M_(J,te)):k(U,Wl(J,te))}}m()}}let S={};for(let M of w)if(M.outputFile){let U=r.fetchedSourcesStore.readSourceData(l,M.outputFile);U!==null&&(S[M.bindTo]=U)}let _={};for(let[M,U]of Object.entries(u.state??{}))if(U!==null&&typeof U=="object"&&!Array.isArray(U)){let J=U[M];_[M]=J!==void 0?J:U}else _[M]=U;let g={id:l,card_data:{...d},requires:_,source_defs:w,compute:c.compute};g._sourcesData=S,c.compute&&qr.runSync(g,{sourcesData:S}),(s??r.outputStore.writeComputedValues.bind(r.outputStore))(l,g.computed_values??{});let p={...c},E=qr.enrichSourcesSync(Array.isArray(c.source_defs)?c.source_defs:void 0,{card_data:c.card_data,requires:_}),j=e.value;p.source_defs=Array.isArray(E)?E.map(M=>({...M,boardDir:typeof M.boardDir=="string"&&M.boardDir?M.boardDir:j})):E;let x=F_(),C=u.update?void 0:x,q=$.filter(M=>{let U=M.outputFile;if(typeof U!="string"||!U)return!0;let J=f(U);C&&(J={...J,queueRequestedToken:C},k(U,J));let te=J.queueRequestedToken??J.lastRequestedToken??x,W=Jl(J,te);return W==="in-flight"?!1:W==="dispatch"});if(m(),q.length>0){let M=!1,U=x;for(let J of q){let te=J.outputFile;if(typeof te!="string"||!te)continue;let W=f(te),T=W.queueRequestedToken??x;k(te,{...W,lastRequestedToken:T}),U=T,M=!0}return M&&m(),M&&(i.push({taskKind:"source-fetch",payload:{boardRef:ze(e),enrichedCard:p,callbackToken:u.callbackToken,rqt:U}}),r.executionRequestStore.appendEntries(t,i)),"task-initiated"}if($.some(M=>{let U=M.outputFile;if(typeof U!="string"||!U)return!1;let J=f(U),te=J.queueRequestedToken??J.lastRequestedToken??x;return Jl(J,te)==="in-flight"}))return"task-initiated";let F=c.provides??[],H={};for(let{bindTo:M,ref:U}of F)H[M]=qr.resolve(g,U);return(o??r.outputStore.writeDataObjects.bind(r.outputStore))(H),w.filter(M=>{if(M.optionalForCompletionGating!==!0)return!1;let U=f(M.outputFile);return!U.lastRequestedToken||!U.lastCompletedToken?!0:U.lastCompletedToken<=U.lastRequestedToken}).length>0&&i.push({taskKind:"source-fetch",payload:{boardRef:ze(e),enrichedCard:p,callbackToken:u.callbackToken,rqt:x}}),a(u.nodeId,H),i.length>0&&r.executionRequestStore.appendEntries(t,i),"task-initiated"}}var z_={settings:{completion:"manual",refreshStrategy:"data-changed"},tasks:{}};function U_(e){return{[wa]:e.graph,[kd]:e.lastDrainedJournalId}}function L_(e){let t=e[wa],r=e[kd];if(!t||typeof t!="object")throw new Error(`State snapshot is missing required key: ${wa}`);return{graph:t,lastDrainedJournalId:typeof r=="string"?r:""}}function H_(e){let t=e.requires,r=e.provides?.map(a=>a.bindTo)??[];return{requires:t&&t.length>0?t:void 0,provides:r,taskHandlers:["card-handler"],description:e.meta?.title??e.id}}function K_(e){function t(s){return{status:"success",data:s}}function r(s){return{status:"fail",error:s}}function a(s){return{status:"error",error:s instanceof Error?s.message:String(s)}}function n(s){if(Array.isArray(s))return s;if(s&&typeof s=="object"){let o=s;return Array.isArray(o.files)?o.files:[s]}return null}return{get(s){try{let o=s.params?.id;if(o){let u=e.readCard(o);return u?t({cards:[u]}):r(`card "${o}" not found`)}return t({cards:e.readAllCards()})}catch(o){return a(o)}},set(s){try{let o=s.body;if(o==null)return r("set requires a body (card object or array of cards)");let u=Array.isArray(o)?o:[o];for(let i of u){if(typeof i.id!="string")return r("each card must have a string `id` field");e.writeCard(i.id,i)}return t({count:u.length})}catch(o){return a(o)}},del(s){try{let o=s.body?.ids??[],u=s.params?.id,i=u?[...o,u]:o;if(i.length===0)return r("del requires body.ids (string[]) or params.id");for(let c of i)e.removeCard(c);return t({count:i.length})}catch(o){return a(o)}},patch(s){try{let o=s.params?.id,u=s.params?.path;if(!o)return r("patch requires params.id");if(!u)return r("patch requires params.path");let i=s.body,c=i&&Object.prototype.hasOwnProperty.call(i,"value")?i.value:s.body;return e.patchCard(o,u,c),t({count:1})}catch(o){return a(o)}},appendFiles(s){try{let o=s.params?.id;if(!o)return r("appendFiles requires params.id");let u=e.readCard(o);if(!u)return r(`card "${o}" not found`);let i=n(s.body);if(!i||i.length===0)return r("appendFiles requires a file metadata object, array, or body.files array");let c=u.card_data&&typeof u.card_data=="object"&&!Array.isArray(u.card_data)?u.card_data:{},l=Array.isArray(c.files)?c.files:[],d=[...l,...i],w=i.map((h,v)=>({idx:l.length+v,entry:h})),$=this.patch({params:{id:o,path:"card_data.files"},body:{value:d}});return $.status!=="success"?$:t({files_added:w})}catch(o){return a(o)}}}}function pe(e){return e!==void 0?{status:"success",data:e}:{status:"success"}}function ne(e){return{status:"fail",error:e}}function me(e){return{status:"error",error:e instanceof Error?e.message:String(e)}}function G_(e){let t=new TextEncoder().encode(e),r=Array.from(t,a=>String.fromCharCode(a)).join("");return btoa(r).replace(/\+/g,"-").replace(/\//g,"_").replace(/=/g,"")}function Ed(e){let t=e.replace(/-/g,"+").replace(/_/g,"/"),r=t+"=".repeat((4-t.length%4)%4),a=atob(r),n=Uint8Array.from(a,s=>s.charCodeAt(0));return new TextDecoder().decode(n)}function bn(e){try{let t=JSON.parse(Ed(e));return typeof t?.t=="string"?{taskName:t.t}:null}catch{return null}}function B_(e){return G_(JSON.stringify(e))}function Xl(e){try{let t=JSON.parse(Ed(e));return typeof t?.cbk=="string"&&typeof t?.cid=="string"&&typeof t?.b=="string"&&typeof t?.d=="string"?t:null}catch{return null}}function Ke(){return new Date().toISOString()}function Wo(e,t){let r=t.onWarn??(()=>{}),a=ze(e);function n(z){if(z.length!==0)try{let b=t.publishBoardChangeNotifications?.(z);b&&typeof b.catch=="function"&&b.catch(N=>r(`[board-live-cards-public] publishBoardChangeNotifications failed: ${N instanceof Error?N.message:String(N)}`))}catch(b){r(`[board-live-cards-public] publishBoardChangeNotifications failed: ${b instanceof Error?b.message:String(b)}`)}}function s(){let z=u().readCardStoreRef();if(!z)throw new Error(`Board at ${e.value} has no card store configured. Run: init --base-ref <ref> --store-ref <b64-ref>`);let b=t.kvStorageForRef(z);return{readIndex(){return b.read("_index")},writeIndex(N){b.write("_index",N)},readCard(N){return b.read(N)},writeCard(N,I){return b.write(N,I),t.hashFn(I)},removeCard(N){b.delete(N)},cardExists(N){return b.read(N)!==null},defaultCardKey(N){return N}}}let o={readValues(z){let b=t.kvStorage("state-snapshot"),N=b.listKeys().sort();if(N.length===0)return{version:null,values:{}};let I={};for(let L of N)I[L]=b.read(L);return{version:t.hashFn(I),values:I}},writeValues(z,b,N){let I=t.kvStorage("state-snapshot");for(let L of N)I.delete(L);for(let[L,B]of Object.entries(b))I.write(L,B);return t.hashFn(b)}},u=()=>ii(t.kvStorage("config")),i=()=>A_(o),c=()=>x_(t.journalAdapter()),l=()=>bd(s(),r),d=()=>{let z=u().readOutputsStoreRef();if(!z)throw new Error(`Board at ${e.value} has no outputs store configured. Run: init --outputs-store-ref <b64-ref>`);return q_(t.kvStorageForRef(z))},w=()=>{let z=u().readArchiveStoreRef();return z?t.archiveFactoryForRef(z):t.archiveFactory()};function $(){return!!i().readSnapshot(e.value).values[wa]}function h(){let z=i().readSnapshot(e.value);if(!z.values[wa])throw new Error(`Board not initialized at ${e.value}`);return L_(z.values)}function v(z,b){let N=i().commitSnapshot(e.value,{schemaVersion:Sd,expectedVersion:b,commitId:t.genId(),committedAt:Ke(),deleteKeys:[],shallowMerge:U_(z)});if(!N.ok)throw new Error(`Snapshot commit failed (version mismatch): expected=${b??"null"} current=${N.currentVersion??"null"}`)}function m(z){c().appendEvent(z)}async function f(){let z=(Y,se)=>{let Oe=Y.payload,kt=(Oe?.enrichedCard??{}).id??Oe?.cardId??"unknown";m({type:"task-failed",taskName:kt,error:se,timestamp:Ke()})},b=R_(t.kvStorage("execution-requests"),z),N=I_(t.kvStorage("card-runtime")),I=Bo(t.blobStorage("sources"),Y=>t.resolveBlob(Y)),L=new Map,B={readRuntime(Y){return L.get(Y)??N.readRuntime(Y)},writeRuntime(Y,se){L.set(Y,se)}},ae=[],le=new Map,ke={readSourceData(Y,se){let Oe=`${Y}/${se}`;return le.has(Oe)?le.get(Oe):I.readSourceData(Y,se)},ingestSourceDataStaged(Y,se,Oe,kt){I.ingestSourceDataStaged(Y,se,Oe,kt)},commitSourceData(Y,se,Oe){let kt=`${Y}/.staged/${Oe}/${se}`,it=t.blobStorage("sources").read(kt);if(it==null)return!1;let ka=`${Y}/${se}`,fr=it.trim();try{le.set(ka,JSON.parse(fr))}catch{le.set(ka,fr)}return ae.push({cardId:Y,outputFile:se,deliveryToken:Oe}),!0},hasSource(Y,se){let Oe=`${Y}/${se}`;return le.has(Oe)?!0:I.hasSource(Y,se)},listSources(Y){let se=I.listSources(Y),Oe=new Set;for(let it of le.keys())it.startsWith(`${Y}/`)&&Oe.add(it.slice(`${Y}/`.length));let kt=new Set([...se,...Oe]);return Array.from(kt)}},Pe={cardStore:l(),cardRuntimeStore:B,fetchedSourcesStore:ke,outputStore:d(),executionRequestStore:b},Ie=h(),je=Ko(Ie.graph),{events:Ze,newCursor:qe}=c().readEntriesAfterCursor(Ie.lastDrainedJournalId),ot=[],St=[],Bt=[],lr=new Map,Dr=new Set,An=(Y,se)=>{ot.push({type:"task-completed",taskName:Y,data:se,timestamp:Ke()});try{w().stream("exec-history").append({taskName:Y,status:"completed",completedAt:Ke()})}catch{}},ui=(Y,se)=>{m({type:"task-failed",taskName:Y,error:se,timestamp:Ke()});try{w().stream("exec-history").append({taskName:Y,status:"failed",error:se,completedAt:Ke()})}catch{}},ba=__(je,{handlers:{"card-handler":V_(e,qe,Pe,An,ui,(Y,se)=>{St.push({cardId:Y,values:se})},Y=>{Bt.push(Y)})},onNodeRemoved:Y=>{lr.delete(Y),L.delete(Y),Dr.add(Y)}});for(ot=Ze;ot.length>0;){let Y=ot;ot=[];for(let se of Y)if(se.type==="task-restart"){let Oe=Pe.cardStore.readCard(se.taskName);Oe&&lr.set(se.taskName,Oe)}ba.pushAll(Y),await ba.waitForHandlers()}let ci=ba.getState();await ba.dispose({wait:!0});let jd=i().readSnapshot(e.value).version;v({lastDrainedJournalId:qe,graph:Qo(ci)},jd);for(let{cardId:Y,values:se}of St)Pe.outputStore.writeComputedValues(Y,se);for(let Y of Bt)Pe.outputStore.writeDataObjects(Y);for(let[Y,se]of L)N.writeRuntime(Y,se);for(let{cardId:Y,outputFile:se,deliveryToken:Oe}of ae)I.commitSourceData(Y,se,Oe);let Sa;try{Sa=Jo(a,ci),Pe.outputStore.writeStatusSnapshot(Sa)}catch(Y){r(`[board-live-cards-public] status publish failed: ${Y instanceof Error?Y.message:String(Y)}`)}let dr=[];for(let{cardId:Y,values:se}of St)dr.push({kind:"computed_values",cardId:Y,values:se});for(let Y of Bt)for(let[se,Oe]of Object.entries(Y))se&&dr.push({kind:"data_object",key:se,payload:Oe});for(let[Y,se]of lr)dr.push({kind:"card_refreshed",cardId:Y,card:se});for(let Y of Dr)dr.push({kind:"card_removed",cardId:Y});Sa!==void 0&&dr.push({kind:"status",status:Sa}),n(dr);let Od=u().readTaskExecutorRef()??{howToRun:"built-in",whatToRun:ze({kind:"built-in",value:"source-cli-task-executor"})};b.dispatchEntriesForJournalId(qe,Y=>{if(Y.taskKind!=="source-fetch"){r(`[process-accumulated-events] unknown taskKind "${Y.taskKind}" \u2014 skipping`);return}let se=Y.payload,Oe=se.enrichedCard?.id??"unknown",kt=se.enrichedCard?.source_defs??[];for(let it of kt){if(!it.outputFile){r(`[dispatch] source "${it.bindTo}" has no outputFile \u2014 skipping`);continue}let ka=B_({cbk:se.callbackToken,rg:e.value,br:ze(e),cid:Oe,b:it.bindTo,d:it.outputFile,cs:void 0,rqt:se.rqt});t.dispatchExecution(Od,{source_def:it,base_ref:ze(e),callback:{token:ka,via:t.selfRef}}).catch(fr=>ui(Oe,fr instanceof Error?fr.message:String(fr)))}})}async function k(){try{let z=()=>{let N=h(),{events:I}=c().readEntriesAfterCursor(N.lastDrainedJournalId);I.length<=0||(k(),t.requestProcessAccumulated?.())},b=await i0(t.lock,f,z);return pe({ran:b!==!1})}catch(z){return me(z)}}function y(){k(),t.requestProcessAccumulated?.()}function S(z){try{let b=z.params?.cardStoreRef;if(!b)return ne("init requires params.cardStoreRef \u2014 create a card store with card-store-cli and pass its ref here");if(!$()){let Pe=vd(z_);v({lastDrainedJournalId:"",graph:Qo(Pe)},null)}let N=z.params?.outputsStoreRef;if(!N)return ne("init requires params.outputsStoreRef \u2014 pass the outputs store ref here");let I=z.params?.scratchStoreRef,L=z.params?.archiveStoreRef,B=z.params?.chatStoreRef,ae=z.params?.artifactsStoreRef,le=u();le.writeCardStoreRef(b),le.writeOutputsStoreRef(N),I&&le.writeScratchStoreRef(I),L&&le.writeArchiveStoreRef(L),B&&le.writeChatStoreRef(B),ae&&le.writeArtifactsStoreRef(ae);let ke=z.body??{};ke["task-executor-ref"]&&le.writeTaskExecutorRef(ke["task-executor-ref"]),Object.prototype.hasOwnProperty.call(ke,"chat-handler-flow")&&le.writeChatHandlerFlow(ke["chat-handler-flow"]);try{d().writeStatusSnapshot(Jo(a,Ko(h().graph)))}catch{}return pe()}catch(b){return me(b)}}function _(z){try{let b=d().readStatusSnapshot();if(!b){b=Jo(a,Ko(h().graph));try{d().writeStatusSnapshot(b)}catch{}}return pe(b)}catch(b){return me(b)}}function g(z){try{let b=z.params?.id;return b?(m({type:"task-removal",taskName:b,timestamp:Ke()}),y(),pe()):ne("removeCard requires params.id")}catch(b){return me(b)}}function p(z){try{let b=z.params?.cardId;if(!b)return ne("addCardFiles requires params.cardId");let N=K_(l()).appendFiles({params:{id:b},body:z.body});if(N.status!=="success")return N;let I=E({params:{cardId:b}});return I.status!=="success"?I:pe({cardId:b,files_added:N.data.files_added,notified:!0})}catch(b){return me(b)}}function E(z){try{let b=z.params?.cardId;if(!b)return ne("cardRefreshedNotify requires params.cardId");let N=l().readCard(b);return N?(n([{kind:"card_refreshed",cardId:b,card:N}]),pe({cardId:b,notified:!0})):ne(`Card "${b}" not found in board at ${e.value}`)}catch(b){return me(b)}}function j(z){try{let b=z.params?.id;return b?(m({type:"task-restart",taskName:b,timestamp:Ke()}),y(),pe()):ne("retrigger requires params.id")}catch(b){return me(b)}}async function x(z){return k()}function C(z){try{let b=z.params?.cardId,N=z.params?.all,I=!!z.params?.restart;if(!b&&!N)return ne("upsertCard requires --card-id <id> or --all");let L=N?l().readAllCards().map(B=>B.id):[b];for(let B of L)if(!l().readCard(B))return ne(`Card "${B}" not found in board at ${e.value}`);for(let B of L){let ae=l().readCard(B),le=H_(ae),ke=t.hashFn(le),Pe=t.kvStorage("card-upsert"),Ie=Pe.read(B),je=Ie?.taskConfigHash!==ke;if(!(!je&&!I)){if(je){let Ze=Ie?.blobRef??l().readCardKey(B)??B;m({type:"task-upsert",taskName:B,taskConfig:le,timestamp:Ke()}),Pe.write(B,{blobRef:Ze,taskConfigHash:ke,updatedAt:Ke()})}I&&m({type:"task-restart",taskName:B,timestamp:Ke()})}}return y(),pe()}catch(b){return me(b)}}function q(z){try{let b=z.params?.token;if(!b)return ne("taskFailed requires params.token");let N=z.params?.error??"unknown error",I=bn(b);if(!I)return ne("Invalid callback token");m({type:"task-failed",taskName:I.taskName,error:N,timestamp:Ke()});try{w().stream("exec-history").append({taskName:I.taskName,status:"failed",error:N,completedAt:Ke()})}catch{}return y(),pe()}catch(b){return me(b)}}function F(z){try{let b=z.params?.token;if(!b)return ne("taskProgress requires params.token");let N=(z.body??{}).update??{},I=bn(b);return I?(m({type:"task-progress",taskName:I.taskName,update:N,timestamp:Ke()}),y(),pe()):ne("Invalid callback token")}catch(b){return me(b)}}function H(z){try{let b=z.params?.token,N=z.params?.ref;if(!b)return ne("sourceDataFetched requires params.token");if(!N)return ne("sourceDataFetched requires params.ref");let I=Xl(b);if(!I)return ne("Invalid source token");let{cbk:L,cid:B,b:ae,d:le,cs:ke,rqt:Pe}=I,Ie=Bo(t.blobStorage("sources"),ot=>t.resolveBlob(ot)),je=t.genId();Ie.ingestSourceDataStaged(B,le,ht(N),je);let Ze=bn(L);if(!Ze)return ne("Invalid callback token embedded in source token");let qe=Ke();return m({type:"task-progress",taskName:Ze.taskName,update:{bindTo:ae,outputFile:le,fetchedAt:qe,deliveryToken:je,sourceChecksum:ke,rqt:Pe},timestamp:qe}),y(),pe()}catch(b){return me(b)}}function M(z){try{let b=z.params?.token,N=z.params?.reason??"unknown";if(!b)return ne("sourceDataFetchFailure requires params.token");let I=Xl(b);if(!I)return ne("Invalid source token");let{cbk:L,b:B,d:ae,cs:le,rqt:ke}=I,Pe=bn(L);return Pe?(m({type:"task-progress",taskName:Pe.taskName,update:{bindTo:B,outputFile:ae,failure:!0,reason:N,sourceChecksum:le,rqt:ke},timestamp:Ke()}),y(),pe()):ne("Invalid callback token embedded in source token")}catch(b){return me(b)}}function U(z){try{let b=u().readCardStoreRef();return b?pe({storeRef:b}):ne(`Board at ${e.value} has no card store configured`)}catch(b){return me(b)}}function J(z){try{let b=u().readOutputsStoreRef();return b?pe({storeRef:b}):ne(`Board at ${e.value} has no outputs store configured`)}catch(b){return me(b)}}function te(z){try{let b=u().readScratchStoreRef();return pe({storeRef:b})}catch(b){return me(b)}}function W(z){try{let b=u().readArchiveStoreRef();return pe({storeRef:b})}catch(b){return me(b)}}function T(z){try{let b=u().readChatStoreRef();return pe({storeRef:b})}catch(b){return me(b)}}function A(z){try{let b=u().readArtifactsStoreRef();return pe({storeRef:b})}catch(b){return me(b)}}function V(z){try{let b=z.params?.key;if(!b)return ne("getConfig requires params.key");let N=u(),I;switch(b){case"task-executor":I=N.readTaskExecutorRef()??null;break;case"chat-handler-flow":I=N.readChatHandlerFlow()??null;break;case"card-store-ref":I=N.readCardStoreRef();break;case"outputs-store-ref":I=N.readOutputsStoreRef();break;case"scratch-store-ref":I=N.readScratchStoreRef();break;case"archive-store-ref":I=N.readArchiveStoreRef();break;case"chat-store-ref":I=N.readChatStoreRef();break;case"artifacts-store-ref":I=N.readArtifactsStoreRef();break;default:return ne(`getConfig: unknown key "${b}"`)}return pe({value:I})}catch(b){return me(b)}}function P(z){try{let b=z.params?.key;if(!b)return ne("getOutputsDataObject requires params.key");let N=d().readDataObject(b);return pe(N)}catch(b){return me(b)}}function O(z){try{return pe(d().readAllDataObjects())}catch(b){return me(b)}}function R(z){try{let b=z.params?.key;if(!b)return ne("getOutputsComputedValues requires params.key");let N=d().readComputedValues(b);return pe(N)}catch(b){return me(b)}}function K(z){try{return pe(d().readAllComputedValues())}catch(b){return me(b)}}function Z(){return Bo(t.blobStorage("sources"),z=>t.resolveBlob(z))}function ie(z){let b=t.blobStorage("sources").keyRef?.(z);return b?ze(b):z}function re(z){try{let b=z.params?.key;if(!b)return ne("getOutputsFetchedSources requires params.key");let N=Z().listSources(b),I={};for(let L of N)I[L]=ie(`${b}/${L}`);return pe(I)}catch(b){return me(b)}}function be(z){try{let b=Z(),N=new Set;for(let L of t.blobStorage("sources").listKeys()){let B=L.indexOf("/");B>0&&!L.includes("/.staged/")&&N.add(L.slice(0,B))}let I={};for(let L of N){let B=b.listSources(L);if(B.length>0){I[L]={};for(let ae of B)I[L][ae]=ie(`${L}/${ae}`)}}return pe(I)}catch(b){return me(b)}}return{init:S,status:_,getCardStoreRef:U,getOutputsStoreRef:J,getScratchStoreRef:te,getArchiveStoreRef:W,getChatStoreRef:T,getArtifactsStoreRef:A,getConfig:V,getOutputsDataObject:P,getAllOutputsDataObjects:O,getOutputsComputedValues:R,getAllOutputsComputedValues:K,getOutputsFetchedSources:re,getAllOutputsFetchedSources:be,removeCard:g,addCardFiles:p,cardRefreshedNotify:E,retrigger:j,processAccumulatedEvents:x,upsertCard:C,taskFailed:q,taskProgress:F,sourceDataFetched:H,sourceDataFetchFailure:M}}function ur(e,t){let r=()=>ii(t.kvStorage("config"));function a(){let _=r().readCardStoreRef();if(!_)throw new Error(`Board at ${e.value} has no card store configured. Run: init --base-ref <ref> --store-ref <b64-ref>`);let g=t.kvStorageForRef(_);return{readIndex(){return g.read("_index")},writeIndex(p){g.write("_index",p)},readCard(p){return g.read(p)},writeCard(p,E){return g.write(p,E),t.hashFn(E)},removeCard(p){g.delete(p)},cardExists(p){return g.read(p)!==null},defaultCardKey(p){return p}}}let n=()=>bd(a(),t.onWarn??(()=>{})),s=()=>{let _=r().readScratchStoreRef();return _?t.scratchStorageForRef(_):t.scratchStorage()};function o(_,g){let p=t.validateSchema(g),E=[],j=r().readTaskExecutorRef();if(j&&Array.isArray(g.source_defs))for(let C of g.source_defs){let q=typeof C.bindTo=="string"?C.bindTo:"(unknown)";try{let F;try{F=t.invokeExecutorSync(j,"validate-source-def",[],{timeout:t.executorTimeouts?.validationMs??1e4,input:JSON.stringify(C)})}catch(M){let U=M;if(F=typeof U?.stdout=="string"?U.stdout:"",!F.trim()){E.push(`source "${q}": executor validate-source-def failed \u2014 ${M instanceof Error?M.message:String(M)}`);continue}}let H=JSON.parse(F.trim());if(!H.ok&&Array.isArray(H.errors))for(let M of H.errors)E.push(`source "${q}": ${M}`)}catch(F){E.push(`source "${q}": executor validate-source-def failed \u2014 ${F instanceof Error?F.message:String(F)}`)}}let x=[...p.errors,...E];return pe({cardId:_,isValid:x.length===0,issues:x})}function u(_,g){let p=r().readTaskExecutorRef();if(!p)throw new Error("No task-executor registered for this board");let E=typeof _.bindTo=="string"?_.bindTo:"source",j=s(),x={..._,boardDir:e.value,_projections:g},C=j.create(JSON.stringify(x,null,2),`probe-in-${E}`,".json"),q=j.getUniqueKey(`probe-out-${E}`,".json"),F=j.getUniqueKey(`probe-err-${E}`,".txt"),H=ze(j.keyRef(C)),M=ze(j.keyRef(q)),U=ze(j.keyRef(F)),J=null;try{if(t.invokeExecutorSync(p,"run-source-fetch",["--in-ref",H,"--out-ref",M,"--err-ref",U],{timeout:_.timeout??t.executorTimeouts?.probeMs??6e4}),J=j.read(q),J===null)throw new Error("Executor produced no output file")}catch(te){let W=j.read(F)?.trim()??(te instanceof Error?te.message:String(te));throw new Error(`Probe failed: ${W}`)}finally{try{j.remove(C)}catch{}try{j.remove(F)}catch{}}return{bindTo:E,result:J}}function i(_,g,p){let E;try{E=u(_,g)}catch(j){return ne(j instanceof Error?j.message:String(j))}if(p){let j=ht(p);t.absoluteBlob.write(j.value,E.result)}return pe({bindTo:E.bindTo,resultSizeBytes:E.result.length})}function c(_,g){let p=_.params?.sourceIdx,E=_.params?.outRef;if(p===void 0)return ne(`${g} requires params.sourceIdx`);if(!_.body||typeof _.body!="object"||Array.isArray(_.body))return ne(`${g} requires card JSON object in body`);let j=_.body,x=j["card-content"]??j,C=j["mock-projections"]??{},q=x.source_defs??[];if(p<0||p>=q.length)return ne(`sourceIdx ${p} out of range (card has ${q.length} source(s))`);let F=q[p],H=typeof F.bindTo=="string"?F.bindTo:"source";return{src:F,bindTo:H,outRef:E,mockProjections:C}}function l(_){try{let g=_.params?.cardId,p=_.params?.all;if(!g&&!p)return ne("validateCard requires --card-id <id> or --all");let E=p?n().readAllCards().map(x=>x.id):[g],j=[];for(let x of E){let C=n().readCard(x);if(!C){j.push({cardId:x,isValid:!1,issues:[`Card "${x}" not found`]});continue}let q=o(x,C);if(q.status!=="success")return q;j.push(q.data)}return pe(j)}catch(g){return me(g)}}function d(_){try{if(!_.body||typeof _.body!="object"||Array.isArray(_.body))return ne("validateCardPreflight requires card JSON object in body");let g=_.body,p=g["card-content"]??g,E=typeof p.id=="string"?p.id:"(unknown)";return o(E,p)}catch(g){return me(g)}}function w(_){try{let g=_.params?.cardId,p=_.params?.sourceIdx,E=_.params?.outRef;if(!g)return ne("probeSource requires params.cardId");if(p===void 0)return ne("probeSource requires params.sourceIdx");let j=(_.body??{})["mock-projections"]??{},x=n().readCard(g);if(!x)return ne(`Card "${g}" not found`);let C=x.source_defs??[];return p<0||p>=C.length?ne(`sourceIdx ${p} out of range (card has ${C.length} source(s))`):i(C[p],j,E)}catch(g){return me(g)}}function $(_){try{let g=_.params?.outRef,p=_.body;if(!p)return ne('probeTmpSource requires body with "source-def" and "mock-projections"');let E=p["source-def"],j=p["mock-projections"]??{};return E?i(E,j,g):ne('probeTmpSource body requires "source-def"')}catch(g){return me(g)}}function h(_){try{let g=c(_,"probeSourcePreflight");if("status"in g)return g;let p=r().readTaskExecutorRef();if(!p)return ne("No task-executor registered for this board");try{let E={...g.src,_projections:g.mockProjections},j=t.invokeExecutorSync(p,"probe-source-preflight",[],{timeout:g.src.timeout??t.executorTimeouts?.preflightMs??6e4,input:JSON.stringify(E)}),x=JSON.parse(j.trim());return x.ok?pe({bindTo:g.bindTo,reachable:x.reachable,latencyMs:x.latencyMs,note:x.note}):ne(x.error??"Preflight probe failed")}catch{return ne("Executor does not support probe-source-preflight")}}catch(g){return me(g)}}function v(_){try{let g=c(_,"runSourcePreflight");if("status"in g)return g;try{let p=u(g.src,g.mockProjections);if(g.outRef){let j=ht(g.outRef);t.absoluteBlob.write(j.value,p.result)}let E=p.result;try{E=JSON.parse(p.result)}catch{}return pe({bindTo:p.bindTo,ok:!0,result:E,issues:[]})}catch(p){let E=p instanceof Error?p.message:String(p);return E==="No task-executor registered for this board"?ne(E):pe({bindTo:g.bindTo,ok:!1,result:null,issues:[E]})}}catch(g){return me(g)}}function m(_){try{let g=r().readTaskExecutorRef();if(!g)return ne("No task-executor registered for this board");let p=t.invokeExecutorSync(g,"describe-capabilities",[],{timeout:t.executorTimeouts?.describeMs??1e4});return pe(JSON.parse(p.trim()))}catch(g){return me(g)}}function f(_){try{let g=_.body;if(!g||!Array.isArray(g.ops))return ne("updatesInCardStore requires body.ops array");let p=g.ops,E=n();for(let j of p){let x=j.op,C=j.id;if(!C)return ne('op is missing "id"');if(x==="update"){let q=j["card-content"];if(!q)return ne(`update op for "${C}" is missing "card-content"`);E.writeCard(C,q)}else return ne(`Unknown op type: "${x??"(none)"}"`)}return pe()}catch(g){return me(g)}}function k(_){try{let g=_.body;if(!g||!Array.isArray(g.ids))return ne("readFromCardStore requires body.ids array");let p=g.ids,E=n(),j=p.map(x=>({id:x,"card-content":E.readCard(x)}));return pe({cards:j})}catch(g){return me(g)}}function y(_){try{if(!_.body||typeof _.body!="object"||Array.isArray(_.body))return ne("evalCardCompute requires a JSON object in body");let g=_.body,p=g["card-content"]??g,E=typeof p.id=="string"?p.id:"(unknown)",j=g["mock-fetched-sources"]??{},x=g["mock-requires"]??{},C=p.compute;if(!C||!Array.isArray(C)||C.length===0)return pe({cardId:E,ok:!0,computed_values:{},errors:[]});let q={id:E,card_data:p.card_data??{},requires:x,source_defs:p.source_defs,compute:C},F=qr.runSync(q,{sourcesData:j}),H=F.node.computed_values??{},M=F.errors??[];return pe({cardId:E,ok:M.length===0,computed_values:H,errors:M})}catch(g){return me(g)}}function S(_){try{if(!_.body||typeof _.body!="object"||Array.isArray(_.body))return ne("simulateCardCycle requires a JSON object in body");let g=_.body,p=g["card-content"]??g,E=typeof p.id=="string"?p.id:"(unknown)",j=g["mock-fetched-sources"]??{},x=g["mock-requires"]??{},C=o(E,p),q=C.status==="success"?{isValid:C.data.isValid,issues:C.data.issues}:{isValid:!1,issues:[C.status==="fail"?C.error:"internal error"]},F=p.source_defs??[],H=p.card_data??{},M=[],U=[];if(F.length>0){M=qr.enrichSourcesSync(F,{card_data:H,requires:x});for(let R of M){let K=R.projections,Z=R._projections;if(K&&Z){for(let ie of Object.keys(K))if(Z[ie]===void 0){let re=typeof R.bindTo=="string"?R.bindTo:"(unknown)";U.push({bindTo:re,key:ie,error:`Projection "${ie}" resolved to undefined`})}}}}let J=[],te={...j},W=g["task-executor-ref"],T=(W?.howToRun&&W?.whatToRun?W:void 0)??r().readTaskExecutorRef();for(let R=0;R<M.length;R++){let K=M[R],Z=typeof K.bindTo=="string"?K.bindTo:`source_${R}`;if(!T){J.push({bindTo:Z,skipped:!0,error:"No task executor configured"});continue}try{let ie={...K},re=t.invokeExecutorSync(T,"run-source-preflight",[],{timeout:K.timeout??t.executorTimeouts?.preflightMs??6e4,input:JSON.stringify(ie)}),be=JSON.parse(re.trim());be.ok&&!Object.prototype.hasOwnProperty.call(j,Z)&&Object.prototype.hasOwnProperty.call(be,"resultValue")&&(te[Z]=be.resultValue),J.push({bindTo:Z,reachable:be.reachable,latencyMs:be.latencyMs,error:be.ok?void 0:be.error})}catch{J.push({bindTo:Z,skipped:!0,error:"Executor does not support run-source-preflight"})}}let A=p.compute,V={},P=[];if(A&&Array.isArray(A)&&A.length>0){let R={id:E,card_data:H,requires:x,source_defs:p.source_defs,compute:A},K=qr.runSync(R,{sourcesData:te});V=K.node.computed_values??{},P=K.errors??[]}let O=q.isValid&&U.length===0&&P.length===0&&J.every(R=>R.reachable!==!1);return pe({cardId:E,ok:O,validation:q,source_probes:J,projection_errors:U,fetched_sources:te,computed_values:V,compute_errors:P})}catch(g){return me(g)}}return{validateCard:l,validateCardPreflight:d,probeSource:w,probeTmpSource:$,probeSourcePreflight:h,runSourcePreflight:v,evalCardCompute:y,simulateCardCycle:S,describeTaskExecutorCapabilities:m,updatesInCardStore:f,readFromCardStore:k}}var J_=".board.lock";function W_(e,t){return typeof e=="string"?{cliDir:e,opts:t}:{cliDir:void 0,opts:e}}function X_(e,t){return typeof e=="string"?{cliDir:e,opts:t}:{cliDir:void 0,opts:e}}function Pd(e){if(e)return e;let t=dd(import.meta.url),r=[t,Rt(t,"..","cli","node"),Rt(t,"..","..","cli","node")];for(let a of r)try{return hd(a),a}catch{}throw new Error(`createFsBoardPlatformAdapter: could not resolve a public CLI directory from module dir ${t}`)}function _a(e,t,r){let{cliDir:a,opts:n}=W_(t,r),s=Pd(a),o=e.value,u={meta:"board-live-cards",howToRun:"local-node",whatToRun:!n?.suppressSpawn&&hd(s)?ze({kind:"yaml-flow-cli",value:"board-live-cards-cli.js"}):"",...n?.notifyChannel?{extra:{notifyChannel:n.notifyChannel}}:{}};return{kvStorage:i=>Ml(Rt(o,`.${i}`)),blobStorage:i=>va(i?Rt(o,i):o),scratchStorage:()=>Lo(Rt(o,".tmp")),scratchStorageForRef:i=>Lo(ht(i).value),archiveFactory:()=>Ho(Rt(o,"archive")),archiveFactoryForRef:i=>Ho(ht(i).value),journalAdapter:()=>D0(o),lock:M0(Rt(o,J_)),selfRef:u,async dispatchExecution(i,c){if(n?.suppressSpawn)return{dispatched:!1};try{let l=c.source_def?.bindTo??Il().slice(0,8),d=Lo(Rt(o,".tmp")),w=d.create(JSON.stringify(c,null,2),`exec-in-${l}`,".json"),$=d.getUniqueKey(`exec-out-${l}`,".json"),h=d.getUniqueKey(`exec-err-${l}`,".txt"),v=ze(d.keyRef(w)),m=ze(d.keyRef($)),f=ze(d.keyRef(h));return O0(i,{subcommand:"run-source-fetch",inRef:v,outRef:m,errRef:f},s),{dispatched:!0}}catch(l){let d=l instanceof Error?l.message:String(l);try{let w=Ho(Rt(o,"archive")),$=new Date().toISOString().replace(/[:.]/g,"-"),h=c.source_def?.bindTo??"unknown";w.blob("exec-failures").write(`${$}-${h}.json`,JSON.stringify({error:d,args:c,ref:i,at:new Date().toISOString()},null,2))}catch{}return{dispatched:!1,error:d}}},resolveBlob(i){let c=u0(i.value)?yd().read(i.value):va(o).read(i.value);if(c===null)throw new Error(`resolveBlob: blob not found: ::${i.kind}::${i.value}`);return c},hashFn:q0,genId:()=>c0(`${Date.now()}-${Math.random()}`).slice(0,32),kvStorageForRef:i=>Ml(ht(i).value),requestProcessAccumulated(){n?.suppressSpawn||p0(s,e,n?.notifyChannel)},publishBoardChangeNotifications(i){if(!n?.notifyChannel||i.length===0)return;let c=i.map(l=>({id:Il(),ts:new Date().toISOString(),boardRef:ze(e),notification:l}));m0(n.notifyChannel,c,n.onWarn)},onWarn:n?.onWarn}}function cr(e,t,r){let{cliDir:a,opts:n}=X_(t,r),s=Pd(a),o=_a(e,s,n),u=y0();return{...o,invokeExecutorSync(i,c,l,d){let{command:w,baseArgs:$}=P0(i,s),h=i.extra?["--extra",Buffer.from(JSON.stringify(i.extra)).toString("base64")]:[];return u.executeSync(w,[...$,c,...l,...h],{timeout:d?.timeout??3e4,encoding:"utf-8",input:d?.input})},validateSchema(i){let c=J0(i);return{ok:c.errors.length===0,errors:c.errors}},absoluteBlob:yd()}}function Yl(e){try{let t=JSON.parse(Buffer.from(e,"base64url").toString());return typeof t.br=="string"?t.br:null}catch{return null}}var pt=dd(import.meta.url);function Ae(e,t,r){let a=e.indexOf(t),n=a!==-1?e[a+1]:void 0;if(!n)throw new Error(`Missing ${t}
28
+ `,"utf-8")},generateId(){return et()}}}function M0(e){return{tryAcquire(){try{if(!D.existsSync(e)){D.mkdirSync(Q.dirname(e),{recursive:!0});try{D.writeFileSync(e,"{}",{flag:"wx"})}catch{}}return(0,td.lockSync)(e,{retries:0})}catch{return null}}}}var F0={$schema:"http://json-schema.org/draft-07/schema#",$id:"https://nsreehari.github.io/boards/live-cards.schema.json",definitions:{bind_ref:{description:"A card data path reference, e.g. 'card_data.raw_quotes' or 'requires.upstream'",type:"string",pattern:"^(card_data|requires|fetched_sources|computed_values)(\\.|$)"},bind_or_literal:{description:"A literal value or a bind reference object",oneOf:[{type:"string"},{type:"number"},{type:"boolean"},{type:"array"},{type:"object",properties:{bind:{$ref:"#/definitions/bind_ref"}},required:["bind"]}]},compute_expr:{description:"A declarative JSON compute expression",type:"object",required:["fn"],properties:{fn:{type:"string",description:"Function name from the built-in vocabulary",enum:["sum","avg","min","max","count","first","last","add","sub","mul","div","round","abs","mod","gt","gte","lt","lte","eq","neq","if","and","or","not","concat","upper","lower","template","filter","pluck","map","sort","slice","flat","unique","group","get","default","now","diff_days","format_date"]},input:{description:"card_data.path, literal, array of inputs, or nested compute_expr",oneOf:[{type:"string"},{type:"number"},{type:"boolean"},{type:"array"},{$ref:"#/definitions/compute_expr"}]},field:{type:"string",description:"For pluck/sum/group \u2014 the object key to extract"},where:{$ref:"#/definitions/compute_expr",description:"For filter \u2014 predicate expression ($ = current item)"},cond:{$ref:"#/definitions/compute_expr",description:"For if \u2014 condition expression"},then:{description:"For if \u2014 value when cond is truthy"},else:{description:"For if \u2014 value when cond is falsy"},format:{type:"string",description:"For format_date \u2014 date format string"}}},meta:{type:"object",properties:{title:{type:"string"},tags:{type:"array",items:{type:"string"}}}},requires:{type:"array",items:{type:"string"},description:"IDs of upstream nodes this node depends on"},provides:{type:"array",items:{type:"object",required:["bindTo","ref"],properties:{bindTo:{type:"string",description:"Token name published downstream"},ref:{type:"string",description:"Path to read value from (card_data.*, requires.*, fetched_sources.*, computed_values.*)"}}},description:"Explicit bindings exposing computed or card_data values downstream as named tokens"},compute_step:{description:"A single ordered compute step: reads card_data.*/requires.*/computed_values.*, writes to computed_values[bindTo]",type:"object",required:["bindTo","expr"],properties:{bindTo:{type:"string",description:"Key in computed_values to write result"},expr:{type:"string",description:"JSONata expression evaluated against { card_data, requires, fetched_sources, computed_values }"}}},source_def:{description:"One source entry. The engine requires 'bindTo' (compute namespace key) and 'outputFile' (delivery signal path). bindTo and outputFile must be unique across all source_defs in a card. Every other property is yours \u2014 add whatever your task-executor needs: kind, url, headers, mailbox, channel, model, query, etc. The full object is passed verbatim as the --in JSON to the executor.",type:"object",required:["bindTo","outputFile"],additionalProperties:!0,properties:{bindTo:{type:"string",description:"Key under fetched_sources.* available in compute expressions"},outputFile:{type:"string",description:"Board-relative path the executor writes its JSON result to. Presence of this file signals delivery."},projections:{type:"object",description:"Named data projections from card_data or requires, evaluated before the executor is called. Each key is a ref name; each value is a JSONata expression rooted at card_data or requires. The resolved values are passed to the executor as _projections. fetched_sources, computed_values, and source_defs are not accessible here \u2014 sources run before those exist.",additionalProperties:{type:"string"}},optionalForCompletionGating:{type:"boolean",default:!1,description:"When true this source does not gate card completion. Default false when absent, so source_defs are completion-gating by default."},timeout:{type:"integer",minimum:0,default:12e4,description:"Executor/script timeout in ms. Default: 120 000 (2 min)."},script:{type:"string",description:"Legacy direct-run: shell command executed when no .task-executor is registered. stdout is captured as the result."}}},render_element:{type:"object",required:["kind"],properties:{id:{type:"string",description:"Optional element ID for targeted updates"},kind:{enum:["metric","table","editable-table","chart","form","filter","list","notes","todo","alert","narrative","badge","text","markdown","ref","custom","actions"]},label:{type:"string",description:"Heading above this element"},className:{type:"string",description:"Bootstrap grid class, e.g. 'col-12 col-md-6'"},visible:{type:"string",description:"card_data/requires/fetched_sources/computed_values path \u2014 element shown only if truthy"},data:{type:"object",properties:{bind:{$ref:"#/definitions/bind_ref",description:"card_data/requires/fetched_sources/computed_values path to read data from"},writeTo:{$ref:"#/definitions/bind_ref",description:"card_data path for user input (form, filter, todo, notes)"},columns:{type:"array",items:{type:"string"},description:"table: visible columns"},maxRows:{type:"integer",description:"table/list: max rows to display"},sortable:{type:"boolean",default:!0,description:"table: enable click-to-sort"},placeholder:{type:"string",description:"Empty-state message"},chartType:{enum:["bar","line","pie","doughnut"]},chartOptions:{type:"object",description:"Chart.js options passthrough"},fields:{type:"object",description:"JSON Schema for form/filter fields"},thresholds:{type:"object",properties:{green:{type:"string"},amber:{type:"string"}}},colorMap:{type:"object",description:"badge: value \u2192 Bootstrap color"},style:{enum:["heading","muted","default"],description:"text: display style"},upload:{type:"boolean",default:!0,description:"file-upload: show drop zone (false = read-only file list)"},accept:{type:"array",items:{type:"string"},description:"file-upload: allowed extensions"},multiple:{type:"boolean",default:!0,description:"file-upload: allow multiple files"},fileAttach:{type:"boolean",default:!1,description:"chat: enable inline file attachments"},fileAccept:{type:"array",items:{type:"string"},description:"chat: allowed attachment extensions"},buttons:{type:"array",description:"actions: button definitions",items:{type:"object",required:["id","label"],properties:{id:{type:"string"},label:{type:"string"},style:{type:"string",description:"Bootstrap button variant, e.g. 'success', 'outline-danger'"},size:{type:"string",default:"sm"},disabled:{oneOf:[{type:"boolean"},{type:"string",description:"card_data/requires/fetched_sources/computed_values path \u2014 truthy = disabled"}]}}}}}}}},view:{type:"object",required:["elements"],properties:{elements:{type:"array",minItems:1,items:{$ref:"#/definitions/render_element"}},layout:{type:"object",properties:{board:{type:"object",properties:{col:{type:"integer",minimum:1,maximum:12},order:{type:"integer"}}},canvas:{type:"object",properties:{x:{type:"number"},y:{type:"number"},w:{type:"number"},h:{type:"number"}}}}},features:{type:"object",properties:{chat:{type:"boolean",default:!1},notes:{type:"boolean",default:!1},refresh:{type:"boolean",default:!0}}}}}},title:"LiveCard",description:"A unified card node. Behavior depends on which sections are present (source_defs, compute, view, etc.)",type:"object",required:["id"],additionalProperties:!1,properties:{id:{type:"string"},requires:{$ref:"#/definitions/requires"},provides:{$ref:"#/definitions/provides"},meta:{$ref:"#/definitions/meta"},view:{$ref:"#/definitions/view"},card_data:{type:"object",description:"Authored card data and runtime metadata. Includes uploaded-file metadata maintained by host handlers and inference evaluation results.",properties:{files:{type:"array",description:"Optional uploaded-file metadata maintained by host handlers. Stored name is normalized and serial-prefixed (for example 001-my_file.pdf).",items:{type:"object",required:["name","stored_name"],properties:{name:{type:"string",minLength:1},stored_name:{type:"string",minLength:5,maxLength:32,pattern:"^[0-9]{3,}-[a-z0-9._-]+$"},size:{oneOf:[{type:"integer",minimum:0},{type:"null"}]},mime_type:{type:"string"},path:{type:"string",pattern:"^[^\\s]+/files/[0-9]{3,}-[a-z0-9._-]+$"},uploaded_at:{type:"string",format:"date-time"},chat:{type:"boolean",description:"Whether this file entry is associated with a chat interaction"}},additionalProperties:!1}}},additionalProperties:!0},source_defs:{type:"array",description:"Source entries. Each entry is passed verbatim to the board's .task-executor (registered via init --task-executor) as the --in JSON file. The executor fetches/generates the data and writes JSON to --out. If no executor is registered, the built-in executor runs the entry's 'cli' command directly. Sources gate completion by default. Set optionalForCompletionGating: true for enrichment-only source_defs that should not block task-completed.",items:{$ref:"#/definitions/source_def"}},compute:{type:"array",description:"Ordered array of compute steps. Each reads card_data.*/requires.*/fetched_sources.*/computed_values.* and writes to ephemeral computed_values[bindTo].",items:{$ref:"#/definitions/compute_step"}}}},V0=dv(n0()),z0=On(import.meta.url),U0=z0("./jsonata-sync.cjs"),wn=null,Fl=/\b(card_data|requires|fetched_sources|computed_values|source_defs)\b/g,L0=/^\s*(card_data|requires|fetched_sources|computed_values|source_defs)(\.|$)/;function H0(e){let t=new Set,r;for(Fl.lastIndex=0;(r=Fl.exec(e))!==null;)t.add(r[1]);return t}function gd(e){let t=L0.exec(e);return t?t[1]:null}function Vl(e,t,r,a){try{U0(e)}catch(s){let o=s instanceof Error?s.message:String(s);a.push(`${t}: invalid JSONata expression (${o})`);return}let n=H0(e);for(let s of n)r.has(s)||a.push(`${t}: disallowed namespace "${s}" in expression`)}function Yo(e,t,r){if(Array.isArray(e)){e.forEach((n,s)=>{Yo(n,`${t}/${s}`,r)});return}if(typeof e=="string"){let n=gd(e);if(!n)return;new Set(["card_data","requires","computed_values"]).has(n)||r.push(`${t}: disallowed namespace "${n}" in view reference`);return}if(!e||typeof e!="object")return;let a=e;for(let[n,s]of Object.entries(a))Yo(s,`${t}/${n}`,r)}function K0(){if(wn)return wn;let e=new V0.default({allErrors:!0});return(0,rd.default)(e),wn=e.compile(F0),wn}function G0(e){let t=K0(),r=t(e),a=(t.errors??[]).map(n=>`${n.instancePath||"/"}: ${n.message??"unknown error"}`);if(e&&typeof e=="object"&&!Array.isArray(e)){let n=e.source_defs;if(Array.isArray(n)){let s=new Set,o=new Set;n.forEach((u,i)=>{if(!u||typeof u!="object"||Array.isArray(u))return;let c=u;typeof c.bindTo=="string"&&c.bindTo&&(s.has(c.bindTo)&&a.push(`/source_defs/${i}/bindTo: bindTo "${c.bindTo}" must be unique across all source_defs`),s.add(c.bindTo)),typeof c.outputFile=="string"&&c.outputFile&&(o.has(c.outputFile)&&a.push(`/source_defs/${i}/outputFile: outputFile "${c.outputFile}" must be unique across all source_defs`),o.add(c.outputFile))})}}return!r||a.length>0?{ok:!1,errors:a}:{ok:!0,errors:[]}}function B0(e){let t=[];if(!e||typeof e!="object"||Array.isArray(e))return{ok:!0,errors:[]};let r=e,a=r.compute;Array.isArray(a)&&a.forEach((c,l)=>{if(!c||typeof c!="object"||Array.isArray(c))return;let d=c.expr;typeof d!="string"||d.trim().length===0||Vl(d,`/compute/${l}/expr`,new Set(["card_data","requires","fetched_sources","computed_values"]),t)});let n=new Set(["card_data","requires","fetched_sources","computed_values"]),s=r.provides;Array.isArray(s)&&s.forEach((c,l)=>{if(!c||typeof c!="object"||Array.isArray(c))return;let d=c.ref;if(typeof d!="string"||d.trim().length===0)return;let w=gd(d);w===null?t.push(`/provides/${l}/ref: path "${d}" must start with a valid namespace (${[...n].join(", ")})`):n.has(w)||t.push(`/provides/${l}/ref: disallowed namespace "${w}" in path "${d}" (valid: ${[...n].join(", ")})`)});let o=r.view;o&&typeof o=="object"&&!Array.isArray(o)&&Yo(o,"/view",t);let u=new Set(["card_data","requires"]),i=r.source_defs;return Array.isArray(i)&&i.forEach((c,l)=>{if(!c||typeof c!="object"||Array.isArray(c))return;let d=c.projections;if(!(!d||typeof d!="object"||Array.isArray(d)))for(let[w,$]of Object.entries(d))typeof $!="string"||$.trim().length===0||Vl($,`/source_defs/${l}/projections/${w}`,u,t)}),{ok:t.length===0,errors:t}}function J0(e){let t=G0(e);if(!t.ok)return t;let r=B0(e);return r.ok?{ok:!0,errors:[]}:{ok:!1,errors:r.errors}}var Ar={RUNNING:"running",COMPLETED:"completed",FAILED:"failed",INACTIVATED:"inactivated"};function bt(e){return e?Array.isArray(e.provides)?e.provides:[]:[]}function $a(e){return e?Array.isArray(e.requires)?e.requires:[]:[]}function W0(e){return e.tasks??{}}function zl(e){return e?e.status===Ar.FAILED||e.status===Ar.INACTIVATED:!1}function X0(e,t){return e.refreshStrategy??t?.refreshStrategy??"data-changed"}function Y0(e){return e.maxExecutions}function Q0(e,t){let r=new Set;for(let[a,n]of Object.entries(t))if(n.status===Ar.COMPLETED){let s=e.tasks[a];s&&bt(s).forEach(o=>r.add(o))}return Array.from(r)}function Z0(e,t){let r={};return e.forEach(a=>{let n=t[a];n&&bt(n).forEach(s=>{r[s]||(r[s]=[]),r[s].push(a)})}),r}function e_(e,t,r){let a=e.tasks[t]??In(),n={};if(r){let o=r.tasks[t],u=$a(o);for(let i of u)for(let[c,l]of Object.entries(r.tasks))if(bt(l).includes(i)){let d=e.tasks[c];d?.lastDataHash&&(n[i]=d.lastDataHash);break}}let s={...a,status:"running",startedAt:new Date().toISOString(),lastUpdated:new Date().toISOString(),progress:0,error:void 0,startConsumedHashes:n};return{...e,tasks:{...e.tasks,[t]:s},lastUpdated:new Date().toISOString()}}function t_(e,t,r,a,n,s){let o=e.tasks[r]??In(),u=t.tasks[r];if(!u)throw new Error(`Task "${r}" not found in graph`);let i;a&&u.on&&u.on[a]?i=u.on[a]:i=bt(u);let c=o.startConsumedHashes?{...o.startConsumedHashes}:{...o.lastConsumedHashes};if(!o.startConsumedHashes){let w=u.requires??[];for(let $ of w)for(let[h,v]of Object.entries(t.tasks))if(bt(v).includes($)){let m=e.tasks[h];m?.lastDataHash&&(c[$]=m.lastDataHash);break}}let l={...o,status:"completed",completedAt:new Date().toISOString(),lastUpdated:new Date().toISOString(),executionCount:o.executionCount+1,lastEpoch:o.executionCount+1,lastDataHash:n,data:s,lastConsumedHashes:c,error:void 0},d=[...new Set([...e.availableOutputs,...i])];return{...e,tasks:{...e.tasks,[r]:l},availableOutputs:d,lastUpdated:new Date().toISOString()}}function r_(e,t,r,a){let n=e.tasks[r]??In(),s=t.tasks[r];if(s?.retry){let i=n.retryCount+1;if(i<=s.retry.max_attempts){let c={...n,status:"not-started",retryCount:i,lastUpdated:new Date().toISOString(),error:a};return{...e,tasks:{...e.tasks,[r]:c},lastUpdated:new Date().toISOString()}}}let o={...n,status:"failed",failedAt:new Date().toISOString(),lastUpdated:new Date().toISOString(),error:a,executionCount:n.executionCount+1},u=e.availableOutputs;if(s?.on_failure&&s.on_failure.length>0&&(u=[...new Set([...e.availableOutputs,...s.on_failure])]),s?.circuit_breaker&&o.executionCount>=s.circuit_breaker.max_executions){let i=s.circuit_breaker.on_break;u=[...new Set([...u,...i])]}return{...e,tasks:{...e.tasks,[r]:o},availableOutputs:u,lastUpdated:new Date().toISOString()}}function a_(e,t,r,a){let n=e.tasks[t]??In(),s={...n,progress:typeof a=="number"?a:n.progress,messages:[...n.messages??[],...r?[{message:r,timestamp:new Date().toISOString(),status:n.status}]:[]],lastUpdated:new Date().toISOString()};return{...e,tasks:{...e.tasks,[t]:s},lastUpdated:new Date().toISOString()}}function n_(e,t){let r=e.tasks[t];if(!r)return e;let a={...r,status:"not-started",startedAt:void 0,completedAt:void 0,failedAt:void 0,error:void 0,data:void 0,progress:null,lastUpdated:new Date().toISOString()};return{...e,tasks:{...e.tasks,[t]:a},lastUpdated:new Date().toISOString()}}function In(){return{status:"not-started",executionCount:0,retryCount:0,lastEpoch:0,messages:[],progress:null}}function vd(e,t){let r=`live-${Date.now()}`,a={};for(let s of Object.keys(e.tasks))a[s]=_d();let n={status:"running",tasks:a,availableOutputs:[],stuckDetection:{is_stuck:!1,stuck_description:null,outputs_unresolvable:[],tasks_blocked:[]},lastUpdated:new Date().toISOString(),executionId:r,executionConfig:{executionMode:e.settings.execution_mode??"eligibility-mode",conflictStrategy:e.settings.conflict_strategy??"alphabetical",completionStrategy:e.settings.completion}};return{config:e,state:n}}function s_(e,t){let{config:r,state:a}=e;if("executionId"in t&&t.executionId&&t.executionId!==a.executionId)return e;switch(t.type){case"task-started":return{config:r,state:e_(a,t.taskName,r)};case"task-completed":return{config:r,state:t_(a,r,t.taskName,t.result,t.dataHash,t.data)};case"task-failed":return{config:r,state:r_(a,r,t.taskName,t.error)};case"task-progress":return{config:r,state:a_(a,t.taskName,t.message,t.progress)};case"task-restart":return{config:r,state:n_(a,t.taskName)};case"inject-tokens":return{config:r,state:{...a,availableOutputs:[...new Set([...a.availableOutputs,...t.tokens])],lastUpdated:new Date().toISOString()}};case"agent-action":return{config:r,state:p_(a,t.action)};case"task-upsert":return i_(e,t.taskName,t.taskConfig);case"task-removal":return u_(e,t.taskName);case"node-requires-add":return c_(e,t.nodeName,t.tokens);case"node-requires-remove":return l_(e,t.nodeName,t.tokens);case"node-provides-add":return d_(e,t.nodeName,t.tokens);case"node-provides-remove":return f_(e,t.nodeName,t.tokens);default:return e}}function o_(e,t){return t.reduce((r,a)=>s_(r,a),e)}function i_(e,t,r){let a=!!e.config.tasks[t];return{config:{...e.config,tasks:{...e.config.tasks,[t]:r}},state:{...e.state,tasks:{...e.state.tasks,[t]:a?e.state.tasks[t]:_d()},lastUpdated:new Date().toISOString()}}}function u_(e,t){if(!e.config.tasks[t])return e;let{[t]:r,...a}=e.config.tasks,{[t]:n,...s}=e.state.tasks;return{config:{...e.config,tasks:a},state:{...e.state,tasks:s,lastUpdated:new Date().toISOString()}}}function c_(e,t,r){let a=e.config.tasks[t];if(!a)return e;let n=$a(a),s=r.filter(o=>!n.includes(o));return s.length===0?e:{config:{...e.config,tasks:{...e.config.tasks,[t]:{...a,requires:[...n,...s]}}},state:e.state}}function l_(e,t,r){let a=e.config.tasks[t];if(!a)return e;let n=$a(a),s=n.filter(o=>!r.includes(o));return s.length===n.length?e:{config:{...e.config,tasks:{...e.config.tasks,[t]:{...a,requires:s}}},state:e.state}}function d_(e,t,r){let a=e.config.tasks[t];if(!a)return e;let n=bt(a),s=r.filter(o=>!n.includes(o));return s.length===0?e:{config:{...e.config,tasks:{...e.config.tasks,[t]:{...a,provides:[...n,...s]}}},state:e.state}}function f_(e,t,r){let a=e.config.tasks[t];if(!a)return e;let n=bt(a),s=n.filter(o=>!r.includes(o));return s.length===n.length?e:{config:{...e.config,tasks:{...e.config.tasks,[t]:{...a,provides:s}}},state:e.state}}function Qo(e){return{version:1,config:e.config,state:e.state,snapshotAt:new Date().toISOString()}}function Ko(e){if(!e||typeof e!="object")throw new Error("Invalid snapshot: expected an object");let t=e;if(!t.config||typeof t.config!="object")throw new Error('Invalid snapshot: missing or invalid "config"');if(!t.state||typeof t.state!="object")throw new Error('Invalid snapshot: missing or invalid "state"');let r=t.config,a=t.state;if(!r.settings||typeof r.settings!="object")throw new Error("Invalid snapshot: config.settings missing");if(!r.tasks||typeof r.tasks!="object")throw new Error("Invalid snapshot: config.tasks missing");if(!a.tasks||typeof a.tasks!="object")throw new Error("Invalid snapshot: state.tasks missing");if(!Array.isArray(a.availableOutputs))throw new Error("Invalid snapshot: state.availableOutputs must be an array");return{config:r,state:a}}function _d(){return{status:"not-started",executionCount:0,retryCount:0,lastEpoch:0,messages:[],progress:null}}function p_(e,t){let r=new Date().toISOString();switch(t){case"stop":return{...e,status:"stopped",lastUpdated:r};case"pause":return{...e,status:"paused",lastUpdated:r};case"resume":return{...e,status:"running",lastUpdated:r};default:return e}}function Zo(e){let{config:t,state:r}=e,a=W0(t);if(Object.keys(a).length===0)return{eligible:[],pending:[],unresolved:[],blocked:[],conflicts:{}};let n=h_(a),s=Q0(t,r.tasks),o=new Set([...s,...r.availableOutputs]),u=[],i=[],c=[],l=[];for(let[w,$]of Object.entries(a)){let h=r.tasks[w],v=X0($,t.settings),m=v!=="once";if(h?.status===Ar.RUNNING||zl(h))continue;let f=Y0($);if(f!==void 0&&h&&h.executionCount>=f||$.circuit_breaker&&h&&h.executionCount>=$.circuit_breaker.max_executions||!m&&h?.status===Ar.COMPLETED)continue;if(m&&h?.status===Ar.COMPLETED){let g=$a($),p=!1;switch(v){case"data-changed":{g.length>0&&g.some(E=>{for(let[j,x]of Object.entries(a))if(bt(x).includes(E)){let C=r.tasks[j];if(!C)continue;let q=h.lastConsumedHashes?.[E];return C.lastDataHash==null?C.executionCount>h.lastEpoch:C.lastDataHash!==q}return!1})||(p=!0);break}case"epoch-changed":{g.length>0&&g.some(E=>{for(let[j,x]of Object.entries(a))if(bt(x).includes(E)){let C=r.tasks[j];if(C&&C.executionCount>h.lastEpoch)return!0}return!1})||(p=!0);break}case"time-based":{let E=$.refreshInterval??0;if(E<=0){p=!0;break}let j=h.completedAt;if(!j){p=!0;break}(Date.now()-Date.parse(j))/1e3<E&&(p=!0);break}case"manual":p=!0;break}if(p)continue}let k=$a($);if(k.length===0){u.push(w);continue}let y=[],S=[],_=[];for(let g of k){if(o.has(g))continue;let p=n[g]||[];p.length===0?y.push(g):p.every(E=>zl(r.tasks[E]))?_.push({token:g,failedProducer:p[0]}):S.push(g)}y.length>0?c.push({taskName:w,missingTokens:y}):_.length>0?l.push({taskName:w,failedTokens:_.map(g=>g.token),failedProducers:[...new Set(_.map(g=>g.failedProducer))]}):S.length>0?i.push({taskName:w,waitingOn:S}):u.push(w)}let d={};if(u.length>1){let w=Z0(u,a);for(let[$,h]of Object.entries(w))h.length>1&&(d[$]=h)}return{eligible:u,pending:i,unresolved:c,blocked:l,conflicts:d}}function h_(e){let t={};for(let[r,a]of Object.entries(e)){for(let n of bt(a))t[n]||(t[n]=[]),t[n].push(r);if(a.on)for(let n of Object.values(a.on))for(let s of n)t[s]||(t[s]=[]),t[s].includes(r)||t[s].push(r);if(a.on_failure)for(let n of a.on_failure)t[n]||(t[n]=[]),t[n].includes(r)||t[n].push(r)}return t}var Ul=class{buffer=[];append(e){this.buffer.push(e)}drain(){let e=this.buffer;return this.buffer=[],e}get size(){return this.buffer.length}};function Go(e){let t=ei(e);return m_(t)}function ei(e){if(e==null||typeof e!="object")return JSON.stringify(e);if(Array.isArray(e))return"["+e.map(ei).join(",")+"]";let t=e;return"{"+Object.keys(t).sort().map(r=>JSON.stringify(r)+":"+ei(t[r])).join(",")+"}"}function m_(e){let t=0xcbf29ce484222325n,r=0x100000001b3n,a=0xffffffffffffffffn;for(let n=0;n<e.length;n++)t^=BigInt(e.charCodeAt(n)),t=t*r&a;return t.toString(16).padStart(16,"0")}function y_(e){if(typeof Buffer<"u")return Buffer.from(e,"utf8").toString("base64url");if(typeof btoa=="function"){let t=new TextEncoder().encode(e),r="";for(let a of t)r+=String.fromCharCode(a);return btoa(r).replace(/\+/g,"-").replace(/\//g,"_").replace(/=+$/g,"")}throw new Error("No base64 encoder available in this runtime")}function g_(e){if(typeof Buffer<"u")return Buffer.from(e,"base64url").toString("utf8");if(typeof atob=="function"){let t=e.replace(/-/g,"+").replace(/_/g,"/"),r=t+"=".repeat((4-t.length%4)%4),a=atob(r),n=new Uint8Array(a.length);for(let s=0;s<a.length;s++)n[s]=a.charCodeAt(s);return new TextDecoder().decode(n)}throw new Error("No base64 decoder available in this runtime")}function Ll(e){let t=JSON.stringify({t:e,n:Date.now().toString(36)+Math.random().toString(36).slice(2,6)});return y_(t)}function v_(e){try{let t=JSON.parse(g_(e));return typeof t?.t=="string"?{taskName:t.t}:null}catch{return null}}function __(e,t,r){let{handlers:a,onNodeRemoved:n,onDrain:s}=t,o=new Ul,u="state"in e&&"config"in e?e:vd(e),i=!1,c=new Set,l=new Map(Object.entries(a)),d=new Ul,w=!1,$=!1;function h(){if(!i){if(w){$=!0;return}w=!0;try{do $=!1,v();while($)}finally{w=!1}}}function v(){let y=d.drain(),S=o.drain(),_=[...y,...S];if(_.length>0&&(u=o_(u,_),n)){for(let p of _)if(p.type==="task-removal")try{n(p.taskName)}catch(E){console.warn("[reactive] onNodeRemoved failed:",E instanceof Error?E.message:String(E))}}let g=Zo(u);_.length>0&&s?.(_,u,g);for(let p of g.eligible)k(p);for(let p of _)if(p.type==="task-progress"){let{taskName:E,update:j}=p;if(!u.config.tasks[E])continue;let x=u.state.tasks[E];if(!x||x.status!=="running")continue;let C=Ll(E),q=f(E,C,j).catch(F=>{i||(d.append({type:"task-failed",taskName:E,error:F.message??String(F),timestamp:new Date().toISOString()}),h())}).finally(()=>{c.delete(q)});c.add(q)}}function m(y){let S=u.config.tasks[y].requires??[],_=new Map;for(let[p,E]of Object.entries(u.config.tasks))for(let j of E.provides??[])_.set(j,p);let g={};for(let p of S){let E=_.get(p);E?g[p]=u.state.tasks[E]?.data:g[p]=void 0}return g}async function f(y,S,_){let g=u.config.tasks[y],p=g.taskHandlers??[],E=m(y);for(let j of p){let x=l.get(j);if(!x)throw new Error(`Handler '${j}' not found in registry (task '${y}')`);let C={nodeId:y,state:E,taskState:u.state.tasks[y],config:g,callbackToken:S,update:_};if(await x(C)==="task-initiate-failure")throw new Error(`Handler '${j}' returned task-initiate-failure (task '${y}')`)}}function k(y){let S=u.config.tasks[y]?.taskHandlers;if(!S||S.length===0)return;d.append({type:"task-started",taskName:y,timestamp:new Date().toISOString()}),h();let _=Ll(y),g=f(y,_).catch(p=>{i||(d.append({type:"task-failed",taskName:y,error:p.message??String(p),timestamp:new Date().toISOString()}),h())}).finally(()=>{c.delete(g)});c.add(g)}return{push(y){i||(y.type==="task-completed"&&y.data&&!y.dataHash&&(y={...y,dataHash:Go(y.data)}),o.append(y),h())},pushAll(y){if(!i){for(let S of y)S.type==="task-completed"&&S.data&&!S.dataHash?o.append({...S,dataHash:Go(S.data)}):o.append(S);h()}},resolveCallback(y,S,_){if(i)return;let g=v_(y);if(!g)return;let{taskName:p}=g;if(u.config.tasks[p]){if(_&&_.length>0)o.append({type:"task-failed",taskName:p,error:_.join("; "),timestamp:new Date().toISOString()});else{let E=S&&Object.keys(S).length>0?Go(S):void 0;o.append({type:"task-completed",taskName:p,data:S,dataHash:E,timestamp:new Date().toISOString()})}h()}},addNode(y,S){i||(o.append({type:"task-upsert",taskName:y,taskConfig:S,timestamp:new Date().toISOString()}),h())},removeNode(y){i||(o.append({type:"task-removal",taskName:y,timestamp:new Date().toISOString()}),h())},addRequires(y,S){i||(o.append({type:"node-requires-add",nodeName:y,tokens:S,timestamp:new Date().toISOString()}),h())},removeRequires(y,S){i||(o.append({type:"node-requires-remove",nodeName:y,tokens:S,timestamp:new Date().toISOString()}),h())},addProvides(y,S){i||(o.append({type:"node-provides-add",nodeName:y,tokens:S,timestamp:new Date().toISOString()}),h())},removeProvides(y,S){i||(o.append({type:"node-provides-remove",nodeName:y,tokens:S,timestamp:new Date().toISOString()}),h())},registerHandler(y,S){l.set(y,S)},unregisterHandler(y){l.delete(y)},retrigger(y){i||u.config.tasks[y]&&(o.append({type:"task-restart",taskName:y,timestamp:new Date().toISOString()}),h())},retriggerAll(y){if(!i){for(let S of y)u.config.tasks[S]&&o.append({type:"task-restart",taskName:S,timestamp:new Date().toISOString()});h()}},snapshot(){return Qo(u)},getState(){return u},getSchedule(){return Zo(u)},async waitForHandlers(){c.size>0&&await Promise.allSettled([...c])},async dispose(y){y?.wait&&c.size>0&&await Promise.allSettled([...c]),i=!0}}}var $_=On(import.meta.url),Cn=$_("./jsonata-sync.cjs"),$d=Cn;function Hl(e,t){if(!t||!e)return;let r=t.split("."),a=e;for(let n=0;n<r.length;n++){if(a==null)return;a=a[r[n]]}return a}function wd(e,t,r){let a=t.split("."),n=e;for(let s=0;s<a.length-1;s++)(n[a[s]]==null||typeof n[a[s]]!="object")&&(n[a[s]]={}),n=n[a[s]];n[a[a.length-1]]=r}async function w_(e,t){if(!e?.compute?.length)return e;e.card_data||(e.card_data={}),e.computed_values={},e._sourcesData=t?.sourcesData??{};let r=e.requires??{},a={card_data:e.card_data,requires:r,expects_data:r,fetched_sources:e._sourcesData,data:e.computed_values,computed_values:e.computed_values};for(let n of e.compute)try{let s=await Cn(n.expr).evaluate(a);wd(e.computed_values,n.bindTo,s),a.computed_values=e.computed_values}catch{}return e}function b_(e,t){if(!e?.compute?.length)return{ok:!0,node:e};e.card_data||(e.card_data={}),e.computed_values={},e._sourcesData=t?.sourcesData??{};let r=e.requires??{},a={card_data:e.card_data,requires:r,expects_data:r,fetched_sources:e._sourcesData,data:e.computed_values,computed_values:e.computed_values},n=[];for(let s of e.compute)try{let o=$d(s.expr).evaluate(a);wd(e.computed_values,s.bindTo,o),a.computed_values=e.computed_values}catch(o){let u=o instanceof Error?o.message:String(o);n.push({bindTo:s.bindTo,error:u})}return n.length>0?{ok:!0,node:e,errors:n}:{ok:!0,node:e}}async function S_(e,t,r){let a={...r??{},card_data:t.card_data??{},requires:t.requires??{},fetched_sources:t._sourcesData??{},computed_values:t.computed_values??{}};return Cn(e).evaluate(a)}function k_(e,t){return t.startsWith("fetched_sources.")?Hl(e._sourcesData??{},t.slice(16)):Hl(e,t)}var Kl=new Set(["metric","table","editable-table","chart","form","filter","list","notes","todo","alert","narrative","badge","text","markdown","ref","custom","actions"]),E_=new Set(["id","meta","requires","provides","view","card_data","compute","source_defs"]);function P_(e){let t=[];if(!e||typeof e!="object"||Array.isArray(e))return{ok:!1,errors:["Node must be a non-null object"]};let r=e;(typeof r.id!="string"||!r.id)&&t.push("id: required, must be a non-empty string");for(let a of Object.keys(r))E_.has(a)||t.push(`Unknown top-level key: "${a}"`);if((r.card_data==null||typeof r.card_data!="object"||Array.isArray(r.card_data))&&t.push("card_data: required, must be an object"),r.meta!=null)if(typeof r.meta!="object"||Array.isArray(r.meta))t.push("meta: must be an object");else{let a=r.meta;a.title!=null&&typeof a.title!="string"&&t.push("meta.title: must be a string"),a.tags!=null&&!Array.isArray(a.tags)&&t.push("meta.tags: must be an array")}if(r.requires!=null&&!Array.isArray(r.requires)&&t.push("requires: must be an array of strings"),r.provides!=null&&(Array.isArray(r.provides)?r.provides.forEach((a,n)=>{if(!a||typeof a!="object"||Array.isArray(a))t.push(`provides[${n}]: must be an object with bindTo and ref`);else{let s=a;(typeof s.bindTo!="string"||!s.bindTo)&&t.push(`provides[${n}]: missing required "bindTo" string`),(typeof s.ref!="string"||!s.ref)&&t.push(`provides[${n}]: missing required "ref" string`)}}):t.push("provides: must be an array of { bindTo, ref } bindings")),r.compute!=null&&(Array.isArray(r.compute)?r.compute.forEach((a,n)=>{if(!a||typeof a!="object"||Array.isArray(a))t.push(`compute[${n}]: must be a compute step object`);else{let s=a;(typeof s.bindTo!="string"||!s.bindTo)&&t.push(`compute[${n}]: missing required "bindTo" property`),(typeof s.expr!="string"||!s.expr)&&t.push(`compute[${n}]: missing required "expr" string (JSONata expression)`)}}):t.push("compute: must be an array of compute steps")),r.source_defs!=null)if(!Array.isArray(r.source_defs))t.push("source_defs: must be an array");else{let a=new Set,n=new Set;r.source_defs.forEach((s,o)=>{if(!s||typeof s!="object"||Array.isArray(s))t.push(`source_defs[${o}]: must be an object`);else{let u=s;typeof u.bindTo!="string"||!u.bindTo?t.push(`source_defs[${o}]: missing required "bindTo" property`):(a.has(u.bindTo)&&t.push(`source_defs[${o}]: bindTo "${u.bindTo}" is not unique across source_defs`),a.add(u.bindTo)),typeof u.outputFile!="string"||!u.outputFile?t.push(`source_defs[${o}]: missing required "outputFile" property`):(n.has(u.outputFile)&&t.push(`source_defs[${o}]: outputFile "${u.outputFile}" is not unique across source_defs`),n.add(u.outputFile)),u.optionalForCompletionGating!=null&&typeof u.optionalForCompletionGating!="boolean"&&t.push(`source_defs[${o}]: optionalForCompletionGating must be a boolean`)}})}if(r.view!=null)if(typeof r.view!="object"||Array.isArray(r.view))t.push("view: must be an object");else{let a=r.view;!Array.isArray(a.elements)||a.elements.length===0?t.push("view.elements: required, must be a non-empty array"):a.elements.forEach((n,s)=>{if(!n||typeof n!="object"){t.push(`view.elements[${s}]: must be an object`);return}!n.kind||typeof n.kind!="string"?t.push(`view.elements[${s}].kind: required, must be a string`):Kl.has(n.kind)||t.push(`view.elements[${s}].kind: unknown kind "${n.kind}". Valid: ${[...Kl].join(", ")}`),n.data!=null&&(typeof n.data!="object"||Array.isArray(n.data))&&t.push(`view.elements[${s}].data: must be an object`)}),a.layout!=null&&(typeof a.layout!="object"||Array.isArray(a.layout))&&t.push("view.layout: must be an object"),a.features!=null&&(typeof a.features!="object"||Array.isArray(a.features))&&t.push("view.features: must be an object")}return{ok:t.length===0,errors:t}}async function j_(e,t){if(!e||e.length===0)return[];let r={card_data:t.card_data??{},requires:t.requires??{}};return Promise.all(e.map(async a=>{let n={};if(a.projections&&typeof a.projections=="object"&&!Array.isArray(a.projections)){for(let[s,o]of Object.entries(a.projections))if(typeof o=="string"&&o.trim().length>0)try{n[s]=await Cn(o).evaluate(r)}catch{n[s]=void 0}}return{...a,_projections:n}}))}function O_(e,t){if(!e||e.length===0)return[];let r={card_data:t.card_data??{},requires:t.requires??{}};return e.map(a=>{let n={};if(a.projections&&typeof a.projections=="object"&&!Array.isArray(a.projections)){for(let[s,o]of Object.entries(a.projections))if(typeof o=="string"&&o.trim().length>0)try{n[s]=$d(o).evaluate(r)}catch{n[s]=void 0}}return{...a,_projections:n}})}var qr={run:w_,runSync:b_,eval:S_,resolve:k_,validate:P_,enrichSources:j_,enrichSourcesSync:O_};function N_(e){return JSON.stringify(e)}function T_(e){let t;try{t=JSON.parse(e)}catch{throw new Error(`parseExecutionRef: invalid JSON \u2014 ${e}`)}if(typeof t!="object"||t===null||typeof t.howToRun!="string"||typeof t.whatToRun!="string")throw new Error(`parseExecutionRef: missing required fields howToRun/whatToRun \u2014 ${e}`);return t}function bd(e,t){function r(){return e.readIndex()??{}}function a(n,s,o){let u=String(s||"").split(".").filter(Boolean);if(u.length===0)return o&&typeof o=="object"&&!Array.isArray(o)?o:{value:o};let i={...n},c=i;for(let l=0;l<u.length-1;l++){let d=u[l],w=c[d],$=w&&typeof w=="object"&&!Array.isArray(w)?{...w}:{};c[d]=$,c=$}return c[u[u.length-1]]=o,i}return{readCard(n){let s=r()[n];return!s||!e.cardExists(s.key)?null:e.readCard(s.key)},readCardKey(n){return r()[n]?.key??null},readAllCards(){let n=[];for(let[s,o]of Object.entries(r())){if(!e.cardExists(o.key))continue;let u=e.readCard(o.key);u?n.push(u):t?.(`[card-store] could not read card "${s}" at key "${o.key}"`)}return n},readChecksumIndex(){let n={};for(let[s,o]of Object.entries(r()))n[s]=o.checksum;return n},changedSince(n){let s=r(),o=[];for(let[u,i]of Object.entries(s))n[u]!==i.checksum&&o.push(u);for(let u of Object.keys(n))s[u]||o.push(u);return o},validateUpsert(n,s){let o=r(),u=o[n],i=Object.entries(o).find(([,c])=>c.key===s);return u&&u.key!==s?{ok:!1,error:`Card id "${n}" is already mapped to key "${u.key}", cannot remap to "${s}"`}:i&&i[0]!==n?{ok:!1,error:`Key "${s}" is already mapped to card id "${i[0]}", cannot remap to "${n}"`}:{ok:!0}},writeCard(n,s,o){let u=r(),i=o??u[n]?.key??e.defaultCardKey(n),c=e.writeCard(i,s);u[n]={key:i,checksum:c,updatedAt:new Date().toISOString()},e.writeIndex(u)},patchCard(n,s,o){let u=r(),i=u[n];if(!i||!e.cardExists(i.key))throw new Error(`card "${n}" not found`);let c=e.readCard(i.key);if(!c||typeof c!="object"||Array.isArray(c))throw new Error(`card "${n}" is not patchable`);let l=a(c,s,o),d=e.writeCard(i.key,l);u[n]={key:i.key,checksum:d,updatedAt:new Date().toISOString()},e.writeIndex(u)},removeCard(n){let s=r(),o=s[n];o&&(e.removeCard(o.key),delete s[n],e.writeIndex(s))},readIndex(){return r()}}}function Bo(e,t){return{readSourceData(r,a){let n=e.read(`${r}/${a}`);if(n==null)return null;let s=n.trim();if(!s)return null;try{return JSON.parse(s)}catch{return s}},ingestSourceDataStaged(r,a,n,s){let o=t(n);e.write(`${r}/.staged/${s}/${a}`,o)},commitSourceData(r,a,n){let s=`${r}/.staged/${n}/${a}`,o=e.read(s);return o==null?!1:(e.write(`${r}/${a}`,o),e.remove(s),!0)},hasSource(r,a){return e.exists(`${r}/${a}`)},listSources(r){return e.listKeys(`${r}/`).filter(a=>!a.includes("/.staged/")).map(a=>a.slice(`${r}/`.length))}}}function x_(e){function t(r){let a=e.readAllEntries();if(!r)return a;let n=a.findIndex(s=>s.id===r);return n===-1?a:a.slice(n+1)}return{readEntriesAfterCursor(r){let a=t(r);return a.length===0?{events:[],newCursor:r}:{events:a.map(n=>n.event),newCursor:a[a.length-1].id}},pendingCount(r){return t(r).length},appendEvent(r){e.appendEntry({id:e.generateId(),event:r})}}}function R_(e,t){return{appendEntries(r,a){if(!r||a.length===0)return;let n=e.read(r)??[];e.write(r,[...n,...a])},dispatchEntriesForJournalId(r,a){if(!r)return;let n=e.read(r);if(!(!n||n.length===0)){for(let s of n)try{a(s)}catch(o){let u=o instanceof Error?o.message:String(o);try{t(s,u)}catch{}}e.delete(r)}}}}var Sd="v1",wa="board/graph",kd="board/lastJournalProcessedId";function Gl(e){return`cards/${e}/runtime`}function I_(e){return{readRuntime(t){return e.read(Gl(t))??{_sources:{}}},writeRuntime(t,r){e.write(Gl(t),r)}}}function C_(e,t){let r={...e};for(let a of t.deleteKeys)delete r[a];return{...r,...t.shallowMerge}}function A_(e){return{readSnapshot(t){return e.readValues(t)},commitSnapshot(t,r){if(r.schemaVersion!==Sd)throw new Error(`Unsupported snapshot schema version: ${r.schemaVersion}`);let a=e.readValues(t);if(a.version!==r.expectedVersion)return{ok:!1,reason:"version-mismatch",currentVersion:a.version};let n=C_(a.values,r);return{ok:!0,newVersion:e.writeValues(t,n,r.deleteKeys)}}}}function ii(e){function t(r){let a=e.read(r);return a==null?null:typeof a=="string"?a:JSON.stringify(a)}return{readTaskExecutorRef(){let r=t("task-executor");if(r?.trim())return T_(r.trim())},writeTaskExecutorRef(r){e.write("task-executor",N_(r))},readChatHandlerFlow(){return e.read("chat-handler-flow")},writeChatHandlerFlow(r){e.write("chat-handler-flow",r)},readCardStoreRef(){return t("card-store-ref")},writeCardStoreRef(r){e.write("card-store-ref",r)},readOutputsStoreRef(){return t("outputs-store-ref")},writeOutputsStoreRef(r){e.write("outputs-store-ref",r)},readScratchStoreRef(){return t("scratch-store-ref")},writeScratchStoreRef(r){e.write("scratch-store-ref",r)},readArchiveStoreRef(){return t("archive-store-ref")},writeArchiveStoreRef(r){e.write("archive-store-ref",r)},readChatStoreRef(){return t("chat-store-ref")},writeChatStoreRef(r){e.write("chat-store-ref",r)},readArtifactsStoreRef(){return t("artifacts-store-ref")},writeArtifactsStoreRef(r){e.write("artifacts-store-ref",r)}}}function q_(e){return{writeComputedValues(t,r){e.write(`cards/${t}/computed_values`,r)},readComputedValues(t){return e.read(`cards/${t}/computed_values`)},readAllComputedValues(){let t={};for(let r of e.listKeys("cards/")){let a=r.match(/^cards\/([^/]+)\/computed_values$/);a&&(t[a[1]]=e.read(r))}return t},writeDataObjects(t){for(let[r,a]of Object.entries(t))r&&e.write(`data-objects/${r}`,a)},readDataObject(t){return e.read(`data-objects/${t}`)},readAllDataObjects(){let t={};for(let r of e.listKeys("data-objects/"))t[r.slice(13)]=e.read(r);return t},writeStatusSnapshot(t){e.write("status",t)},readStatusSnapshot(){return e.read("status")}}}function Bl(e){return e?{lastRequestedToken:e.lastRequestedToken,lastCompletedToken:e.lastCompletedToken,lastCompletionStatus:e.lastCompletionStatus??(e.lastCompletedToken?"success":"not-started"),queueRequestedToken:e.queueRequestedToken}:{lastCompletionStatus:"not-started"}}function D_(e){return e?.lastRequestedToken?e.lastCompletedToken!==e.lastRequestedToken:!1}function Jl(e,t){return e?.lastRequestedToken?D_(e)?"in-flight":!e.lastCompletedToken||e.lastCompletedToken<t?"dispatch":"idle":"dispatch"}function M_(e,t){return{...e,lastCompletedToken:t,lastCompletionStatus:"success"}}function Wl(e,t){return{...e,lastCompletedToken:t,lastCompletionStatus:"failure"}}function Jo(e,t){let r=t.state.tasks,a=t.config.tasks,n=Object.keys(r),s=Zo(t),o={completed:0,failed:0,in_progress:0,pending:0,blocked:0,unresolved:0},u=new Map;for(let h of s.pending)u.set(h.taskName,h.waitingOn);for(let h of s.unresolved)u.set(h.taskName,h.missingTokens);for(let h of s.blocked)u.set(h.taskName,h.failedTokens);let i=new Map;for(let[h,v]of Object.entries(a))for(let m of v.requires??[]){let f=i.get(m)??[];f.push(h),i.set(m,f)}let c=n.sort().map(h=>{let v=r[h],m=a[h]??{requires:[],provides:[]};v.status==="completed"?o.completed+=1:v.status==="failed"?o.failed+=1:v.status==="in-progress"&&(o.in_progress+=1);let f=m.requires??[],k=m.provides??[],y=Object.keys(v.data??{}).sort(),S=f.filter(x=>t.state.availableOutputs.includes(x)),_=f.filter(x=>!t.state.availableOutputs.includes(x)),g=u.get(h)??_,p=new Set;for(let x of k)for(let C of i.get(x)??[])C!==h&&p.add(C);let E=v.failedAt,j=v.error?{message:v.error,code:"TASK_FAILED",at:E,source:"task-runtime"}:void 0;return{name:h,status:v.status,error:j,requires:f,requires_satisfied:S,requires_missing:_,provides_declared:k,provides_runtime:y,blocked_by:g,unblocks:Array.from(p).sort(),runtime:{attempt_count:v.executionCount??0,restart_count:v.retryCount??0,in_progress_since:v.status==="in-progress"?v.startedAt??null:null,last_transition_at:v.lastUpdated??null,last_completed_at:v.completedAt??null,last_restarted_at:v.startedAt??null,status_age_ms:v.lastUpdated?0:null}}});o.pending=s.pending.length,o.blocked=s.blocked.length,o.unresolved=s.unresolved.length;let l=c.map(h=>({name:h.name,fanOut:h.unblocks.length})).sort((h,v)=>v.fanOut-h.fanOut||h.name.localeCompare(v.name)),d=l.length>0?l[0]:{name:null,fanOut:0},w=new Set;for(let h of Object.values(a))for(let v of h.requires??[])w.add(v);let $=0;for(let[h,v]of Object.entries(a)){let m=(v.requires??[]).length===0,f=(v.provides??[]).some(k=>(i.get(k)??[]).some(y=>y!==h));m&&!f&&($+=1)}return{schema_version:"v1",meta:{board:{path:e}},summary:{card_count:n.length,completed:o.completed,eligible:s.eligible.length,pending:o.pending,blocked:o.blocked,unresolved:o.unresolved,failed:o.failed,in_progress:o.in_progress,orphan_cards:$,topology:{edge_count:Array.from(w).length,max_fan_out_card:d.name,max_fan_out:d.fanOut}},cards:c}}function F_(){return new Date().toISOString()}function V_(e,t,r,a,n,s,o){return async u=>{let i=[],c=r.cardStore.readCard(u.nodeId);if(!c)return"task-initiate-failure";let l=c.id,d=c.card_data??{},w=c.source_defs??[],$=w.filter(M=>M.optionalForCompletionGating!==!0),h=r.cardRuntimeStore.readRuntime(l),v=!1,m=()=>{v&&(r.cardRuntimeStore.writeRuntime(l,h),v=!1)},f=M=>Bl(h._sources[M]),k=(M,U)=>{h._sources[M]=Bl(U),v=!0},y=u.taskState?.executionCount??0;if(h._lastExecutionCount!==y&&(h._sources={},h._lastExecutionCount=y,v=!0),u.update){let M=u.update,U=M.outputFile;if(U){let J=f(U);if(M.failure){let te=M.rqt??J.lastRequestedToken??J.queueRequestedToken;te&&k(U,Wl(J,te))}else{let te=M.rqt;if(!J.lastCompletedToken||te>J.lastCompletedToken){let W=typeof M.deliveryToken=="string"?M.deliveryToken:void 0,T=!1;W&&(T=r.fetchedSourcesStore.commitSourceData(l,U,W)),T?k(U,M_(J,te)):k(U,Wl(J,te))}}m()}}let S={};for(let M of w)if(M.outputFile){let U=r.fetchedSourcesStore.readSourceData(l,M.outputFile);U!==null&&(S[M.bindTo]=U)}let _={};for(let[M,U]of Object.entries(u.state??{}))if(U!==null&&typeof U=="object"&&!Array.isArray(U)){let J=U[M];_[M]=J!==void 0?J:U}else _[M]=U;let g={id:l,card_data:{...d},requires:_,source_defs:w,compute:c.compute};g._sourcesData=S,c.compute&&qr.runSync(g,{sourcesData:S}),(s??r.outputStore.writeComputedValues.bind(r.outputStore))(l,g.computed_values??{});let p={...c},E=qr.enrichSourcesSync(Array.isArray(c.source_defs)?c.source_defs:void 0,{card_data:c.card_data,requires:_}),j=e.value;p.source_defs=Array.isArray(E)?E.map(M=>({...M,boardDir:typeof M.boardDir=="string"&&M.boardDir?M.boardDir:j})):E;let x=F_(),C=u.update?void 0:x,q=$.filter(M=>{let U=M.outputFile;if(typeof U!="string"||!U)return!0;let J=f(U);C&&(J={...J,queueRequestedToken:C},k(U,J));let te=J.queueRequestedToken??J.lastRequestedToken??x,W=Jl(J,te);return W==="in-flight"?!1:W==="dispatch"});if(m(),q.length>0){let M=!1,U=x;for(let J of q){let te=J.outputFile;if(typeof te!="string"||!te)continue;let W=f(te),T=W.queueRequestedToken??x;k(te,{...W,lastRequestedToken:T}),U=T,M=!0}return M&&m(),M&&(i.push({taskKind:"source-fetch",payload:{boardRef:ze(e),enrichedCard:p,callbackToken:u.callbackToken,rqt:U}}),r.executionRequestStore.appendEntries(t,i)),"task-initiated"}if($.some(M=>{let U=M.outputFile;if(typeof U!="string"||!U)return!1;let J=f(U),te=J.queueRequestedToken??J.lastRequestedToken??x;return Jl(J,te)==="in-flight"}))return"task-initiated";let F=c.provides??[],H={};for(let{bindTo:M,ref:U}of F)H[M]=qr.resolve(g,U);return(o??r.outputStore.writeDataObjects.bind(r.outputStore))(H),w.filter(M=>{if(M.optionalForCompletionGating!==!0)return!1;let U=f(M.outputFile);return!U.lastRequestedToken||!U.lastCompletedToken?!0:U.lastCompletedToken<=U.lastRequestedToken}).length>0&&i.push({taskKind:"source-fetch",payload:{boardRef:ze(e),enrichedCard:p,callbackToken:u.callbackToken,rqt:x}}),a(u.nodeId,H),i.length>0&&r.executionRequestStore.appendEntries(t,i),"task-initiated"}}var z_={settings:{completion:"manual",refreshStrategy:"data-changed"},tasks:{}};function U_(e){return{[wa]:e.graph,[kd]:e.lastDrainedJournalId}}function L_(e){let t=e[wa],r=e[kd];if(!t||typeof t!="object")throw new Error(`State snapshot is missing required key: ${wa}`);return{graph:t,lastDrainedJournalId:typeof r=="string"?r:""}}function H_(e){let t=e.requires,r=e.provides?.map(a=>a.bindTo)??[];return{requires:t&&t.length>0?t:void 0,provides:r,taskHandlers:["card-handler"],description:e.meta?.title??e.id}}function K_(e){function t(s){return{status:"success",data:s}}function r(s){return{status:"fail",error:s}}function a(s){return{status:"error",error:s instanceof Error?s.message:String(s)}}function n(s){if(Array.isArray(s))return s;if(s&&typeof s=="object"){let o=s;return Array.isArray(o.files)?o.files:[s]}return null}return{get(s){try{let o=s.params?.id;if(o){let u=e.readCard(o);return u?t({cards:[u]}):r(`card "${o}" not found`)}return t({cards:e.readAllCards()})}catch(o){return a(o)}},set(s){try{let o=s.body;if(o==null)return r("set requires a body (card object or array of cards)");let u=Array.isArray(o)?o:[o];for(let i of u){if(typeof i.id!="string")return r("each card must have a string `id` field");e.writeCard(i.id,i)}return t({count:u.length})}catch(o){return a(o)}},del(s){try{let o=s.body?.ids??[],u=s.params?.id,i=u?[...o,u]:o;if(i.length===0)return r("del requires body.ids (string[]) or params.id");for(let c of i)e.removeCard(c);return t({count:i.length})}catch(o){return a(o)}},patch(s){try{let o=s.params?.id,u=s.params?.path;if(!o)return r("patch requires params.id");if(!u)return r("patch requires params.path");let i=s.body,c=i&&Object.prototype.hasOwnProperty.call(i,"value")?i.value:s.body;return e.patchCard(o,u,c),t({count:1})}catch(o){return a(o)}},appendFiles(s){try{let o=s.params?.id;if(!o)return r("appendFiles requires params.id");let u=e.readCard(o);if(!u)return r(`card "${o}" not found`);let i=n(s.body);if(!i||i.length===0)return r("appendFiles requires a file metadata object, array, or body.files array");let c=u.card_data&&typeof u.card_data=="object"&&!Array.isArray(u.card_data)?u.card_data:{},l=Array.isArray(c.files)?c.files:[],d=[...l,...i],w=i.map((h,v)=>({idx:l.length+v,entry:h})),$=this.patch({params:{id:o,path:"card_data.files"},body:{value:d}});return $.status!=="success"?$:t({files_added:w})}catch(o){return a(o)}}}}function pe(e){return e!==void 0?{status:"success",data:e}:{status:"success"}}function ne(e){return{status:"fail",error:e}}function me(e){return{status:"error",error:e instanceof Error?e.message:String(e)}}function G_(e){let t=new TextEncoder().encode(e),r=Array.from(t,a=>String.fromCharCode(a)).join("");return btoa(r).replace(/\+/g,"-").replace(/\//g,"_").replace(/=/g,"")}function Ed(e){let t=e.replace(/-/g,"+").replace(/_/g,"/"),r=t+"=".repeat((4-t.length%4)%4),a=atob(r),n=Uint8Array.from(a,s=>s.charCodeAt(0));return new TextDecoder().decode(n)}function bn(e){try{let t=JSON.parse(Ed(e));return typeof t?.t=="string"?{taskName:t.t}:null}catch{return null}}function B_(e){return G_(JSON.stringify(e))}function Xl(e){try{let t=JSON.parse(Ed(e));return typeof t?.cbk=="string"&&typeof t?.cid=="string"&&typeof t?.b=="string"&&typeof t?.d=="string"?t:null}catch{return null}}function Ke(){return new Date().toISOString()}function Wo(e,t){let r=t.onWarn??(()=>{}),a=ze(e);function n(z){if(z.length!==0)try{let b=t.publishBoardChangeNotifications?.(z);b&&typeof b.catch=="function"&&b.catch(N=>r(`[board-live-cards-public] publishBoardChangeNotifications failed: ${N instanceof Error?N.message:String(N)}`))}catch(b){r(`[board-live-cards-public] publishBoardChangeNotifications failed: ${b instanceof Error?b.message:String(b)}`)}}function s(){let z=u().readCardStoreRef();if(!z)throw new Error(`Board at ${e.value} has no card store configured. Run: init --base-ref <ref> --store-ref <b64-ref>`);let b=t.kvStorageForRef(z);return{readIndex(){return b.read("_index")},writeIndex(N){b.write("_index",N)},readCard(N){return b.read(N)},writeCard(N,I){return b.write(N,I),t.hashFn(I)},removeCard(N){b.delete(N)},cardExists(N){return b.read(N)!==null},defaultCardKey(N){return N}}}let o={readValues(z){let b=t.kvStorage("state-snapshot"),N=b.listKeys().sort();if(N.length===0)return{version:null,values:{}};let I={};for(let L of N)I[L]=b.read(L);return{version:t.hashFn(I),values:I}},writeValues(z,b,N){let I=t.kvStorage("state-snapshot");for(let L of N)I.delete(L);for(let[L,B]of Object.entries(b))I.write(L,B);return t.hashFn(b)}},u=()=>ii(t.kvStorage("config")),i=()=>A_(o),c=()=>x_(t.journalAdapter()),l=()=>bd(s(),r),d=()=>{let z=u().readOutputsStoreRef();if(!z)throw new Error(`Board at ${e.value} has no outputs store configured. Run: init --outputs-store-ref <b64-ref>`);return q_(t.kvStorageForRef(z))},w=()=>{let z=u().readArchiveStoreRef();return z?t.archiveFactoryForRef(z):t.archiveFactory()};function $(){return!!i().readSnapshot(e.value).values[wa]}function h(){let z=i().readSnapshot(e.value);if(!z.values[wa])throw new Error(`Board not initialized at ${e.value}`);return L_(z.values)}function v(z,b){let N=i().commitSnapshot(e.value,{schemaVersion:Sd,expectedVersion:b,commitId:t.genId(),committedAt:Ke(),deleteKeys:[],shallowMerge:U_(z)});if(!N.ok)throw new Error(`Snapshot commit failed (version mismatch): expected=${b??"null"} current=${N.currentVersion??"null"}`)}function m(z){c().appendEvent(z)}async function f(){let z=(Y,se)=>{let Oe=Y.payload,kt=(Oe?.enrichedCard??{}).id??Oe?.cardId??"unknown";m({type:"task-failed",taskName:kt,error:se,timestamp:Ke()})},b=R_(t.kvStorage("execution-requests"),z),N=I_(t.kvStorage("card-runtime")),I=Bo(t.blobStorage("sources"),Y=>t.resolveBlob(Y)),L=new Map,B={readRuntime(Y){return L.get(Y)??N.readRuntime(Y)},writeRuntime(Y,se){L.set(Y,se)}},ae=[],le=new Map,ke={readSourceData(Y,se){let Oe=`${Y}/${se}`;return le.has(Oe)?le.get(Oe):I.readSourceData(Y,se)},ingestSourceDataStaged(Y,se,Oe,kt){I.ingestSourceDataStaged(Y,se,Oe,kt)},commitSourceData(Y,se,Oe){let kt=`${Y}/.staged/${Oe}/${se}`,it=t.blobStorage("sources").read(kt);if(it==null)return!1;let ka=`${Y}/${se}`,fr=it.trim();try{le.set(ka,JSON.parse(fr))}catch{le.set(ka,fr)}return ae.push({cardId:Y,outputFile:se,deliveryToken:Oe}),!0},hasSource(Y,se){let Oe=`${Y}/${se}`;return le.has(Oe)?!0:I.hasSource(Y,se)},listSources(Y){let se=I.listSources(Y),Oe=new Set;for(let it of le.keys())it.startsWith(`${Y}/`)&&Oe.add(it.slice(`${Y}/`.length));let kt=new Set([...se,...Oe]);return Array.from(kt)}},Pe={cardStore:l(),cardRuntimeStore:B,fetchedSourcesStore:ke,outputStore:d(),executionRequestStore:b},Ie=h(),je=Ko(Ie.graph),{events:Ze,newCursor:qe}=c().readEntriesAfterCursor(Ie.lastDrainedJournalId),ot=[],St=[],Bt=[],lr=new Map,Dr=new Set,An=(Y,se)=>{ot.push({type:"task-completed",taskName:Y,data:se,timestamp:Ke()});try{w().stream("exec-history").append({taskName:Y,status:"completed",completedAt:Ke()})}catch{}},ui=(Y,se)=>{m({type:"task-failed",taskName:Y,error:se,timestamp:Ke()});try{w().stream("exec-history").append({taskName:Y,status:"failed",error:se,completedAt:Ke()})}catch{}},ba=__(je,{handlers:{"card-handler":V_(e,qe,Pe,An,ui,(Y,se)=>{St.push({cardId:Y,values:se})},Y=>{Bt.push(Y)})},onNodeRemoved:Y=>{lr.delete(Y),L.delete(Y),Dr.add(Y)}});for(ot=Ze;ot.length>0;){let Y=ot;ot=[];for(let se of Y)if(se.type==="task-restart"){let Oe=Pe.cardStore.readCard(se.taskName);Oe&&lr.set(se.taskName,Oe)}ba.pushAll(Y),await ba.waitForHandlers()}let ci=ba.getState();await ba.dispose({wait:!0});let jd=i().readSnapshot(e.value).version;v({lastDrainedJournalId:qe,graph:Qo(ci)},jd);for(let{cardId:Y,values:se}of St)Pe.outputStore.writeComputedValues(Y,se);for(let Y of Bt)Pe.outputStore.writeDataObjects(Y);for(let[Y,se]of L)N.writeRuntime(Y,se);for(let{cardId:Y,outputFile:se,deliveryToken:Oe}of ae)I.commitSourceData(Y,se,Oe);let Sa;try{Sa=Jo(a,ci),Pe.outputStore.writeStatusSnapshot(Sa)}catch(Y){r(`[board-live-cards-public] status publish failed: ${Y instanceof Error?Y.message:String(Y)}`)}let dr=[];for(let{cardId:Y,values:se}of St)dr.push({kind:"computed_values",cardId:Y,values:se});for(let Y of Bt)for(let[se,Oe]of Object.entries(Y))se&&dr.push({kind:"data_object",key:se,payload:Oe});for(let[Y,se]of lr)dr.push({kind:"card_refreshed",cardId:Y,card:se});for(let Y of Dr)dr.push({kind:"card_removed",cardId:Y});Sa!==void 0&&dr.push({kind:"status",status:Sa}),n(dr);let Od=u().readTaskExecutorRef()??{howToRun:"built-in",whatToRun:ze({kind:"built-in",value:"source-cli-task-executor"})};b.dispatchEntriesForJournalId(qe,Y=>{if(Y.taskKind!=="source-fetch"){r(`[process-accumulated-events] unknown taskKind "${Y.taskKind}" \u2014 skipping`);return}let se=Y.payload,Oe=se.enrichedCard?.id??"unknown",kt=se.enrichedCard?.source_defs??[];for(let it of kt){if(!it.outputFile){r(`[dispatch] source "${it.bindTo}" has no outputFile \u2014 skipping`);continue}let ka=B_({cbk:se.callbackToken,rg:e.value,br:ze(e),cid:Oe,b:it.bindTo,d:it.outputFile,cs:void 0,rqt:se.rqt});t.dispatchExecution(Od,{source_def:it,base_ref:ze(e),callback:{token:ka,via:t.selfRef}}).catch(fr=>ui(Oe,fr instanceof Error?fr.message:String(fr)))}})}async function k(){try{let z=()=>{let N=h(),{events:I}=c().readEntriesAfterCursor(N.lastDrainedJournalId);I.length<=0||(k(),t.requestProcessAccumulated?.())},b=await i0(t.lock,f,z);return pe({ran:b!==!1})}catch(z){return me(z)}}function y(){k(),t.requestProcessAccumulated?.()}function S(z){try{let b=z.params?.cardStoreRef;if(!b)return ne("init requires params.cardStoreRef \u2014 create a card store with card-store-cli and pass its ref here");if(!$()){let Pe=vd(z_);v({lastDrainedJournalId:"",graph:Qo(Pe)},null)}let N=z.params?.outputsStoreRef;if(!N)return ne("init requires params.outputsStoreRef \u2014 pass the outputs store ref here");let I=z.params?.scratchStoreRef,L=z.params?.archiveStoreRef,B=z.params?.chatStoreRef,ae=z.params?.artifactsStoreRef,le=u();le.writeCardStoreRef(b),le.writeOutputsStoreRef(N),I&&le.writeScratchStoreRef(I),L&&le.writeArchiveStoreRef(L),B&&le.writeChatStoreRef(B),ae&&le.writeArtifactsStoreRef(ae);let ke=z.body??{};ke["task-executor-ref"]&&le.writeTaskExecutorRef(ke["task-executor-ref"]),Object.prototype.hasOwnProperty.call(ke,"chat-handler-flow")&&le.writeChatHandlerFlow(ke["chat-handler-flow"]);try{d().writeStatusSnapshot(Jo(a,Ko(h().graph)))}catch{}return pe()}catch(b){return me(b)}}function _(z){try{let b=d().readStatusSnapshot();if(!b){b=Jo(a,Ko(h().graph));try{d().writeStatusSnapshot(b)}catch{}}return pe(b)}catch(b){return me(b)}}function g(z){try{let b=z.params?.id;if(!b)return ne("removeCard requires params.id");try{t.kvStorage("card-upsert").delete(b)}catch{}return m({type:"task-removal",taskName:b,timestamp:Ke()}),y(),pe()}catch(b){return me(b)}}function p(z){try{let b=z.params?.cardId;if(!b)return ne("addCardFiles requires params.cardId");let N=K_(l()).appendFiles({params:{id:b},body:z.body});if(N.status!=="success")return N;let I=E({params:{cardId:b}});return I.status!=="success"?I:pe({cardId:b,files_added:N.data.files_added,notified:!0})}catch(b){return me(b)}}function E(z){try{let b=z.params?.cardId;if(!b)return ne("cardRefreshedNotify requires params.cardId");let N=l().readCard(b);return N?(n([{kind:"card_refreshed",cardId:b,card:N}]),pe({cardId:b,notified:!0})):ne(`Card "${b}" not found in board at ${e.value}`)}catch(b){return me(b)}}function j(z){try{let b=z.params?.id;return b?(m({type:"task-restart",taskName:b,timestamp:Ke()}),y(),pe()):ne("retrigger requires params.id")}catch(b){return me(b)}}async function x(z){return k()}function C(z){try{let b=z.params?.cardId,N=z.params?.all,I=!!z.params?.restart;if(!b&&!N)return ne("upsertCard requires --card-id <id> or --all");let L=N?l().readAllCards().map(B=>B.id):[b];for(let B of L)if(!l().readCard(B))return ne(`Card "${B}" not found in board at ${e.value}`);for(let B of L){let ae=l().readCard(B),le=H_(ae),ke=t.hashFn(le),Pe=t.kvStorage("card-upsert"),Ie=Pe.read(B),je=Ie?.taskConfigHash!==ke;if(!(!je&&!I)){if(je){let Ze=Ie?.blobRef??l().readCardKey(B)??B;m({type:"task-upsert",taskName:B,taskConfig:le,timestamp:Ke()}),Pe.write(B,{blobRef:Ze,taskConfigHash:ke,updatedAt:Ke()})}I&&m({type:"task-restart",taskName:B,timestamp:Ke()})}}return y(),pe()}catch(b){return me(b)}}function q(z){try{let b=z.params?.token;if(!b)return ne("taskFailed requires params.token");let N=z.params?.error??"unknown error",I=bn(b);if(!I)return ne("Invalid callback token");m({type:"task-failed",taskName:I.taskName,error:N,timestamp:Ke()});try{w().stream("exec-history").append({taskName:I.taskName,status:"failed",error:N,completedAt:Ke()})}catch{}return y(),pe()}catch(b){return me(b)}}function F(z){try{let b=z.params?.token;if(!b)return ne("taskProgress requires params.token");let N=(z.body??{}).update??{},I=bn(b);return I?(m({type:"task-progress",taskName:I.taskName,update:N,timestamp:Ke()}),y(),pe()):ne("Invalid callback token")}catch(b){return me(b)}}function H(z){try{let b=z.params?.token,N=z.params?.ref;if(!b)return ne("sourceDataFetched requires params.token");if(!N)return ne("sourceDataFetched requires params.ref");let I=Xl(b);if(!I)return ne("Invalid source token");let{cbk:L,cid:B,b:ae,d:le,cs:ke,rqt:Pe}=I,Ie=Bo(t.blobStorage("sources"),ot=>t.resolveBlob(ot)),je=t.genId();Ie.ingestSourceDataStaged(B,le,ht(N),je);let Ze=bn(L);if(!Ze)return ne("Invalid callback token embedded in source token");let qe=Ke();return m({type:"task-progress",taskName:Ze.taskName,update:{bindTo:ae,outputFile:le,fetchedAt:qe,deliveryToken:je,sourceChecksum:ke,rqt:Pe},timestamp:qe}),y(),pe()}catch(b){return me(b)}}function M(z){try{let b=z.params?.token,N=z.params?.reason??"unknown";if(!b)return ne("sourceDataFetchFailure requires params.token");let I=Xl(b);if(!I)return ne("Invalid source token");let{cbk:L,b:B,d:ae,cs:le,rqt:ke}=I,Pe=bn(L);return Pe?(m({type:"task-progress",taskName:Pe.taskName,update:{bindTo:B,outputFile:ae,failure:!0,reason:N,sourceChecksum:le,rqt:ke},timestamp:Ke()}),y(),pe()):ne("Invalid callback token embedded in source token")}catch(b){return me(b)}}function U(z){try{let b=u().readCardStoreRef();return b?pe({storeRef:b}):ne(`Board at ${e.value} has no card store configured`)}catch(b){return me(b)}}function J(z){try{let b=u().readOutputsStoreRef();return b?pe({storeRef:b}):ne(`Board at ${e.value} has no outputs store configured`)}catch(b){return me(b)}}function te(z){try{let b=u().readScratchStoreRef();return pe({storeRef:b})}catch(b){return me(b)}}function W(z){try{let b=u().readArchiveStoreRef();return pe({storeRef:b})}catch(b){return me(b)}}function T(z){try{let b=u().readChatStoreRef();return pe({storeRef:b})}catch(b){return me(b)}}function A(z){try{let b=u().readArtifactsStoreRef();return pe({storeRef:b})}catch(b){return me(b)}}function V(z){try{let b=z.params?.key;if(!b)return ne("getConfig requires params.key");let N=u(),I;switch(b){case"task-executor":I=N.readTaskExecutorRef()??null;break;case"chat-handler-flow":I=N.readChatHandlerFlow()??null;break;case"card-store-ref":I=N.readCardStoreRef();break;case"outputs-store-ref":I=N.readOutputsStoreRef();break;case"scratch-store-ref":I=N.readScratchStoreRef();break;case"archive-store-ref":I=N.readArchiveStoreRef();break;case"chat-store-ref":I=N.readChatStoreRef();break;case"artifacts-store-ref":I=N.readArtifactsStoreRef();break;default:return ne(`getConfig: unknown key "${b}"`)}return pe({value:I})}catch(b){return me(b)}}function P(z){try{let b=z.params?.key;if(!b)return ne("getOutputsDataObject requires params.key");let N=d().readDataObject(b);return pe(N)}catch(b){return me(b)}}function O(z){try{return pe(d().readAllDataObjects())}catch(b){return me(b)}}function R(z){try{let b=z.params?.key;if(!b)return ne("getOutputsComputedValues requires params.key");let N=d().readComputedValues(b);return pe(N)}catch(b){return me(b)}}function K(z){try{return pe(d().readAllComputedValues())}catch(b){return me(b)}}function Z(){return Bo(t.blobStorage("sources"),z=>t.resolveBlob(z))}function ie(z){let b=t.blobStorage("sources").keyRef?.(z);return b?ze(b):z}function re(z){try{let b=z.params?.key;if(!b)return ne("getOutputsFetchedSources requires params.key");let N=Z().listSources(b),I={};for(let L of N)I[L]=ie(`${b}/${L}`);return pe(I)}catch(b){return me(b)}}function be(z){try{let b=Z(),N=new Set;for(let L of t.blobStorage("sources").listKeys()){let B=L.indexOf("/");B>0&&!L.includes("/.staged/")&&N.add(L.slice(0,B))}let I={};for(let L of N){let B=b.listSources(L);if(B.length>0){I[L]={};for(let ae of B)I[L][ae]=ie(`${L}/${ae}`)}}return pe(I)}catch(b){return me(b)}}return{init:S,status:_,getCardStoreRef:U,getOutputsStoreRef:J,getScratchStoreRef:te,getArchiveStoreRef:W,getChatStoreRef:T,getArtifactsStoreRef:A,getConfig:V,getOutputsDataObject:P,getAllOutputsDataObjects:O,getOutputsComputedValues:R,getAllOutputsComputedValues:K,getOutputsFetchedSources:re,getAllOutputsFetchedSources:be,removeCard:g,addCardFiles:p,cardRefreshedNotify:E,retrigger:j,processAccumulatedEvents:x,upsertCard:C,taskFailed:q,taskProgress:F,sourceDataFetched:H,sourceDataFetchFailure:M}}function ur(e,t){let r=()=>ii(t.kvStorage("config"));function a(){let _=r().readCardStoreRef();if(!_)throw new Error(`Board at ${e.value} has no card store configured. Run: init --base-ref <ref> --store-ref <b64-ref>`);let g=t.kvStorageForRef(_);return{readIndex(){return g.read("_index")},writeIndex(p){g.write("_index",p)},readCard(p){return g.read(p)},writeCard(p,E){return g.write(p,E),t.hashFn(E)},removeCard(p){g.delete(p)},cardExists(p){return g.read(p)!==null},defaultCardKey(p){return p}}}let n=()=>bd(a(),t.onWarn??(()=>{})),s=()=>{let _=r().readScratchStoreRef();return _?t.scratchStorageForRef(_):t.scratchStorage()};function o(_,g){let p=t.validateSchema(g),E=[],j=r().readTaskExecutorRef();if(j&&Array.isArray(g.source_defs))for(let C of g.source_defs){let q=typeof C.bindTo=="string"?C.bindTo:"(unknown)";try{let F;try{F=t.invokeExecutorSync(j,"validate-source-def",[],{timeout:t.executorTimeouts?.validationMs??1e4,input:JSON.stringify(C)})}catch(M){let U=M;if(F=typeof U?.stdout=="string"?U.stdout:"",!F.trim()){E.push(`source "${q}": executor validate-source-def failed \u2014 ${M instanceof Error?M.message:String(M)}`);continue}}let H=JSON.parse(F.trim());if(!H.ok&&Array.isArray(H.errors))for(let M of H.errors)E.push(`source "${q}": ${M}`)}catch(F){E.push(`source "${q}": executor validate-source-def failed \u2014 ${F instanceof Error?F.message:String(F)}`)}}let x=[...p.errors,...E];return pe({cardId:_,isValid:x.length===0,issues:x})}function u(_,g){let p=r().readTaskExecutorRef();if(!p)throw new Error("No task-executor registered for this board");let E=typeof _.bindTo=="string"?_.bindTo:"source",j=s(),x={..._,boardDir:e.value,_projections:g},C=j.create(JSON.stringify(x,null,2),`probe-in-${E}`,".json"),q=j.getUniqueKey(`probe-out-${E}`,".json"),F=j.getUniqueKey(`probe-err-${E}`,".txt"),H=ze(j.keyRef(C)),M=ze(j.keyRef(q)),U=ze(j.keyRef(F)),J=null;try{if(t.invokeExecutorSync(p,"run-source-fetch",["--in-ref",H,"--out-ref",M,"--err-ref",U],{timeout:_.timeout??t.executorTimeouts?.probeMs??6e4}),J=j.read(q),J===null)throw new Error("Executor produced no output file")}catch(te){let W=j.read(F)?.trim()??(te instanceof Error?te.message:String(te));throw new Error(`Probe failed: ${W}`)}finally{try{j.remove(C)}catch{}try{j.remove(F)}catch{}}return{bindTo:E,result:J}}function i(_,g,p){let E;try{E=u(_,g)}catch(j){return ne(j instanceof Error?j.message:String(j))}if(p){let j=ht(p);t.absoluteBlob.write(j.value,E.result)}return pe({bindTo:E.bindTo,resultSizeBytes:E.result.length})}function c(_,g){let p=_.params?.sourceIdx,E=_.params?.outRef;if(p===void 0)return ne(`${g} requires params.sourceIdx`);if(!_.body||typeof _.body!="object"||Array.isArray(_.body))return ne(`${g} requires card JSON object in body`);let j=_.body,x=j["card-content"]??j,C=j["mock-projections"]??{},q=x.source_defs??[];if(p<0||p>=q.length)return ne(`sourceIdx ${p} out of range (card has ${q.length} source(s))`);let F=q[p],H=typeof F.bindTo=="string"?F.bindTo:"source";return{src:F,bindTo:H,outRef:E,mockProjections:C}}function l(_){try{let g=_.params?.cardId,p=_.params?.all;if(!g&&!p)return ne("validateCard requires --card-id <id> or --all");let E=p?n().readAllCards().map(x=>x.id):[g],j=[];for(let x of E){let C=n().readCard(x);if(!C){j.push({cardId:x,isValid:!1,issues:[`Card "${x}" not found`]});continue}let q=o(x,C);if(q.status!=="success")return q;j.push(q.data)}return pe(j)}catch(g){return me(g)}}function d(_){try{if(!_.body||typeof _.body!="object"||Array.isArray(_.body))return ne("validateCardPreflight requires card JSON object in body");let g=_.body,p=g["card-content"]??g,E=typeof p.id=="string"?p.id:"(unknown)";return o(E,p)}catch(g){return me(g)}}function w(_){try{let g=_.params?.cardId,p=_.params?.sourceIdx,E=_.params?.outRef;if(!g)return ne("probeSource requires params.cardId");if(p===void 0)return ne("probeSource requires params.sourceIdx");let j=(_.body??{})["mock-projections"]??{},x=n().readCard(g);if(!x)return ne(`Card "${g}" not found`);let C=x.source_defs??[];return p<0||p>=C.length?ne(`sourceIdx ${p} out of range (card has ${C.length} source(s))`):i(C[p],j,E)}catch(g){return me(g)}}function $(_){try{let g=_.params?.outRef,p=_.body;if(!p)return ne('probeTmpSource requires body with "source-def" and "mock-projections"');let E=p["source-def"],j=p["mock-projections"]??{};return E?i(E,j,g):ne('probeTmpSource body requires "source-def"')}catch(g){return me(g)}}function h(_){try{let g=c(_,"probeSourcePreflight");if("status"in g)return g;let p=r().readTaskExecutorRef();if(!p)return ne("No task-executor registered for this board");try{let E={...g.src,_projections:g.mockProjections},j=t.invokeExecutorSync(p,"probe-source-preflight",[],{timeout:g.src.timeout??t.executorTimeouts?.preflightMs??6e4,input:JSON.stringify(E)}),x=JSON.parse(j.trim());return x.ok?pe({bindTo:g.bindTo,reachable:x.reachable,latencyMs:x.latencyMs,note:x.note}):ne(x.error??"Preflight probe failed")}catch{return ne("Executor does not support probe-source-preflight")}}catch(g){return me(g)}}function v(_){try{let g=c(_,"runSourcePreflight");if("status"in g)return g;try{let p=u(g.src,g.mockProjections);if(g.outRef){let j=ht(g.outRef);t.absoluteBlob.write(j.value,p.result)}let E=p.result;try{E=JSON.parse(p.result)}catch{}return pe({bindTo:p.bindTo,ok:!0,result:E,issues:[]})}catch(p){let E=p instanceof Error?p.message:String(p);return E==="No task-executor registered for this board"?ne(E):pe({bindTo:g.bindTo,ok:!1,result:null,issues:[E]})}}catch(g){return me(g)}}function m(_){try{let g=r().readTaskExecutorRef();if(!g)return ne("No task-executor registered for this board");let p=t.invokeExecutorSync(g,"describe-capabilities",[],{timeout:t.executorTimeouts?.describeMs??1e4});return pe(JSON.parse(p.trim()))}catch(g){return me(g)}}function f(_){try{let g=_.body;if(!g||!Array.isArray(g.ops))return ne("updatesInCardStore requires body.ops array");let p=g.ops,E=n();for(let j of p){let x=j.op,C=j.id;if(!C)return ne('op is missing "id"');if(x==="update"){let q=j["card-content"];if(!q)return ne(`update op for "${C}" is missing "card-content"`);E.writeCard(C,q)}else return ne(`Unknown op type: "${x??"(none)"}"`)}return pe()}catch(g){return me(g)}}function k(_){try{let g=_.body;if(!g||!Array.isArray(g.ids))return ne("readFromCardStore requires body.ids array");let p=g.ids,E=n(),j=p.map(x=>({id:x,"card-content":E.readCard(x)}));return pe({cards:j})}catch(g){return me(g)}}function y(_){try{if(!_.body||typeof _.body!="object"||Array.isArray(_.body))return ne("evalCardCompute requires a JSON object in body");let g=_.body,p=g["card-content"]??g,E=typeof p.id=="string"?p.id:"(unknown)",j=g["mock-fetched-sources"]??{},x=g["mock-requires"]??{},C=p.compute;if(!C||!Array.isArray(C)||C.length===0)return pe({cardId:E,ok:!0,computed_values:{},errors:[]});let q={id:E,card_data:p.card_data??{},requires:x,source_defs:p.source_defs,compute:C},F=qr.runSync(q,{sourcesData:j}),H=F.node.computed_values??{},M=F.errors??[];return pe({cardId:E,ok:M.length===0,computed_values:H,errors:M})}catch(g){return me(g)}}function S(_){try{if(!_.body||typeof _.body!="object"||Array.isArray(_.body))return ne("simulateCardCycle requires a JSON object in body");let g=_.body,p=g["card-content"]??g,E=typeof p.id=="string"?p.id:"(unknown)",j=g["mock-fetched-sources"]??{},x=g["mock-requires"]??{},C=o(E,p),q=C.status==="success"?{isValid:C.data.isValid,issues:C.data.issues}:{isValid:!1,issues:[C.status==="fail"?C.error:"internal error"]},F=p.source_defs??[],H=p.card_data??{},M=[],U=[];if(F.length>0){M=qr.enrichSourcesSync(F,{card_data:H,requires:x});for(let R of M){let K=R.projections,Z=R._projections;if(K&&Z){for(let ie of Object.keys(K))if(Z[ie]===void 0){let re=typeof R.bindTo=="string"?R.bindTo:"(unknown)";U.push({bindTo:re,key:ie,error:`Projection "${ie}" resolved to undefined`})}}}}let J=[],te={...j},W=g["task-executor-ref"],T=(W?.howToRun&&W?.whatToRun?W:void 0)??r().readTaskExecutorRef();for(let R=0;R<M.length;R++){let K=M[R],Z=typeof K.bindTo=="string"?K.bindTo:`source_${R}`;if(!T){J.push({bindTo:Z,skipped:!0,error:"No task executor configured"});continue}try{let ie={...K},re=t.invokeExecutorSync(T,"run-source-preflight",[],{timeout:K.timeout??t.executorTimeouts?.preflightMs??6e4,input:JSON.stringify(ie)}),be=JSON.parse(re.trim());be.ok&&!Object.prototype.hasOwnProperty.call(j,Z)&&Object.prototype.hasOwnProperty.call(be,"resultValue")&&(te[Z]=be.resultValue),J.push({bindTo:Z,reachable:be.reachable,latencyMs:be.latencyMs,error:be.ok?void 0:be.error})}catch{J.push({bindTo:Z,skipped:!0,error:"Executor does not support run-source-preflight"})}}let A=p.compute,V={},P=[];if(A&&Array.isArray(A)&&A.length>0){let R={id:E,card_data:H,requires:x,source_defs:p.source_defs,compute:A},K=qr.runSync(R,{sourcesData:te});V=K.node.computed_values??{},P=K.errors??[]}let O=q.isValid&&U.length===0&&P.length===0&&J.every(R=>R.reachable!==!1);return pe({cardId:E,ok:O,validation:q,source_probes:J,projection_errors:U,fetched_sources:te,computed_values:V,compute_errors:P})}catch(g){return me(g)}}return{validateCard:l,validateCardPreflight:d,probeSource:w,probeTmpSource:$,probeSourcePreflight:h,runSourcePreflight:v,evalCardCompute:y,simulateCardCycle:S,describeTaskExecutorCapabilities:m,updatesInCardStore:f,readFromCardStore:k}}var J_=".board.lock";function W_(e,t){return typeof e=="string"?{cliDir:e,opts:t}:{cliDir:void 0,opts:e}}function X_(e,t){return typeof e=="string"?{cliDir:e,opts:t}:{cliDir:void 0,opts:e}}function Pd(e){if(e)return e;let t=dd(import.meta.url),r=[t,Rt(t,"..","cli","node"),Rt(t,"..","..","cli","node")];for(let a of r)try{return hd(a),a}catch{}throw new Error(`createFsBoardPlatformAdapter: could not resolve a public CLI directory from module dir ${t}`)}function _a(e,t,r){let{cliDir:a,opts:n}=W_(t,r),s=Pd(a),o=e.value,u={meta:"board-live-cards",howToRun:"local-node",whatToRun:!n?.suppressSpawn&&hd(s)?ze({kind:"yaml-flow-cli",value:"board-live-cards-cli.js"}):"",...n?.notifyChannel?{extra:{notifyChannel:n.notifyChannel}}:{}};return{kvStorage:i=>Ml(Rt(o,`.${i}`)),blobStorage:i=>va(i?Rt(o,i):o),scratchStorage:()=>Lo(Rt(o,".tmp")),scratchStorageForRef:i=>Lo(ht(i).value),archiveFactory:()=>Ho(Rt(o,"archive")),archiveFactoryForRef:i=>Ho(ht(i).value),journalAdapter:()=>D0(o),lock:M0(Rt(o,J_)),selfRef:u,async dispatchExecution(i,c){if(n?.suppressSpawn)return{dispatched:!1};try{let l=c.source_def?.bindTo??Il().slice(0,8),d=Lo(Rt(o,".tmp")),w=d.create(JSON.stringify(c,null,2),`exec-in-${l}`,".json"),$=d.getUniqueKey(`exec-out-${l}`,".json"),h=d.getUniqueKey(`exec-err-${l}`,".txt"),v=ze(d.keyRef(w)),m=ze(d.keyRef($)),f=ze(d.keyRef(h));return O0(i,{subcommand:"run-source-fetch",inRef:v,outRef:m,errRef:f},s),{dispatched:!0}}catch(l){let d=l instanceof Error?l.message:String(l);try{let w=Ho(Rt(o,"archive")),$=new Date().toISOString().replace(/[:.]/g,"-"),h=c.source_def?.bindTo??"unknown";w.blob("exec-failures").write(`${$}-${h}.json`,JSON.stringify({error:d,args:c,ref:i,at:new Date().toISOString()},null,2))}catch{}return{dispatched:!1,error:d}}},resolveBlob(i){let c=u0(i.value)?yd().read(i.value):va(o).read(i.value);if(c===null)throw new Error(`resolveBlob: blob not found: ::${i.kind}::${i.value}`);return c},hashFn:q0,genId:()=>c0(`${Date.now()}-${Math.random()}`).slice(0,32),kvStorageForRef:i=>Ml(ht(i).value),requestProcessAccumulated(){n?.suppressSpawn||p0(s,e,n?.notifyChannel)},publishBoardChangeNotifications(i){if(!n?.notifyChannel||i.length===0)return;let c=i.map(l=>({id:Il(),ts:new Date().toISOString(),boardRef:ze(e),notification:l}));m0(n.notifyChannel,c,n.onWarn)},onWarn:n?.onWarn}}function cr(e,t,r){let{cliDir:a,opts:n}=X_(t,r),s=Pd(a),o=_a(e,s,n),u=y0();return{...o,invokeExecutorSync(i,c,l,d){let{command:w,baseArgs:$}=P0(i,s),h=i.extra?["--extra",Buffer.from(JSON.stringify(i.extra)).toString("base64")]:[];return u.executeSync(w,[...$,c,...l,...h],{timeout:d?.timeout??3e4,encoding:"utf-8",input:d?.input})},validateSchema(i){let c=J0(i);return{ok:c.errors.length===0,errors:c.errors}},absoluteBlob:yd()}}function Yl(e){try{let t=JSON.parse(Buffer.from(e,"base64url").toString());return typeof t.br=="string"?t.br:null}catch{return null}}var pt=dd(import.meta.url);function Ae(e,t,r){let a=e.indexOf(t),n=a!==-1?e[a+1]:void 0;if(!n)throw new Error(`Missing ${t}
29
29
  Usage: ${r}`);return n}function Je(e,t){let r=e.indexOf(t);return r!==-1?e[r+1]:void 0}function $e(e){console.log(JSON.stringify(e,null,2))}async function xt(){if(process.stdin.isTTY)return;let e=[];for await(let r of process.stdin)e.push(Buffer.isBuffer(r)?r:Buffer.from(r));let t=Buffer.concat(e).toString("utf-8").trim();if(t)return JSON.parse(t)}function Y_(e){return String(e||"").replace(/[^a-zA-Z0-9_-]/g,"_")||"unknown-card"}function Q_(e,t,r,a){if(!e)throw new Error("get-attachment-content requires --base-ref <ref>");let n=_a(e,pt,{onWarn:console.warn,notifyChannel:t}),s=ii(n.kvStorage("config")),o=s.readCardStoreRef();if(!o)throw new Error(`Board at ${e.value} has no card store configured`);let u=n.kvStorageForRef(o).read(r);if(!u)throw new Error(`Card "${r}" not found in board at ${e.value}`);let i=u.card_data&&typeof u.card_data=="object"&&!Array.isArray(u.card_data)?u.card_data:{},c=Array.isArray(i.files)?i.files:[],l=a===void 0?0:Number(a);if(!Number.isInteger(l)||l<0)throw new Error("get-attachment-content requires --file-idx to be a non-negative integer");if(l>=c.length)throw new Error(`attachment index ${l} is out of range for card "${r}"`);let d=c[l];if(!d||typeof d!="object"||Array.isArray(d))throw new Error(`attachment index ${l} for card "${r}" is not an object`);let w=d.stored_name;if(typeof w!="string"||!w)throw new Error(`attachment index ${l} for card "${r}" has no stored_name`);let $=`${Y_(r)}/${w}`,h=s.readArtifactsStoreRef();if(!h)throw new Error(`Board at ${e.value} has no artifacts store configured`);let v=va(ht(h).value).readBytes;if(!v)throw new Error("configured artifacts store does not support byte reads");let m=v($);if(m===null)throw new Error(`attachment content not found for key "${$}"`);return m}async function Z_(e){let t=e[0],r=e.slice(1);if(t==="help"||t==="--help"||t==="-h"){console.log("board-live-cards \u2014 see board-live-cards-cli-PARAMS.md for command reference");return}let a=Je(r,"--base-ref"),n=Je(r,"--notify-channel"),s=a?ht(a):void 0;if(t==="source-data-fetched"){let i=Ae(r,"--token","source-data-fetched --token <token> --ref <sourcefile>"),c=Ae(r,"--ref","source-data-fetched --token <token> --ref <sourcefile>"),l=Yl(i);if(!l)throw new Error("source-data-fetched: could not decode board ref from token \u2014 is this a valid source token?");let d=ht(l),w=Wo(d,_a(d,pt,{onWarn:console.warn,notifyChannel:n}));$e(w.sourceDataFetched({params:{token:i,ref:c}}));return}if(t==="source-data-fetch-failure"){let i=Ae(r,"--token","source-data-fetch-failure --token <token> [--reason <message>]"),c=Yl(i);if(!c)throw new Error("source-data-fetch-failure: could not decode board ref from token \u2014 is this a valid source token?");let l=ht(c),d=Wo(l,_a(l,pt,{onWarn:console.warn,notifyChannel:n})),w={token:i},$=Je(r,"--reason");$&&(w.reason=$),$e(d.sourceDataFetchFailure({params:w}));return}if(t==="validate-card-preflight"){let i=s??{kind:"fs-path",value:Kt(".")},c=ur(i,cr(i,pt,{onWarn:console.warn})),l=await xt();$e(c.validateCardPreflight({body:l}));return}if(t==="probe-source-preflight"){let i=Ae(r,"--source-idx","probe-source-preflight --source-idx <n>"),c=Je(r,"--out-ref"),l=s??{kind:"fs-path",value:Kt(".")},d=ur(l,cr(l,pt,{onWarn:console.warn})),w=await xt(),$={sourceIdx:parseInt(i,10)};c&&($.outRef=c),$e(d.probeSourcePreflight({params:$,body:w}));return}if(t==="run-source-preflight"){let i=Ae(r,"--source-idx","run-source-preflight --source-idx <n>"),c=Je(r,"--out-ref"),l=s??{kind:"fs-path",value:Kt(".")},d=ur(l,cr(l,pt,{onWarn:console.warn})),w=await xt(),$={sourceIdx:parseInt(i,10)};c&&($.outRef=c),$e(d.runSourcePreflight({params:$,body:w}));return}if(t==="eval-card-compute"){let i=s??{kind:"fs-path",value:Kt(".")},c=ur(i,cr(i,pt,{onWarn:console.warn})),l=await xt();$e(c.evalCardCompute({body:l}));return}if(t==="simulate-card-cycle"){let i=s??{kind:"fs-path",value:Kt(".")},c=ur(i,cr(i,pt,{onWarn:console.warn})),l=await xt();$e(c.simulateCardCycle({body:l}));return}if(t==="probe-tmp-source"){let i=Ae(r,"--out-ref","probe-tmp-source --out-ref <ref>"),c=s??{kind:"fs-path",value:Kt(".")},l=ur(c,cr(c,pt,{onWarn:console.warn})),d=await xt();$e(l.probeTmpSource({params:{outRef:i},body:d}));return}if(!s)throw new Error(`--base-ref is required for command "${t??"(none)"}"`);let o=()=>Wo(s,_a(s,pt,{onWarn:console.warn,notifyChannel:n})),u=()=>ur(s,cr(s,pt,{onWarn:console.warn}));switch(t){case"init":{let i=Ae(r,"--card-store-ref","init --base-ref <ref> --card-store-ref <b64-ref> --outputs-store-ref <b64-ref>"),c=Ae(r,"--outputs-store-ref","init --base-ref <ref> --card-store-ref <b64-ref> --outputs-store-ref <b64-ref>"),l=Je(r,"--scratch-store-ref"),d=Je(r,"--archive-store-ref"),w=Je(r,"--artifacts-store-ref"),$=await xt();$e(o().init({params:{cardStoreRef:i,outputsStoreRef:c,...l?{scratchStoreRef:l}:{},...d?{archiveStoreRef:d}:{},...w?{artifactsStoreRef:w}:{}},body:$}));return}case"status":{$e(o().status({}));return}case"get-card-store-ref":{$e(o().getCardStoreRef({}));return}case"get-outputs-store-ref":{$e(o().getOutputsStoreRef({}));return}case"get-scratch-store-ref":{$e(o().getScratchStoreRef({}));return}case"get-archive-store-ref":{$e(o().getArchiveStoreRef({}));return}case"get-chat-store-ref":{$e(o().getChatStoreRef({}));return}case"get-artifacts-store-ref":{$e(o().getArtifactsStoreRef({}));return}case"get-outputs":{let i=Ae(r,"--type","get-outputs --base-ref <ref> --type <data-object|computed-values> [--key <key>] [--all]"),c=r.includes("--all");if(i==="data-object")if(c)$e(o().getAllOutputsDataObjects({}));else{let l=Ae(r,"--key","get-outputs --type data-object --base-ref <ref> --key <datakey>");$e(o().getOutputsDataObject({params:{key:l}}))}else if(i==="computed-values")if(c)$e(o().getAllOutputsComputedValues({}));else{let l=Ae(r,"--key","get-outputs --type computed-values --base-ref <ref> --key <card-id>");$e(o().getOutputsComputedValues({params:{key:l}}))}else if(i==="fetched_sources")if(c)$e(o().getAllOutputsFetchedSources({}));else{let l=Ae(r,"--key","get-outputs --type fetched_sources --base-ref <ref> --key <card-id>");$e(o().getOutputsFetchedSources({params:{key:l}}))}else throw new Error(`get-outputs: unknown --type "${i}", expected data-object | computed-values | fetched_sources`);return}case"remove-card":{let i=Ae(r,"--id","remove-card --base-ref <ref> --id <card-id>");$e(o().removeCard({params:{id:i}}));return}case"add-card-files":{let i=Ae(r,"--card-id","add-card-files --base-ref <ref> --card-id <card-id> [--value-json <json>]"),c=Je(r,"--value-json"),l=c?JSON.parse(c):await xt();$e(o().addCardFiles({params:{cardId:i},body:l}));return}case"get-attachment-content":{let i=Ae(r,"--card-id","get-attachment-content --base-ref <ref> --card-id <card-id> [--file-idx <n>]"),c=Je(r,"--file-idx");process.stdout.write(Buffer.from(Q_(s,n,i,c)));return}case"card-refreshed-notify":{let i=Ae(r,"--card-id","card-refreshed-notify --base-ref <ref> --card-id <card-id>");$e(o().cardRefreshedNotify({params:{cardId:i}}));return}case"retrigger":{let i=Ae(r,"--id","retrigger --base-ref <ref> --id <card-id>");$e(o().retrigger({params:{id:i}}));return}case"process-accumulated-events":{$e(await o().processAccumulatedEvents({}));return}case"upsert-card":{let i=Je(r,"--card-id"),c=r.includes("--all"),l=r.includes("--restart");if(!i&&!c)throw new Error("upsert-card requires --card-id <id> or --all");let d={};i&&(d.cardId=i),c&&(d.all=!0),l&&(d.restart=!0),$e(o().upsertCard({params:d}));return}case"task-failed":{let i={token:Ae(r,"--token","task-failed --base-ref <ref> --token <token> [--error <message>]")},c=Je(r,"--error");c&&(i.error=c),$e(o().taskFailed({params:i}));return}case"task-progress":{let i=Ae(r,"--token","task-progress --base-ref <ref> --token <token> [--update <json>]"),c=Je(r,"--update"),l=c?JSON.parse(c):{};$e(o().taskProgress({params:{token:i},body:{update:l}}));return}case"validate-card":{let i=Je(r,"--card-id"),c=r.includes("--all");if(!i&&!c)throw new Error("validate-card requires --card-id <id> or --all");let l={};i&&(l.cardId=i),c&&(l.all=!0),$e(u().validateCard({params:l}));return}case"probe-source":{let i=Ae(r,"--card-id","probe-source --base-ref <ref> --card-id <id> --source-idx <n> --out-ref <ref>"),c=Ae(r,"--source-idx","probe-source --base-ref <ref> --card-id <id> --source-idx <n> --out-ref <ref>"),l=Je(r,"--out-ref"),d=await xt(),w={cardId:i,sourceIdx:parseInt(c,10)};l&&(w.outRef=l),$e(u().probeSource({params:w,body:d}));return}case"describe-task-executor-capabilities":{$e(u().describeTaskExecutorCapabilities({}));return}default:throw new Error(`Unknown command: ${t??"(none)"}`)}}var e$=process.argv[1]&&Kt(process.argv[1])===Kt(new URL(import.meta.url).pathname.replace(/^\/([A-Z]:)/,"$1"));e$&&Z_(process.argv.slice(2)).catch(e=>{let t=e instanceof Error?e.message:String(e);console.error(t),process.exit(1)});export{Z_ as cli};
@@ -19,8 +19,8 @@
19
19
  <script src="https://cdn.jsdelivr.net/npm/marked/marked.min.js"></script>
20
20
  <script src="https://cdn.jsdelivr.net/npm/dompurify/dist/purify.min.js"></script>
21
21
  <script src="https://cdn.jsdelivr.net/npm/leader-line/leader-line.min.js"></script>
22
- <script src="https://cdn.jsdelivr.net/npm/yaml-flow@8.5.2/browser/live-cards.js"></script>
23
- <script src="https://cdn.jsdelivr.net/npm/yaml-flow@8.5.2/browser/board-livecards-client.js"></script>
22
+ <script src="https://cdn.jsdelivr.net/npm/yaml-flow@8.5.3/browser/live-cards.js"></script>
23
+ <script src="https://cdn.jsdelivr.net/npm/yaml-flow@8.5.3/browser/board-livecards-client.js"></script>
24
24
  </head>
25
25
  <body class="bg-light">
26
26
  <div class="container-fluid py-3">
@@ -37,8 +37,8 @@
37
37
  <script src="https://cdn.jsdelivr.net/npm/marked/marked.min.js"></script>
38
38
  <script src="https://cdn.jsdelivr.net/npm/dompurify/dist/purify.min.js"></script>
39
39
  <script src="https://cdn.jsdelivr.net/npm/leader-line/leader-line.min.js"></script>
40
- <script src="https://cdn.jsdelivr.net/npm/yaml-flow@8.5.2/browser/live-cards.js"></script>
41
- <script src="https://cdn.jsdelivr.net/npm/yaml-flow@8.5.2/browser/board-livecards-client.js"></script>
40
+ <script src="https://cdn.jsdelivr.net/npm/yaml-flow@8.5.3/browser/live-cards.js"></script>
41
+ <script src="https://cdn.jsdelivr.net/npm/yaml-flow@8.5.3/browser/board-livecards-client.js"></script>
42
42
  </head>
43
43
  <body class="bg-light">
44
44
  <div class="container-fluid py-3">
@@ -262,9 +262,9 @@ Validates, stores, and registers a card definition. Triggers a board restart for
262
262
 
263
263
  ---
264
264
 
265
- ### `manage.deprecate`
265
+ ### `manage.remove-card`
266
266
 
267
- Removes a card from the board.
267
+ Removes a card from both the live board runtime and persistent card storage.
268
268
 
269
269
  **Args:**
270
270
 
@@ -272,11 +272,21 @@ Removes a card from the board.
272
272
  |---|---|---|
273
273
  | `card_id` | string | yes |
274
274
 
275
- **Returns:** the `board.removeCard` result normalized into the MCP success envelope. On success:
275
+ **Returns:** the card removal result. On success:
276
276
  ```json
277
- { "status": "success", "data": {} }
277
+ {
278
+ "status": "success",
279
+ "data": {
280
+ "board_result": { "status": "success" },
281
+ "store_result": { "status": "success", "data": { "count": 1 } }
282
+ }
283
+ }
278
284
  ```
279
285
 
286
+ > **Behavior notes:**
287
+ > - The card is fully removed from persistent storage. `readAll` will not return it after removal.
288
+ > - Re-upserting a card with the same `card_id` after removal creates a fresh card with no prior state.
289
+
280
290
  ---
281
291
 
282
292
  ### `manage.upload-card-file`