@crewx/sdk 0.9.0-rc.57 → 0.9.0-rc.59

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (40) hide show
  1. package/dist/config/migrate-grok-mode.d.ts +6 -0
  2. package/dist/config/models.generated.d.ts +12 -2
  3. package/dist/config/overdrive.d.ts +2 -0
  4. package/dist/config/pricing.generated.d.ts +2 -2
  5. package/dist/conversation/index.d.ts +1 -1
  6. package/dist/conversation/to-template-messages.d.ts +7 -0
  7. package/dist/conversation/types.d.ts +1 -0
  8. package/dist/esm/index.js +221 -147
  9. package/dist/esm/plugins/index.js +85 -72
  10. package/dist/esm/repository/index.js +92 -79
  11. package/dist/esm/testing/index.js +1 -1
  12. package/dist/facade/Crewx.d.ts +2 -0
  13. package/dist/index.browser.js +4 -4
  14. package/dist/index.d.ts +8 -1
  15. package/dist/index.js +221 -147
  16. package/dist/migrations/0014_organic_mongu.sql +73 -0
  17. package/dist/migrations/meta/0014_snapshot.json +1975 -0
  18. package/dist/migrations/meta/_journal.json +7 -0
  19. package/dist/plugins/index.js +85 -72
  20. package/dist/provider/acp/meta.d.ts +2 -0
  21. package/dist/provider/bridge.d.ts +1 -0
  22. package/dist/provider/cli/adapters/cli-knob.util.d.ts +2 -0
  23. package/dist/provider/models.d.ts +1 -1
  24. package/dist/repository/index.js +92 -79
  25. package/dist/repository/task.repository.d.ts +1 -0
  26. package/dist/schema/index.d.ts +2 -0
  27. package/dist/schema/ui-action-receipts.d.ts +303 -0
  28. package/dist/schema/ui-instances.d.ts +267 -0
  29. package/dist/testing/index.js +1 -1
  30. package/dist/types/index.d.ts +2 -0
  31. package/dist/ui-card/index.d.ts +2 -0
  32. package/dist/ui-card/legacy-card-parser.d.ts +11 -0
  33. package/dist/ui-instance/definition.d.ts +6 -0
  34. package/dist/ui-instance/errors.d.ts +17 -0
  35. package/dist/ui-instance/index.d.ts +6 -0
  36. package/dist/ui-instance/json.d.ts +5 -0
  37. package/dist/ui-instance/runtime.d.ts +13 -0
  38. package/dist/ui-instance/store.d.ts +65 -0
  39. package/dist/ui-instance/types.d.ts +200 -0
  40. package/package.json +1 -1
@@ -1,19 +1,52 @@
1
- import*as F from'path';import F__default,{join,dirname}from'path';import {fileURLToPath}from'url';import {existsSync,mkdirSync,writeFileSync,appendFileSync,readFileSync}from'fs';import ae,{homedir}from'os';import {createHash}from'crypto';import {sql,eq,desc,and,isNull,lt,or,notLike,like,asc,inArray,gte,isNotNull,ne}from'drizzle-orm';import {sqliteTable,text,integer,real,index,unique,uniqueIndex,primaryKey}from'drizzle-orm/sqlite-core';var dt=(d=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(d,{get:(t,n)=>(typeof require<"u"?require:t)[n]}):d)(function(d){if(typeof require<"u")return require.apply(this,arguments);throw Error('Dynamic require of "'+d+'" is not supported')});var Qt=()=>fileURLToPath(import.meta.url),Zt=()=>F__default.dirname(Qt()),k=Zt();var j=class{detach(t){}};function Ot(d){let t=n=>String(n).padStart(2,"0");return `${d.getFullYear()}${t(d.getMonth()+1)}${t(d.getDate())}T${t(d.getHours())}${t(d.getMinutes())}${t(d.getSeconds())}`}function wt(d){let t=d.toISOString();return `${t.slice(0,10)} ${t.slice(11,19)} UTC`}var Et=class extends j{name="file-logger";unsubs=[];logFiles=new Map;logsDir;version;constructor(t){super(),this.logsDir=join(t?.workspaceRoot??process.cwd(),".crewx","logs"),this.version=t?.version??"unknown";}attach(t){this.unsubs.push(t.on("task:start",n=>{try{existsSync(this.logsDir)||mkdirSync(this.logsDir,{recursive:!0});let s=Ot(n.timestamp),r=join(this.logsDir,`${s}_${n.traceId}.log`);this.logFiles.set(n.traceId,r);let o=`=== TASK LOG: ${n.traceId} ===
1
+ import*as J from'path';import J__default,{join,dirname}from'path';import {fileURLToPath}from'url';import {existsSync,mkdirSync,writeFileSync,appendFileSync,readFileSync}from'fs';import me,{homedir}from'os';import {createHash}from'crypto';import {sql,eq,desc,and,isNull,lt,or,notLike,like,asc,inArray,gte,isNotNull,ne}from'drizzle-orm';import {sqliteTable,text,integer,real,index,unique,uniqueIndex,primaryKey,check}from'drizzle-orm/sqlite-core';var gt=(o=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(o,{get:(t,n)=>(typeof require<"u"?require:t)[n]}):o)(function(o){if(typeof require<"u")return require.apply(this,arguments);throw Error('Dynamic require of "'+o+'" is not supported')});var de=()=>fileURLToPath(import.meta.url),ce=()=>J__default.dirname(de()),k=ce();var Q=class{detach(t){}};function Ut(o){let t=n=>String(n).padStart(2,"0");return `${o.getFullYear()}${t(o.getMonth()+1)}${t(o.getDate())}T${t(o.getHours())}${t(o.getMinutes())}${t(o.getSeconds())}`}function Nt(o){let t=o.toISOString();return `${t.slice(0,10)} ${t.slice(11,19)} UTC`}var Ct=class extends Q{name="file-logger";unsubs=[];logFiles=new Map;logsDir;version;constructor(t){super(),this.logsDir=join(t?.workspaceRoot??process.cwd(),".crewx","logs"),this.version=t?.version??"unknown";}attach(t){this.unsubs.push(t.on("task:start",n=>{try{existsSync(this.logsDir)||mkdirSync(this.logsDir,{recursive:!0});let s=Ut(n.timestamp),r=join(this.logsDir,`${s}_${n.traceId}.log`);this.logFiles.set(n.traceId,r);let i=`=== TASK LOG: ${n.traceId} ===
2
2
  CrewX Version: ${this.version}
3
3
  Mode: ${n.mode}
4
4
  Agent: ${n.agentRef}
5
- Started: ${wt(n.timestamp)}
5
+ Started: ${Nt(n.timestamp)}
6
6
  Message: ${n.message}
7
7
 
8
- `;writeFileSync(r,o,{encoding:"utf8",mode:384});}catch{}}),t.on("task:output",n=>{try{let s=this.logFiles.get(n.traceId);if(!s)return;let r=new Date().toISOString();appendFileSync(s,`[${r}] STDOUT: ${n.output}
9
- `,"utf8");}catch{}}),t.on("task:end",n=>{try{let s=this.logFiles.get(n.traceId);if(!s)return;let r=wt(new Date),o=n.error?`failed: ${n.error.message}`:"completed successfully",i=`[${r}] INFO: Task ${o} in ${n.durationMs}ms
8
+ `;writeFileSync(r,i,{encoding:"utf8",mode:384});}catch{}}),t.on("task:output",n=>{try{let s=this.logFiles.get(n.traceId);if(!s)return;let r=new Date().toISOString();appendFileSync(s,`[${r}] STDOUT: ${n.output}
9
+ `,"utf8");}catch{}}),t.on("task:end",n=>{try{let s=this.logFiles.get(n.traceId);if(!s)return;let r=Nt(new Date),i=n.error?`failed: ${n.error.message}`:"completed successfully",a=`[${r}] INFO: Task ${i} in ${n.durationMs}ms
10
10
  [${r}] INFO: Process closed with exit code: ${n.error?1:0}
11
- `;appendFileSync(s,i,"utf8"),this.logFiles.delete(n.traceId);}catch{}}));}detach(t){this.unsubs.forEach(n=>n()),this.unsubs=[],this.logFiles.clear();}};function re(d){let t=F.resolve(d);return process.platform==="win32"&&(t=t.replace(/\\/g,"/"),t=t.replace(/^([A-Z]):/,(n,s)=>`${s.toLowerCase()}:`)),t.length>1&&!/^[a-zA-Z]:\/$/.test(t)&&(t=t.replace(/\/+$/,"")),t}function $t(d){let t=re(d);return createHash("sha256").update(t).digest("hex")}var nt=class{resolveDbPath(){return process.env.CREWX_DB?process.env.CREWX_DB:process.env.CREWX_TRACES_DB?process.env.CREWX_TRACES_DB:join(ae.homedir(),".crewx","crewx.db")}resolveDbPaths(){return [this.resolveDbPath()]}isMissingTableError(t){return t instanceof Error&&/no such table:/i.test(t.message)}dbExists(t){return existsSync(t??this.resolveDbPath())}};function b(d){let t=dt("better-sqlite3"),{drizzle:n}=dt("drizzle-orm/better-sqlite3"),s=new t(d);return s.exec("PRAGMA journal_mode = WAL"),s.exec("PRAGMA busy_timeout = 5000"),s.exec("PRAGMA foreign_keys = ON"),s.exec("PRAGMA analysis_limit = 400"),s.exec("PRAGMA optimize"),{db:n(s),runRaw:(r,o=[])=>s.prepare(r).run(...o),close:()=>s.close()}}var Lt=new Set,de={agent_id:"TEXT",status:"TEXT DEFAULT 'running'",started_at:"TEXT",trace_id:"TEXT",parent_task_id:"TEXT",crewx_version:"TEXT",pid:"INTEGER",thread_id:"TEXT",workspace_id:"TEXT",workspace_ref:"TEXT",workspace_name:"TEXT",project_id:"TEXT",project_name:"TEXT"};function St(d,t){return (d.get(`SELECT count(*) as cnt FROM sqlite_master WHERE type='table' AND name='${t}'`)?.cnt??0)>0}function le(d,t){if(t>0||!St(d,"tasks"))return;let n=d.all("PRAGMA table_info(tasks)"),s=new Set(n.map(r=>r.name));for(let[r,o]of Object.entries(de))s.has(r)||d.run(`ALTER TABLE tasks ADD COLUMN ${r} ${o}`);}var ce={"0002_normalize_task_names":{workspace_name:"TEXT",project_name:"TEXT"}};function ue(d,t,n){if(!St(d,"__drizzle_migrations")||!St(d,"tasks"))return;let s=d.all(n`SELECT hash FROM __drizzle_migrations`),r=new Set(s.map(i=>i.hash)),o=JSON.parse(readFileSync(F__default.join(t,"meta/_journal.json"),"utf-8"));for(let i of o.entries){let a=ce[i.tag];if(!a)continue;let c=F__default.join(t,`${i.tag}.sql`);if(!existsSync(c))continue;let l=readFileSync(c,"utf-8"),u=createHash("sha256").update(l).digest("hex");if(r.has(u))continue;let h=d.all("PRAGMA table_info(tasks)"),g=new Set(h.map(y=>y.name));for(let[y,C]of Object.entries(a))g.has(y)||(d.run(`ALTER TABLE tasks ADD COLUMN ${y} ${C}`),g.add(y));}}function pe(d,t,n){let s=d.all(n`SELECT hash FROM __drizzle_migrations`),r=new Set(s.map(i=>i.hash)),o=JSON.parse(readFileSync(F__default.join(t,"meta/_journal.json"),"utf-8"));for(let i of o.entries){let a=F__default.join(t,`${i.tag}.sql`);if(!existsSync(a))continue;let c=readFileSync(a,"utf-8"),l=createHash("sha256").update(c).digest("hex");if(r.has(l))continue;let u=/ALTER\s+TABLE\s+[`"]?(\w+)[`"]?\s+ADD\s+[`"]?(\w+)[`"]?/gi,h=[],g;for(;(g=u.exec(c))!==null;)h.push({table:g[1],column:g[2]});if(h.length===0||!c.split(/-->\s*statement-breakpoint/).map(N=>N.trim()).filter(Boolean).every(N=>/^ALTER\s+TABLE\s+.+\s+ADD\s+/i.test(N)))continue;h.every(({table:N,column:$})=>d.all(`PRAGMA table_info("${N}")`).some(B=>B.name===$))&&d.run(n`INSERT INTO __drizzle_migrations (hash, created_at) VALUES (${l}, ${i.when})`);}}function _e(d){let{migrate:t}=dt("drizzle-orm/better-sqlite3/migrator"),{sql:n}=dt("drizzle-orm"),s=[F__default.join(k,"../migrations"),F__default.join(k,"migrations"),F__default.join(k,"../../../../drizzle/migrations"),F__default.join(process.cwd(),"drizzle/migrations")],r=s.find(l=>existsSync(F__default.join(l,"meta/_journal.json")));if(!r)throw new Error(`migrations folder not found. Searched:
11
+ `;appendFileSync(s,a,"utf8"),this.logFiles.delete(n.traceId);}catch{}}));}detach(t){this.unsubs.forEach(n=>n()),this.unsubs=[],this.logFiles.clear();}};function he(o){let t=J.resolve(o);return process.platform==="win32"&&(t=t.replace(/\\/g,"/"),t=t.replace(/^([A-Z]):/,(n,s)=>`${s.toLowerCase()}:`)),t.length>1&&!/^[a-zA-Z]:\/$/.test(t)&&(t=t.replace(/\/+$/,"")),t}function qt(o){let t=he(o);return createHash("sha256").update(t).digest("hex")}var dt=class{resolveDbPath(){return process.env.CREWX_DB?process.env.CREWX_DB:process.env.CREWX_TRACES_DB?process.env.CREWX_TRACES_DB:join(me.homedir(),".crewx","crewx.db")}resolveDbPaths(){return [this.resolveDbPath()]}isMissingTableError(t){return t instanceof Error&&/no such table:/i.test(t.message)}dbExists(t){return existsSync(t??this.resolveDbPath())}};function y(o){let t=gt("better-sqlite3"),{drizzle:n}=gt("drizzle-orm/better-sqlite3"),s=new t(o);return s.exec("PRAGMA journal_mode = WAL"),s.exec("PRAGMA busy_timeout = 5000"),s.exec("PRAGMA foreign_keys = ON"),s.exec("PRAGMA analysis_limit = 400"),s.exec("PRAGMA optimize"),{db:n(s),runRaw:(r,i=[])=>s.prepare(r).run(...i),close:()=>s.close()}}var jt=new Set,ke={agent_id:"TEXT",status:"TEXT DEFAULT 'running'",started_at:"TEXT",trace_id:"TEXT",parent_task_id:"TEXT",crewx_version:"TEXT",pid:"INTEGER",thread_id:"TEXT",workspace_id:"TEXT",workspace_ref:"TEXT",workspace_name:"TEXT",project_id:"TEXT",project_name:"TEXT"};function Dt(o,t){return (o.get(`SELECT count(*) as cnt FROM sqlite_master WHERE type='table' AND name='${t}'`)?.cnt??0)>0}function we(o,t){if(t>0||!Dt(o,"tasks"))return;let n=o.all("PRAGMA table_info(tasks)"),s=new Set(n.map(r=>r.name));for(let[r,i]of Object.entries(ke))s.has(r)||o.run(`ALTER TABLE tasks ADD COLUMN ${r} ${i}`);}var Ee={"0002_normalize_task_names":{workspace_name:"TEXT",project_name:"TEXT"}};function Se(o,t,n){if(!Dt(o,"__drizzle_migrations")||!Dt(o,"tasks"))return;let s=o.all(n`SELECT hash FROM __drizzle_migrations`),r=new Set(s.map(a=>a.hash)),i=JSON.parse(readFileSync(J__default.join(t,"meta/_journal.json"),"utf-8"));for(let a of i.entries){let d=Ee[a.tag];if(!d)continue;let u=J__default.join(t,`${a.tag}.sql`);if(!existsSync(u))continue;let c=readFileSync(u,"utf-8"),l=createHash("sha256").update(c).digest("hex");if(r.has(l))continue;let h=o.all("PRAGMA table_info(tasks)"),m=new Set(h.map(w=>w.name));for(let[w,$]of Object.entries(d))m.has(w)||(o.run(`ALTER TABLE tasks ADD COLUMN ${w} ${$}`),m.add(w));}}function Te(o,t,n){let s=o.all(n`SELECT hash FROM __drizzle_migrations`),r=new Set(s.map(a=>a.hash)),i=JSON.parse(readFileSync(J__default.join(t,"meta/_journal.json"),"utf-8"));for(let a of i.entries){let d=J__default.join(t,`${a.tag}.sql`);if(!existsSync(d))continue;let u=readFileSync(d,"utf-8"),c=createHash("sha256").update(u).digest("hex");if(r.has(c))continue;let l=/ALTER\s+TABLE\s+[`"]?(\w+)[`"]?\s+ADD\s+[`"]?(\w+)[`"]?/gi,h=[],m;for(;(m=l.exec(u))!==null;)h.push({table:m[1],column:m[2]});if(h.length===0||!u.split(/-->\s*statement-breakpoint/).map(v=>v.trim()).filter(Boolean).every(v=>/^ALTER\s+TABLE\s+.+\s+ADD\s+/i.test(v)))continue;h.every(({table:v,column:B})=>o.all(`PRAGMA table_info("${v}")`).some(G=>G.name===B))&&o.run(n`INSERT INTO __drizzle_migrations (hash, created_at) VALUES (${c}, ${a.when})`);}}function Re(o){let{migrate:t}=gt("drizzle-orm/better-sqlite3/migrator"),{sql:n}=gt("drizzle-orm"),s=[J__default.join(k,"../migrations"),J__default.join(k,"migrations"),J__default.join(k,"../../../../drizzle/migrations"),J__default.join(process.cwd(),"drizzle/migrations")],r=s.find(c=>existsSync(J__default.join(c,"meta/_journal.json")));if(!r)throw new Error(`migrations folder not found. Searched:
12
12
  ${s.join(`
13
- `)}`);let o=d.get(n`SELECT count(*) as cnt FROM sqlite_master WHERE type='table' AND name='__drizzle_migrations'`),i=0;o?.cnt&&(i=d.get(n`SELECT count(*) as cnt FROM __drizzle_migrations`)?.cnt??0),le(d,i),o?.cnt&&(pe(d,r,n),ue(d,r,n)),t(d,{migrationsFolder:r});let c=(d.get(n`SELECT count(*) as cnt FROM __drizzle_migrations`)?.cnt??0)-i;if(c>0){let l=o?.cnt?"Database migrated":"Database initialized";console.error(`[crewx] ${l} (${c} migration${c>1?"s":""} applied).`);}}function ct(d,t){Lt.has(t)||(_e(d),Lt.add(t));}var _=class extends Error{code;cause;constructor(t,n,s){super(n),this.name="RepositoryError",this.code=t,this.cause=s,Object.setPrototypeOf(this,new.target.prototype);}};var st=sqliteTable("workspaces",{id:text("id").primaryKey(),slug:text("slug").notNull().unique(),name:text("name").notNull(),workspace_path:text("workspace_path"),description:text("description"),is_active:integer("is_active").notNull().default(1),created_at:text("created_at").notNull(),updated_at:text("updated_at").notNull()});var e=sqliteTable("tasks",{id:text("id").primaryKey(),agent_id:text("agent_id").notNull(),user_id:text("user_id"),prompt:text("prompt").notNull(),mode:text("mode").notNull().default("execute"),status:text("status").notNull().default("running"),result:text("result"),error:text("error"),started_at:text("started_at").notNull(),completed_at:text("completed_at"),duration_ms:integer("duration_ms"),metadata:text("metadata"),workspace_id:text("workspace_id"),trace_id:text("trace_id"),parent_task_id:text("parent_task_id"),caller_agent_id:text("caller_agent_id"),model:text("model"),platform:text("platform").default("cli"),crewx_version:text("crewx_version"),input_tokens:integer("input_tokens").default(0),output_tokens:integer("output_tokens").default(0),cost_usd:real("cost_usd").default(0),pid:integer("pid"),rendered_prompt:text("rendered_prompt"),command:text("command"),coding_agent_command:text("coding_agent_command"),exit_code:integer("exit_code"),logs:text("logs"),thread_id:text("thread_id"),workspace_ref:text("workspace_ref"),project_id:text("project_id"),project_ref:text("project_ref"),cached_input_tokens:integer("cached_input_tokens").default(0),run_epoch:integer("run_epoch").default(0)},d=>({idx_tasks_agent_id:index("idx_tasks_agent_id").on(d.agent_id),idx_tasks_status:index("idx_tasks_status").on(d.status),idx_tasks_started_at:index("idx_tasks_started_at").on(d.started_at),idx_tasks_trace_id:index("idx_tasks_trace_id").on(d.trace_id),idx_tasks_parent_task_id:index("idx_tasks_parent_task_id").on(d.parent_task_id),idx_tasks_crewx_version:index("idx_tasks_crewx_version").on(d.crewx_version),idx_tasks_pid:index("idx_tasks_pid").on(d.pid),idx_tasks_thread_id:index("idx_tasks_thread_id").on(d.thread_id),idx_tasks_workspace_id:index("idx_tasks_workspace_id").on(d.workspace_id),idx_tasks_workspace_ref:index("idx_tasks_workspace_ref").on(d.workspace_ref),idx_tasks_project_id:index("idx_tasks_project_id").on(d.project_id),idx_tasks_ws_started:index("idx_tasks_ws_started").on(d.workspace_id,d.started_at)}));var p=sqliteTable("threads",{id:text("id").primaryKey(),workspace_id:text("workspace_id").references(()=>st.id,{onDelete:"set null"}),platform:text("platform").notNull().default("cli"),title:text("title"),first_message:text("first_message"),last_message:text("last_message"),message_count:integer("message_count").notNull().default(0),created_at:text("created_at").notNull(),updated_at:text("updated_at").notNull(),metadata:text("metadata"),title_locked:integer("title_locked").notNull().default(0),pinned:integer("pinned").notNull().default(0),starred:integer("starred").notNull().default(0)},d=>({idx_threads_updated_at:index("idx_threads_updated_at").on(d.updated_at),idx_threads_workspace_id:index("idx_threads_workspace_id").on(d.workspace_id),idx_threads_ws_updated:index("idx_threads_ws_updated").on(d.workspace_id,d.updated_at),idx_threads_title:index("idx_threads_title").on(d.title)}));var Se=sqliteTable("spans",{id:text("id").primaryKey(),task_id:text("task_id").references(()=>e.id,{onDelete:"set null"}),parent_span_id:text("parent_span_id").references(()=>Se.id,{onDelete:"set null"}),name:text("name").notNull(),kind:text("kind").notNull().default("internal"),status:text("status").notNull().default("ok"),started_at:text("started_at").notNull(),completed_at:text("completed_at"),duration_ms:integer("duration_ms"),input:text("input"),output:text("output"),error:text("error"),attributes:text("attributes")},d=>({idx_spans_task_id:index("idx_spans_task_id").on(d.task_id),idx_spans_parent_span_id:index("idx_spans_parent_span_id").on(d.parent_span_id)}));sqliteTable("tool_calls",{id:text("id").primaryKey(),task_id:text("task_id").references(()=>e.id,{onDelete:"cascade"}),session_id:text("session_id"),tool_name:text("tool_name").notNull(),files:text("files"),input:text("input"),output:text("output"),duration_ms:integer("duration_ms"),timestamp:text("timestamp").notNull()},d=>({idx_tool_calls_task_id:index("idx_tool_calls_task_id").on(d.task_id),idx_tool_calls_tool_name:index("idx_tool_calls_tool_name").on(d.tool_name),idx_tool_calls_timestamp:index("idx_tool_calls_timestamp").on(d.timestamp)}));sqliteTable("thread_boxes",{id:text("id").primaryKey(),thread_id:text("thread_id").notNull().references(()=>p.id,{onDelete:"cascade"}),seq:integer("seq").notNull(),first_task_id:text("first_task_id").notNull(),mid_task_id:text("mid_task_id").notNull(),last_task_id:text("last_task_id").notNull(),task_count:integer("task_count").notNull(),summary:text("summary"),source_tokens:integer("source_tokens").notNull(),summary_tokens:integer("summary_tokens"),created_at:text("created_at").notNull()},d=>({idx_thread_boxes_thread_id:index("idx_thread_boxes_thread_id").on(d.thread_id),idx_thread_boxes_seq:index("idx_thread_boxes_seq").on(d.thread_id,d.seq),uniq_thread_boxes_thread_seq:unique().on(d.thread_id,d.seq)}));sqliteTable("request_logs",{id:text("id").primaryKey(),path:text("path").notNull(),method:text("method").notNull(),status_code:integer("status_code").notNull(),duration_ms:integer("duration_ms").notNull(),ip:text("ip"),request_headers:text("request_headers"),response_headers:text("response_headers"),request_body:text("request_body"),response_body:text("response_body"),query:text("query"),user_id:text("user_id"),project_id:text("project_id"),partition_key:text("partition_key").notNull(),timestamp:text("timestamp").notNull().default(sql`(datetime('now'))`),metadata:text("metadata")},d=>({idx_request_logs_timestamp:index("idx_request_logs_timestamp").on(d.timestamp),idx_request_logs_path:index("idx_request_logs_path").on(d.path),idx_request_logs_status_code:index("idx_request_logs_status_code").on(d.status_code),idx_request_logs_partition_key:index("idx_request_logs_partition_key").on(d.partition_key)}));sqliteTable("usage_limit_snapshots",{id:text("id").primaryKey(),provider:text("provider").notNull(),account_ref:text("account_ref").notNull().default("default"),limit_window:text("limit_window").notNull(),bucket_start:text("bucket_start").notNull(),captured_at:text("captured_at").notNull(),used_percent:integer("used_percent").notNull(),remaining_percent:integer("remaining_percent").notNull(),resets_at:text("resets_at"),source:text("source").notNull(),metadata:text("metadata")},d=>({uniq_usage_limit_snapshots_bucket:uniqueIndex("uniq_usage_limit_snapshots_bucket").on(d.provider,d.account_ref,d.limit_window,d.bucket_start),idx_usage_limit_snapshots_window_bucket:index("idx_usage_limit_snapshots_window_bucket").on(d.limit_window,d.bucket_start),idx_usage_limit_snapshots_provider_window_bucket:index("idx_usage_limit_snapshots_provider_window_bucket").on(d.provider,d.limit_window,d.bucket_start)}));sqliteTable("usage_reports",{id:text("id").primaryKey(),workspace_id:text("workspace_id").notNull(),month:text("month").notNull(),generated_at:text("generated_at").notNull(),source_range:text("source_range").notNull(),tier:text("tier").notNull(),total_tokens:integer("total_tokens").notNull(),total_cost_usd:real("total_cost_usd").notNull(),payload:text("payload").notNull(),payload_hash:text("payload_hash"),signature:text("signature"),signed_at:text("signed_at"),issuer:text("issuer")},d=>({uniq_usage_reports_ws_month:uniqueIndex("uniq_usage_reports_ws_month").on(d.workspace_id,d.month)}));sqliteTable("notifications",{id:text("id").primaryKey(),workspace_id:text("workspace_id").notNull(),agent_id:text("agent_id"),task_id:text("task_id"),thread_id:text("thread_id"),source:text("source").notNull().default("agent"),level:text("level").notNull().default("info"),title:text("title").notNull(),body:text("body"),target_user_id:text("target_user_id"),created_at:text("created_at").notNull(),metadata:text("metadata")},d=>({idx_notifications_ws_created:index("idx_notifications_ws_created").on(d.workspace_id,sql`${d.created_at} DESC`)}));sqliteTable("notification_reads",{notification_id:text("notification_id").notNull(),user_id:text("user_id").notNull(),read_at:text("read_at").notNull()},d=>({pk:primaryKey({columns:[d.notification_id,d.user_id]})}));sqliteTable("agent_suggestions",{id:text("id").primaryKey(),workspace_id:text("workspace_id").notNull(),agent_id:text("agent_id").notNull(),task_id:text("task_id"),type:text("type").notNull(),status:text("status").notNull().default("pending"),payload:text("payload").notNull(),applied_commit_sha:text("applied_commit_sha"),created_at:text("created_at").notNull(),updated_at:text("updated_at").notNull()},d=>({idx_agent_suggestions_ws_agent:index("idx_agent_suggestions_ws_agent").on(d.workspace_id,d.agent_id),idx_agent_suggestions_ws_created:index("idx_agent_suggestions_ws_created").on(d.workspace_id,d.created_at)}));function Wt(d){let t=d.toLowerCase().trim();t=t.replace(/\[[^\]]*\]$/g,"");let n=t.lastIndexOf("/");return n>=0&&(t=t.slice(n+1)),t=t.replace(/-\d{8}$/,""),t}var G="2026-05-09",je="0.8.9-rc.13",X=10,Y=parseInt(je.split("rc.")[1]),Ke=new Set(["workflow","mcp"]),jt=600*1e3,mt=class extends nt{dbPath;pidNullObservedSince=new Map;constructor(t={}){super(),t.dbPath?this.dbPath=t.dbPath:t.dbRoot&&(this.dbPath=join(t.dbRoot,".crewx","crewx.db"));}resolveDbPath(){return this.dbPath?this.dbPath:super.resolveDbPath()}openHandle(t){let n=this.resolveDbPath();if(t){let r=dirname(n);existsSync(r)||mkdirSync(r,{recursive:true});}else if(!existsSync(n))throw new _("NOT_FOUND","Database not found");let s=b(n);if(t)try{ct(s.db,n);}catch(r){throw s.close(),r}return s}startTask(t){let n=this.openHandle(true);try{n.db.insert(e).values({id:t.id,agent_id:t.agentId,prompt:t.prompt,mode:t.mode,status:t.status,started_at:t.startedAt,pid:t.pid??null,parent_task_id:t.parentTaskId??null,caller_agent_id:t.callerAgentId??null,trace_id:t.traceId??null,command:t.command??null,metadata:t.metadata??null,workspace_id:t.workspaceId??null,platform:t.platform??"cli",crewx_version:t.crewxVersion??null,thread_id:t.threadId??null,model:t.model??null,rendered_prompt:t.renderedPrompt??null,coding_agent_command:t.codingAgentCommand??null}).onConflictDoUpdate({target:e.id,set:{pid:sql`COALESCE(excluded.pid, ${e.pid})`},setWhere:eq(e.status,"running")}).run();}catch(s){throw s instanceof _?s:new _("DB_ERROR","Failed to start task",s)}finally{n.close();}}finishTask(t){let n=this.openHandle(true);try{let s=t.runEpoch??null;n.runRaw(`UPDATE tasks SET status=?, result=?, error=?, completed_at=?, duration_ms=?,
13
+ `)}`);let i=o.get(n`SELECT count(*) as cnt FROM sqlite_master WHERE type='table' AND name='__drizzle_migrations'`),a=0;i?.cnt&&(a=o.get(n`SELECT count(*) as cnt FROM __drizzle_migrations`)?.cnt??0),we(o,a),i?.cnt&&(Te(o,r,n),Se(o,r,n)),t(o,{migrationsFolder:r});let u=(o.get(n`SELECT count(*) as cnt FROM __drizzle_migrations`)?.cnt??0)-a;if(u>0){let c=i?.cnt?"Database migrated":"Database initialized";console.error(`[crewx] ${c} (${u} migration${u>1?"s":""} applied).`);}}function kt(o,t){jt.has(t)||(Re(o),jt.add(t));}var p=class extends Error{code;cause;constructor(t,n,s){super(n),this.name="RepositoryError",this.code=t,this.cause=s,Object.setPrototypeOf(this,new.target.prototype);}};var ct=sqliteTable("workspaces",{id:text("id").primaryKey(),slug:text("slug").notNull().unique(),name:text("name").notNull(),workspace_path:text("workspace_path"),description:text("description"),is_active:integer("is_active").notNull().default(1),created_at:text("created_at").notNull(),updated_at:text("updated_at").notNull()});var e=sqliteTable("tasks",{id:text("id").primaryKey(),agent_id:text("agent_id").notNull(),user_id:text("user_id"),prompt:text("prompt").notNull(),mode:text("mode").notNull().default("execute"),status:text("status").notNull().default("running"),result:text("result"),error:text("error"),started_at:text("started_at").notNull(),completed_at:text("completed_at"),duration_ms:integer("duration_ms"),metadata:text("metadata"),workspace_id:text("workspace_id"),trace_id:text("trace_id"),parent_task_id:text("parent_task_id"),caller_agent_id:text("caller_agent_id"),model:text("model"),platform:text("platform").default("cli"),crewx_version:text("crewx_version"),input_tokens:integer("input_tokens").default(0),output_tokens:integer("output_tokens").default(0),cost_usd:real("cost_usd").default(0),pid:integer("pid"),rendered_prompt:text("rendered_prompt"),command:text("command"),coding_agent_command:text("coding_agent_command"),exit_code:integer("exit_code"),logs:text("logs"),thread_id:text("thread_id"),workspace_ref:text("workspace_ref"),project_id:text("project_id"),project_ref:text("project_ref"),cached_input_tokens:integer("cached_input_tokens").default(0),run_epoch:integer("run_epoch").default(0)},o=>({idx_tasks_agent_id:index("idx_tasks_agent_id").on(o.agent_id),idx_tasks_status:index("idx_tasks_status").on(o.status),idx_tasks_started_at:index("idx_tasks_started_at").on(o.started_at),idx_tasks_trace_id:index("idx_tasks_trace_id").on(o.trace_id),idx_tasks_parent_task_id:index("idx_tasks_parent_task_id").on(o.parent_task_id),idx_tasks_crewx_version:index("idx_tasks_crewx_version").on(o.crewx_version),idx_tasks_pid:index("idx_tasks_pid").on(o.pid),idx_tasks_thread_id:index("idx_tasks_thread_id").on(o.thread_id),idx_tasks_workspace_id:index("idx_tasks_workspace_id").on(o.workspace_id),idx_tasks_workspace_ref:index("idx_tasks_workspace_ref").on(o.workspace_ref),idx_tasks_project_id:index("idx_tasks_project_id").on(o.project_id),idx_tasks_ws_started:index("idx_tasks_ws_started").on(o.workspace_id,o.started_at)}));var _=sqliteTable("threads",{id:text("id").primaryKey(),workspace_id:text("workspace_id").references(()=>ct.id,{onDelete:"set null"}),platform:text("platform").notNull().default("cli"),title:text("title"),first_message:text("first_message"),last_message:text("last_message"),message_count:integer("message_count").notNull().default(0),created_at:text("created_at").notNull(),updated_at:text("updated_at").notNull(),metadata:text("metadata"),title_locked:integer("title_locked").notNull().default(0),pinned:integer("pinned").notNull().default(0),starred:integer("starred").notNull().default(0)},o=>({idx_threads_updated_at:index("idx_threads_updated_at").on(o.updated_at),idx_threads_workspace_id:index("idx_threads_workspace_id").on(o.workspace_id),idx_threads_ws_updated:index("idx_threads_ws_updated").on(o.workspace_id,o.updated_at),idx_threads_title:index("idx_threads_title").on(o.title)}));var Oe=sqliteTable("spans",{id:text("id").primaryKey(),task_id:text("task_id").references(()=>e.id,{onDelete:"set null"}),parent_span_id:text("parent_span_id").references(()=>Oe.id,{onDelete:"set null"}),name:text("name").notNull(),kind:text("kind").notNull().default("internal"),status:text("status").notNull().default("ok"),started_at:text("started_at").notNull(),completed_at:text("completed_at"),duration_ms:integer("duration_ms"),input:text("input"),output:text("output"),error:text("error"),attributes:text("attributes")},o=>({idx_spans_task_id:index("idx_spans_task_id").on(o.task_id),idx_spans_parent_span_id:index("idx_spans_parent_span_id").on(o.parent_span_id)}));sqliteTable("tool_calls",{id:text("id").primaryKey(),task_id:text("task_id").references(()=>e.id,{onDelete:"cascade"}),session_id:text("session_id"),tool_name:text("tool_name").notNull(),files:text("files"),input:text("input"),output:text("output"),duration_ms:integer("duration_ms"),timestamp:text("timestamp").notNull()},o=>({idx_tool_calls_task_id:index("idx_tool_calls_task_id").on(o.task_id),idx_tool_calls_tool_name:index("idx_tool_calls_tool_name").on(o.tool_name),idx_tool_calls_timestamp:index("idx_tool_calls_timestamp").on(o.timestamp)}));sqliteTable("thread_boxes",{id:text("id").primaryKey(),thread_id:text("thread_id").notNull().references(()=>_.id,{onDelete:"cascade"}),seq:integer("seq").notNull(),first_task_id:text("first_task_id").notNull(),mid_task_id:text("mid_task_id").notNull(),last_task_id:text("last_task_id").notNull(),task_count:integer("task_count").notNull(),summary:text("summary"),source_tokens:integer("source_tokens").notNull(),summary_tokens:integer("summary_tokens"),created_at:text("created_at").notNull()},o=>({idx_thread_boxes_thread_id:index("idx_thread_boxes_thread_id").on(o.thread_id),idx_thread_boxes_seq:index("idx_thread_boxes_seq").on(o.thread_id,o.seq),uniq_thread_boxes_thread_seq:unique().on(o.thread_id,o.seq)}));sqliteTable("request_logs",{id:text("id").primaryKey(),path:text("path").notNull(),method:text("method").notNull(),status_code:integer("status_code").notNull(),duration_ms:integer("duration_ms").notNull(),ip:text("ip"),request_headers:text("request_headers"),response_headers:text("response_headers"),request_body:text("request_body"),response_body:text("response_body"),query:text("query"),user_id:text("user_id"),project_id:text("project_id"),partition_key:text("partition_key").notNull(),timestamp:text("timestamp").notNull().default(sql`(datetime('now'))`),metadata:text("metadata")},o=>({idx_request_logs_timestamp:index("idx_request_logs_timestamp").on(o.timestamp),idx_request_logs_path:index("idx_request_logs_path").on(o.path),idx_request_logs_status_code:index("idx_request_logs_status_code").on(o.status_code),idx_request_logs_partition_key:index("idx_request_logs_partition_key").on(o.partition_key)}));sqliteTable("usage_limit_snapshots",{id:text("id").primaryKey(),provider:text("provider").notNull(),account_ref:text("account_ref").notNull().default("default"),limit_window:text("limit_window").notNull(),bucket_start:text("bucket_start").notNull(),captured_at:text("captured_at").notNull(),used_percent:integer("used_percent").notNull(),remaining_percent:integer("remaining_percent").notNull(),resets_at:text("resets_at"),source:text("source").notNull(),metadata:text("metadata")},o=>({uniq_usage_limit_snapshots_bucket:uniqueIndex("uniq_usage_limit_snapshots_bucket").on(o.provider,o.account_ref,o.limit_window,o.bucket_start),idx_usage_limit_snapshots_window_bucket:index("idx_usage_limit_snapshots_window_bucket").on(o.limit_window,o.bucket_start),idx_usage_limit_snapshots_provider_window_bucket:index("idx_usage_limit_snapshots_provider_window_bucket").on(o.provider,o.limit_window,o.bucket_start)}));sqliteTable("usage_reports",{id:text("id").primaryKey(),workspace_id:text("workspace_id").notNull(),month:text("month").notNull(),generated_at:text("generated_at").notNull(),source_range:text("source_range").notNull(),tier:text("tier").notNull(),total_tokens:integer("total_tokens").notNull(),total_cost_usd:real("total_cost_usd").notNull(),payload:text("payload").notNull(),payload_hash:text("payload_hash"),signature:text("signature"),signed_at:text("signed_at"),issuer:text("issuer")},o=>({uniq_usage_reports_ws_month:uniqueIndex("uniq_usage_reports_ws_month").on(o.workspace_id,o.month)}));sqliteTable("notifications",{id:text("id").primaryKey(),workspace_id:text("workspace_id").notNull(),agent_id:text("agent_id"),task_id:text("task_id"),thread_id:text("thread_id"),source:text("source").notNull().default("agent"),level:text("level").notNull().default("info"),title:text("title").notNull(),body:text("body"),target_user_id:text("target_user_id"),created_at:text("created_at").notNull(),metadata:text("metadata")},o=>({idx_notifications_ws_created:index("idx_notifications_ws_created").on(o.workspace_id,sql`${o.created_at} DESC`)}));sqliteTable("notification_reads",{notification_id:text("notification_id").notNull(),user_id:text("user_id").notNull(),read_at:text("read_at").notNull()},o=>({pk:primaryKey({columns:[o.notification_id,o.user_id]})}));sqliteTable("agent_suggestions",{id:text("id").primaryKey(),workspace_id:text("workspace_id").notNull(),agent_id:text("agent_id").notNull(),task_id:text("task_id"),type:text("type").notNull(),status:text("status").notNull().default("pending"),payload:text("payload").notNull(),applied_commit_sha:text("applied_commit_sha"),created_at:text("created_at").notNull(),updated_at:text("updated_at").notNull()},o=>({idx_agent_suggestions_ws_agent:index("idx_agent_suggestions_ws_agent").on(o.workspace_id,o.agent_id),idx_agent_suggestions_ws_created:index("idx_agent_suggestions_ws_created").on(o.workspace_id,o.created_at)}));sqliteTable("ui_instances",{id:text("id").primaryKey().notNull(),definition_id:text("definition_id").notNull(),definition_version:integer("definition_version").notNull(),definition_hash:text("definition_hash").notNull(),workspace_id:text("workspace_id").notNull(),thread_id:text("thread_id").notNull(),anchor_task_id:text("anchor_task_id"),domain_ref_json:text("domain_ref_json").notNull(),state_json:text("state_json").notNull(),revision:integer("revision").notNull().default(0),status:text("status").notNull().default("active"),granted_capabilities_json:text("granted_capabilities_json").notNull().default("[]"),created_at:integer("created_at").notNull(),updated_at:integer("updated_at").notNull()},o=>({idCheck:check("ui_instances_id_ck",sql`length(${o.id}) BETWEEN 5 AND 128 AND ${o.id} GLOB 'uic_*'`),definitionIdCheck:check("ui_instances_definition_id_ck",sql`length(${o.definition_id}) BETWEEN 1 AND 128`),definitionVersionCheck:check("ui_instances_definition_version_ck",sql`${o.definition_version} >= 1`),definitionHashCheck:check("ui_instances_definition_hash_ck",sql`length(${o.definition_hash}) = 64 AND ${o.definition_hash} NOT GLOB '*[^0-9a-f]*'`),workspaceIdCheck:check("ui_instances_workspace_id_ck",sql`length(${o.workspace_id}) BETWEEN 1 AND 256`),threadIdCheck:check("ui_instances_thread_id_ck",sql`length(${o.thread_id}) BETWEEN 1 AND 256`),domainRefJsonCheck:check("ui_instances_domain_ref_json_ck",sql`json_valid(${o.domain_ref_json}) AND json_type(${o.domain_ref_json}) = 'object'`),stateJsonCheck:check("ui_instances_state_json_ck",sql`json_valid(${o.state_json}) AND json_type(${o.state_json}) = 'object'`),revisionCheck:check("ui_instances_revision_ck",sql`${o.revision} >= 0`),statusCheck:check("ui_instances_status_ck",sql`${o.status} IN ('active', 'completed', 'expired', 'revoked', 'unsupported')`),grantedCapabilitiesJsonCheck:check("ui_instances_granted_capabilities_json_ck",sql`json_valid(${o.granted_capabilities_json}) AND json_type(${o.granted_capabilities_json}) = 'array'`),createdAtCheck:check("ui_instances_created_at_ck",sql`${o.created_at} >= 0`),updatedAtCheck:check("ui_instances_updated_at_ck",sql`${o.updated_at} >= ${o.created_at}`),workspaceThreadIdx:index("ui_instances_workspace_thread_idx").on(o.workspace_id,o.thread_id)}));sqliteTable("ui_action_receipts",{id:text("id").primaryKey().notNull(),instance_id:text("instance_id").notNull(),request_id:text("request_id").notNull(),action_id:text("action_id").notNull(),actor_json:text("actor_json").notNull(),source:text("source").notNull(),expected_revision:integer("expected_revision").notNull(),before_revision:integer("before_revision").notNull(),after_revision:integer("after_revision"),status:text("status").notNull(),outcome:text("outcome"),input_json:text("input_json").notNull(),result_json:text("result_json"),error_code:text("error_code"),requested_at:integer("requested_at").notNull(),settled_at:integer("settled_at")},o=>({idCheck:check("ui_action_receipts_id_ck",sql`length(${o.id}) BETWEEN 5 AND 128`),instanceIdCheck:check("ui_action_receipts_instance_id_ck",sql`length(${o.instance_id}) BETWEEN 1 AND 128`),requestIdCheck:check("ui_action_receipts_request_id_ck",sql`length(${o.request_id}) BETWEEN 1 AND 128`),actionIdCheck:check("ui_action_receipts_action_id_ck",sql`length(${o.action_id}) BETWEEN 1 AND 128`),actorJsonCheck:check("ui_action_receipts_actor_json_ck",sql`json_valid(${o.actor_json}) AND json_type(${o.actor_json}) = 'object'`),sourceCheck:check("ui_action_receipts_source_ck",sql`${o.source} IN ('ui_host', 'cli', 'system')`),expectedRevisionCheck:check("ui_action_receipts_expected_revision_ck",sql`${o.expected_revision} >= 0`),beforeRevisionCheck:check("ui_action_receipts_before_revision_ck",sql`${o.before_revision} >= 0`),afterRevisionCheck:check("ui_action_receipts_after_revision_ck",sql`${o.after_revision} IS NULL OR ${o.after_revision} >= 0`),statusCheck:check("ui_action_receipts_status_ck",sql`${o.status} IN ('requested', 'settled')`),outcomeCheck:check("ui_action_receipts_outcome_ck",sql`${o.outcome} IS NULL OR ${o.outcome} IN ('succeeded', 'rejected', 'failed', 'conflicted', 'expired')`),inputJsonCheck:check("ui_action_receipts_input_json_ck",sql`json_valid(${o.input_json}) AND json_type(${o.input_json}) = 'object'`),resultJsonCheck:check("ui_action_receipts_result_json_ck",sql`${o.result_json} IS NULL OR (json_valid(${o.result_json}) AND json_type(${o.result_json}) = 'object')`),requestedAtCheck:check("ui_action_receipts_requested_at_ck",sql`${o.requested_at} >= 0`),settledAtCheck:check("ui_action_receipts_settled_at_ck",sql`${o.settled_at} IS NULL OR ${o.settled_at} >= ${o.requested_at}`),statusTransitionCheck:check("ui_action_receipts_status_transition_ck",sql`(
14
+ (${o.status} = 'requested' AND ${o.after_revision} IS NULL AND ${o.outcome} IS NULL AND ${o.settled_at} IS NULL)
15
+ OR
16
+ (${o.status} = 'settled' AND ${o.after_revision} IS NOT NULL AND ${o.outcome} IS NOT NULL AND ${o.settled_at} IS NOT NULL)
17
+ )`),instanceRequestUnique:uniqueIndex("ui_action_receipts_instance_request_uq").on(o.instance_id,o.request_id),instanceIdIdx:index("ui_action_receipts_instance_id_idx").on(o.instance_id),requestedAtIdx:index("ui_action_receipts_requested_at_idx").on(o.requested_at)}));function Zt(o){let t=o.toLowerCase().trim();t=t.replace(/\[[^\]]*\]$/g,"");let n=t.lastIndexOf("/");return n>=0&&(t=t.slice(n+1)),t=t.replace(/-\d{8}$/,""),t}var tt="2026-05-09",on="0.8.9-rc.13",et=10,nt=parseInt(on.split("rc.")[1]);function te(){let o=sql`
18
+ CASE
19
+ WHEN ${e.model} LIKE 'claude-%' OR ${e.model} IN ('opus', 'sonnet', 'haiku', 'opus[1m]', 'sonnet[1m]') THEN 'claude'
20
+ WHEN ${e.model} LIKE 'gpt-%' OR ${e.model} LIKE 'codex-%' THEN 'codex'
21
+ WHEN ${e.model} LIKE 'gemini-%' THEN 'gemini'
22
+ WHEN ${e.model} LIKE 'grok-%' THEN 'grok'
23
+ WHEN ${e.model} LIKE 'zai-%' OR ${e.model} LIKE 'openrouter/z-ai/%' THEN 'opencode'
24
+ WHEN ${e.model} LIKE 'minimax/%' THEN 'minimax'
25
+ WHEN ${e.model} LIKE 'qwen%' THEN 'qwen'
26
+ ELSE 'unknown'
27
+ END
28
+ `,t=sql`json_extract(${e.metadata}, '$.provider')`,n=sql`trim(${t})`,s=sql`substr(${n}, 1, instr(${n}, '/') - 1)`,r=sql`
29
+ CASE
30
+ WHEN instr(${n}, '/') > 0
31
+ AND ${s} IN ('cli', 'acp', 'api', 'plugin', 'remote')
32
+ THEN substr(${n}, instr(${n}, '/') + 1)
33
+ ELSE ${n}
34
+ END
35
+ `;return sql`
36
+ CASE
37
+ WHEN ${e.metadata} IS NULL THEN ${o}
38
+ WHEN json_valid(${e.metadata}) = 0 THEN 'unknown'
39
+ WHEN json_type(${e.metadata}, '$') IS NOT 'object' THEN 'unknown'
40
+ WHEN json_type(${e.metadata}, '$.provider') IS NULL THEN ${o}
41
+ WHEN json_type(${e.metadata}, '$.provider') IS NOT 'text' THEN 'unknown'
42
+ WHEN ${n} = '' THEN 'unknown'
43
+ WHEN trim(${r}) = '' THEN 'unknown'
44
+ ELSE ${r}
45
+ END
46
+ `}var an=new Set(["workflow","mcp"]),ee=600*1e3,xt=class extends dt{dbPath;pidNullObservedSince=new Map;constructor(t={}){super(),t.dbPath?this.dbPath=t.dbPath:t.dbRoot&&(this.dbPath=join(t.dbRoot,".crewx","crewx.db"));}resolveDbPath(){return this.dbPath?this.dbPath:super.resolveDbPath()}openHandle(t){let n=this.resolveDbPath();if(t){let r=dirname(n);existsSync(r)||mkdirSync(r,{recursive:true});}else if(!existsSync(n))throw new p("NOT_FOUND","Database not found");let s=y(n);if(t)try{kt(s.db,n);}catch(r){throw s.close(),r}return s}startTask(t){let n=this.openHandle(true);try{n.db.insert(e).values({id:t.id,agent_id:t.agentId,prompt:t.prompt,mode:t.mode,status:t.status,started_at:t.startedAt,pid:t.pid??null,parent_task_id:t.parentTaskId??null,caller_agent_id:t.callerAgentId??null,trace_id:t.traceId??null,command:t.command??null,metadata:t.metadata??null,workspace_id:t.workspaceId??null,platform:t.platform??"cli",crewx_version:t.crewxVersion??null,thread_id:t.threadId??null,model:t.model??null,rendered_prompt:t.renderedPrompt??null,coding_agent_command:t.codingAgentCommand??null}).onConflictDoUpdate({target:e.id,set:{pid:sql`COALESCE(excluded.pid, ${e.pid})`},setWhere:eq(e.status,"running")}).run();}catch(s){throw s instanceof p?s:new p("DB_ERROR","Failed to start task",s)}finally{n.close();}}finishTask(t){let n=this.openHandle(true);try{let s=t.runEpoch??null;n.runRaw(`UPDATE tasks SET status=?, result=?, error=?, completed_at=?, duration_ms=?,
14
47
  exit_code=?, input_tokens=?, output_tokens=?, cached_input_tokens=?, cost_usd=?,
15
48
  model=COALESCE(?, model)
16
- WHERE id=? AND status='running' AND COALESCE(run_epoch, 0) = COALESCE(?, 0)`,[t.status,t.result??null,t.error??null,t.completedAt,t.durationMs??null,t.exitCode??null,t.inputTokens??0,t.outputTokens??0,t.cachedInputTokens??0,t.costUsd??0,t.model??null,t.id,s]);}catch(s){throw s instanceof _?s:new _("DB_ERROR","Failed to finish task",s)}finally{n.close();}}appendLog(t,n){let s=this.openHandle(true);try{s.db.transaction(r=>{let o=r.select({logs:e.logs}).from(e).where(eq(e.id,t)).limit(1).get(),i=o?.logs?JSON.parse(o.logs):[];i.push(n),r.update(e).set({logs:JSON.stringify(i)}).where(eq(e.id,t)).run();},{behavior:"immediate"});}catch(r){throw r instanceof _?r:new _("DB_ERROR","Failed to append log",r)}finally{s.close();}}getRunningTasks(){if(!this.dbExists())return [];let t=this.openHandle(false);try{return t.db.select().from(e).where(eq(e.status,"running")).orderBy(desc(e.started_at)).all()}catch(n){throw new _("DB_ERROR","Failed to get running tasks",n)}finally{t.close();}}getAllTasks(){if(!this.dbExists())return [];let t=this.openHandle(false);try{return t.db.select().from(e).orderBy(desc(e.started_at)).limit(100).all()}catch(n){throw new _("DB_ERROR","Failed to get all tasks",n)}finally{t.close();}}getTask(t){if(!this.dbExists())return;let n=this.openHandle(false);try{return n.db.select().from(e).where(eq(e.id,t)).limit(1).get()??void 0}catch(s){throw new _("DB_ERROR","Failed to get task",s)}finally{n.close();}}killTask(t){if(!this.dbExists())return {killed:false};let n=this.openHandle(true);try{let s=n.db.select({id:e.id,status:e.status,pid:e.pid}).from(e).where(eq(e.id,t)).limit(1).get();if(!s||s.status!=="running")return {killed:!1};if(s.pid)try{process.kill(s.pid,"SIGTERM");}catch{}return n.db.update(e).set({status:"failed",error:"Killed by user",completed_at:new Date().toISOString()}).where(and(eq(e.id,t),eq(e.status,"running"))).run(),{killed:!0,pid:s.pid??void 0}}catch(s){throw s instanceof _?s:new _("DB_ERROR","Failed to kill task",s)}finally{n.close();}}reapOrphanedTasks(){if(!this.dbExists())return 0;let t=this.openHandle(true);try{let n=t.db.select({id:e.id,pid:e.pid,platform:e.platform,run_epoch:e.run_epoch}).from(e).where(eq(e.status,"running")).all(),s=Date.now(),r=new Set,o=0;for(let i of n){if(i.pid){let l=!1;try{process.kill(i.pid,0),l=!0;}catch{}l||(t.db.update(e).set({status:"failed",error:"Reaped: process not found (orphaned task)",completed_at:new Date().toISOString()}).where(and(eq(e.id,i.id),eq(e.status,"running"))).run(),o++);continue}if(Ke.has(i.platform??"cli"))continue;let a=`${i.id}:${i.run_epoch??0}`;r.add(a);let c=this.pidNullObservedSince.get(a);if(c===void 0){this.pidNullObservedSince.set(a,s);continue}s-c>=jt&&(t.db.update(e).set({status:"failed",error:"Reaped: pid never recorded after resume (stale running_instruction)",completed_at:new Date().toISOString()}).where(and(eq(e.id,i.id),eq(e.status,"running"))).run(),o++,this.pidNullObservedSince.delete(a));}for(let i of Array.from(this.pidNullObservedSince.keys()))r.has(i)||this.pidNullObservedSince.delete(i);return o}finally{t.close();}}reapRunningWorkflowTasks(t=jt){if(!this.dbExists())return 0;let n=this.openHandle(true);try{let s=new Date(Date.now()-t).toISOString();return n.db.update(e).set({status:"failed",error:"Reaped: stale workflow run (finally not executed)",completed_at:new Date().toISOString()}).where(and(eq(e.status,"running"),eq(e.platform,"workflow"),isNull(e.pid),lt(e.started_at,s),or(isNull(e.metadata),notLike(e.metadata,'%"kind":"workflow_card"%')))).run().changes??0}finally{n.close();}}findTaskStatus(t,n){let s=this.resolveDbPaths();for(let r of s){if(!existsSync(r))continue;let o=b(r);try{let i=n?eq(e.workspace_id,n):void 0,a=i?and(eq(e.id,t),i):eq(e.id,t),c=o.db.select().from(e).where(a).limit(1).get()??void 0;if(!c){let l=or(eq(e.thread_id,t),and(isNull(e.thread_id),like(e.command,`%--thread=${t}%`))),u=i?and(l,i):l;c=o.db.select().from(e).where(u).orderBy(desc(e.started_at)).limit(1).get()??void 0;}if(c)return c}catch(i){throw new _("DB_ERROR","Failed to find task status",i)}finally{o.close();}}}findChildTasks(t,n){let s=this.resolveDbPaths(),r=new Set,o=[];for(let i of s){if(!existsSync(i))continue;let a=b(i);try{let c=n?and(eq(e.parent_task_id,t),eq(e.workspace_id,n)):eq(e.parent_task_id,t),l=a.db.select().from(e).where(c).orderBy(asc(e.started_at)).all();for(let u of l)r.has(u.id)||(r.add(u.id),o.push(u));}catch(c){throw new _("DB_ERROR","Failed to find child tasks",c)}finally{a.close();}}return o}getWorkspaceUsageSummary(t){if(!this.dbExists())return [];let n=this.openHandle(false);try{return n.db.all(t?sql`
49
+ WHERE id=? AND status='running' AND COALESCE(run_epoch, 0) = COALESCE(?, 0)`,[t.status,t.result??null,t.error??null,t.completedAt,t.durationMs??null,t.exitCode??null,t.inputTokens??0,t.outputTokens??0,t.cachedInputTokens??0,t.costUsd??0,t.model??null,t.id,s]);}catch(s){throw s instanceof p?s:new p("DB_ERROR","Failed to finish task",s)}finally{n.close();}}appendLog(t,n){let s=this.openHandle(true);try{s.db.transaction(r=>{let i=r.select({logs:e.logs}).from(e).where(eq(e.id,t)).limit(1).get(),a=i?.logs?JSON.parse(i.logs):[];a.push(n),r.update(e).set({logs:JSON.stringify(a)}).where(eq(e.id,t)).run();},{behavior:"immediate"});}catch(r){throw r instanceof p?r:new p("DB_ERROR","Failed to append log",r)}finally{s.close();}}getRunningTasks(){if(!this.dbExists())return [];let t=this.openHandle(false);try{return t.db.select().from(e).where(eq(e.status,"running")).orderBy(desc(e.started_at)).all()}catch(n){throw new p("DB_ERROR","Failed to get running tasks",n)}finally{t.close();}}getAllTasks(){if(!this.dbExists())return [];let t=this.openHandle(false);try{return t.db.select().from(e).orderBy(desc(e.started_at)).limit(100).all()}catch(n){throw new p("DB_ERROR","Failed to get all tasks",n)}finally{t.close();}}getTask(t){if(!this.dbExists())return;let n=this.openHandle(false);try{return n.db.select().from(e).where(eq(e.id,t)).limit(1).get()??void 0}catch(s){throw new p("DB_ERROR","Failed to get task",s)}finally{n.close();}}killTask(t){if(!this.dbExists())return {killed:false};let n=this.openHandle(true);try{let s=n.db.select({id:e.id,status:e.status,pid:e.pid}).from(e).where(eq(e.id,t)).limit(1).get();if(!s||s.status!=="running")return {killed:!1};if(s.pid)try{process.kill(s.pid,"SIGTERM");}catch{}return n.db.update(e).set({status:"failed",error:"Killed by user",completed_at:new Date().toISOString()}).where(and(eq(e.id,t),eq(e.status,"running"))).run(),{killed:!0,pid:s.pid??void 0}}catch(s){throw s instanceof p?s:new p("DB_ERROR","Failed to kill task",s)}finally{n.close();}}reapOrphanedTasks(){if(!this.dbExists())return 0;let t=this.openHandle(true);try{let n=t.db.select({id:e.id,pid:e.pid,platform:e.platform,run_epoch:e.run_epoch}).from(e).where(eq(e.status,"running")).all(),s=Date.now(),r=new Set,i=0;for(let a of n){if(a.pid){let c=!1;try{process.kill(a.pid,0),c=!0;}catch{}c||(t.db.update(e).set({status:"failed",error:"Reaped: process not found (orphaned task)",completed_at:new Date().toISOString()}).where(and(eq(e.id,a.id),eq(e.status,"running"))).run(),i++);continue}if(an.has(a.platform??"cli"))continue;let d=`${a.id}:${a.run_epoch??0}`;r.add(d);let u=this.pidNullObservedSince.get(d);if(u===void 0){this.pidNullObservedSince.set(d,s);continue}s-u>=ee&&(t.db.update(e).set({status:"failed",error:"Reaped: pid never recorded after resume (stale running_instruction)",completed_at:new Date().toISOString()}).where(and(eq(e.id,a.id),eq(e.status,"running"))).run(),i++,this.pidNullObservedSince.delete(d));}for(let a of Array.from(this.pidNullObservedSince.keys()))r.has(a)||this.pidNullObservedSince.delete(a);return i}finally{t.close();}}reapRunningWorkflowTasks(t=ee){if(!this.dbExists())return 0;let n=this.openHandle(true);try{let s=new Date(Date.now()-t).toISOString();return n.db.update(e).set({status:"failed",error:"Reaped: stale workflow run (finally not executed)",completed_at:new Date().toISOString()}).where(and(eq(e.status,"running"),eq(e.platform,"workflow"),isNull(e.pid),lt(e.started_at,s),or(isNull(e.metadata),and(notLike(e.metadata,'%"kind":"workflow_card"%'),notLike(e.metadata,'%"kind":"workflow_ui_instance"%'))))).run().changes??0}finally{n.close();}}findTaskStatus(t,n){let s=this.resolveDbPaths();for(let r of s){if(!existsSync(r))continue;let i=y(r);try{let a=n?eq(e.workspace_id,n):void 0,d=a?and(eq(e.id,t),a):eq(e.id,t),u=i.db.select().from(e).where(d).limit(1).get()??void 0;if(!u){let c=or(eq(e.thread_id,t),and(isNull(e.thread_id),like(e.command,`%--thread=${t}%`))),l=a?and(c,a):c;u=i.db.select().from(e).where(l).orderBy(desc(e.started_at)).limit(1).get()??void 0;}if(u)return u}catch(a){throw new p("DB_ERROR","Failed to find task status",a)}finally{i.close();}}}findChildTasks(t,n){let s=this.resolveDbPaths(),r=new Set,i=[];for(let a of s){if(!existsSync(a))continue;let d=y(a);try{let u=n?and(eq(e.parent_task_id,t),eq(e.workspace_id,n)):eq(e.parent_task_id,t),c=d.db.select().from(e).where(u).orderBy(asc(e.started_at)).all();for(let l of c)r.has(l.id)||(r.add(l.id),i.push(l));}catch(u){throw new p("DB_ERROR","Failed to find child tasks",u)}finally{d.close();}}return i}getWorkspaceUsageSummary(t){if(!this.dbExists())return [];let n=this.openHandle(false);try{return n.db.all(t?sql`
17
50
  SELECT
18
51
  COALESCE(workspace_id, 'unknown') AS workspace_id,
19
52
  COALESCE(SUM(input_tokens), 0) AS input_tokens,
@@ -34,7 +67,7 @@ ${s.join(`
34
67
  FROM tasks
35
68
  GROUP BY workspace_id
36
69
  ORDER BY (COALESCE(SUM(input_tokens), 0) + COALESCE(SUM(output_tokens), 0)) DESC
37
- `)}catch(s){throw new _("DB_ERROR","Failed to get workspace usage summary",s)}finally{n.close();}}getThreadTokenUsage(t,n){let s=this.resolveDbPaths(),r=new Set,o=0,i=0,a=0;for(let c of s){if(!existsSync(c))continue;let l=b(c);try{let u=or(eq(e.thread_id,t),and(isNull(e.thread_id),like(e.command,`%--thread=${t}%`))),h=n?and(u,eq(e.workspace_id,n)):u,g=l.db.select({id:e.id,input_tokens:e.input_tokens,output_tokens:e.output_tokens,cost_usd:e.cost_usd}).from(e).where(h).all();for(let y of g)r.has(y.id)||(r.add(y.id),o+=y.input_tokens??0,i+=y.output_tokens??0,a+=y.cost_usd??0);}catch(u){throw new _("DB_ERROR","Failed to get thread token usage",u)}finally{l.close();}}return {inputTokens:o,outputTokens:i,costUsd:a}}findTasksByThread(t,n){let s=this.resolveDbPaths(),r=new Set,o=[];for(let i of s){if(!existsSync(i))continue;let a=b(i);try{let c=or(eq(e.thread_id,t),and(isNull(e.thread_id),like(e.command,`%--thread=${t}%`))),l=n?and(c,eq(e.workspace_id,n)):c,u=a.db.select().from(e).where(l).orderBy(asc(e.started_at)).all();for(let h of u)r.has(h.id)||(r.add(h.id),o.push(h));}catch(c){throw new _("DB_ERROR","Failed to find tasks by thread",c)}finally{a.close();}}return o}parseWorkflowCardMetadata(t){if(!t)return {};try{let n=JSON.parse(t);return {kind:typeof n.kind=="string"?n.kind:void 0,workflowRunId:typeof n.workflowRunId=="string"?n.workflowRunId:void 0}}catch{return {}}}extractThreadIdFromCommand(t){return t?/--thread=(\S+)/.exec(t)?.[1]??null:null}findRunningWorkflowParentTasks(){if(!this.dbExists())return [];let t=[];for(let n of this.resolveDbPaths()){if(!existsSync(n))continue;let s=b(n);try{t.push(...s.db.select({id:e.id,agent_id:e.agent_id,thread_id:e.thread_id,workspace_id:e.workspace_id,platform:e.platform,status:e.status,error:e.error,completed_at:e.completed_at,duration_ms:e.duration_ms,started_at:e.started_at,metadata:e.metadata}).from(e).where(and(eq(e.platform,"workflow"),like(e.metadata,'%"kind":"workflow_card"%'))).orderBy(desc(e.started_at)).all());}catch(r){throw new _("DB_ERROR","Failed to find workflow parent tasks",r)}finally{s.close();}}return t}batchFetchWorkflowCards(t,n){let s=new Map;if(t.length===0)return s;let r=new Set(t),o=new Map,i=n?eq(e.workspace_id,n):void 0,a=(c,l)=>{if(!c)return;let u=o.get(c);if(u&&l.started_at<=u)return;let h=this.parseWorkflowCardMetadata(l.metadata);h.kind==="workflow_card"&&(o.set(c,l.started_at),s.set(c,{taskId:l.id,workflowRunId:h.workflowRunId,raw:l.result??void 0}));};for(let c of this.resolveDbPaths()){if(!existsSync(c))continue;let l=b(c);try{let u=and(inArray(e.thread_id,t),like(e.metadata,'%"kind":"workflow_card"%')),h=l.db.select({id:e.id,thread_id:e.thread_id,metadata:e.metadata,result:e.result,started_at:e.started_at}).from(e).where(i?and(u,i):u).all();for(let C of h)a(C.thread_id,C);let g=and(isNull(e.thread_id),like(e.metadata,'%"kind":"workflow_card"%')),y=l.db.select({id:e.id,command:e.command,metadata:e.metadata,result:e.result,started_at:e.started_at}).from(e).where(i?and(g,i):g).all();for(let C of y){let N=this.extractThreadIdFromCommand(C.command);!N||!r.has(N)||a(N,C);}}catch(u){throw new _("DB_ERROR","Failed to batch fetch workflow cards",u)}finally{l.close();}}return s}findAllTasks(t){if(!this.dbExists())return {rows:[],total:0};let n=this.openHandle(false);try{let s=[];t.workspaceId&&s.push(eq(e.workspace_id,t.workspaceId));let r=t.agents&&t.agents.length>0?t.agents:t.agentId?[t.agentId]:null;r&&s.push(inArray(e.agent_id,r));let o=t.statuses&&t.statuses.length>0?t.statuses:t.status?[t.status]:null;o&&s.push(inArray(e.status,o));let i=t.q??t.search;i&&s.push(like(e.prompt,`%${i}%`)),t.from&&s.push(gte(e.started_at,t.from)),t.to&&s.push(lt(e.started_at,t.to));let a=s.length>0?and(...s):void 0,c=n.db.select({count:sql`count(*)`}).from(e).where(a).get(),l=(t.sortDir??"DESC")==="ASC"?asc(e.started_at):desc(e.started_at);return {rows:n.db.select().from(e).where(a).orderBy(l).limit(t.limit).offset(t.offset).all(),total:c?.count??0}}catch(s){throw new _("DB_ERROR","Failed to find all tasks",s)}finally{n.close();}}getAgentUsage(t,n,s){if(!this.dbExists())return [];let r=this.openHandle(false);try{return r.db.all(s?sql`
70
+ `)}catch(s){throw new p("DB_ERROR","Failed to get workspace usage summary",s)}finally{n.close();}}getThreadTokenUsage(t,n){let s=this.resolveDbPaths(),r=new Set,i=0,a=0,d=0;for(let u of s){if(!existsSync(u))continue;let c=y(u);try{let l=or(eq(e.thread_id,t),and(isNull(e.thread_id),like(e.command,`%--thread=${t}%`))),h=n?and(l,eq(e.workspace_id,n)):l,m=c.db.select({id:e.id,input_tokens:e.input_tokens,output_tokens:e.output_tokens,cost_usd:e.cost_usd}).from(e).where(h).all();for(let w of m)r.has(w.id)||(r.add(w.id),i+=w.input_tokens??0,a+=w.output_tokens??0,d+=w.cost_usd??0);}catch(l){throw new p("DB_ERROR","Failed to get thread token usage",l)}finally{c.close();}}return {inputTokens:i,outputTokens:a,costUsd:d}}findTasksByThread(t,n){let s=this.resolveDbPaths(),r=new Set,i=[];for(let a of s){if(!existsSync(a))continue;let d=y(a);try{let u=or(eq(e.thread_id,t),and(isNull(e.thread_id),like(e.command,`%--thread=${t}%`))),c=n?and(u,eq(e.workspace_id,n)):u,l=d.db.select().from(e).where(c).orderBy(asc(e.started_at)).all();for(let h of l)r.has(h.id)||(r.add(h.id),i.push(h));}catch(u){throw new p("DB_ERROR","Failed to find tasks by thread",u)}finally{d.close();}}return i}parseWorkflowCardMetadata(t){if(!t)return {};try{let n=JSON.parse(t);return {kind:typeof n.kind=="string"?n.kind:void 0,workflowRunId:typeof n.workflowRunId=="string"?n.workflowRunId:void 0}}catch{return {}}}extractThreadIdFromCommand(t){return t?/--thread=(\S+)/.exec(t)?.[1]??null:null}findRunningWorkflowParentTasks(){if(!this.dbExists())return [];let t=[];for(let n of this.resolveDbPaths()){if(!existsSync(n))continue;let s=y(n);try{t.push(...s.db.select({id:e.id,agent_id:e.agent_id,thread_id:e.thread_id,workspace_id:e.workspace_id,platform:e.platform,status:e.status,error:e.error,completed_at:e.completed_at,duration_ms:e.duration_ms,started_at:e.started_at,metadata:e.metadata}).from(e).where(and(eq(e.platform,"workflow"),or(like(e.metadata,'%"kind":"workflow_card"%'),like(e.metadata,'%"kind":"workflow_ui_instance"%')))).orderBy(desc(e.started_at)).all());}catch(r){throw new p("DB_ERROR","Failed to find workflow parent tasks",r)}finally{s.close();}}return t}batchFetchWorkflowCards(t,n){let s=new Map;if(t.length===0)return s;let r=new Set(t),i=new Map,a=n?eq(e.workspace_id,n):void 0,d=(u,c)=>{if(!u)return;let l=i.get(u);if(l&&c.started_at<=l)return;let h=this.parseWorkflowCardMetadata(c.metadata);h.kind!=="workflow_card"&&h.kind!=="workflow_ui_instance"||(i.set(u,c.started_at),s.set(u,{taskId:c.id,workflowRunId:h.workflowRunId,raw:c.result??void 0}));};for(let u of this.resolveDbPaths()){if(!existsSync(u))continue;let c=y(u);try{let l=and(inArray(e.thread_id,t),or(like(e.metadata,'%"kind":"workflow_card"%'),like(e.metadata,'%"kind":"workflow_ui_instance"%'))),h=c.db.select({id:e.id,thread_id:e.thread_id,metadata:e.metadata,result:e.result,started_at:e.started_at}).from(e).where(a?and(l,a):l).all();for(let $ of h)d($.thread_id,$);let m=and(isNull(e.thread_id),or(like(e.metadata,'%"kind":"workflow_card"%'),like(e.metadata,'%"kind":"workflow_ui_instance"%'))),w=c.db.select({id:e.id,command:e.command,metadata:e.metadata,result:e.result,started_at:e.started_at}).from(e).where(a?and(m,a):m).all();for(let $ of w){let v=this.extractThreadIdFromCommand($.command);!v||!r.has(v)||d(v,$);}}catch(l){throw new p("DB_ERROR","Failed to batch fetch workflow cards",l)}finally{c.close();}}return s}findAllTasks(t){if(!this.dbExists())return {rows:[],total:0};let n=this.openHandle(false);try{let s=[];t.workspaceId&&s.push(eq(e.workspace_id,t.workspaceId));let r=t.agents&&t.agents.length>0?t.agents:t.agentId?[t.agentId]:null;r&&s.push(inArray(e.agent_id,r));let i=t.statuses&&t.statuses.length>0?t.statuses:t.status?[t.status]:null;i&&s.push(inArray(e.status,i));let a=t.q??t.search;a&&s.push(like(e.prompt,`%${a}%`)),t.from&&s.push(gte(e.started_at,t.from)),t.to&&s.push(lt(e.started_at,t.to));let d=s.length>0?and(...s):void 0,u=n.db.select({count:sql`count(*)`}).from(e).where(d).get(),c=(t.sortDir??"DESC")==="ASC"?asc(e.started_at):desc(e.started_at);return {rows:n.db.select().from(e).where(d).orderBy(c).limit(t.limit).offset(t.offset).all(),total:u?.count??0}}catch(s){throw new p("DB_ERROR","Failed to find all tasks",s)}finally{n.close();}}getAgentUsage(t,n,s){if(!this.dbExists())return [];let r=this.openHandle(false);try{return r.db.all(s?sql`
38
71
  SELECT
39
72
  t.agent_id,
40
73
  t.workspace_id,
@@ -42,11 +75,11 @@ ${s.join(`
42
75
  COALESCE(SUM(
43
76
  COALESCE(t.input_tokens, 0)
44
77
  + CASE
45
- WHEN t.started_at >= ${G}
78
+ WHEN t.started_at >= ${tt}
46
79
  AND (
47
80
  t.crewx_version IS NULL
48
81
  OR (t.crewx_version LIKE '0.8.%' AND t.crewx_version NOT LIKE '0.8.9%')
49
- OR (t.crewx_version LIKE '0.8.9-rc.%' AND CAST(SUBSTR(t.crewx_version, ${X}) AS INTEGER) < ${Y})
82
+ OR (t.crewx_version LIKE '0.8.9-rc.%' AND CAST(SUBSTR(t.crewx_version, ${et}) AS INTEGER) < ${nt})
50
83
  )
51
84
  THEN COALESCE(t.cached_input_tokens, 0)
52
85
  ELSE 0
@@ -65,11 +98,11 @@ ${s.join(`
65
98
  COALESCE(SUM(
66
99
  COALESCE(t.input_tokens, 0)
67
100
  + CASE
68
- WHEN t.started_at >= ${G}
101
+ WHEN t.started_at >= ${tt}
69
102
  AND (
70
103
  t.crewx_version IS NULL
71
104
  OR (t.crewx_version LIKE '0.8.%' AND t.crewx_version NOT LIKE '0.8.9%')
72
- OR (t.crewx_version LIKE '0.8.9-rc.%' AND CAST(SUBSTR(t.crewx_version, ${X}) AS INTEGER) < ${Y})
105
+ OR (t.crewx_version LIKE '0.8.9-rc.%' AND CAST(SUBSTR(t.crewx_version, ${et}) AS INTEGER) < ${nt})
73
106
  )
74
107
  THEN COALESCE(t.cached_input_tokens, 0)
75
108
  ELSE 0
@@ -85,11 +118,11 @@ ${s.join(`
85
118
  COALESCE(SUM(
86
119
  COALESCE(t.input_tokens, 0)
87
120
  + CASE
88
- WHEN t.started_at >= ${G}
121
+ WHEN t.started_at >= ${tt}
89
122
  AND (
90
123
  t.crewx_version IS NULL
91
124
  OR (t.crewx_version LIKE '0.8.%' AND t.crewx_version NOT LIKE '0.8.9%')
92
- OR (t.crewx_version LIKE '0.8.9-rc.%' AND CAST(SUBSTR(t.crewx_version, ${X}) AS INTEGER) < ${Y})
125
+ OR (t.crewx_version LIKE '0.8.9-rc.%' AND CAST(SUBSTR(t.crewx_version, ${et}) AS INTEGER) < ${nt})
93
126
  )
94
127
  THEN COALESCE(t.cached_input_tokens, 0)
95
128
  ELSE 0
@@ -107,11 +140,11 @@ ${s.join(`
107
140
  COALESCE(SUM(
108
141
  COALESCE(t.input_tokens, 0)
109
142
  + CASE
110
- WHEN t.started_at >= ${G}
143
+ WHEN t.started_at >= ${tt}
111
144
  AND (
112
145
  t.crewx_version IS NULL
113
146
  OR (t.crewx_version LIKE '0.8.%' AND t.crewx_version NOT LIKE '0.8.9%')
114
- OR (t.crewx_version LIKE '0.8.9-rc.%' AND CAST(SUBSTR(t.crewx_version, ${X}) AS INTEGER) < ${Y})
147
+ OR (t.crewx_version LIKE '0.8.9-rc.%' AND CAST(SUBSTR(t.crewx_version, ${et}) AS INTEGER) < ${nt})
115
148
  )
116
149
  THEN COALESCE(t.cached_input_tokens, 0)
117
150
  ELSE 0
@@ -119,18 +152,18 @@ ${s.join(`
119
152
  ), 0)
120
153
  + COALESCE(SUM(t.output_tokens), 0)
121
154
  ) DESC
122
- `).map(i=>({agentId:i.agent_id,workspaceId:i.workspace_id??null,totalTasks:i.total_tasks,inputTokens:i.input_tokens,outputTokens:i.output_tokens,cachedInputTokens:i.cached_input_tokens,costUsd:i.cost_usd,totalTokens:i.input_tokens+i.output_tokens}))}catch(o){throw new _("DB_ERROR","Failed to get agent usage",o)}finally{r.close();}}getAgentUsageTrendRaw(t,n,s){if(!this.dbExists())return [];let r=this.openHandle(false);try{return r.db.all(s?sql`
155
+ `).map(a=>({agentId:a.agent_id,workspaceId:a.workspace_id??null,totalTasks:a.total_tasks,inputTokens:a.input_tokens,outputTokens:a.output_tokens,cachedInputTokens:a.cached_input_tokens,costUsd:a.cost_usd,totalTokens:a.input_tokens+a.output_tokens}))}catch(i){throw new p("DB_ERROR","Failed to get agent usage",i)}finally{r.close();}}getAgentUsageTrendRaw(t,n,s){if(!this.dbExists())return [];let r=this.openHandle(false);try{return r.db.all(s?sql`
123
156
  SELECT
124
157
  date(t.started_at) AS date,
125
158
  t.agent_id,
126
159
  COALESCE(SUM(
127
160
  COALESCE(t.input_tokens, 0)
128
161
  + CASE
129
- WHEN t.started_at >= ${G}
162
+ WHEN t.started_at >= ${tt}
130
163
  AND (
131
164
  t.crewx_version IS NULL
132
165
  OR (t.crewx_version LIKE '0.8.%' AND t.crewx_version NOT LIKE '0.8.9%')
133
- OR (t.crewx_version LIKE '0.8.9-rc.%' AND CAST(SUBSTR(t.crewx_version, ${X}) AS INTEGER) < ${Y})
166
+ OR (t.crewx_version LIKE '0.8.9-rc.%' AND CAST(SUBSTR(t.crewx_version, ${et}) AS INTEGER) < ${nt})
134
167
  )
135
168
  THEN COALESCE(t.cached_input_tokens, 0)
136
169
  ELSE 0
@@ -153,11 +186,11 @@ ${s.join(`
153
186
  COALESCE(SUM(
154
187
  COALESCE(t.input_tokens, 0)
155
188
  + CASE
156
- WHEN t.started_at >= ${G}
189
+ WHEN t.started_at >= ${tt}
157
190
  AND (
158
191
  t.crewx_version IS NULL
159
192
  OR (t.crewx_version LIKE '0.8.%' AND t.crewx_version NOT LIKE '0.8.9%')
160
- OR (t.crewx_version LIKE '0.8.9-rc.%' AND CAST(SUBSTR(t.crewx_version, ${X}) AS INTEGER) < ${Y})
193
+ OR (t.crewx_version LIKE '0.8.9-rc.%' AND CAST(SUBSTR(t.crewx_version, ${et}) AS INTEGER) < ${nt})
161
194
  )
162
195
  THEN COALESCE(t.cached_input_tokens, 0)
163
196
  ELSE 0
@@ -172,79 +205,59 @@ ${s.join(`
172
205
  AND t.started_at < ${n}
173
206
  GROUP BY date(t.started_at), t.agent_id
174
207
  ORDER BY date(t.started_at) ASC
175
- `).map(i=>({date:i.date,agentId:i.agent_id,inputTokens:i.input_tokens,outputTokens:i.output_tokens,cachedInputTokens:i.cached_input_tokens,costUsd:i.cost_usd,totalTokens:i.input_tokens+i.output_tokens}))}catch(o){throw new _("DB_ERROR","Failed to get agent usage trend",o)}finally{r.close();}}findTaskForStop(t,n){if(!this.dbExists())return;let s=this.openHandle(false);try{return s.db.select().from(e).where(and(eq(e.id,t),eq(e.workspace_id,n))).limit(1).get()??void 0}catch(r){throw new _("DB_ERROR","Failed to find task for stop",r)}finally{s.close();}}findLatestTaskByMetadata(t){if(!this.dbExists())return null;let n=this.openHandle(false);try{return n.db.select({id:e.id,thread_id:e.thread_id,status:e.status,result:e.result,error:e.error,started_at:e.started_at,completed_at:e.completed_at}).from(e).where(and(eq(e.agent_id,t.agentId),eq(e.workspace_id,t.workspaceId),sql`${e.metadata} IS NOT NULL AND json_valid(${e.metadata}) AND json_extract(${e.metadata}, '$.' || ${t.metaKey}) = ${t.metaValue}`)).orderBy(desc(e.started_at)).limit(1).get()??null}catch(s){throw new _("DB_ERROR","Failed to find latest task by metadata",s)}finally{n.close();}}markTaskFailed(t,n,s){if(!this.dbExists())return;let r=this.openHandle(true);try{let o=new Date().toISOString(),i=s?and(eq(e.id,t),eq(e.status,"running"),eq(e.workspace_id,s)):and(eq(e.id,t),eq(e.status,"running"));r.db.update(e).set({status:"failed",error:n,completed_at:o}).where(i).run();}catch(o){throw o instanceof _?o:new _("DB_ERROR","Failed to mark task failed",o)}finally{r.close();}}findTasksByPromptHint(t,n){let s=this.resolveDbPaths(),r=new Set,o=[];for(let i of s){if(!existsSync(i))continue;let a=b(i);try{let c=n?and(like(e.prompt,`%${t}%`),eq(e.workspace_id,n)):like(e.prompt,`%${t}%`),l=a.db.select().from(e).where(c).orderBy(asc(e.started_at)).all();for(let u of l)r.has(u.id)||(r.add(u.id),o.push(u));}catch(c){throw new _("DB_ERROR","Failed to find tasks by prompt hint",c)}finally{a.close();}}return o}getProviderUsage(t,n,s){if(!this.dbExists())return [];let r=this.openHandle(false);try{let o=sql`
176
- CASE
177
- WHEN ${e.model} LIKE 'claude-%' OR ${e.model} IN ('opus', 'sonnet', 'haiku', 'opus[1m]', 'sonnet[1m]') THEN 'claude'
178
- WHEN ${e.model} LIKE 'gpt-%' OR ${e.model} LIKE 'codex-%' THEN 'codex'
179
- WHEN ${e.model} LIKE 'gemini-%' THEN 'gemini'
180
- WHEN ${e.model} LIKE 'zai-%' OR ${e.model} LIKE 'openrouter/z-ai/%' THEN 'opencode'
181
- WHEN ${e.model} LIKE 'minimax/%' THEN 'minimax'
182
- WHEN ${e.model} LIKE 'qwen%' THEN 'qwen'
183
- ELSE 'unknown'
184
- END
185
- `,i=sql`
208
+ `).map(a=>({date:a.date,agentId:a.agent_id,inputTokens:a.input_tokens,outputTokens:a.output_tokens,cachedInputTokens:a.cached_input_tokens,costUsd:a.cost_usd,totalTokens:a.input_tokens+a.output_tokens}))}catch(i){throw new p("DB_ERROR","Failed to get agent usage trend",i)}finally{r.close();}}findTaskForStop(t,n){if(!this.dbExists())return;let s=this.openHandle(false);try{return s.db.select().from(e).where(and(eq(e.id,t),eq(e.workspace_id,n))).limit(1).get()??void 0}catch(r){throw new p("DB_ERROR","Failed to find task for stop",r)}finally{s.close();}}findLatestTaskByMetadata(t){if(!this.dbExists())return null;let n=this.openHandle(false);try{return n.db.select({id:e.id,thread_id:e.thread_id,status:e.status,result:e.result,error:e.error,started_at:e.started_at,completed_at:e.completed_at,metadata:e.metadata}).from(e).where(and(eq(e.agent_id,t.agentId),eq(e.workspace_id,t.workspaceId),sql`${e.metadata} IS NOT NULL AND json_valid(${e.metadata}) AND json_extract(${e.metadata}, '$.' || ${t.metaKey}) = ${t.metaValue}`)).orderBy(desc(e.started_at)).limit(1).get()??null}catch(s){throw new p("DB_ERROR","Failed to find latest task by metadata",s)}finally{n.close();}}markTaskFailed(t,n,s){if(!this.dbExists())return;let r=this.openHandle(true);try{let i=new Date().toISOString(),a=s?and(eq(e.id,t),eq(e.status,"running"),eq(e.workspace_id,s)):and(eq(e.id,t),eq(e.status,"running"));r.db.update(e).set({status:"failed",error:n,completed_at:i}).where(a).run();}catch(i){throw i instanceof p?i:new p("DB_ERROR","Failed to mark task failed",i)}finally{r.close();}}findTasksByPromptHint(t,n){let s=this.resolveDbPaths(),r=new Set,i=[];for(let a of s){if(!existsSync(a))continue;let d=y(a);try{let u=n?and(like(e.prompt,`%${t}%`),eq(e.workspace_id,n)):like(e.prompt,`%${t}%`),c=d.db.select().from(e).where(u).orderBy(asc(e.started_at)).all();for(let l of c)r.has(l.id)||(r.add(l.id),i.push(l));}catch(u){throw new p("DB_ERROR","Failed to find tasks by prompt hint",u)}finally{d.close();}}return i}getProviderUsage(t,n,s){if(!this.dbExists())return [];let r=this.openHandle(false);try{let i=te(),a=sql`
186
209
  COALESCE(${e.input_tokens}, 0)
187
210
  + CASE
188
- WHEN ${e.started_at} >= ${G}
211
+ WHEN ${e.started_at} >= ${tt}
189
212
  AND (
190
213
  ${e.crewx_version} IS NULL
191
214
  OR (${e.crewx_version} LIKE '0.8.%' AND ${e.crewx_version} NOT LIKE '0.8.9%')
192
- OR (${e.crewx_version} LIKE '0.8.9-rc.%' AND CAST(SUBSTR(${e.crewx_version}, ${X}) AS INTEGER) < ${Y})
215
+ OR (${e.crewx_version} LIKE '0.8.9-rc.%' AND CAST(SUBSTR(${e.crewx_version}, ${et}) AS INTEGER) < ${nt})
193
216
  )
194
217
  THEN COALESCE(${e.cached_input_tokens}, 0)
195
218
  ELSE 0
196
219
  END
197
- `,a=s?sql`WHERE ${e.status} IN ('completed', 'success') AND ${e.started_at} >= ${t} AND ${e.started_at} < ${n} AND ${e.workspace_id} = ${s}`:sql`WHERE ${e.status} IN ('completed', 'success') AND ${e.started_at} >= ${t} AND ${e.started_at} < ${n}`;return r.db.all(sql`
220
+ `,d=s?sql`WHERE ${e.status} IN ('completed', 'success') AND ${e.started_at} >= ${t} AND ${e.started_at} < ${n} AND ${e.workspace_id} = ${s}`:sql`WHERE ${e.status} IN ('completed', 'success') AND ${e.started_at} >= ${t} AND ${e.started_at} < ${n}`;return r.db.all(sql`
198
221
  SELECT
199
- ${o} AS provider,
222
+ ${i} AS provider,
200
223
  COUNT(*) AS total_tasks,
201
- COALESCE(SUM(${i}), 0) AS input_tokens,
224
+ COALESCE(SUM(${a}), 0) AS input_tokens,
202
225
  COALESCE(SUM(${e.output_tokens}), 0) AS output_tokens,
203
226
  COALESCE(SUM(${e.cached_input_tokens}), 0) AS cached_input_tokens,
204
227
  COALESCE(SUM(${e.cost_usd}), 0) AS cost_usd,
205
228
  COALESCE(SUM(${e.duration_ms}), 0) AS active_duration_ms,
206
229
  MAX(${e.completed_at}) AS last_active_at
207
230
  FROM ${e}
208
- ${a}
209
- GROUP BY provider
210
- ORDER BY (COALESCE(SUM(${i}), 0) + COALESCE(SUM(${e.output_tokens}), 0)) DESC
211
- `).map(l=>({provider:l.provider,totalTasks:l.total_tasks,inputTokens:l.input_tokens,outputTokens:l.output_tokens,cachedInputTokens:l.cached_input_tokens,costUsd:l.cost_usd,totalTokens:l.input_tokens+l.output_tokens,activeDurationMs:l.active_duration_ms??0,lastActiveAt:l.last_active_at??null}))}catch(o){throw new _("DB_ERROR","Failed to get provider usage",o)}finally{r.close();}}getModelUsage(t,n,s){if(!this.dbExists())return [];let r=this.openHandle(false);try{let o=sql`
212
- CASE
213
- WHEN ${e.model} LIKE 'claude-%' OR ${e.model} IN ('opus', 'sonnet', 'haiku', 'opus[1m]', 'sonnet[1m]') THEN 'claude'
214
- WHEN ${e.model} LIKE 'gpt-%' OR ${e.model} LIKE 'codex-%' THEN 'codex'
215
- WHEN ${e.model} LIKE 'gemini-%' THEN 'gemini'
216
- WHEN ${e.model} LIKE 'zai-%' OR ${e.model} LIKE 'openrouter/z-ai/%' THEN 'opencode'
217
- WHEN ${e.model} LIKE 'minimax/%' THEN 'minimax'
218
- WHEN ${e.model} LIKE 'qwen%' THEN 'qwen'
219
- ELSE 'unknown'
220
- END
221
- `,i=sql`
231
+ ${d}
232
+ GROUP BY ${i}
233
+ ORDER BY (COALESCE(SUM(${a}), 0) + COALESCE(SUM(${e.output_tokens}), 0)) DESC
234
+ `).map(c=>({provider:c.provider,totalTasks:c.total_tasks,inputTokens:c.input_tokens,outputTokens:c.output_tokens,cachedInputTokens:c.cached_input_tokens,costUsd:c.cost_usd,totalTokens:c.input_tokens+c.output_tokens,activeDurationMs:c.active_duration_ms??0,lastActiveAt:c.last_active_at??null}))}catch(i){throw new p("DB_ERROR","Failed to get provider usage",i)}finally{r.close();}}getModelUsage(t,n,s){if(!this.dbExists())return [];let r=this.openHandle(false);try{let i=te(),a=sql`
222
235
  COALESCE(${e.input_tokens}, 0)
223
236
  + CASE
224
- WHEN ${e.started_at} >= ${G}
237
+ WHEN ${e.started_at} >= ${tt}
225
238
  AND (
226
239
  ${e.crewx_version} IS NULL
227
240
  OR (${e.crewx_version} LIKE '0.8.%' AND ${e.crewx_version} NOT LIKE '0.8.9%')
228
- OR (${e.crewx_version} LIKE '0.8.9-rc.%' AND CAST(SUBSTR(${e.crewx_version}, ${X}) AS INTEGER) < ${Y})
241
+ OR (${e.crewx_version} LIKE '0.8.9-rc.%' AND CAST(SUBSTR(${e.crewx_version}, ${et}) AS INTEGER) < ${nt})
229
242
  )
230
243
  THEN COALESCE(${e.cached_input_tokens}, 0)
231
244
  ELSE 0
232
245
  END
233
- `,a=s?sql`WHERE ${e.status} IN ('completed', 'success') AND ${e.started_at} >= ${t} AND ${e.started_at} < ${n} AND ${e.workspace_id} = ${s}`:sql`WHERE ${e.status} IN ('completed', 'success') AND ${e.started_at} >= ${t} AND ${e.started_at} < ${n}`,c=r.db.all(sql`
246
+ `,d=s?sql`WHERE ${e.status} IN ('completed', 'success') AND ${e.started_at} >= ${t} AND ${e.started_at} < ${n} AND ${e.workspace_id} = ${s}`:sql`WHERE ${e.status} IN ('completed', 'success') AND ${e.started_at} >= ${t} AND ${e.started_at} < ${n}`,u=r.db.all(sql`
234
247
  SELECT
235
248
  ${e.model} AS model,
236
- ${o} AS provider,
249
+ ${i} AS provider,
237
250
  COUNT(*) AS total_tasks,
238
- COALESCE(SUM(${i}), 0) AS input_tokens,
251
+ COALESCE(SUM(${a}), 0) AS input_tokens,
239
252
  COALESCE(SUM(${e.output_tokens}), 0) AS output_tokens,
240
253
  COALESCE(SUM(${e.cached_input_tokens}), 0) AS cached_input_tokens,
241
254
  COALESCE(SUM(${e.cost_usd}), 0) AS cost_usd,
242
255
  COALESCE(SUM(${e.duration_ms}), 0) AS active_duration_ms,
243
256
  MAX(${e.completed_at}) AS last_active_at
244
257
  FROM ${e}
245
- ${a}
246
- GROUP BY ${e.model}
247
- `),l=new Map;for(let u of c){let h=Wt(u.model??""),g=l.get(h);g?(g.totalTasks+=u.total_tasks,g.inputTokens+=u.input_tokens,g.outputTokens+=u.output_tokens,g.cachedInputTokens+=u.cached_input_tokens,g.costUsd+=u.cost_usd,g.totalTokens+=u.input_tokens+u.output_tokens,g.activeDurationMs+=u.active_duration_ms??0,u.last_active_at&&(!g.lastActiveAt||u.last_active_at>g.lastActiveAt)&&(g.lastActiveAt=u.last_active_at)):l.set(h,{model:h,provider:u.provider,totalTasks:u.total_tasks,inputTokens:u.input_tokens,outputTokens:u.output_tokens,cachedInputTokens:u.cached_input_tokens,costUsd:u.cost_usd,totalTokens:u.input_tokens+u.output_tokens,activeDurationMs:u.active_duration_ms??0,lastActiveAt:u.last_active_at??null});}return Array.from(l.values()).sort((u,h)=>h.costUsd-u.costUsd)}catch(o){throw new _("DB_ERROR","Failed to get model usage",o)}finally{r.close();}}getTasksForReport(t,n,s){if(!this.dbExists())return [];let r=this.openHandle(false);try{let o=s?sql`WHERE ${e.started_at} >= ${t} AND ${e.started_at} < ${n} AND ${e.workspace_id} = ${s}`:sql`WHERE ${e.started_at} >= ${t} AND ${e.started_at} < ${n}`;return r.db.all(sql`
258
+ ${d}
259
+ GROUP BY ${e.model}, ${i}
260
+ `),c=new Map;for(let l of u){let h=Zt(l.model??""),m=JSON.stringify([l.provider,h]),w=c.get(m);w?(w.totalTasks+=l.total_tasks,w.inputTokens+=l.input_tokens,w.outputTokens+=l.output_tokens,w.cachedInputTokens+=l.cached_input_tokens,w.costUsd+=l.cost_usd,w.totalTokens+=l.input_tokens+l.output_tokens,w.activeDurationMs+=l.active_duration_ms??0,l.last_active_at&&(!w.lastActiveAt||l.last_active_at>w.lastActiveAt)&&(w.lastActiveAt=l.last_active_at)):c.set(m,{model:h,provider:l.provider,totalTasks:l.total_tasks,inputTokens:l.input_tokens,outputTokens:l.output_tokens,cachedInputTokens:l.cached_input_tokens,costUsd:l.cost_usd,totalTokens:l.input_tokens+l.output_tokens,activeDurationMs:l.active_duration_ms??0,lastActiveAt:l.last_active_at??null});}return Array.from(c.values()).sort((l,h)=>h.costUsd-l.costUsd)}catch(i){throw new p("DB_ERROR","Failed to get model usage",i)}finally{r.close();}}getTasksForReport(t,n,s){if(!this.dbExists())return [];let r=this.openHandle(false);try{let i=s?sql`WHERE ${e.started_at} >= ${t} AND ${e.started_at} < ${n} AND ${e.workspace_id} = ${s}`:sql`WHERE ${e.started_at} >= ${t} AND ${e.started_at} < ${n}`;return r.db.all(sql`
248
261
  SELECT
249
262
  ${e.thread_id} AS thread_id,
250
263
  ${e.agent_id} AS agent_id,
@@ -253,13 +266,13 @@ ${s.join(`
253
266
  ${e.error} AS error,
254
267
  ${e.exit_code} AS exit_code
255
268
  FROM ${e}
256
- ${o}
269
+ ${i}
257
270
  ORDER BY ${e.started_at} ASC
258
- `).map(a=>({threadId:a.thread_id,agentId:a.agent_id,startedAt:a.started_at,status:a.status,error:a.error,exitCode:a.exit_code}))}catch(o){throw new _("DB_ERROR","Failed to get tasks for report",o)}finally{r.close();}}findTaskEvidence(t){if(!this.dbExists())return [];let n=this.openHandle(false);try{let s=[];t.workspaceId&&s.push(eq(e.workspace_id,t.workspaceId)),t.agents&&t.agents.length>0&&s.push(inArray(e.agent_id,t.agents)),t.statuses&&t.statuses.length>0&&s.push(inArray(e.status,t.statuses)),t.from&&s.push(gte(e.started_at,t.from)),t.to&&s.push(lt(e.started_at,t.to));let r=s.length>0?and(...s):void 0,o=(t.order??"DESC")==="ASC"?asc(e.started_at):desc(e.started_at),i={id:e.id,agent_id:e.agent_id,status:e.status,prompt:e.prompt,started_at:e.started_at,completed_at:e.completed_at,thread_id:e.thread_id};return t.limit?n.db.select(i).from(e).where(r).orderBy(o).limit(t.limit).all():n.db.select(i).from(e).where(r).orderBy(o).all()}catch(s){throw new _("DB_ERROR","Failed to find task evidence",s)}finally{n.close();}}findThreadChains(t){if(!this.dbExists())return [];let n=this.openHandle(false);try{let s=t.maxThreads??8,r=t.maxTurnsPerThread??4,o=[isNotNull(e.thread_id),isNull(e.parent_task_id),isNull(e.caller_agent_id),or(isNull(e.platform),ne(e.platform,"workflow")),or(isNull(e.metadata),notLike(e.metadata,'%"kind":"workflow_card"%')),or(isNull(e.metadata),notLike(e.metadata,'%"retriedFromTaskId"%'))];t.workspaceId&&o.push(eq(e.workspace_id,t.workspaceId)),t.from&&o.push(gte(e.started_at,t.from)),t.to&&o.push(lt(e.started_at,t.to));let i=n.db.select({id:e.id,agent_id:e.agent_id,status:e.status,prompt:e.prompt,started_at:e.started_at,completed_at:e.completed_at,thread_id:e.thread_id}).from(e).where(and(...o)).orderBy(asc(e.started_at),asc(e.id)).all(),a=new Map;for(let l of i){if(!l.thread_id)continue;let u={id:l.id,agentId:l.agent_id,status:l.status,prompt:l.prompt,startedAt:l.started_at,completedAt:l.completed_at},h=a.get(l.thread_id);h?h.push(u):a.set(l.thread_id,[u]);}let c=[];for(let[l,u]of a){let h=u.filter(g=>g.agentId===t.targetAgentId).length;h<2||c.push({threadId:l,targetAgentTurnCount:h,turns:u});}return c.sort((l,u)=>{let h=l.turns[l.turns.length-1].startedAt,g=u.turns[u.turns.length-1].startedAt;return h<g?1:h>g?-1:0}),c.slice(0,s).map(l=>({threadId:l.threadId,targetAgentTurnCount:l.targetAgentTurnCount,turns:l.turns.slice(-r)}))}catch(s){throw new _("DB_ERROR","Failed to find thread chains",s)}finally{n.close();}}};var At=class extends j{name="sqlite-tracing";unsubs=[];dbPath;version;constructor(t){super(),this.dbPath=join(t?.dbRoot??homedir(),".crewx","crewx.db"),this.version=t?.version??"unknown";}attach(t){let n=new mt({dbPath:this.dbPath}),s=process.cwd(),o=existsSync(join(s,"crewx.yaml"))||existsSync(join(s,"crewx.yml"))?$t(s):null,i=process.argv.join(" ");this.unsubs.push(t.on("task:start",a=>{try{let c=a.callerAgentId??null,l=a.parentTaskId??null,u=a.rootTraceId??a.traceId,h=a.metadata?JSON.stringify(a.metadata):JSON.stringify({provider:a.provider??"cli/claude"});n.startTask({id:a.traceId,agentId:a.agentRef.replace(/^@/,""),prompt:a.message,mode:a.mode,status:"running",pid:a.pid??null,startedAt:a.timestamp.toISOString(),crewxVersion:this.version,platform:a.platform??"cli",model:a.model??null,renderedPrompt:a.renderedPrompt??null,command:i,codingAgentCommand:a.codingAgentCommand??null,workspaceId:a.workspaceId??o,callerAgentId:c,parentTaskId:l,traceId:u,metadata:h,threadId:a.threadId??null});}catch{}}),t.on("task:output",a=>{try{n.appendLog(a.traceId,{timestamp:a.timestamp.toISOString(),level:a.level??"stdout",message:a.output});}catch{}}),t.on("task:end",a=>{try{let c=typeof a.metadata?.runEpoch=="number"?a.metadata.runEpoch:null,l=a.error?JSON.stringify({code:a.error.code,message:a.error.message,...a.error.providerCode?{providerCode:a.error.providerCode}:{}}):null;n.finishTask({id:a.traceId,status:a.error?"failed":"success",result:a.result??null,error:l,completedAt:a.timestamp.toISOString(),durationMs:a.durationMs,exitCode:a.exitCode??null,inputTokens:a.inputTokens??0,outputTokens:a.outputTokens??0,cachedInputTokens:a.cachedInputTokens??0,costUsd:a.costUsd??0,model:a.model??null,runEpoch:c});}catch{}}));}detach(t){this.unsubs.forEach(n=>n()),this.unsubs=[];}};var ft=class extends nt{dbPath;constructor(t={}){super(),t.dbPath?this.dbPath=t.dbPath:t.dbRoot&&(this.dbPath=join(t.dbRoot,".crewx","crewx.db"));}resolveDbPath(){return this.dbPath?this.dbPath:super.resolveDbPath()}openHandle(t){let n=this.resolveDbPath();if(t){let r=dirname(n);existsSync(r)||mkdirSync(r,{recursive:true});}else if(!existsSync(n))throw new _("NOT_FOUND","Database not found");let s=b(n);if(t)try{ct(s.db,n);}catch(r){throw s.close(),r}return s}validateWorkspaceId(t,n){return t.db.select({id:st.id}).from(st).where(eq(st.id,n)).limit(1).get()?n:null}topLevelTaskPredicateSql(t="child"){return sql.raw(`NOT EXISTS (
271
+ `).map(d=>({threadId:d.thread_id,agentId:d.agent_id,startedAt:d.started_at,status:d.status,error:d.error,exitCode:d.exit_code}))}catch(i){throw new p("DB_ERROR","Failed to get tasks for report",i)}finally{r.close();}}findTaskEvidence(t){if(!this.dbExists())return [];let n=this.openHandle(false);try{let s=[];t.workspaceId&&s.push(eq(e.workspace_id,t.workspaceId)),t.agents&&t.agents.length>0&&s.push(inArray(e.agent_id,t.agents)),t.statuses&&t.statuses.length>0&&s.push(inArray(e.status,t.statuses)),t.from&&s.push(gte(e.started_at,t.from)),t.to&&s.push(lt(e.started_at,t.to));let r=s.length>0?and(...s):void 0,i=(t.order??"DESC")==="ASC"?asc(e.started_at):desc(e.started_at),a={id:e.id,agent_id:e.agent_id,status:e.status,prompt:e.prompt,started_at:e.started_at,completed_at:e.completed_at,thread_id:e.thread_id};return t.limit?n.db.select(a).from(e).where(r).orderBy(i).limit(t.limit).all():n.db.select(a).from(e).where(r).orderBy(i).all()}catch(s){throw new p("DB_ERROR","Failed to find task evidence",s)}finally{n.close();}}findThreadChains(t){if(!this.dbExists())return [];let n=this.openHandle(false);try{let s=t.maxThreads??8,r=t.maxTurnsPerThread??4,i=[isNotNull(e.thread_id),isNull(e.parent_task_id),isNull(e.caller_agent_id),or(isNull(e.platform),ne(e.platform,"workflow")),or(isNull(e.metadata),and(notLike(e.metadata,'%"kind":"workflow_card"%'),notLike(e.metadata,'%"kind":"workflow_ui_instance"%'))),or(isNull(e.metadata),notLike(e.metadata,'%"retriedFromTaskId"%'))];t.workspaceId&&i.push(eq(e.workspace_id,t.workspaceId)),t.from&&i.push(gte(e.started_at,t.from)),t.to&&i.push(lt(e.started_at,t.to));let a=n.db.select({id:e.id,agent_id:e.agent_id,status:e.status,prompt:e.prompt,started_at:e.started_at,completed_at:e.completed_at,thread_id:e.thread_id}).from(e).where(and(...i)).orderBy(asc(e.started_at),asc(e.id)).all(),d=new Map;for(let c of a){if(!c.thread_id)continue;let l={id:c.id,agentId:c.agent_id,status:c.status,prompt:c.prompt,startedAt:c.started_at,completedAt:c.completed_at},h=d.get(c.thread_id);h?h.push(l):d.set(c.thread_id,[l]);}let u=[];for(let[c,l]of d){let h=l.filter(m=>m.agentId===t.targetAgentId).length;h<2||u.push({threadId:c,targetAgentTurnCount:h,turns:l});}return u.sort((c,l)=>{let h=c.turns[c.turns.length-1].startedAt,m=l.turns[l.turns.length-1].startedAt;return h<m?1:h>m?-1:0}),u.slice(0,s).map(c=>({threadId:c.threadId,targetAgentTurnCount:c.targetAgentTurnCount,turns:c.turns.slice(-r)}))}catch(s){throw new p("DB_ERROR","Failed to find thread chains",s)}finally{n.close();}}};var Lt=class extends Q{name="sqlite-tracing";unsubs=[];dbPath;version;constructor(t){super(),this.dbPath=join(t?.dbRoot??homedir(),".crewx","crewx.db"),this.version=t?.version??"unknown";}attach(t){let n=new xt({dbPath:this.dbPath}),s=process.cwd(),i=existsSync(join(s,"crewx.yaml"))||existsSync(join(s,"crewx.yml"))?qt(s):null,a=process.argv.join(" ");this.unsubs.push(t.on("task:start",d=>{try{let u=d.callerAgentId??null,c=d.parentTaskId??null,l=d.rootTraceId??d.traceId,h=d.metadata?JSON.stringify(d.metadata):JSON.stringify({provider:d.provider??"cli/claude"});n.startTask({id:d.traceId,agentId:d.agentRef.replace(/^@/,""),prompt:d.message,mode:d.mode,status:"running",pid:d.pid??null,startedAt:d.timestamp.toISOString(),crewxVersion:this.version,platform:d.platform??"cli",model:d.model??null,renderedPrompt:d.renderedPrompt??null,command:a,codingAgentCommand:d.codingAgentCommand??null,workspaceId:d.workspaceId??i,callerAgentId:u,parentTaskId:c,traceId:l,metadata:h,threadId:d.threadId??null});}catch{}}),t.on("task:output",d=>{try{n.appendLog(d.traceId,{timestamp:d.timestamp.toISOString(),level:d.level??"stdout",message:d.output});}catch{}}),t.on("task:end",d=>{try{let u=typeof d.metadata?.runEpoch=="number"?d.metadata.runEpoch:null,c=d.error?JSON.stringify({code:d.error.code,message:d.error.message,...d.error.providerCode?{providerCode:d.error.providerCode}:{}}):null;n.finishTask({id:d.traceId,status:d.error?"failed":"success",result:d.result??null,error:c,completedAt:d.timestamp.toISOString(),durationMs:d.durationMs,exitCode:d.exitCode??null,inputTokens:d.inputTokens??0,outputTokens:d.outputTokens??0,cachedInputTokens:d.cachedInputTokens??0,costUsd:d.costUsd??0,model:d.model??null,runEpoch:u});}catch{}}));}detach(t){this.unsubs.forEach(n=>n()),this.unsubs=[];}};var bt=class extends dt{dbPath;constructor(t={}){super(),t.dbPath?this.dbPath=t.dbPath:t.dbRoot&&(this.dbPath=join(t.dbRoot,".crewx","crewx.db"));}resolveDbPath(){return this.dbPath?this.dbPath:super.resolveDbPath()}openHandle(t){let n=this.resolveDbPath();if(t){let r=dirname(n);existsSync(r)||mkdirSync(r,{recursive:true});}else if(!existsSync(n))throw new p("NOT_FOUND","Database not found");let s=y(n);if(t)try{kt(s.db,n);}catch(r){throw s.close(),r}return s}validateWorkspaceId(t,n){return t.db.select({id:ct.id}).from(ct).where(eq(ct.id,n)).limit(1).get()?n:null}topLevelTaskPredicateSql(t="child"){return sql.raw(`NOT EXISTS (
259
272
  SELECT 1 FROM tasks parent
260
273
  WHERE parent.id = ${t}.parent_task_id
261
274
  AND parent.thread_id = ${t}.thread_id
262
- )`)}findAllThreads(t){let n=this.resolveDbPaths(),s=new Set,r=[];for(let o of n){if(!existsSync(o))continue;let i=b(o);try{let a=t?eq(p.workspace_id,t):void 0,c=i.db.select().from(p).where(a).orderBy(desc(p.updated_at)).all();for(let l of c)s.has(l.id)||(s.add(l.id),r.push(l));}catch(a){throw new _("DB_ERROR","Failed to find all threads",a)}finally{i.close();}}return r}findThreadsByIdsOrTitles(t,n){if(t.length===0)return [];let s=this.resolveDbPaths(),r=new Set,o=[];for(let i of s){if(!existsSync(i))continue;let a=b(i);try{let c=or(inArray(p.id,t),inArray(p.title,t)),l=n?and(c,eq(p.workspace_id,n)):c,u=a.db.select().from(p).where(l).orderBy(desc(p.updated_at)).all();for(let h of u)r.has(h.id)||(r.add(h.id),o.push(h));}catch(c){throw new _("DB_ERROR","Failed to find threads by ids or titles",c)}finally{a.close();}}return o}findThreadById(t,n){let s=this.resolveDbPaths();for(let r of s){if(!existsSync(r))continue;let o=b(r);try{let i=eq(p.id,t),a=n?and(i,eq(p.workspace_id,n)):i,c=o.db.select().from(p).where(a).limit(1).get()??void 0;if(c)return c}catch(i){throw new _("DB_ERROR","Failed to find thread by id",i)}finally{o.close();}}}threadExists(t,n){let s=this.resolveDbPaths();for(let r of s){if(!existsSync(r))continue;let o=b(r);try{let i=eq(p.id,t),a=n?and(i,eq(p.workspace_id,n)):i;if(o.db.select({id:p.id}).from(p).where(a).limit(1).get())return !0}catch(i){throw new _("DB_ERROR","Failed to check thread existence",i)}finally{o.close();}}return false}aggregateTaskStats(t,n){let s=this.resolveDbPaths(),r=0,o=0,i=0,a=0,c=0,l=new Set;for(let u of s){if(!existsSync(u))continue;let h=b(u);try{let g=h.db.get(sql`
275
+ )`)}findAllThreads(t){let n=this.resolveDbPaths(),s=new Set,r=[];for(let i of n){if(!existsSync(i))continue;let a=y(i);try{let d=t?eq(_.workspace_id,t):void 0,u=a.db.select().from(_).where(d).orderBy(desc(_.updated_at)).all();for(let c of u)s.has(c.id)||(s.add(c.id),r.push(c));}catch(d){throw new p("DB_ERROR","Failed to find all threads",d)}finally{a.close();}}return r}findThreadsByIdsOrTitles(t,n){if(t.length===0)return [];let s=this.resolveDbPaths(),r=new Set,i=[];for(let a of s){if(!existsSync(a))continue;let d=y(a);try{let u=or(inArray(_.id,t),inArray(_.title,t)),c=n?and(u,eq(_.workspace_id,n)):u,l=d.db.select().from(_).where(c).orderBy(desc(_.updated_at)).all();for(let h of l)r.has(h.id)||(r.add(h.id),i.push(h));}catch(u){throw new p("DB_ERROR","Failed to find threads by ids or titles",u)}finally{d.close();}}return i}findThreadById(t,n){let s=this.resolveDbPaths();for(let r of s){if(!existsSync(r))continue;let i=y(r);try{let a=eq(_.id,t),d=n?and(a,eq(_.workspace_id,n)):a,u=i.db.select().from(_).where(d).limit(1).get()??void 0;if(u)return u}catch(a){throw new p("DB_ERROR","Failed to find thread by id",a)}finally{i.close();}}}threadExists(t,n){let s=this.resolveDbPaths();for(let r of s){if(!existsSync(r))continue;let i=y(r);try{let a=eq(_.id,t),d=n?and(a,eq(_.workspace_id,n)):a;if(i.db.select({id:_.id}).from(_).where(d).limit(1).get())return !0}catch(a){throw new p("DB_ERROR","Failed to check thread existence",a)}finally{i.close();}}return false}aggregateTaskStats(t,n){let s=this.resolveDbPaths(),r=0,i=0,a=0,d=0,u=0,c=new Set;for(let l of s){if(!existsSync(l))continue;let h=y(l);try{let m=h.db.get(sql`
263
276
  SELECT
264
277
  count(*) AS cnt,
265
278
  COALESCE(SUM(child.input_tokens), 0) AS total_input,
@@ -270,13 +283,13 @@ ${s.join(`
270
283
  WHERE child.thread_id = ${t}
271
284
  AND ${this.topLevelTaskPredicateSql()}
272
285
  ${n?sql`AND child.workspace_id = ${n}`:sql``}
273
- `);g&&(r+=g.cnt,o+=g.total_input,i+=g.total_output,a+=g.total_cached,c+=g.total_cost);let y=h.db.all(sql`
286
+ `);m&&(r+=m.cnt,i+=m.total_input,a+=m.total_output,d+=m.total_cached,u+=m.total_cost);let w=h.db.all(sql`
274
287
  SELECT DISTINCT child.agent_id FROM tasks child
275
288
  WHERE child.thread_id = ${t}
276
289
  AND child.agent_id IS NOT NULL AND child.agent_id != ''
277
290
  AND ${this.topLevelTaskPredicateSql()}
278
291
  ${n?sql`AND child.workspace_id = ${n}`:sql``}
279
- `);for(let C of y)l.add(C.agent_id);}catch(g){throw new _("DB_ERROR","Failed to aggregate task stats",g)}finally{h.close();}}return {taskCount:r,inputTokens:o,outputTokens:i,cachedInputTokens:a,costUsd:c,agentIds:Array.from(l)}}findTopLevelTasks(t,n,s){let r=this.resolveDbPaths(),o=new Set,i=[];for(let a of r){if(!existsSync(a))continue;let c=b(a);try{let l;s!==void 0?l=c.db.all(sql`
292
+ `);for(let $ of w)c.add($.agent_id);}catch(m){throw new p("DB_ERROR","Failed to aggregate task stats",m)}finally{h.close();}}return {taskCount:r,inputTokens:i,outputTokens:a,cachedInputTokens:d,costUsd:u,agentIds:Array.from(c)}}findTopLevelTasks(t,n,s){let r=this.resolveDbPaths(),i=new Set,a=[];for(let d of r){if(!existsSync(d))continue;let u=y(d);try{let c;s!==void 0?c=u.db.all(sql`
280
293
  SELECT * FROM (
281
294
  SELECT child.*,
282
295
  ROW_NUMBER() OVER (PARTITION BY child.agent_id ORDER BY child.started_at DESC) AS rn
@@ -287,13 +300,13 @@ ${s.join(`
287
300
  ) ranked
288
301
  WHERE rn <= ${s}
289
302
  ORDER BY started_at ASC
290
- `):l=c.db.all(sql`
303
+ `):c=u.db.all(sql`
291
304
  SELECT child.* FROM tasks child
292
305
  WHERE child.thread_id = ${t}
293
306
  AND ${this.topLevelTaskPredicateSql()}
294
307
  ${n?sql`AND child.workspace_id = ${n}`:sql``}
295
308
  ORDER BY child.started_at ASC
296
- `);for(let u of l)o.has(u.id)||(o.add(u.id),i.push(u));}catch(l){throw new _("DB_ERROR","Failed to find top-level tasks",l)}finally{c.close();}}if(s!==void 0&&r.length>1){let a=new Map;for(let c of i){let l=c.agent_id??"";a.has(l)||a.set(l,[]),a.get(l).push(c);}i=[];for(let c of a.values())c.sort((l,u)=>(u.started_at??"").localeCompare(l.started_at??"")),i.push(...c.slice(0,s));i.sort((c,l)=>(c.started_at??"").localeCompare(l.started_at??""));}return i}findAllTasks(t,n){let s=this.resolveDbPaths(),r=new Set,o=[];for(let i of s){if(!existsSync(i))continue;let a=b(i);try{let c=eq(e.thread_id,t),l=n?and(c,eq(e.workspace_id,n)):c,u=a.db.select().from(e).where(l).orderBy(asc(e.started_at)).all();for(let h of u)r.has(h.id)||(r.add(h.id),o.push(h));}catch(c){throw new _("DB_ERROR","Failed to find all tasks for thread",c)}finally{a.close();}}return o}findTaskById(t,n,s){let r=this.resolveDbPaths();for(let o of r){if(!existsSync(o))continue;let i=b(o);try{let a=and(eq(e.id,n),eq(e.thread_id,t)),c=s?and(a,eq(e.workspace_id,s)):a,l=i.db.select().from(e).where(c).limit(1).get();if(!l)continue;let u=i.db.select().from(e).where(eq(e.parent_task_id,l.id)).orderBy(asc(e.started_at)).all();return {task:l,children:u}}catch(a){throw new _("DB_ERROR","Failed to find task by id",a)}finally{i.close();}}}batchFetchTasksQuery(t,n){return sql`
309
+ `);for(let l of c)i.has(l.id)||(i.add(l.id),a.push(l));}catch(c){throw new p("DB_ERROR","Failed to find top-level tasks",c)}finally{u.close();}}if(s!==void 0&&r.length>1){let d=new Map;for(let u of a){let c=u.agent_id??"";d.has(c)||d.set(c,[]),d.get(c).push(u);}a=[];for(let u of d.values())u.sort((c,l)=>(l.started_at??"").localeCompare(c.started_at??"")),a.push(...u.slice(0,s));a.sort((u,c)=>(u.started_at??"").localeCompare(c.started_at??""));}return a}findAllTasks(t,n){let s=this.resolveDbPaths(),r=new Set,i=[];for(let a of s){if(!existsSync(a))continue;let d=y(a);try{let u=eq(e.thread_id,t),c=n?and(u,eq(e.workspace_id,n)):u,l=d.db.select().from(e).where(c).orderBy(asc(e.started_at)).all();for(let h of l)r.has(h.id)||(r.add(h.id),i.push(h));}catch(u){throw new p("DB_ERROR","Failed to find all tasks for thread",u)}finally{d.close();}}return i}findTaskById(t,n,s){let r=this.resolveDbPaths();for(let i of r){if(!existsSync(i))continue;let a=y(i);try{let d=and(eq(e.id,n),eq(e.thread_id,t)),u=s?and(d,eq(e.workspace_id,s)):d,c=a.db.select().from(e).where(u).limit(1).get();if(!c)continue;let l=a.db.select().from(e).where(eq(e.parent_task_id,c.id)).orderBy(asc(e.started_at)).all();return {task:c,children:l}}catch(d){throw new p("DB_ERROR","Failed to find task by id",d)}finally{a.close();}}}batchFetchTasksQuery(t,n){return sql`
297
310
  SELECT child.id, child.thread_id, child.agent_id, child.status,
298
311
  child.parent_task_id, child.started_at, child.completed_at,
299
312
  child.duration_ms, child.input_tokens, child.output_tokens,
@@ -303,16 +316,16 @@ ${s.join(`
303
316
  AND ${this.topLevelTaskPredicateSql()}
304
317
  ${n?sql`AND child.workspace_id = ${n}`:sql``}
305
318
  ORDER BY child.started_at ASC
306
- `}batchFetchTasks(t,n){let s=new Map;if(t.length===0)return s;let r=this.resolveDbPaths();for(let o of r){if(!existsSync(o))continue;let i=b(o);try{let a=i.db.all(this.batchFetchTasksQuery(t,n));for(let c of a){let l=c.thread_id;s.has(l)||s.set(l,[]),s.get(l).push(c);}}catch(a){throw new _("DB_ERROR","Failed to batch fetch tasks",a)}finally{i.close();}}return s}explainBatchFetchTasksPlan(t,n){let s=this.resolveDbPaths();for(let r of s){if(!existsSync(r))continue;let o=b(r);try{return o.db.all(sql`EXPLAIN QUERY PLAN ${this.batchFetchTasksQuery(t,n)}`).map(a=>a.detail)}finally{o.close();}}return []}updateThreadTitle(t,n,s){if(!this.dbExists())return;let r=this.openHandle(true);try{let o=eq(p.id,t),i=s?and(o,eq(p.workspace_id,s)):o;if(!r.db.select({id:p.id}).from(p).where(i).limit(1).get())return;r.db.update(p).set({title:n,title_locked:1,updated_at:new Date().toISOString()}).where(eq(p.id,t)).run();}catch(o){throw o instanceof _?o:new _("DB_ERROR","Failed to update thread title",o)}finally{r.close();}}upsertThread(t,n){let s=this.openHandle(true);try{let r=n.workspaceId?this.validateWorkspaceId(s,n.workspaceId):null,o=new Date().toISOString();if(s.db.select({id:p.id,message_count:p.message_count}).from(p).where(eq(p.id,t)).limit(1).get()){let a={updated_at:o};n.title!==void 0&&(a.title=n.title),n.titleLocked!==void 0&&(a.title_locked=n.titleLocked?1:0),s.db.update(p).set(a).where(eq(p.id,t)).run();}else s.db.insert(p).values({id:t,platform:n.platform,workspace_id:r,title:n.title??null,title_locked:n.titleLocked?1:0,message_count:0,created_at:o,updated_at:o}).run();}catch(r){throw r instanceof _?r:new _("DB_ERROR","Failed to upsert thread",r)}finally{s.close();}}ensureThread(t,n,s){let r=this.openHandle(true);try{let o=s?this.validateWorkspaceId(r,s):null,i=r.db.select({id:p.id,platform:p.platform,workspace_id:p.workspace_id}).from(p).where(eq(p.id,t)).limit(1).get();if(i){o&&!i.workspace_id&&r.db.update(p).set({workspace_id:o}).where(eq(p.id,t)).run();return}let a=new Date().toISOString();r.db.insert(p).values({id:t,platform:n,workspace_id:o,message_count:0,created_at:a,updated_at:a}).run();}catch(o){throw o instanceof _?o:new _("DB_ERROR","Failed to ensure thread",o)}finally{r.close();}}saveUserMessage(t,n,s){if(!this.dbExists())return {firstMessage:false};let r=this.openHandle(true);try{let o=new Date().toISOString();return {firstMessage:r.db.transaction(a=>{let l=a.select({message_count:p.message_count}).from(p).where(eq(p.id,t)).limit(1).get()?.message_count===0;return a.run(sql`
319
+ `}batchFetchTasks(t,n){let s=new Map;if(t.length===0)return s;let r=this.resolveDbPaths();for(let i of r){if(!existsSync(i))continue;let a=y(i);try{let d=a.db.all(this.batchFetchTasksQuery(t,n));for(let u of d){let c=u.thread_id;s.has(c)||s.set(c,[]),s.get(c).push(u);}}catch(d){throw new p("DB_ERROR","Failed to batch fetch tasks",d)}finally{a.close();}}return s}explainBatchFetchTasksPlan(t,n){let s=this.resolveDbPaths();for(let r of s){if(!existsSync(r))continue;let i=y(r);try{return i.db.all(sql`EXPLAIN QUERY PLAN ${this.batchFetchTasksQuery(t,n)}`).map(d=>d.detail)}finally{i.close();}}return []}updateThreadTitle(t,n,s){if(!this.dbExists())return;let r=this.openHandle(true);try{let i=eq(_.id,t),a=s?and(i,eq(_.workspace_id,s)):i;if(!r.db.select({id:_.id}).from(_).where(a).limit(1).get())return;r.db.update(_).set({title:n,title_locked:1,updated_at:new Date().toISOString()}).where(eq(_.id,t)).run();}catch(i){throw i instanceof p?i:new p("DB_ERROR","Failed to update thread title",i)}finally{r.close();}}upsertThread(t,n){let s=this.openHandle(true);try{let r=n.workspaceId?this.validateWorkspaceId(s,n.workspaceId):null,i=new Date().toISOString();if(s.db.select({id:_.id,message_count:_.message_count}).from(_).where(eq(_.id,t)).limit(1).get()){let d={updated_at:i};n.title!==void 0&&(d.title=n.title),n.titleLocked!==void 0&&(d.title_locked=n.titleLocked?1:0),s.db.update(_).set(d).where(eq(_.id,t)).run();}else s.db.insert(_).values({id:t,platform:n.platform,workspace_id:r,title:n.title??null,title_locked:n.titleLocked?1:0,message_count:0,created_at:i,updated_at:i}).run();}catch(r){throw r instanceof p?r:new p("DB_ERROR","Failed to upsert thread",r)}finally{s.close();}}ensureThread(t,n,s){let r=this.openHandle(true);try{let i=s?this.validateWorkspaceId(r,s):null,a=r.db.select({id:_.id,platform:_.platform,workspace_id:_.workspace_id}).from(_).where(eq(_.id,t)).limit(1).get();if(a){i&&!a.workspace_id&&r.db.update(_).set({workspace_id:i}).where(eq(_.id,t)).run();return}let d=new Date().toISOString();r.db.insert(_).values({id:t,platform:n,workspace_id:i,message_count:0,created_at:d,updated_at:d}).run();}catch(i){throw i instanceof p?i:new p("DB_ERROR","Failed to ensure thread",i)}finally{r.close();}}saveUserMessage(t,n,s){if(!this.dbExists())return {firstMessage:false};let r=this.openHandle(true);try{let i=new Date().toISOString();return {firstMessage:r.db.transaction(d=>{let c=d.select({message_count:_.message_count}).from(_).where(eq(_.id,t)).limit(1).get()?.message_count===0;return d.run(sql`
307
320
  UPDATE threads
308
321
  SET first_message = COALESCE(first_message, ${n}),
309
322
  title = CASE WHEN title_locked = 0 AND title IS NULL THEN substr(${n}, 1, 60) ELSE title END,
310
323
  last_message = ${n},
311
324
  message_count = message_count + 1,
312
- updated_at = ${o}
325
+ updated_at = ${i}
313
326
  WHERE id = ${t}
314
- `),l},{behavior:"immediate"})}}catch(o){throw o instanceof _?o:new _("DB_ERROR","Failed to save user message",o)}finally{r.close();}}saveAssistantMessage(t,n,s){if(!this.dbExists())return;let r=this.openHandle(true);try{let o=new Date().toISOString();r.db.update(p).set({last_message:n,updated_at:o}).where(eq(p.id,t)).run();}catch(o){throw o instanceof _?o:new _("DB_ERROR","Failed to save assistant message",o)}finally{r.close();}}updateThread(t,n){if(!this.dbExists())return;let s=this.openHandle(true);try{let r={updated_at:new Date().toISOString()};n.title!==void 0&&(r.title=n.title,r.title_locked=1),n.titleLocked!==void 0&&(r.title_locked=n.titleLocked?1:0),s.db.update(p).set(r).where(eq(p.id,t)).run();}catch(r){throw r instanceof _?r:new _("DB_ERROR","Failed to update thread",r)}finally{s.close();}}togglePin(t,n){let s=this.openHandle(true);try{let r=n?and(eq(p.id,t),eq(p.workspace_id,n)):eq(p.id,t),o=s.db.select({pinned:p.pinned,metadata:p.metadata}).from(p).where(r).get();if(!o)return null;let i=o.pinned?0:1,a=o.metadata?JSON.parse(o.metadata):{};if(i){let c=n?and(eq(p.pinned,1),eq(p.workspace_id,n)):eq(p.pinned,1),l=s.db.select({metadata:p.metadata}).from(p).where(c).all(),u=null;for(let h of l){let g=h.metadata?JSON.parse(h.metadata):{};typeof g.pinOrder=="number"&&(u===null||g.pinOrder<u)&&(u=g.pinOrder);}a.pinOrder=u===null?0:u-1;}else delete a.pinOrder;return s.db.update(p).set({pinned:i,metadata:Object.keys(a).length>0?JSON.stringify(a):null}).where(r).run(),{pinned:!!i}}catch(r){throw r instanceof _?r:new _("DB_ERROR","Failed to toggle pin",r)}finally{s.close();}}reorderPins(t,n){let s=this.openHandle(true);try{for(let r=0;r<t.length;r++){let o=n?and(eq(p.id,t[r]),eq(p.workspace_id,n)):eq(p.id,t[r]),i=s.db.select({metadata:p.metadata}).from(p).where(o).get();if(!i)continue;let a=i.metadata?JSON.parse(i.metadata):{};a.pinOrder=r+1,s.db.update(p).set({metadata:JSON.stringify(a)}).where(o).run();}}catch(r){throw r instanceof _?r:new _("DB_ERROR","Failed to reorder pins",r)}finally{s.close();}}toggleStar(t,n){let s=this.openHandle(true);try{let r=n?and(eq(p.id,t),eq(p.workspace_id,n)):eq(p.id,t),o=s.db.select({starred:p.starred}).from(p).where(r).get();if(!o)return null;let i=o.starred?0:1;return s.db.update(p).set({starred:i}).where(r).run(),{starred:!!i}}catch(r){throw r instanceof _?r:new _("DB_ERROR","Failed to toggle star",r)}finally{s.close();}}resolveOverdriveForRequest(t,n,s,r){let i=this.openHandle(true);try{let a=n?and(eq(p.id,t),eq(p.workspace_id,n)):eq(p.id,t);return i.db.transaction(l=>{let u=l.select({metadata:p.metadata}).from(p).where(a).get();if(!u)return null;let h=u.metadata?JSON.parse(u.metadata):{},g=h.overdrive??{},y=r?.defaultTurns??g.defaultTurns??3,C=r?.updatedBy??"ui",N=new Date().toISOString(),$,M,B,rt;switch(s){case "enable-count":{let ot=r?.turns??y,it=r?.consumeCurrent?Math.max(ot-1,0):ot;$=it>0?"count":"off",M=it,B=!0,rt="count";break}case "enable-latch":{$="latch",M=0,B=!0,rt="latch";break}case "disable":{$="off",M=0,B=!1;break}default:{let ot=g.state??"off",it=typeof g.remaining=="number"?g.remaining:0;if(ot==="count"&&it>0){let Nt=it-1;Nt<=0?($="off",M=0):($="count",M=Nt),B=!0,rt="count";}else ot==="latch"?($="latch",M=0,B=!0,rt="latch"):($="off",M=0,B=!1);break}}return h.overdrive={state:$,remaining:M,defaultTurns:y,updatedAt:N,updatedBy:C},l.update(p).set({metadata:JSON.stringify(h),updated_at:N}).where(a).run(),{applied:B,appliedMode:rt,state:$,remaining:M}},{behavior:"immediate"})}catch(a){throw a instanceof _?a:new _("DB_ERROR","Failed to resolve overdrive",a)}finally{i.close();}}};function tn(d){return d.replace(/<conversation_history[^>]*>[\s\S]*?<\/conversation_history>/g,"").split(`
327
+ `),c},{behavior:"immediate"})}}catch(i){throw i instanceof p?i:new p("DB_ERROR","Failed to save user message",i)}finally{r.close();}}saveAssistantMessage(t,n,s){if(!this.dbExists())return;let r=this.openHandle(true);try{let i=new Date().toISOString();r.db.update(_).set({last_message:n,updated_at:i}).where(eq(_.id,t)).run();}catch(i){throw i instanceof p?i:new p("DB_ERROR","Failed to save assistant message",i)}finally{r.close();}}updateThread(t,n){if(!this.dbExists())return;let s=this.openHandle(true);try{let r={updated_at:new Date().toISOString()};n.title!==void 0&&(r.title=n.title,r.title_locked=1),n.titleLocked!==void 0&&(r.title_locked=n.titleLocked?1:0),s.db.update(_).set(r).where(eq(_.id,t)).run();}catch(r){throw r instanceof p?r:new p("DB_ERROR","Failed to update thread",r)}finally{s.close();}}togglePin(t,n){let s=this.openHandle(true);try{let r=n?and(eq(_.id,t),eq(_.workspace_id,n)):eq(_.id,t),i=s.db.select({pinned:_.pinned,metadata:_.metadata}).from(_).where(r).get();if(!i)return null;let a=i.pinned?0:1,d=i.metadata?JSON.parse(i.metadata):{};if(a){let u=n?and(eq(_.pinned,1),eq(_.workspace_id,n)):eq(_.pinned,1),c=s.db.select({metadata:_.metadata}).from(_).where(u).all(),l=null;for(let h of c){let m=h.metadata?JSON.parse(h.metadata):{};typeof m.pinOrder=="number"&&(l===null||m.pinOrder<l)&&(l=m.pinOrder);}d.pinOrder=l===null?0:l-1;}else delete d.pinOrder;return s.db.update(_).set({pinned:a,metadata:Object.keys(d).length>0?JSON.stringify(d):null}).where(r).run(),{pinned:!!a}}catch(r){throw r instanceof p?r:new p("DB_ERROR","Failed to toggle pin",r)}finally{s.close();}}reorderPins(t,n){let s=this.openHandle(true);try{for(let r=0;r<t.length;r++){let i=n?and(eq(_.id,t[r]),eq(_.workspace_id,n)):eq(_.id,t[r]),a=s.db.select({metadata:_.metadata}).from(_).where(i).get();if(!a)continue;let d=a.metadata?JSON.parse(a.metadata):{};d.pinOrder=r+1,s.db.update(_).set({metadata:JSON.stringify(d)}).where(i).run();}}catch(r){throw r instanceof p?r:new p("DB_ERROR","Failed to reorder pins",r)}finally{s.close();}}toggleStar(t,n){let s=this.openHandle(true);try{let r=n?and(eq(_.id,t),eq(_.workspace_id,n)):eq(_.id,t),i=s.db.select({starred:_.starred}).from(_).where(r).get();if(!i)return null;let a=i.starred?0:1;return s.db.update(_).set({starred:a}).where(r).run(),{starred:!!a}}catch(r){throw r instanceof p?r:new p("DB_ERROR","Failed to toggle star",r)}finally{s.close();}}resolveOverdriveForRequest(t,n,s,r){let a=this.openHandle(true);try{let d=n?and(eq(_.id,t),eq(_.workspace_id,n)):eq(_.id,t);return a.db.transaction(c=>{let l=c.select({metadata:_.metadata}).from(_).where(d).get();if(!l)return null;let h=l.metadata?JSON.parse(l.metadata):{},m=h.overdrive??{},w=r?.defaultTurns??m.defaultTurns??3,$=r?.updatedBy??"ui",v=new Date().toISOString(),B,j,G,ut;switch(s){case "enable-count":{let lt=r?.turns??w,_t=r?.consumeCurrent?Math.max(lt-1,0):lt;B=_t>0?"count":"off",j=_t,G=!0,ut="count";break}case "enable-latch":{B="latch",j=0,G=!0,ut="latch";break}case "disable":{B="off",j=0,G=!1;break}default:{let lt=m.state??"off",_t=typeof m.remaining=="number"?m.remaining:0;if(lt==="count"&&_t>0){let Mt=_t-1;Mt<=0?(B="off",j=0):(B="count",j=Mt),G=!0,ut="count";}else lt==="latch"?(B="latch",j=0,G=!0,ut="latch"):(B="off",j=0,G=!1);break}}return h.overdrive={state:B,remaining:j,defaultTurns:w,updatedAt:v,updatedBy:$},c.update(_).set({metadata:JSON.stringify(h),updated_at:v}).where(d).run(),{applied:G,appliedMode:ut,state:B,remaining:j}},{behavior:"immediate"})}catch(d){throw d instanceof p?d:new p("DB_ERROR","Failed to resolve overdrive",d)}finally{a.close();}}};function fn(o){return o.replace(/<conversation_history[^>]*>[\s\S]*?<\/conversation_history>/g,"").split(`
315
328
  `).filter(r=>!(r.startsWith("Loaded ")&&r.includes("layouts from")||r.includes("[dotenv@")||r.includes("[Nest]")&&r.includes("DEBUG")||r.startsWith("Registered custom layout:")||r.startsWith("Updated custom layout:"))).join(`
316
- `).trim()}function en(d){if(!d)return "";let t=d;try{let n=JSON.parse(t);Array.isArray(n)?t=n.filter(s=>s?.type==="text"&&s?.text).map(s=>s.text).join(`
317
- `):n&&typeof n=="object"&&n.result!==void 0&&(t=n.result||"");}catch{t=tn(t);}return t}var kt=class{dbPath;constructor(t){this.dbPath=t??join(homedir(),".crewx","crewx.db");}getThreadRepo(){return new ft({dbPath:this.dbPath})}updateThread(t,n){this.getThreadRepo().updateThread(t,{title:n.title});}async ensureThread(t,n,s){let r=this.getThreadRepo(),o=r.findThreadById(t);if(o){if(o.platform!==n)throw new Error(`Thread '${t}' already exists with platform '${o.platform}' \u2014 cannot change to '${n}' (platform is immutable)`);return {created:false}}return r.ensureThread(t,n,s),{created:true}}async fetchHistory(t,n){let s=n?.limit??100,r=this.getThreadRepo(),o=r.findThreadById(t),i=r.findTopLevelTasks(t,void 0,s),a=new Set(["queued","cancelled"]);i=i.filter(u=>(!u.status||!a.has(u.status))&&(!n?.currentTraceId||u.trace_id!==n.currentTraceId));let c=o?.platform??"cli",l=this.rowsToMessages(i);return {threadId:t,platform:c,messages:l,metadata:{title:o?.title??void 0,firstMessage:o?.first_message??void 0,lastMessage:o?.last_message??void 0,messageCount:o?.message_count??0,updatedAt:o?.updated_at?new Date(o.updated_at).getTime():void 0}}}async saveUserMessage(t,n,s,r){let{firstMessage:o}=this.getThreadRepo().saveUserMessage(t,n);return {id:t,firstMessage:o}}async saveAssistantMessage(t,n,s,r){return this.getThreadRepo().saveAssistantMessage(t,n),{id:t}}close(){}normalizeStatus(t){if(t&&!["success","completed","done"].includes(t)){if(["failed","error"].includes(t))return "failed";if(t==="running")return "running"}}rowsToMessages(t){let n=[];for(let s of t){s.prompt&&n.push({id:`${s.id}-user`,text:s.prompt,isAssistant:false,timestamp:new Date(s.started_at).getTime(),metadata:{caller_agent_id:s.caller_agent_id}});let r=en(s.result),o=this.normalizeStatus(s.status);if(r||o==="running"||o==="failed"){let i={agent_id:s.agent_id,task_id:s.id};o&&(i.status=o),o==="failed"&&s.error&&(i.reason=s.error.split(`
318
- `)[0].slice(0,200)),n.push({id:`${s.id}-assistant`,text:r,isAssistant:true,timestamp:new Date(s.started_at).getTime(),metadata:i});}}return n}};var Ct=class extends j{name="conversation";_provider;unsubStart=null;unsubEnd=null;constructor(t){super(),this._provider=new kt(t?.dbPath);}get conversationProvider(){return this._provider}async afterUserMessage(t,n,s,r){}async afterAssistantMessage(t,n,s){}attach(t){this.unsubStart=t.on("task:start",async n=>{if(!n.threadId)return;let s=n.platform??"cli";try{let r=await this._provider.ensureThread(n.threadId,s,n.workspaceId),o=await this._provider.saveUserMessage(n.threadId,n.message??"");await this.afterUserMessage(n.threadId,o.id,r.created||o.firstMessage,n);}catch{}}),this.unsubEnd=t.on("task:end",async n=>{if(!n.result)return;let s=n.metadata?.threadId;if(!s)return;let r=n.agentRef?.replace(/^@/,"")??"";try{let{id:o}=await this._provider.saveAssistantMessage(s,n.result,r);await this.afterAssistantMessage(s,o,n);}catch{}});}detach(t){this.unsubStart?.(),this.unsubStart=null,this.unsubEnd?.(),this.unsubEnd=null,this._provider.close?.();}};export{Ct as ConversationPlugin,Et as FileLoggerPlugin,At as SqliteTracingPlugin};
329
+ `).trim()}function gn(o){if(!o)return "";let t=o;try{let n=JSON.parse(t);Array.isArray(n)?t=n.filter(s=>s?.type==="text"&&s?.text).map(s=>s.text).join(`
330
+ `):n&&typeof n=="object"&&n.result!==void 0&&(t=n.result||"");}catch{t=fn(t);}return t}var At=class{dbPath;constructor(t){this.dbPath=t??join(homedir(),".crewx","crewx.db");}getThreadRepo(){return new bt({dbPath:this.dbPath})}updateThread(t,n){this.getThreadRepo().updateThread(t,{title:n.title});}async ensureThread(t,n,s){let r=this.getThreadRepo(),i=r.findThreadById(t);if(i){if(i.platform!==n)throw new Error(`Thread '${t}' already exists with platform '${i.platform}' \u2014 cannot change to '${n}' (platform is immutable)`);return {created:false}}return r.ensureThread(t,n,s),{created:true}}async fetchHistory(t,n){let s=n?.limit??100,r=this.getThreadRepo(),i=r.findThreadById(t),a=r.findTopLevelTasks(t,void 0,s),d=new Set(["queued","cancelled"]);a=a.filter(l=>(!l.status||!d.has(l.status))&&(!n?.currentTraceId||l.trace_id!==n.currentTraceId));let u=i?.platform??"cli",c=this.rowsToMessages(a);return {threadId:t,platform:u,messages:c,metadata:{title:i?.title??void 0,firstMessage:i?.first_message??void 0,lastMessage:i?.last_message??void 0,messageCount:i?.message_count??0,updatedAt:i?.updated_at?new Date(i.updated_at).getTime():void 0}}}async saveUserMessage(t,n,s,r){let{firstMessage:i}=this.getThreadRepo().saveUserMessage(t,n);return {id:t,firstMessage:i}}async saveAssistantMessage(t,n,s,r){return this.getThreadRepo().saveAssistantMessage(t,n),{id:t}}close(){}normalizeStatus(t){if(t&&!["success","completed","done"].includes(t)){if(["failed","error"].includes(t))return "failed";if(t==="running")return "running"}}rowsToMessages(t){let n=[];for(let s of t){s.prompt&&n.push({id:`${s.id}-user`,text:s.prompt,isAssistant:false,timestamp:new Date(s.started_at).getTime(),metadata:{caller_agent_id:s.caller_agent_id}});let r=gn(s.result),i=this.normalizeStatus(s.status);if(r||i==="running"||i==="failed"){let a={agent_id:s.agent_id,task_id:s.id};i&&(a.status=i),i==="failed"&&s.error&&(a.reason=s.error.split(`
331
+ `)[0].slice(0,200)),n.push({id:`${s.id}-assistant`,text:r,isAssistant:true,timestamp:new Date(s.started_at).getTime(),metadata:a});}}return n}};var Pt=class extends Q{name="conversation";_provider;unsubStart=null;unsubEnd=null;constructor(t){super(),this._provider=new At(t?.dbPath);}get conversationProvider(){return this._provider}async afterUserMessage(t,n,s,r){}async afterAssistantMessage(t,n,s){}attach(t){this.unsubStart=t.on("task:start",async n=>{if(!n.threadId)return;let s=n.platform??"cli";try{let r=await this._provider.ensureThread(n.threadId,s,n.workspaceId),i=await this._provider.saveUserMessage(n.threadId,n.message??"");await this.afterUserMessage(n.threadId,i.id,r.created||i.firstMessage,n);}catch{}}),this.unsubEnd=t.on("task:end",async n=>{if(!n.result)return;let s=n.metadata?.threadId;if(!s)return;let r=n.agentRef?.replace(/^@/,"")??"";try{let{id:i}=await this._provider.saveAssistantMessage(s,n.result,r);await this.afterAssistantMessage(s,i,n);}catch{}});}detach(t){this.unsubStart?.(),this.unsubStart=null,this.unsubEnd?.(),this.unsubEnd=null,this._provider.close?.();}};export{Pt as ConversationPlugin,Ct as FileLoggerPlugin,Lt as SqliteTracingPlugin};