create-principles-disciple 1.145.1 → 1.145.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/_release/product-identity.json +1 -1
- package/console/dist/server/models/ApprovalsGroupedConsoleModel.js +4 -4
- package/console/dist/ui/i18n/en.json +17 -16
- package/console/dist/ui/i18n/zh-CN.json +17 -16
- package/console/dist/ui/pages/focus/FocusPage.js +9 -5
- package/console/dist/ui/pages/focus/OwnerDecisionCard.js +1 -1
- package/console/dist/ui/pages/principles/PrincipleDetailPage.js +10 -4
- package/console/dist/ui/pages/principles/PrinciplesPage.js +1 -1
- package/console/dist/ui/utils/reading-layout.d.ts +19 -0
- package/console/dist/ui/utils/reading-layout.js +46 -0
- package/console/dist/web/assets/app.js +30 -28
- package/core/dist/runtime-v2/index.d.ts +10 -0
- package/core/dist/runtime-v2/index.d.ts.map +1 -1
- package/core/dist/runtime-v2/index.js +5 -0
- package/core/dist/runtime-v2/index.js.map +1 -1
- package/core/dist/runtime-v2/internalization/artificer-prompt-builder.d.ts +25 -6
- package/core/dist/runtime-v2/internalization/artificer-prompt-builder.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization/artificer-prompt-builder.js +21 -7
- package/core/dist/runtime-v2/internalization/artificer-prompt-builder.js.map +1 -1
- package/core/dist/runtime-v2/internalization/artificer-run-correlation.d.ts +82 -0
- package/core/dist/runtime-v2/internalization/artificer-run-correlation.d.ts.map +1 -0
- package/core/dist/runtime-v2/internalization/artificer-run-correlation.js +79 -0
- package/core/dist/runtime-v2/internalization/artificer-run-correlation.js.map +1 -0
- package/core/dist/runtime-v2/internalization/artificer-runner.d.ts +16 -2
- package/core/dist/runtime-v2/internalization/artificer-runner.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization/artificer-runner.js +89 -9
- package/core/dist/runtime-v2/internalization/artificer-runner.js.map +1 -1
- package/core/dist/runtime-v2/internalization/consumer-evidence-preflight.d.ts +141 -0
- package/core/dist/runtime-v2/internalization/consumer-evidence-preflight.d.ts.map +1 -0
- package/core/dist/runtime-v2/internalization/consumer-evidence-preflight.js +284 -0
- package/core/dist/runtime-v2/internalization/consumer-evidence-preflight.js.map +1 -0
- package/core/dist/runtime-v2/internalization/evidence-readiness.d.ts +170 -0
- package/core/dist/runtime-v2/internalization/evidence-readiness.d.ts.map +1 -0
- package/core/dist/runtime-v2/internalization/evidence-readiness.js +335 -0
- package/core/dist/runtime-v2/internalization/evidence-readiness.js.map +1 -0
- package/core/dist/runtime-v2/internalization/owner-evidence-recovery.d.ts +190 -0
- package/core/dist/runtime-v2/internalization/owner-evidence-recovery.d.ts.map +1 -0
- package/core/dist/runtime-v2/internalization/owner-evidence-recovery.js +488 -0
- package/core/dist/runtime-v2/internalization/owner-evidence-recovery.js.map +1 -0
- package/core/dist/runtime-v2/internalization/owner-retry.d.ts +23 -1
- package/core/dist/runtime-v2/internalization/owner-retry.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization/owner-retry.js +19 -3
- package/core/dist/runtime-v2/internalization/owner-retry.js.map +1 -1
- package/core/dist/runtime-v2/internalization/peer-runner-contracts.d.ts +8 -0
- package/core/dist/runtime-v2/internalization/peer-runner-contracts.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization/peer-runner-contracts.js.map +1 -1
- package/core/dist/runtime-v2/internalization/pitask-metadata.d.ts +12 -0
- package/core/dist/runtime-v2/internalization/pitask-metadata.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization/pitask-metadata.js +24 -0
- package/core/dist/runtime-v2/internalization/pitask-metadata.js.map +1 -1
- package/core/dist/runtime-v2/recovery-actions-log.d.ts +40 -0
- package/core/dist/runtime-v2/recovery-actions-log.d.ts.map +1 -1
- package/core/dist/runtime-v2/recovery-actions-log.js +77 -2
- package/core/dist/runtime-v2/recovery-actions-log.js.map +1 -1
- package/core/dist/runtime-v2/store/runtime-state-manager.d.ts +6 -1
- package/core/dist/runtime-v2/store/runtime-state-manager.d.ts.map +1 -1
- package/core/dist/runtime-v2/store/runtime-state-manager.js +6 -2
- package/core/dist/runtime-v2/store/runtime-state-manager.js.map +1 -1
- package/core/dist/runtime-v2/store/task/memory-task-store.d.ts +3 -1
- package/core/dist/runtime-v2/store/task/memory-task-store.d.ts.map +1 -1
- package/core/dist/runtime-v2/store/task/memory-task-store.js +6 -1
- package/core/dist/runtime-v2/store/task/memory-task-store.js.map +1 -1
- package/core/dist/runtime-v2/store/task/sqlite-task-store.d.ts +3 -1
- package/core/dist/runtime-v2/store/task/sqlite-task-store.d.ts.map +1 -1
- package/core/dist/runtime-v2/store/task/sqlite-task-store.js +10 -2
- package/core/dist/runtime-v2/store/task/sqlite-task-store.js.map +1 -1
- package/core/dist/runtime-v2/store/task/task-store.d.ts +11 -5
- package/core/dist/runtime-v2/store/task/task-store.d.ts.map +1 -1
- package/core/dist/telemetry-event.d.ts +2 -2
- package/core/dist/telemetry-event.d.ts.map +1 -1
- package/core/dist/telemetry-event.js +13 -0
- package/core/dist/telemetry-event.js.map +1 -1
- package/core/package.json +5 -1
- package/dist/installers/workbuddy-host-installer.d.ts +16 -3
- package/dist/installers/workbuddy-host-installer.d.ts.map +1 -1
- package/dist/installers/workbuddy-host-installer.js +57 -10
- package/dist/installers/workbuddy-host-installer.js.map +1 -1
- package/host-runtime/dist/internalization-consumer-cycle.d.ts +12 -1
- package/host-runtime/dist/internalization-consumer-cycle.js +141 -16
- package/host-runtime/dist/workspace-telemetry-emitter.js +13 -0
- package/host-runtime/package.json +1 -1
- package/package.json +2 -2
- package/pd-cli/dist/commands/runtime-internalization-audit-artificer-evidence.d.ts +44 -0
- package/pd-cli/dist/commands/runtime-internalization-audit-artificer-evidence.d.ts.map +1 -0
- package/pd-cli/dist/commands/runtime-internalization-audit-artificer-evidence.js +138 -0
- package/pd-cli/dist/commands/runtime-internalization-audit-artificer-evidence.js.map +1 -0
- package/pd-cli/dist/commands/runtime-internalization-evidence.d.ts +72 -0
- package/pd-cli/dist/commands/runtime-internalization-evidence.d.ts.map +1 -0
- package/pd-cli/dist/commands/runtime-internalization-evidence.js +424 -0
- package/pd-cli/dist/commands/runtime-internalization-evidence.js.map +1 -0
- package/pd-cli/dist/commands/runtime-internalization-run-once.d.ts.map +1 -1
- package/pd-cli/dist/commands/runtime-internalization-run-once.js +22 -1
- package/pd-cli/dist/commands/runtime-internalization-run-once.js.map +1 -1
- package/pd-cli/dist/commands/runtime-internalization-run-rulehost.d.ts.map +1 -1
- package/pd-cli/dist/commands/runtime-internalization-run-rulehost.js +45 -4
- package/pd-cli/dist/commands/runtime-internalization-run-rulehost.js.map +1 -1
- package/pd-cli/dist/index.js +8 -0
- package/pd-cli/dist/index.js.map +1 -1
- package/pd-cli/dist/services/artificer-evidence-audit.d.ts +156 -0
- package/pd-cli/dist/services/artificer-evidence-audit.d.ts.map +1 -0
- package/pd-cli/dist/services/artificer-evidence-audit.js +321 -0
- package/pd-cli/dist/services/artificer-evidence-audit.js.map +1 -0
- package/pd-cli/dist/services/rulehost-pipeline-runner.d.ts.map +1 -1
- package/pd-cli/dist/services/rulehost-pipeline-runner.js +17 -3
- package/pd-cli/dist/services/rulehost-pipeline-runner.js.map +1 -1
- package/pd-cli/package.json +1 -1
- package/plugin/dist/bundle.js +491 -491
- package/plugin/dist/openclaw.plugin.json +1 -1
- package/plugin/dist/rulehost-evidence.js +26 -26
- package/plugin/openclaw.plugin.json +1 -1
- package/plugin/package.json +1 -1
- package/release-manager/dist/installers/workbuddy-host-installer.d.ts +16 -3
- package/release-manager/dist/installers/workbuddy-host-installer.d.ts.map +1 -1
- package/release-manager/dist/installers/workbuddy-host-installer.js +57 -10
- package/release-manager/dist/installers/workbuddy-host-installer.js.map +1 -1
- package/release-manager/package.json +2 -2
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
"id": "principles-disciple",
|
|
3
3
|
"name": "Principles Disciple",
|
|
4
4
|
"description": "Principles Disciple is an AI Agent Governance System. Stop correcting the same AI behavior across sessions. Turn repeated Agent corrections into Owner-approved, observable, reversible behavior principles.",
|
|
5
|
-
"version": "2.1.
|
|
5
|
+
"version": "2.1.5",
|
|
6
6
|
"activation": {
|
|
7
7
|
"onStartup": true,
|
|
8
8
|
"onCapabilities": [
|
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
import { createRequire } from 'module'; const require = createRequire(import.meta.url);
|
|
2
|
-
var Oe=(r=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(r,{get:(e,t)=>(typeof require<"u"?require:e)[t]}):r)(function(r){if(typeof require<"u")return require.apply(this,arguments);throw Error('Dynamic require of "'+r+'" is not supported')});function D(r,e){if(!r||typeof r!="string")return"";let t=r.replace(/\\/g,"/"),n=e.replace(/\\/g,"/"),s=t.length>=2&&t[1]===":",o=n.length>=2&&n[1]===":",i=t;s&&!o&&(i=`/mnt/${t.charAt(0).toLowerCase()}${t.slice(2)}`);let c=s&&o?i.slice(2):i,a=o?n.slice(2):n,d=c.startsWith("/"),S=a.startsWith("/");if(d&&S){let p=V(a,c);return p.startsWith("../")?i:p}if(!d){let p=ye(a,c),f=V(a,p);return f.startsWith("../")?i:f}return i}function V(r,e){let t=r.split("/").filter(a=>a.length>0),n=e.split("/").filter(a=>a.length>0),s=0;for(;s<t.length&&s<n.length&&t[s]===n[s];)s++;let o=t.length-s,i=n.slice(s),c=[];for(let a=0;a<o;a++)c.push("..");return c.push(...i),c.length===0?".":c.join("/")}function ye(r,e){let t=r.split("/").filter(o=>o.length>0),n=e.split("/").filter(o=>o.length>0),s=[];for(let o of t)o===".."?s.length>0&&s.pop():o!=="."&&s.push(o);for(let o of n)o===".."?s.length>0&&s.pop():o!=="."&&s.push(o);return"/"+s.join("/")}function M(r,e={}){let t=r.file_path||r.path||r.file||r.target;if(typeof t=="string"&&t.length>0)return t;if(e.isBashTool){let n=String(r.command||r.args||"");if(n){let s=/(?:>|>>|sed\s+-i|rm|mv|mkdir|touch|cp)\s+(?:-[a-zA-Z]+\s+)*([^\s;&|<>]+)/.exec(n);return s&&s[1]?s[1]:n}}return e.isWriteTool&&e.toolName?`<tool:${e.toolName}>`:null}function Ne(r){return{isBashTool:r==="execute",isWriteTool:r==="write"}}function be(r){if(r.canonicalKind===void 0)return r;let e=Ne(r.canonicalKind);return{...r,isBashTool:r.isBashTool??e.isBashTool,isWriteTool:r.isWriteTool??e.isWriteTool}}function z(r,e,t,n={}){let s=be(n),o=M(e,{...s,toolName:r}),i=D(o,t);return{toolName:r,normalizedPath:i,paramsSummary:{...e},...s.canonicalKind!==void 0?{canonicalKind:s.canonicalKind}:{}}}var P=new Set(["read","search","write","execute","agent","other"]);function J(r){return typeof r=="string"&&P.has(r)}var v=Object.freeze({read:"read",read_file:"read",read_many_files:"read",grep:"search",grep_search:"search",search_file_content:"search",glob:"search",write:"write",write_file:"write",edit:"write",edit_file:"write",replace:"write",apply_patch:"write",bash:"execute",exec:"execute",execute:"execute",run_shell_command:"execute",execute_command:"execute",run_script:"execute",code_interpreter:"execute",sessions_spawn:"agent"});function j(r,e,t){if(r.status==="unavailable")return{priorReadOfTarget:"unknown",readCount:null,writeCount:null,uniqueWritePathCount:null,sameActionBlockCount:null};let n=0,s=0,o=new Set,i=e===null?"unknown":"no",{calls:c}=r;for(let a of c){let d=a.canonicalKind;d==="read"||d==="search"?(n++,e!==null&&a.normalizedPath===e&&(i="yes")):d==="write"&&(s++,typeof a.normalizedPath=="string"&&o.add(a.normalizedPath))}return{priorReadOfTarget:i,readCount:n,writeCount:s,uniqueWritePathCount:o.size,sameActionBlockCount:t}}var Z={priorReadOfTarget:"unknown",readCount:null,writeCount:null,uniqueWritePathCount:null,sameActionBlockCount:null};Object.freeze(Z);var U={status:"unavailable",unavailableReason:"host did not provide a history window",truncated:!1,calls:[]};Object.freeze(U.calls);Object.freeze(U);var Ae={version:2,history:U,facts:Z};Object.freeze(Ae);var Ie=new Set(["__proto__","constructor","prototype"]),Q=3,Le=5,xe=new Set(["allow","block","propose_correction"]),ve={valid:!0,errors:[]};function B(r){return typeof r=="object"&&r!==null&&!Array.isArray(r)}function re(r){for(let e of Object.keys(r))if(Ie.has(e))return!1;return!0}function Ce(r){return r.length===0?ve:{valid:!1,errors:r}}function F(r){return typeof r=="string"&&r.trim().length>0}function ee(r,e,t){let n=[];return B(r)?re(r)?((!Object.hasOwn(r,"caseId")||!F(r.caseId))&&n.push(`${e}.caseId must be a non-empty string`),(!Object.hasOwn(r,"kind")||r.kind!==t)&&n.push(`${e}.kind must be '${t}'`),(!Object.hasOwn(r,"toolName")||!F(r.toolName))&&n.push(`${e}.toolName must be a non-empty string`),(!Object.hasOwn(r,"params")||!B(r.params))&&n.push(`${e}.params must be a plain object`),!Object.hasOwn(r,"expectedDecision")||typeof r.expectedDecision!="string"||!xe.has(r.expectedDecision)?n.push(`${e}.expectedDecision must be one of allow|block|propose_correction`):t==="positive"&&r.expectedDecision!=="allow"&&n.push(`${e}: positive cases must expect allow`),n):(n.push(`${e} must not carry prototype-pollution keys`),n):(n.push(`${e} must be a plain object`),n)}function te(r,e){let{fieldName:t,maxLength:n,requireNonEmpty:s}=e,o=[];if(!Array.isArray(r))return o.push(`${t} must be an array`),o;s&&r.length===0&&o.push(`${t} must contain at least 1 item`),n!==void 0&&r.length>n&&o.push(`${t} must contain at most ${n} items, got ${r.length}`);for(let i=0;i<r.length;i++)typeof r[i]!="string"&&o.push(`${t}[${i}] must be a string`);return o}function ne(r){if(!B(r))return{valid:!1,errors:["BehaviorExamplePack must be a plain object"]};if(!re(r))return{valid:!1,errors:["BehaviorExamplePack must not carry prototype-pollution keys"]};let e=[];if(Object.hasOwn(r,"sourceNegativeCase")?e.push(...ee(r.sourceNegativeCase,"sourceNegativeCase","negative")):e.push("sourceNegativeCase is required"),(!Object.hasOwn(r,"ownerDesiredOutcome")||!F(r.ownerDesiredOutcome))&&e.push("ownerDesiredOutcome must be a non-empty string"),!Object.hasOwn(r,"positiveCounterexamples"))e.push("positiveCounterexamples is required");else if(!Array.isArray(r.positiveCounterexamples))e.push("positiveCounterexamples must be an array");else{let t=r.positiveCounterexamples;t.length===0&&e.push("positiveCounterexamples must contain at least 1 item"),t.length>Q&&e.push(`positiveCounterexamples must contain at most ${Q} items, got ${t.length}`);for(let n=0;n<t.length;n++)e.push(...ee(t[n],`positiveCounterexamples[${n}]`,"positive"))}return Object.hasOwn(r,"evidenceRefs")?e.push(...te(r.evidenceRefs,{fieldName:"evidenceRefs",maxLength:Le,requireNonEmpty:!0})):e.push("evidenceRefs is required"),Object.hasOwn(r,"redactionNotes")?e.push(...te(r.redactionNotes,{fieldName:"redactionNotes"})):e.push("redactionNotes is required"),Ce(e)}import Je from"better-sqlite3";import E from"fs";import g from"path";import $ from"crypto";import*as _ from"fs";import*as oe from"path";var X=class extends Error{filePath;lockPath;constructor(e,t,n){super(e),this.name="LockAcquisitionError",this.filePath=t,this.lockPath=n}},we={maxRetries:50,baseRetryDelayMs:10,maxRetryDelayMs:500,lockStaleMs:1e4,lockSuffix:".lock"};function ie(r){try{return process.kill(r,0),!0}catch{return!1}}function se(r,e){try{let t=oe.dirname(r);_.existsSync(t)||_.mkdirSync(t,{recursive:!0});let n=_.constants.O_WRONLY|_.constants.O_CREAT|_.constants.O_EXCL,s=_.openSync(r,n);return _.writeSync(s,String(e)),_.fsyncSync(s),_.closeSync(s),!0}catch(t){if(t.code==="EEXIST")return!1;throw t}}function b(r){try{let e=_.readFileSync(r,"utf8"),t=parseInt(e.trim(),10);return Number.isNaN(t)?null:t}catch{return null}}function ke(r,e){try{b(r)===e&&_.unlinkSync(r)}catch{}}function De(r,e){try{let t=_.statSync(r),n=b(r),s=Date.now()-t.mtimeMs>e,o=n===null||!ie(n);if(s||o)try{return _.unlinkSync(r),!0}catch{return!1}return!1}catch{return!1}}function Me(r,e,t){let n=Math.min(e*Math.pow(2,r),t),s=n*.2*Math.random();return Math.floor(n+s)}function Pe(r){let e=Date.now()+r;for(;Date.now()<e;);}function je(r,e){let t=b(e),n=t!==null?ie(t)?`alive (PID ${t})`:`dead (PID ${t})`:"unknown";return new X(`Failed to acquire lock for ${r}. Lock holder: ${n}.`,r,e)}function Ue(r,e,t){let n=r+e.lockSuffix;return se(n,t)&&b(n)===t?{lockPath:n,pid:t,acquiredAt:Date.now()}:(De(n,e.lockStaleMs),se(n,t)&&b(n)===t?{lockPath:n,pid:t,acquiredAt:Date.now()}:null)}function Be(r,e={}){let t={...we,...e},{pid:n}=process;for(let s=0;s<t.maxRetries;s++){let o=Ue(r,t,n);if(o)return o;if(s<t.maxRetries-1){let i=Me(s,t.baseRetryDelayMs,t.maxRetryDelayMs);Pe(i)}}throw je(r,r+t.lockSuffix)}function Fe(r){ke(r.lockPath,r.pid)}function ae(r,e,t={}){let n=Be(r,t);try{return e()}finally{Fe(n)}}import*as O from"fs";var ce=3,Xe=50;function C(r,e){let t=r+".tmp";O.writeFileSync(t,e,"utf8");let n;for(let s=0;s<ce;s++)try{O.renameSync(t,r);return}catch(o){n=o;let i=o.code;if(i==="EPERM"||i==="EBUSY"||i==="EACCES"){if(s<ce-1){let c=Xe*Math.pow(2,s),a=Date.now()+c,d=!1;for(;Date.now()<a;)if(!d&&Date.now()>=a-10){try{Oe("fs").accessSync?.(t)}catch{}d=!0}}continue}break}try{O.unlinkSync(t)}catch{}throw n}import*as R from"path";var l=(...r)=>R.posix.join(...r);function We(r){return/^[A-Za-z]:[\\/]/.test(r)||r.startsWith("\\\\")}function He(r,e){return We(r)?R.win32.join(r,e):r.startsWith("/")?R.posix.join(r,e):R.join(r,e)}var u={IDENTITY:".principles",MODELS:l(".principles","models"),STATE:".state",MEMORY:"memory",OKR:l("memory","okr"),LOGS:l("memory","logs"),SESSIONS:l(".state","sessions"),PAIN_SAMPLES:l("memory","pain"),LOCKS:l("memory",".locks"),IMPL_CODE_DIR:l(".state","principles","implementations")},Ye={PROFILE:l(u.IDENTITY,"PROFILE.json"),PRINCIPLES:l(u.IDENTITY,"PRINCIPLES.md"),THINKING_OS:l(u.IDENTITY,"THINKING_OS.md"),DECISION_POLICY:l(u.IDENTITY,"DECISION_POLICY.json"),MODELS_DIR:u.MODELS,STATE_DIR:u.STATE,WORKBOARD:l(u.STATE,"WORKBOARD.json"),AGENT_SCORECARD:l(u.STATE,"AGENT_SCORECARD.json"),PAIN_FLAG:l(u.STATE,".pain_flag"),SYSTEM_CAPABILITIES:l(u.STATE,"SYSTEM_CAPABILITIES.json"),PAIN_SETTINGS:l(u.STATE,"pain_settings.json"),PAIN_CANDIDATES:l(u.STATE,"pain_candidates.json"),TRAJECTORY_DB:l(u.STATE,"trajectory.db"),TRAJECTORY_BLOBS_DIR:l(u.STATE,"blobs"),EXPORTS_DIR:l(u.STATE,"exports"),SESSION_DIR:u.SESSIONS,DICTIONARY:l(u.STATE,"pain_dictionary.json"),PRINCIPLE_BLACKLIST:l(u.STATE,"principle_blacklist.json"),WORKFLOWS_YAML:l(u.STATE,"workflows.yaml"),IMPL_CODE_DIR:u.IMPL_CODE_DIR,MEMORY_MD:"MEMORY.md",HEARTBEAT:"HEARTBEAT.md",SYSTEM_LOG:l(u.LOGS,"SYSTEM.log"),REFLECTION_LOG:l(u.MEMORY,"reflection-log.md"),USER_CONTEXT:l(u.MEMORY,"USER_CONTEXT.md"),OKR_DIR:u.OKR,CURRENT_FOCUS:l(u.OKR,"CURRENT_FOCUS.md"),WEEK_STATE:l(u.OKR,"WEEK_STATE.json"),EVOLUTION_STREAM:l(u.MEMORY,"evolution.jsonl"),EVOLUTION_LOCK:l(u.LOCKS,"evolution")};function h(r,e){return He(r,Ye[e])}var $e={LOCK_UNAVAILABLE:"lease_conflict",PATH_RESOLUTION_ERROR:"workspace_invalid",WORKSPACE_NOT_FOUND:"workspace_invalid",SAMPLE_NOT_FOUND:"storage_unavailable",CONFIGURATION_ERROR:"input_invalid",DEPENDENCY_ERROR:"runtime_unavailable",EVOLUTION_PROCESSING_ERROR:"execution_failed",TRAJECTORY_ERROR:"storage_unavailable"},W=class extends Error{constructor(t,n,s){super(t,s);this.code=n;this.name="PdError",this.category=$e[n]??"execution_failed"}code;category};var A=class extends W{constructor(e,t){super(`[PD:Sample] Correction sample not found: ${e}`,"SAMPLE_NOT_FOUND",t),this.name="SampleNotFoundError"}};var Ke=["schema_version","ingest_checkpoint","sessions","assistant_turns","user_turns","tool_calls","pain_events","gate_blocks","trust_changes","principle_events","task_outcomes","correction_samples","sample_reviews","signal_confirmations","exports_audit"];function m(r){let e=r instanceof Error?r.message:String(r);return e.includes("duplicate column name")||e.includes("no column named")}function Ge(r,e){return r.prepare("SELECT name FROM sqlite_master WHERE type = 'table' AND name = ?").get(e)!==void 0}function le(r,e={}){let t=[],n=[...Ke];r.exec("CREATE TABLE IF NOT EXISTS schema_version (version INTEGER NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS ingest_checkpoint (source_key TEXT PRIMARY KEY, imported_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS sessions (session_id TEXT PRIMARY KEY, started_at TEXT NOT NULL, updated_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS assistant_turns (id INTEGER PRIMARY KEY AUTOINCREMENT, session_id TEXT NOT NULL, run_id TEXT NOT NULL, provider TEXT NOT NULL, model TEXT NOT NULL, raw_text TEXT, sanitized_text TEXT NOT NULL, usage_json TEXT NOT NULL, empathy_signal_json TEXT NOT NULL, blob_ref TEXT, raw_excerpt TEXT, stop_reason TEXT, thinking_blocks_count INTEGER, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS user_turns (id INTEGER PRIMARY KEY AUTOINCREMENT, session_id TEXT NOT NULL, turn_index INTEGER NOT NULL, raw_text TEXT, blob_ref TEXT, raw_excerpt TEXT, correction_detected INTEGER NOT NULL DEFAULT 0, correction_cue TEXT, references_assistant_turn_id INTEGER, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS tool_calls (id INTEGER PRIMARY KEY AUTOINCREMENT, session_id TEXT NOT NULL, tool_name TEXT NOT NULL, outcome TEXT NOT NULL, duration_ms INTEGER, exit_code INTEGER, error_type TEXT, error_message TEXT, gfi_before REAL, gfi_after REAL, params_json TEXT NOT NULL, result_preview TEXT, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS pain_events (id INTEGER PRIMARY KEY AUTOINCREMENT, session_id TEXT NOT NULL, source TEXT NOT NULL, score REAL NOT NULL, reason TEXT, severity TEXT, origin TEXT, confidence REAL, text TEXT, canonical_pain_id TEXT, runtime_task_id TEXT, host_kind TEXT, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS gate_blocks (id INTEGER PRIMARY KEY AUTOINCREMENT, session_id TEXT, tool_name TEXT NOT NULL, file_path TEXT, reason TEXT NOT NULL, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS trust_changes (id INTEGER PRIMARY KEY AUTOINCREMENT, session_id TEXT, previous_score REAL NOT NULL, new_score REAL NOT NULL, delta REAL NOT NULL, reason TEXT NOT NULL, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS principle_events (id INTEGER PRIMARY KEY AUTOINCREMENT, principle_id TEXT, event_type TEXT NOT NULL, payload_json TEXT NOT NULL, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS task_outcomes (id INTEGER PRIMARY KEY AUTOINCREMENT, session_id TEXT NOT NULL, task_id TEXT, outcome TEXT NOT NULL, summary TEXT, principle_ids_json TEXT NOT NULL, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS correction_samples (sample_id TEXT PRIMARY KEY, session_id TEXT NOT NULL, bad_assistant_turn_id INTEGER NOT NULL, user_correction_turn_id INTEGER NOT NULL, recovery_tool_span_json TEXT NOT NULL, diff_excerpt TEXT NOT NULL, principle_ids_json TEXT NOT NULL, quality_score REAL NOT NULL, review_status TEXT NOT NULL, export_mode TEXT NOT NULL, created_at TEXT NOT NULL, updated_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS sample_reviews (id INTEGER PRIMARY KEY AUTOINCREMENT, sample_id TEXT NOT NULL, review_status TEXT NOT NULL, note TEXT, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS signal_confirmations (id TEXT PRIMARY KEY, session_id TEXT NOT NULL, user_turn_rowid INTEGER NOT NULL UNIQUE, occurrence_id TEXT NOT NULL, excerpt TEXT NOT NULL, terms_json TEXT NOT NULL, suggested_type TEXT NOT NULL, status TEXT NOT NULL DEFAULT 'pending' CHECK (status IN ('pending','confirmed','rejected','abandoned')), attempts INTEGER NOT NULL DEFAULT 0, created_at TEXT NOT NULL, resolved_at TEXT, resolution TEXT)"),r.exec("CREATE TABLE IF NOT EXISTS exports_audit (id INTEGER PRIMARY KEY AUTOINCREMENT, export_kind TEXT NOT NULL, mode TEXT NOT NULL, approved_only INTEGER NOT NULL, file_path TEXT NOT NULL, row_count INTEGER NOT NULL, created_at TEXT NOT NULL)");try{r.exec("ALTER TABLE pain_events ADD COLUMN text TEXT")}catch(s){if(!m(s))throw s}try{r.exec("ALTER TABLE pain_events ADD COLUMN canonical_pain_id TEXT")}catch(s){if(!m(s))throw s}try{r.exec("ALTER TABLE pain_events ADD COLUMN runtime_task_id TEXT")}catch(s){if(!m(s))throw s}try{r.exec("ALTER TABLE pain_events ADD COLUMN host_kind TEXT")}catch(s){if(!m(s))throw s}try{r.exec("ALTER TABLE assistant_turns ADD COLUMN stop_reason TEXT")}catch(s){if(!m(s))throw s}try{r.exec("ALTER TABLE assistant_turns ADD COLUMN thinking_blocks_count INTEGER")}catch(s){if(!m(s))throw s}try{r.exec("ALTER TABLE tool_calls ADD COLUMN result_preview TEXT")}catch(s){if(!m(s))throw s}try{r.exec("ALTER TABLE tool_calls ADD COLUMN tool_use_id TEXT")}catch(s){if(!m(s))throw s}if(r.exec("CREATE INDEX IF NOT EXISTS idx_tool_calls_session_tool_use_id ON tool_calls(session_id, tool_use_id)"),r.exec("CREATE UNIQUE INDEX IF NOT EXISTS idx_pain_events_canonical_pain_id ON pain_events(canonical_pain_id) WHERE canonical_pain_id IS NOT NULL"),Ge(r,"evolution_tasks")){try{r.exec("ALTER TABLE evolution_tasks ADD COLUMN task_kind TEXT")}catch(s){if(!m(s))throw s}try{r.exec("ALTER TABLE evolution_tasks ADD COLUMN priority TEXT")}catch(s){if(!m(s))throw s}try{r.exec("ALTER TABLE evolution_tasks ADD COLUMN retry_count INTEGER")}catch(s){if(!m(s))throw s}try{r.exec("ALTER TABLE evolution_tasks ADD COLUMN max_retries INTEGER")}catch(s){if(!m(s))throw s}try{r.exec("ALTER TABLE evolution_tasks ADD COLUMN last_error TEXT")}catch(s){if(!m(s))throw s}try{r.exec("ALTER TABLE evolution_tasks ADD COLUMN result_ref TEXT")}catch(s){if(!m(s))throw s}}return r.exec("CREATE INDEX IF NOT EXISTS idx_assistant_turns_session_id ON assistant_turns(session_id)"),r.exec("CREATE INDEX IF NOT EXISTS idx_assistant_turns_created_at ON assistant_turns(created_at)"),r.exec("CREATE INDEX IF NOT EXISTS idx_assistant_turns_provider_model ON assistant_turns(provider, model)"),r.exec("CREATE INDEX IF NOT EXISTS idx_user_turns_session_id ON user_turns(session_id)"),r.exec("CREATE INDEX IF NOT EXISTS idx_tool_calls_session_id ON tool_calls(session_id)"),r.exec("CREATE INDEX IF NOT EXISTS idx_tool_calls_created_at ON tool_calls(created_at)"),r.exec("CREATE INDEX IF NOT EXISTS idx_pain_events_session_id ON pain_events(session_id)"),r.exec("CREATE INDEX IF NOT EXISTS idx_correction_samples_review_status ON correction_samples(review_status)"),r.exec("CREATE INDEX IF NOT EXISTS idx_signal_confirmations_status ON signal_confirmations(status, attempts)"),e.views===!0&&(r.exec("CREATE VIEW IF NOT EXISTS v_error_clusters AS SELECT tool_name, COALESCE(error_type, 'unknown') AS error_type, COUNT(*) AS occurrences FROM tool_calls WHERE outcome = 'failure' GROUP BY tool_name, COALESCE(error_type, 'unknown') ORDER BY occurrences DESC"),r.exec("CREATE VIEW IF NOT EXISTS v_principle_effectiveness AS SELECT event_type, COUNT(*) AS total FROM principle_events GROUP BY event_type ORDER BY total DESC"),r.exec("CREATE VIEW IF NOT EXISTS v_sample_queue AS SELECT review_status, COUNT(*) AS total FROM correction_samples GROUP BY review_status")),{tables:n,warnings:t}}import*as H from"path";import*as ue from"os";var qe=[/(^|[/\\])fake[/\\]/i,/(^|[/\\])mock[/\\]/i,/(^|[/\\])tmp[/\\]fake-/i],Ve=H.join(ue.tmpdir(),".pd-test-quarantine");function ze(r){if(!r)return!1;let e=r.replace(/\\/g,"/");return qe.some(t=>t.test(e))}function de(r){if(!r||!(process.env.NODE_ENV==="test"||!!process.env.VITEST)||!ze(r))return r;let t=r.replace(/[:*?"<>|]/g,"_").replace(/[/\\]/g,"_");for(;t.startsWith("_");)t=t.slice(1);for(;t.endsWith("_");)t=t.slice(0,-1);return H.join(Ve,t)}var Ze=16*1024,Qe=5e3,et=7;function Ee(r){return typeof r=="object"&&r!==null&&!Array.isArray(r)}function tt(r){return!Ee(r)||typeof r.id!="number"||typeof r.session_id!="string"?!1:Object.hasOwn(r,"source")&&Object.hasOwn(r,"score")&&Object.hasOwn(r,"reason")&&Object.hasOwn(r,"severity")&&Object.hasOwn(r,"origin")&&Object.hasOwn(r,"confidence")&&Object.hasOwn(r,"text")&&Object.hasOwn(r,"canonical_pain_id")&&Object.hasOwn(r,"runtime_task_id")&&Object.hasOwn(r,"created_at")}function rt(r){let e=le(r,{views:!0});return{tables:e.tables,warnings:e.warnings}}function T(){return new Date().toISOString()}function y(r){return JSON.stringify(r??{})}function _e(r){try{return E.existsSync(r)?E.statSync(r).size:0}catch{return 0}}function nt(r){return r.length>240?`${r.slice(0,237)}...`:r}function pe(r){return r.replace(/[A-Za-z]:\\[^\s"'`]+/g,"<WINDOWS_PATH>").replace(/\/[A-Za-z0-9._-]+(?:\/[A-Za-z0-9._-]+)+/g,"<PATH>").replace(/[A-Z0-9._%+-]+@[A-Z0-9.-]+\.[A-Z]{2,}/gi,"<EMAIL>").replace(/\b(sk|rk|pk)_[A-Za-z0-9]+\b/g,"<TOKEN>")}function st(r){let e=[];try{let t=JSON.parse(String(r.terms_json??"[]"));Array.isArray(t)&&(e=t.filter(n=>typeof n=="string"))}catch{e=[]}return{id:String(r.id),sessionId:String(r.session_id),userTurnRowid:Number(r.user_turn_rowid),occurrenceId:String(r.occurrence_id),excerpt:String(r.excerpt),terms:e,suggestedType:String(r.suggested_type),status:String(r.status),attempts:Number(r.attempts??0),createdAt:String(r.created_at),resolvedAt:r.resolved_at===null||r.resolved_at===void 0?null:String(r.resolved_at),resolution:r.resolution===null||r.resolution===void 0?null:String(r.resolution)}}var w=class{workspaceDir;stateDir;dbPath;blobDir;exportDir;blobInlineThresholdBytes;orphanBlobGraceMs;db;constructor(e){this.workspaceDir=de(g.resolve(e.workspaceDir)),this.stateDir=h(this.workspaceDir,"STATE_DIR"),this.dbPath=h(this.workspaceDir,"TRAJECTORY_DB"),this.blobDir=h(this.workspaceDir,"TRAJECTORY_BLOBS_DIR"),this.exportDir=h(this.workspaceDir,"EXPORTS_DIR"),this.blobInlineThresholdBytes=e.blobInlineThresholdBytes??Ze,this.orphanBlobGraceMs=Math.max(0,(e.orphanBlobGraceDays??et)*24*60*60*1e3),E.mkdirSync(this.stateDir,{recursive:!0}),E.mkdirSync(this.blobDir,{recursive:!0}),E.mkdirSync(this.exportDir,{recursive:!0}),this.db=new Je(this.dbPath),this.db.pragma("journal_mode = WAL"),this.db.pragma("foreign_keys = ON"),this.db.pragma("synchronous = NORMAL"),this.db.pragma(`busy_timeout = ${Math.max(0,e.busyTimeoutMs??Qe)}`),this.initSchema(),this.importLegacyArtifacts(),this.pruneUnreferencedBlobs()}dispose(){this.db.close()}get isOpen(){return this.db.open}recordSession(e){let t=e.startedAt??T();this.withWrite(()=>{this.db.prepare(`
|
|
2
|
+
var be=(r=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(r,{get:(e,t)=>(typeof require<"u"?require:e)[t]}):r)(function(r){if(typeof require<"u")return require.apply(this,arguments);throw Error('Dynamic require of "'+r+'" is not supported')});function P(r,e){if(!r||typeof r!="string")return"";let t=r.replace(/\\/g,"/"),n=e.replace(/\\/g,"/"),s=t.length>=2&&t[1]===":",o=n.length>=2&&n[1]===":",i=t;s&&!o&&(i=`/mnt/${t.charAt(0).toLowerCase()}${t.slice(2)}`);let c=s&&o?i.slice(2):i,a=o?n.slice(2):n,d=c.startsWith("/"),S=a.startsWith("/");if(d&&S){let p=Z(a,c);return p.startsWith("../")?i:p}if(!d){let p=Ne(a,c),f=Z(a,p);return f.startsWith("../")?i:f}return i}function Z(r,e){let t=r.split("/").filter(a=>a.length>0),n=e.split("/").filter(a=>a.length>0),s=0;for(;s<t.length&&s<n.length&&t[s]===n[s];)s++;let o=t.length-s,i=n.slice(s),c=[];for(let a=0;a<o;a++)c.push("..");return c.push(...i),c.length===0?".":c.join("/")}function Ne(r,e){let t=r.split("/").filter(o=>o.length>0),n=e.split("/").filter(o=>o.length>0),s=[];for(let o of t)o===".."?s.length>0&&s.pop():o!=="."&&s.push(o);for(let o of n)o===".."?s.length>0&&s.pop():o!=="."&&s.push(o);return"/"+s.join("/")}function j(r,e={}){let t=r.file_path||r.path||r.file||r.target;if(typeof t=="string"&&t.length>0)return t;if(e.isBashTool){let n=String(r.command||r.args||"");if(n){let s=/(?:>|>>|sed\s+-i|rm|mv|mkdir|touch|cp)\s+(?:-[a-zA-Z]+\s+)*([^\s;&|<>]+)/.exec(n);return s&&s[1]?s[1]:n}}return e.isWriteTool&&e.toolName?`<tool:${e.toolName}>`:null}function Ae(r){return{isBashTool:r==="execute",isWriteTool:r==="write"}}function Ie(r){if(r.canonicalKind===void 0)return r;let e=Ae(r.canonicalKind);return{...r,isBashTool:r.isBashTool??e.isBashTool,isWriteTool:r.isWriteTool??e.isWriteTool}}function Q(r,e,t,n={}){let s=Ie(n),o=j(e,{...s,toolName:r}),i=P(o,t);return{toolName:r,normalizedPath:i,paramsSummary:{...e},...s.canonicalKind!==void 0?{canonicalKind:s.canonicalKind}:{}}}var U=new Set(["read","search","write","execute","agent","other"]);function ee(r){return typeof r=="string"&&U.has(r)}var C=Object.freeze({read:"read",read_file:"read",read_many_files:"read",grep:"search",grep_search:"search",search_file_content:"search",glob:"search",write:"write",write_file:"write",edit:"write",edit_file:"write",replace:"write",apply_patch:"write",bash:"execute",exec:"execute",execute:"execute",run_shell_command:"execute",execute_command:"execute",run_script:"execute",code_interpreter:"execute",sessions_spawn:"agent"});function B(r,e,t){if(r.status==="unavailable")return{priorReadOfTarget:"unknown",readCount:null,writeCount:null,uniqueWritePathCount:null,sameActionBlockCount:null};let n=0,s=0,o=new Set,i=e===null?"unknown":"no",{calls:c}=r;for(let a of c){let d=a.canonicalKind;d==="read"||d==="search"?(n++,e!==null&&a.normalizedPath===e&&(i="yes")):d==="write"&&(s++,typeof a.normalizedPath=="string"&&o.add(a.normalizedPath))}return{priorReadOfTarget:i,readCount:n,writeCount:s,uniqueWritePathCount:o.size,sameActionBlockCount:t}}var te={priorReadOfTarget:"unknown",readCount:null,writeCount:null,uniqueWritePathCount:null,sameActionBlockCount:null};Object.freeze(te);var F={status:"unavailable",unavailableReason:"host did not provide a history window",truncated:!1,calls:[]};Object.freeze(F.calls);Object.freeze(F);var ve={version:2,history:F,facts:te};Object.freeze(ve);var xe=new Set(["__proto__","constructor","prototype"]),re=3,Le=5,Ce=new Set(["allow","block","propose_correction"]),we={valid:!0,errors:[]};function X(r){return typeof r=="object"&&r!==null&&!Array.isArray(r)}function oe(r){for(let e of Object.keys(r))if(xe.has(e))return!1;return!0}function ke(r){return r.length===0?we:{valid:!1,errors:r}}function W(r){return typeof r=="string"&&r.trim().length>0}function ne(r,e,t){let n=[];return X(r)?oe(r)?((!Object.hasOwn(r,"caseId")||!W(r.caseId))&&n.push(`${e}.caseId must be a non-empty string`),(!Object.hasOwn(r,"kind")||r.kind!==t)&&n.push(`${e}.kind must be '${t}'`),(!Object.hasOwn(r,"toolName")||!W(r.toolName))&&n.push(`${e}.toolName must be a non-empty string`),(!Object.hasOwn(r,"params")||!X(r.params))&&n.push(`${e}.params must be a plain object`),!Object.hasOwn(r,"expectedDecision")||typeof r.expectedDecision!="string"||!Ce.has(r.expectedDecision)?n.push(`${e}.expectedDecision must be one of allow|block|propose_correction`):t==="positive"&&r.expectedDecision!=="allow"&&n.push(`${e}: positive cases must expect allow`),n):(n.push(`${e} must not carry prototype-pollution keys`),n):(n.push(`${e} must be a plain object`),n)}function se(r,e){let{fieldName:t,maxLength:n,requireNonEmpty:s}=e,o=[];if(!Array.isArray(r))return o.push(`${t} must be an array`),o;s&&r.length===0&&o.push(`${t} must contain at least 1 item`),n!==void 0&&r.length>n&&o.push(`${t} must contain at most ${n} items, got ${r.length}`);for(let i=0;i<r.length;i++)typeof r[i]!="string"&&o.push(`${t}[${i}] must be a string`);return o}function H(r){if(!X(r))return{valid:!1,errors:["BehaviorExamplePack must be a plain object"]};if(!oe(r))return{valid:!1,errors:["BehaviorExamplePack must not carry prototype-pollution keys"]};let e=[];if(Object.hasOwn(r,"sourceNegativeCase")?e.push(...ne(r.sourceNegativeCase,"sourceNegativeCase","negative")):e.push("sourceNegativeCase is required"),(!Object.hasOwn(r,"ownerDesiredOutcome")||!W(r.ownerDesiredOutcome))&&e.push("ownerDesiredOutcome must be a non-empty string"),!Object.hasOwn(r,"positiveCounterexamples"))e.push("positiveCounterexamples is required");else if(!Array.isArray(r.positiveCounterexamples))e.push("positiveCounterexamples must be an array");else{let t=r.positiveCounterexamples;t.length===0&&e.push("positiveCounterexamples must contain at least 1 item"),t.length>re&&e.push(`positiveCounterexamples must contain at most ${re} items, got ${t.length}`);for(let n=0;n<t.length;n++)e.push(...ne(t[n],`positiveCounterexamples[${n}]`,"positive"))}return Object.hasOwn(r,"evidenceRefs")?e.push(...se(r.evidenceRefs,{fieldName:"evidenceRefs",maxLength:Le,requireNonEmpty:!0})):e.push("evidenceRefs is required"),Object.hasOwn(r,"redactionNotes")?e.push(...se(r.redactionNotes,{fieldName:"redactionNotes"})):e.push("redactionNotes is required"),ke(e)}var De="OwnerEvidenceScopeError";function N(r,e){let t=new Error(e);return t.name=De,Object.assign(t,{ownerEvidenceScopeKind:r}),t}import et from"better-sqlite3";import E from"fs";import g from"path";import q from"crypto";import*as _ from"fs";import*as ae from"path";var $=class extends Error{filePath;lockPath;constructor(e,t,n){super(e),this.name="LockAcquisitionError",this.filePath=t,this.lockPath=n}},Me={maxRetries:50,baseRetryDelayMs:10,maxRetryDelayMs:500,lockStaleMs:1e4,lockSuffix:".lock"};function ce(r){try{return process.kill(r,0),!0}catch{return!1}}function ie(r,e){try{let t=ae.dirname(r);_.existsSync(t)||_.mkdirSync(t,{recursive:!0});let n=_.constants.O_WRONLY|_.constants.O_CREAT|_.constants.O_EXCL,s=_.openSync(r,n);return _.writeSync(s,String(e)),_.fsyncSync(s),_.closeSync(s),!0}catch(t){if(t.code==="EEXIST")return!1;throw t}}function A(r){try{let e=_.readFileSync(r,"utf8"),t=parseInt(e.trim(),10);return Number.isNaN(t)?null:t}catch{return null}}function Pe(r,e){try{A(r)===e&&_.unlinkSync(r)}catch{}}function je(r,e){try{let t=_.statSync(r),n=A(r),s=Date.now()-t.mtimeMs>e,o=n===null||!ce(n);if(s||o)try{return _.unlinkSync(r),!0}catch{return!1}return!1}catch{return!1}}function Ue(r,e,t){let n=Math.min(e*Math.pow(2,r),t),s=n*.2*Math.random();return Math.floor(n+s)}function Be(r){let e=Date.now()+r;for(;Date.now()<e;);}function Fe(r,e){let t=A(e),n=t!==null?ce(t)?`alive (PID ${t})`:`dead (PID ${t})`:"unknown";return new $(`Failed to acquire lock for ${r}. Lock holder: ${n}.`,r,e)}function Xe(r,e,t){let n=r+e.lockSuffix;return ie(n,t)&&A(n)===t?{lockPath:n,pid:t,acquiredAt:Date.now()}:(je(n,e.lockStaleMs),ie(n,t)&&A(n)===t?{lockPath:n,pid:t,acquiredAt:Date.now()}:null)}function We(r,e={}){let t={...Me,...e},{pid:n}=process;for(let s=0;s<t.maxRetries;s++){let o=Xe(r,t,n);if(o)return o;if(s<t.maxRetries-1){let i=Ue(s,t.baseRetryDelayMs,t.maxRetryDelayMs);Be(i)}}throw Fe(r,r+t.lockSuffix)}function He(r){Pe(r.lockPath,r.pid)}function le(r,e,t={}){let n=We(r,t);try{return e()}finally{He(n)}}import*as O from"fs";var ue=3,$e=50;function w(r,e){let t=r+".tmp";O.writeFileSync(t,e,"utf8");let n;for(let s=0;s<ue;s++)try{O.renameSync(t,r);return}catch(o){n=o;let i=o.code;if(i==="EPERM"||i==="EBUSY"||i==="EACCES"){if(s<ue-1){let c=$e*Math.pow(2,s),a=Date.now()+c,d=!1;for(;Date.now()<a;)if(!d&&Date.now()>=a-10){try{be("fs").accessSync?.(t)}catch{}d=!0}}continue}break}try{O.unlinkSync(t)}catch{}throw n}import*as h from"path";var l=(...r)=>h.posix.join(...r);function Ye(r){return/^[A-Za-z]:[\\/]/.test(r)||r.startsWith("\\\\")}function Ke(r,e){return Ye(r)?h.win32.join(r,e):r.startsWith("/")?h.posix.join(r,e):h.join(r,e)}var u={IDENTITY:".principles",MODELS:l(".principles","models"),STATE:".state",MEMORY:"memory",OKR:l("memory","okr"),LOGS:l("memory","logs"),SESSIONS:l(".state","sessions"),PAIN_SAMPLES:l("memory","pain"),LOCKS:l("memory",".locks"),IMPL_CODE_DIR:l(".state","principles","implementations")},Ge={PROFILE:l(u.IDENTITY,"PROFILE.json"),PRINCIPLES:l(u.IDENTITY,"PRINCIPLES.md"),THINKING_OS:l(u.IDENTITY,"THINKING_OS.md"),DECISION_POLICY:l(u.IDENTITY,"DECISION_POLICY.json"),MODELS_DIR:u.MODELS,STATE_DIR:u.STATE,WORKBOARD:l(u.STATE,"WORKBOARD.json"),AGENT_SCORECARD:l(u.STATE,"AGENT_SCORECARD.json"),PAIN_FLAG:l(u.STATE,".pain_flag"),SYSTEM_CAPABILITIES:l(u.STATE,"SYSTEM_CAPABILITIES.json"),PAIN_SETTINGS:l(u.STATE,"pain_settings.json"),PAIN_CANDIDATES:l(u.STATE,"pain_candidates.json"),TRAJECTORY_DB:l(u.STATE,"trajectory.db"),TRAJECTORY_BLOBS_DIR:l(u.STATE,"blobs"),EXPORTS_DIR:l(u.STATE,"exports"),SESSION_DIR:u.SESSIONS,DICTIONARY:l(u.STATE,"pain_dictionary.json"),PRINCIPLE_BLACKLIST:l(u.STATE,"principle_blacklist.json"),WORKFLOWS_YAML:l(u.STATE,"workflows.yaml"),IMPL_CODE_DIR:u.IMPL_CODE_DIR,MEMORY_MD:"MEMORY.md",HEARTBEAT:"HEARTBEAT.md",SYSTEM_LOG:l(u.LOGS,"SYSTEM.log"),REFLECTION_LOG:l(u.MEMORY,"reflection-log.md"),USER_CONTEXT:l(u.MEMORY,"USER_CONTEXT.md"),OKR_DIR:u.OKR,CURRENT_FOCUS:l(u.OKR,"CURRENT_FOCUS.md"),WEEK_STATE:l(u.OKR,"WEEK_STATE.json"),EVOLUTION_STREAM:l(u.MEMORY,"evolution.jsonl"),EVOLUTION_LOCK:l(u.LOCKS,"evolution")};function R(r,e){return Ke(r,Ge[e])}var qe={LOCK_UNAVAILABLE:"lease_conflict",PATH_RESOLUTION_ERROR:"workspace_invalid",WORKSPACE_NOT_FOUND:"workspace_invalid",SAMPLE_NOT_FOUND:"storage_unavailable",CONFIGURATION_ERROR:"input_invalid",DEPENDENCY_ERROR:"runtime_unavailable",EVOLUTION_PROCESSING_ERROR:"execution_failed",TRAJECTORY_ERROR:"storage_unavailable"},Y=class extends Error{constructor(t,n,s){super(t,s);this.code=n;this.name="PdError",this.category=qe[n]??"execution_failed"}code;category};var I=class extends Y{constructor(e,t){super(`[PD:Sample] Correction sample not found: ${e}`,"SAMPLE_NOT_FOUND",t),this.name="SampleNotFoundError"}};var Ve=["schema_version","ingest_checkpoint","sessions","assistant_turns","user_turns","tool_calls","pain_events","gate_blocks","trust_changes","principle_events","task_outcomes","correction_samples","sample_reviews","signal_confirmations","exports_audit"];function T(r){let e=r instanceof Error?r.message:String(r);return e.includes("duplicate column name")||e.includes("no column named")}function ze(r,e){return r.prepare("SELECT name FROM sqlite_master WHERE type = 'table' AND name = ?").get(e)!==void 0}function de(r,e={}){let t=[],n=[...Ve];r.exec("CREATE TABLE IF NOT EXISTS schema_version (version INTEGER NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS ingest_checkpoint (source_key TEXT PRIMARY KEY, imported_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS sessions (session_id TEXT PRIMARY KEY, started_at TEXT NOT NULL, updated_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS assistant_turns (id INTEGER PRIMARY KEY AUTOINCREMENT, session_id TEXT NOT NULL, run_id TEXT NOT NULL, provider TEXT NOT NULL, model TEXT NOT NULL, raw_text TEXT, sanitized_text TEXT NOT NULL, usage_json TEXT NOT NULL, empathy_signal_json TEXT NOT NULL, blob_ref TEXT, raw_excerpt TEXT, stop_reason TEXT, thinking_blocks_count INTEGER, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS user_turns (id INTEGER PRIMARY KEY AUTOINCREMENT, session_id TEXT NOT NULL, turn_index INTEGER NOT NULL, raw_text TEXT, blob_ref TEXT, raw_excerpt TEXT, correction_detected INTEGER NOT NULL DEFAULT 0, correction_cue TEXT, references_assistant_turn_id INTEGER, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS tool_calls (id INTEGER PRIMARY KEY AUTOINCREMENT, session_id TEXT NOT NULL, tool_name TEXT NOT NULL, outcome TEXT NOT NULL, duration_ms INTEGER, exit_code INTEGER, error_type TEXT, error_message TEXT, gfi_before REAL, gfi_after REAL, params_json TEXT NOT NULL, result_preview TEXT, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS pain_events (id INTEGER PRIMARY KEY AUTOINCREMENT, session_id TEXT NOT NULL, source TEXT NOT NULL, score REAL NOT NULL, reason TEXT, severity TEXT, origin TEXT, confidence REAL, text TEXT, canonical_pain_id TEXT, runtime_task_id TEXT, host_kind TEXT, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS gate_blocks (id INTEGER PRIMARY KEY AUTOINCREMENT, session_id TEXT, tool_name TEXT NOT NULL, file_path TEXT, reason TEXT NOT NULL, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS trust_changes (id INTEGER PRIMARY KEY AUTOINCREMENT, session_id TEXT, previous_score REAL NOT NULL, new_score REAL NOT NULL, delta REAL NOT NULL, reason TEXT NOT NULL, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS principle_events (id INTEGER PRIMARY KEY AUTOINCREMENT, principle_id TEXT, event_type TEXT NOT NULL, payload_json TEXT NOT NULL, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS task_outcomes (id INTEGER PRIMARY KEY AUTOINCREMENT, session_id TEXT NOT NULL, task_id TEXT, outcome TEXT NOT NULL, summary TEXT, principle_ids_json TEXT NOT NULL, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS correction_samples (sample_id TEXT PRIMARY KEY, session_id TEXT NOT NULL, bad_assistant_turn_id INTEGER NOT NULL, user_correction_turn_id INTEGER NOT NULL, recovery_tool_span_json TEXT NOT NULL, diff_excerpt TEXT NOT NULL, principle_ids_json TEXT NOT NULL, quality_score REAL NOT NULL, review_status TEXT NOT NULL, export_mode TEXT NOT NULL, created_at TEXT NOT NULL, updated_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS sample_reviews (id INTEGER PRIMARY KEY AUTOINCREMENT, sample_id TEXT NOT NULL, review_status TEXT NOT NULL, note TEXT, created_at TEXT NOT NULL)"),r.exec("CREATE TABLE IF NOT EXISTS signal_confirmations (id TEXT PRIMARY KEY, session_id TEXT NOT NULL, user_turn_rowid INTEGER NOT NULL UNIQUE, occurrence_id TEXT NOT NULL, excerpt TEXT NOT NULL, terms_json TEXT NOT NULL, suggested_type TEXT NOT NULL, status TEXT NOT NULL DEFAULT 'pending' CHECK (status IN ('pending','confirmed','rejected','abandoned')), attempts INTEGER NOT NULL DEFAULT 0, created_at TEXT NOT NULL, resolved_at TEXT, resolution TEXT)"),r.exec("CREATE TABLE IF NOT EXISTS exports_audit (id INTEGER PRIMARY KEY AUTOINCREMENT, export_kind TEXT NOT NULL, mode TEXT NOT NULL, approved_only INTEGER NOT NULL, file_path TEXT NOT NULL, row_count INTEGER NOT NULL, created_at TEXT NOT NULL)");try{r.exec("ALTER TABLE pain_events ADD COLUMN text TEXT")}catch(s){if(!T(s))throw s}try{r.exec("ALTER TABLE pain_events ADD COLUMN canonical_pain_id TEXT")}catch(s){if(!T(s))throw s}try{r.exec("ALTER TABLE pain_events ADD COLUMN runtime_task_id TEXT")}catch(s){if(!T(s))throw s}try{r.exec("ALTER TABLE pain_events ADD COLUMN host_kind TEXT")}catch(s){if(!T(s))throw s}try{r.exec("ALTER TABLE assistant_turns ADD COLUMN stop_reason TEXT")}catch(s){if(!T(s))throw s}try{r.exec("ALTER TABLE assistant_turns ADD COLUMN thinking_blocks_count INTEGER")}catch(s){if(!T(s))throw s}try{r.exec("ALTER TABLE tool_calls ADD COLUMN result_preview TEXT")}catch(s){if(!T(s))throw s}try{r.exec("ALTER TABLE tool_calls ADD COLUMN tool_use_id TEXT")}catch(s){if(!T(s))throw s}if(r.exec("CREATE INDEX IF NOT EXISTS idx_tool_calls_session_tool_use_id ON tool_calls(session_id, tool_use_id)"),r.exec("CREATE UNIQUE INDEX IF NOT EXISTS idx_pain_events_canonical_pain_id ON pain_events(canonical_pain_id) WHERE canonical_pain_id IS NOT NULL"),ze(r,"evolution_tasks")){try{r.exec("ALTER TABLE evolution_tasks ADD COLUMN task_kind TEXT")}catch(s){if(!T(s))throw s}try{r.exec("ALTER TABLE evolution_tasks ADD COLUMN priority TEXT")}catch(s){if(!T(s))throw s}try{r.exec("ALTER TABLE evolution_tasks ADD COLUMN retry_count INTEGER")}catch(s){if(!T(s))throw s}try{r.exec("ALTER TABLE evolution_tasks ADD COLUMN max_retries INTEGER")}catch(s){if(!T(s))throw s}try{r.exec("ALTER TABLE evolution_tasks ADD COLUMN last_error TEXT")}catch(s){if(!T(s))throw s}try{r.exec("ALTER TABLE evolution_tasks ADD COLUMN result_ref TEXT")}catch(s){if(!T(s))throw s}}return r.exec("CREATE INDEX IF NOT EXISTS idx_assistant_turns_session_id ON assistant_turns(session_id)"),r.exec("CREATE INDEX IF NOT EXISTS idx_assistant_turns_created_at ON assistant_turns(created_at)"),r.exec("CREATE INDEX IF NOT EXISTS idx_assistant_turns_provider_model ON assistant_turns(provider, model)"),r.exec("CREATE INDEX IF NOT EXISTS idx_user_turns_session_id ON user_turns(session_id)"),r.exec("CREATE INDEX IF NOT EXISTS idx_tool_calls_session_id ON tool_calls(session_id)"),r.exec("CREATE INDEX IF NOT EXISTS idx_tool_calls_created_at ON tool_calls(created_at)"),r.exec("CREATE INDEX IF NOT EXISTS idx_pain_events_session_id ON pain_events(session_id)"),r.exec("CREATE INDEX IF NOT EXISTS idx_correction_samples_review_status ON correction_samples(review_status)"),r.exec("CREATE INDEX IF NOT EXISTS idx_signal_confirmations_status ON signal_confirmations(status, attempts)"),e.views===!0&&(r.exec("CREATE VIEW IF NOT EXISTS v_error_clusters AS SELECT tool_name, COALESCE(error_type, 'unknown') AS error_type, COUNT(*) AS occurrences FROM tool_calls WHERE outcome = 'failure' GROUP BY tool_name, COALESCE(error_type, 'unknown') ORDER BY occurrences DESC"),r.exec("CREATE VIEW IF NOT EXISTS v_principle_effectiveness AS SELECT event_type, COUNT(*) AS total FROM principle_events GROUP BY event_type ORDER BY total DESC"),r.exec("CREATE VIEW IF NOT EXISTS v_sample_queue AS SELECT review_status, COUNT(*) AS total FROM correction_samples GROUP BY review_status")),{tables:n,warnings:t}}import*as K from"path";import*as _e from"os";var Je=[/(^|[/\\])fake[/\\]/i,/(^|[/\\])mock[/\\]/i,/(^|[/\\])tmp[/\\]fake-/i],Ze=K.join(_e.tmpdir(),".pd-test-quarantine");function Qe(r){if(!r)return!1;let e=r.replace(/\\/g,"/");return Je.some(t=>t.test(e))}function pe(r){if(!r||!(process.env.NODE_ENV==="test"||!!process.env.VITEST)||!Qe(r))return r;let t=r.replace(/[:*?"<>|]/g,"_").replace(/[/\\]/g,"_");for(;t.startsWith("_");)t=t.slice(1);for(;t.endsWith("_");)t=t.slice(0,-1);return K.join(Ze,t)}var tt=16*1024,rt=5e3,nt=7;function Te(r){return typeof r=="object"&&r!==null&&!Array.isArray(r)}function st(r){return!Te(r)||typeof r.id!="number"||typeof r.session_id!="string"?!1:Object.hasOwn(r,"source")&&Object.hasOwn(r,"score")&&Object.hasOwn(r,"reason")&&Object.hasOwn(r,"severity")&&Object.hasOwn(r,"origin")&&Object.hasOwn(r,"confidence")&&Object.hasOwn(r,"text")&&Object.hasOwn(r,"canonical_pain_id")&&Object.hasOwn(r,"runtime_task_id")&&Object.hasOwn(r,"created_at")}function ot(r){let e=de(r,{views:!0});return{tables:e.tables,warnings:e.warnings}}function m(){return new Date().toISOString()}function y(r){return JSON.stringify(r??{})}function Ee(r){try{return E.existsSync(r)?E.statSync(r).size:0}catch{return 0}}function it(r){return r.length>240?`${r.slice(0,237)}...`:r}function me(r){return r.replace(/[A-Za-z]:\\[^\s"'`]+/g,"<WINDOWS_PATH>").replace(/\/[A-Za-z0-9._-]+(?:\/[A-Za-z0-9._-]+)+/g,"<PATH>").replace(/[A-Z0-9._%+-]+@[A-Z0-9.-]+\.[A-Z]{2,}/gi,"<EMAIL>").replace(/\b(sk|rk|pk)_[A-Za-z0-9]+\b/g,"<TOKEN>")}function at(r){let e=[];try{let t=JSON.parse(String(r.terms_json??"[]"));Array.isArray(t)&&(e=t.filter(n=>typeof n=="string"))}catch{e=[]}return{id:String(r.id),sessionId:String(r.session_id),userTurnRowid:Number(r.user_turn_rowid),occurrenceId:String(r.occurrence_id),excerpt:String(r.excerpt),terms:e,suggestedType:String(r.suggested_type),status:String(r.status),attempts:Number(r.attempts??0),createdAt:String(r.created_at),resolvedAt:r.resolved_at===null||r.resolved_at===void 0?null:String(r.resolved_at),resolution:r.resolution===null||r.resolution===void 0?null:String(r.resolution)}}var k=class{workspaceDir;stateDir;dbPath;blobDir;exportDir;blobInlineThresholdBytes;orphanBlobGraceMs;db;constructor(e){this.workspaceDir=pe(g.resolve(e.workspaceDir)),this.stateDir=R(this.workspaceDir,"STATE_DIR"),this.dbPath=R(this.workspaceDir,"TRAJECTORY_DB"),this.blobDir=R(this.workspaceDir,"TRAJECTORY_BLOBS_DIR"),this.exportDir=R(this.workspaceDir,"EXPORTS_DIR"),this.blobInlineThresholdBytes=e.blobInlineThresholdBytes??tt,this.orphanBlobGraceMs=Math.max(0,(e.orphanBlobGraceDays??nt)*24*60*60*1e3),E.mkdirSync(this.stateDir,{recursive:!0}),E.mkdirSync(this.blobDir,{recursive:!0}),E.mkdirSync(this.exportDir,{recursive:!0}),this.db=new et(this.dbPath),this.db.pragma("journal_mode = WAL"),this.db.pragma("foreign_keys = ON"),this.db.pragma("synchronous = NORMAL"),this.db.pragma(`busy_timeout = ${Math.max(0,e.busyTimeoutMs??rt)}`),this.initSchema(),this.importLegacyArtifacts(),this.pruneUnreferencedBlobs()}dispose(){this.db.close()}get isOpen(){return this.db.open}recordSession(e){let t=e.startedAt??m();this.withWrite(()=>{this.db.prepare(`
|
|
3
3
|
INSERT INTO sessions (session_id, started_at, updated_at)
|
|
4
4
|
VALUES (?, ?, ?)
|
|
5
5
|
ON CONFLICT(session_id) DO UPDATE SET updated_at = excluded.updated_at
|
|
6
|
-
`).run(e.sessionId,t,
|
|
6
|
+
`).run(e.sessionId,t,m())})}recordAssistantTurn(e){this.recordSession({sessionId:e.sessionId,startedAt:e.createdAt});let t=this.storeRawText("assistant",e.rawText),n=e.createdAt??m();return this.withWrite(()=>{let s=this.db.prepare(`
|
|
7
7
|
INSERT INTO assistant_turns (
|
|
8
8
|
session_id, run_id, provider, model, raw_text, sanitized_text, usage_json,
|
|
9
9
|
empathy_signal_json, blob_ref, raw_excerpt, stop_reason, thinking_blocks_count, created_at
|
|
10
10
|
) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)
|
|
11
|
-
`).run(e.sessionId,e.runId,e.provider,e.model,t.inlineText,e.sanitizedText,y(e.usageJson),y(e.empathySignalJson),t.blobRef,t.excerpt,e.stopReason??null,e.thinkingBlocksCount??null,n);return Number(s.lastInsertRowid)})}recordUserTurn(e){this.recordSession({sessionId:e.sessionId,startedAt:e.createdAt});let t=this.storeRawText("user",e.rawText),n=e.createdAt??
|
|
11
|
+
`).run(e.sessionId,e.runId,e.provider,e.model,t.inlineText,e.sanitizedText,y(e.usageJson),y(e.empathySignalJson),t.blobRef,t.excerpt,e.stopReason??null,e.thinkingBlocksCount??null,n);return Number(s.lastInsertRowid)})}recordUserTurn(e){this.recordSession({sessionId:e.sessionId,startedAt:e.createdAt});let t=this.storeRawText("user",e.rawText),n=e.createdAt??m();return this.withWrite(()=>{let s=this.db.prepare(`
|
|
12
12
|
INSERT INTO user_turns (
|
|
13
13
|
session_id, turn_index, raw_text, blob_ref, raw_excerpt,
|
|
14
14
|
correction_detected, correction_cue, references_assistant_turn_id, created_at
|
|
@@ -17,7 +17,7 @@ var Oe=(r=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(r,{get:(e,t)=>(
|
|
|
17
17
|
UPDATE user_turns
|
|
18
18
|
SET correction_detected = 1, correction_cue = ?
|
|
19
19
|
WHERE id = ?
|
|
20
|
-
`).run(t??null,e));return Number(n.changes)>0}recordToolCall(e){this.recordSession({sessionId:e.sessionId,startedAt:e.createdAt});let t=e.createdAt??
|
|
20
|
+
`).run(t??null,e));return Number(n.changes)>0}recordToolCall(e){this.recordSession({sessionId:e.sessionId,startedAt:e.createdAt});let t=e.createdAt??m(),n=this.withWrite(()=>{let s=this.db.prepare(`
|
|
21
21
|
INSERT INTO tool_calls (
|
|
22
22
|
session_id, tool_name, outcome, duration_ms, exit_code, error_type, error_message,
|
|
23
23
|
gfi_before, gfi_after, params_json, result_preview, created_at
|
|
@@ -27,7 +27,7 @@ var Oe=(r=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(r,{get:(e,t)=>(
|
|
|
27
27
|
session_id, source, score, reason, severity, origin, confidence, text, created_at,
|
|
28
28
|
canonical_pain_id, runtime_task_id, host_kind
|
|
29
29
|
) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)
|
|
30
|
-
`).run(e.sessionId,e.source,e.score,e.reason??null,e.severity??null,e.origin??null,e.confidence??null,e.text??null,e.createdAt??
|
|
30
|
+
`).run(e.sessionId,e.source,e.score,e.reason??null,e.severity??null,e.origin??null,e.confidence??null,e.text??null,e.createdAt??m(),e.canonicalPainId??null,e.runtimeTaskId??null,e.hostKind??null);t=Number(n.lastInsertRowid)}catch(n){if(e.canonicalPainId&&n instanceof Error&&n.message.includes("UNIQUE constraint failed")&&n.message.includes("canonical_pain_id")){this.db.prepare(`
|
|
31
31
|
UPDATE pain_events
|
|
32
32
|
SET runtime_task_id = COALESCE(?, runtime_task_id),
|
|
33
33
|
host_kind = COALESCE(host_kind, ?)
|
|
@@ -35,16 +35,16 @@ var Oe=(r=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(r,{get:(e,t)=>(
|
|
|
35
35
|
`).run(e.runtimeTaskId??null,e.hostKind??null,e.canonicalPainId);let s=this.db.prepare("SELECT id FROM pain_events WHERE canonical_pain_id = ?").get(e.canonicalPainId);s&&typeof s=="object"&&Object.hasOwn(s,"id")&&typeof s.id=="number"?t=s.id:t=-1}else throw n}}),t}recordGateBlock(e){this.withWrite(()=>{this.db.prepare(`
|
|
36
36
|
INSERT INTO gate_blocks (session_id, tool_name, file_path, reason, created_at)
|
|
37
37
|
VALUES (?, ?, ?, ?, ?)
|
|
38
|
-
`).run(e.sessionId??null,e.toolName,e.filePath??null,e.reason,e.createdAt??
|
|
38
|
+
`).run(e.sessionId??null,e.toolName,e.filePath??null,e.reason,e.createdAt??m())})}recordTrustChange(e){this.withWrite(()=>{this.db.prepare(`
|
|
39
39
|
INSERT INTO trust_changes (session_id, previous_score, new_score, delta, reason, created_at)
|
|
40
40
|
VALUES (?, ?, ?, ?, ?, ?)
|
|
41
|
-
`).run(e.sessionId??null,e.previousScore,e.newScore,e.delta,e.reason,e.createdAt??
|
|
41
|
+
`).run(e.sessionId??null,e.previousScore,e.newScore,e.delta,e.reason,e.createdAt??m())})}recordPrincipleEvent(e){this.withWrite(()=>{this.db.prepare(`
|
|
42
42
|
INSERT INTO principle_events (principle_id, event_type, payload_json, created_at)
|
|
43
43
|
VALUES (?, ?, ?, ?)
|
|
44
|
-
`).run(e.principleId??null,e.eventType,y(e.payload),e.createdAt??
|
|
44
|
+
`).run(e.principleId??null,e.eventType,y(e.payload),e.createdAt??m())})}recordTaskOutcome(e){this.withWrite(()=>{this.db.prepare(`
|
|
45
45
|
INSERT INTO task_outcomes (session_id, task_id, outcome, summary, principle_ids_json, created_at)
|
|
46
46
|
VALUES (?, ?, ?, ?, ?, ?)
|
|
47
|
-
`).run(e.sessionId,e.taskId??null,e.outcome,e.summary??null,y(e.principleIdsJson),e.createdAt??
|
|
47
|
+
`).run(e.sessionId,e.taskId??null,e.outcome,e.summary??null,y(e.principleIdsJson),e.createdAt??m())})}evolutionTableMissing(e){let t=this.db.prepare("SELECT name FROM sqlite_master WHERE type = 'table' AND name = ?").get(e);return!t||typeof t.name!="string"}listEvolutionTasks(e={}){if(this.evolutionTableMissing("evolution_tasks"))return[];let t=[],n=[];e.status&&(t.push("status = ?"),n.push(e.status)),e.dateFrom&&(t.push("created_at >= ?"),n.push(e.dateFrom)),e.dateTo&&(t.push("created_at <= ?"),n.push(e.dateTo));let s=t.length>0?`WHERE ${t.join(" AND ")}`:"",o=e.limit??50,i=e.offset??0;return this.db.prepare(`
|
|
48
48
|
SELECT id, task_id, trace_id, source, reason, score, status,
|
|
49
49
|
enqueued_at, started_at, completed_at, resolution, created_at, updated_at,
|
|
50
50
|
task_kind, priority, retry_count, max_retries, last_error, result_ref
|
|
@@ -101,7 +101,7 @@ var Oe=(r=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(r,{get:(e,t)=>(
|
|
|
101
101
|
FROM tool_calls
|
|
102
102
|
WHERE id = ?
|
|
103
103
|
LIMIT 1
|
|
104
|
-
`).get(e);return!
|
|
104
|
+
`).get(e);return!Te(t)||typeof t.id!="number"||typeof t.session_id!="string"||typeof t.tool_name!="string"||typeof t.outcome!="string"||typeof t.params_json!="string"?null:{id:t.id,sessionId:t.session_id,toolName:t.tool_name,outcome:t.outcome,paramsJson:t.params_json}}getRuleHostContextRowsBefore(e,t,n=20){let s=Math.max(1,Math.floor(n)),o=this.db.prepare(`
|
|
105
105
|
SELECT id, tool_name, outcome, params_json
|
|
106
106
|
FROM tool_calls
|
|
107
107
|
WHERE session_id = ? AND id < ?
|
|
@@ -118,7 +118,7 @@ var Oe=(r=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(r,{get:(e,t)=>(
|
|
|
118
118
|
FROM pain_events
|
|
119
119
|
WHERE canonical_pain_id = ?
|
|
120
120
|
LIMIT 1
|
|
121
|
-
`).get(e);return
|
|
121
|
+
`).get(e);return st(t)?{id:t.id,sessionId:t.session_id,source:String(t.source),score:Number(t.score),reason:t.reason?String(t.reason):null,severity:t.severity?String(t.severity):null,origin:t.origin?String(t.origin):null,confidence:t.confidence!=null?Number(t.confidence):null,text:t.text?String(t.text):null,canonicalPainId:String(t.canonical_pain_id),runtimeTaskId:t.runtime_task_id?String(t.runtime_task_id):null,createdAt:String(t.created_at)}:null}listUserTurnsForSession(e){return this.db.prepare(`
|
|
122
122
|
SELECT id, turn_index, raw_excerpt, correction_detected, correction_cue, created_at
|
|
123
123
|
FROM user_turns
|
|
124
124
|
WHERE session_id = ?
|
|
@@ -146,20 +146,20 @@ var Oe=(r=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(r,{get:(e,t)=>(
|
|
|
146
146
|
LEFT JOIN user_turns ut ON ut.id = cs.user_correction_turn_id
|
|
147
147
|
WHERE cs.session_id = ?
|
|
148
148
|
ORDER BY cs.created_at DESC
|
|
149
|
-
`).all(e).map(n=>({correctionCue:n.correction_cue?String(n.correction_cue):null}))}reviewCorrectionSample(e,t,n){let s=
|
|
149
|
+
`).all(e).map(n=>({correctionCue:n.correction_cue?String(n.correction_cue):null}))}reviewCorrectionSample(e,t,n){let s=m();if(!this.withWrite(()=>this.db.prepare(`
|
|
150
150
|
UPDATE correction_samples
|
|
151
151
|
SET review_status = ?, updated_at = ?
|
|
152
152
|
WHERE sample_id = ?
|
|
153
153
|
`).run(t,s,e).changes===0?!1:(this.db.prepare(`
|
|
154
154
|
INSERT INTO sample_reviews (sample_id, review_status, note, created_at)
|
|
155
155
|
VALUES (?, ?, ?, ?)
|
|
156
|
-
`).run(e,t,n??null,s),!0)))throw new
|
|
156
|
+
`).run(e,t,n??null,s),!0)))throw new I(e);let i=this.db.prepare(`
|
|
157
157
|
SELECT sample_id, session_id, bad_assistant_turn_id, user_correction_turn_id,
|
|
158
158
|
recovery_tool_span_json, diff_excerpt, principle_ids_json, quality_score,
|
|
159
159
|
review_status, export_mode, created_at, updated_at
|
|
160
160
|
FROM correction_samples
|
|
161
161
|
WHERE sample_id = ?
|
|
162
|
-
`).get(e);if(!i)throw new
|
|
162
|
+
`).get(e);if(!i)throw new I(`${e} (after update)`);return t==="rejected"&&this.recordCorrectionRejectedPain({session_id:i.session_id,quality_score:i.quality_score,diff_excerpt:i.diff_excerpt,principle_ids_json:i.principle_ids_json,created_at:i.created_at}),{sampleId:String(i.sample_id),sessionId:String(i.session_id),badAssistantTurnId:Number(i.bad_assistant_turn_id),userCorrectionTurnId:Number(i.user_correction_turn_id),recoveryToolSpanJson:String(i.recovery_tool_span_json),diffExcerpt:String(i.diff_excerpt??""),principleIdsJson:String(i.principle_ids_json??"[]"),qualityScore:Number(i.quality_score),reviewStatus:i.review_status,exportMode:i.export_mode,createdAt:String(i.created_at),updatedAt:String(i.updated_at)}}recordCorrectionRejectedPain(e){let t=String(e.session_id),n=Number(e.quality_score),s=String(e.diff_excerpt??""),o=String(e.principle_ids_json??"[]"),i=Math.max(0,Math.min(100,Math.round(Number(n)||0))),c=`Correction rejected (quality ${n.toFixed(2)}). Principles: ${o}${s?` \u2014 ${s.slice(0,120)}`:""}`;try{this.recordPainEvent({sessionId:t,source:"correction_rejected",score:i,reason:c,severity:i>=70?"severe":i>=40?"moderate":"mild",origin:"system_infer",text:s||void 0,createdAt:String(e.created_at),hostKind:"openclaw"})}catch(a){console.warn(`[Trajectory] Failed to record correction_rejected pain event: ${String(a)}`)}}enqueueSignalConfirmation(e){let t=`sq_${q.createHash("sha256").update(`${e.sessionId}:${e.userTurnRowid}`).digest("hex").slice(0,12)}`;this.withWrite(()=>{this.db.prepare(`
|
|
163
163
|
INSERT OR IGNORE INTO signal_confirmations (
|
|
164
164
|
id, session_id, user_turn_rowid, occurrence_id, excerpt,
|
|
165
165
|
terms_json, suggested_type, status, attempts, created_at
|
|
@@ -169,14 +169,14 @@ var Oe=(r=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(r,{get:(e,t)=>(
|
|
|
169
169
|
WHERE status = 'pending'
|
|
170
170
|
ORDER BY attempts ASC, created_at ASC
|
|
171
171
|
LIMIT ?
|
|
172
|
-
`).all(e).map(
|
|
172
|
+
`).all(e).map(at)}bumpSignalConfirmationAttempt(e){return this.withWrite(()=>{this.db.prepare(`
|
|
173
173
|
UPDATE signal_confirmations SET attempts = attempts + 1
|
|
174
174
|
WHERE id = ? AND status = 'pending'
|
|
175
175
|
`).run(e)}),this.db.prepare("SELECT attempts FROM signal_confirmations WHERE id = ?").get(e)?.attempts??0}markSignalConfirmationResult(e,t,n){let s=this.withWrite(()=>this.db.prepare(`
|
|
176
176
|
UPDATE signal_confirmations
|
|
177
177
|
SET status = ?, resolved_at = ?, resolution = ?
|
|
178
178
|
WHERE id = ? AND status = 'pending'
|
|
179
|
-
`).run(t,
|
|
179
|
+
`).run(t,m(),n.slice(0,500),e));return Number(s.changes)>0}countPendingSignalConfirmations(){return this.db.prepare("SELECT COUNT(*) AS n FROM signal_confirmations WHERE status = 'pending'").get().n}exportCorrections(e){let t=this.db.prepare(`
|
|
180
180
|
SELECT cs.sample_id, cs.session_id, cs.recovery_tool_span_json, cs.diff_excerpt, cs.quality_score,
|
|
181
181
|
at.raw_text AS assistant_raw_text, at.blob_ref AS assistant_blob_ref, at.sanitized_text,
|
|
182
182
|
ut.raw_text AS user_raw_text, ut.blob_ref AS user_blob_ref, ut.correction_cue
|
|
@@ -185,16 +185,16 @@ var Oe=(r=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(r,{get:(e,t)=>(
|
|
|
185
185
|
JOIN user_turns ut ON ut.id = cs.user_correction_turn_id
|
|
186
186
|
WHERE (? = 0 OR cs.review_status = 'approved')
|
|
187
187
|
ORDER BY cs.created_at ASC
|
|
188
|
-
`).all(e.approvedOnly?1:0),n=g.join(this.exportDir,`corrections-${Date.now()}-${e.mode}.jsonl`),s=t.map(o=>{let i=this.restoreRawText(o.assistant_raw_text,o.assistant_blob_ref),c=this.restoreRawText(o.user_raw_text,o.user_blob_ref),a=e.mode==="redacted"?
|
|
188
|
+
`).all(e.approvedOnly?1:0),n=g.join(this.exportDir,`corrections-${Date.now()}-${e.mode}.jsonl`),s=t.map(o=>{let i=this.restoreRawText(o.assistant_raw_text,o.assistant_blob_ref),c=this.restoreRawText(o.user_raw_text,o.user_blob_ref),a=e.mode==="redacted"?me(i):i,d=e.mode==="redacted"?me(c):c;return JSON.stringify({sample_id:o.sample_id,session_id:o.session_id,instruction:d,input_context:a,bad_attempt_summary:String(o.diff_excerpt??""),preferred_response:d,labels:{correction_cue:o.correction_cue,quality_score:o.quality_score},metadata:{mode:e.mode,recovery_tool_span_json:o.recovery_tool_span_json}})});return w(n,`${s.join(`
|
|
189
189
|
`)}${s.length>0?`
|
|
190
|
-
`:""}`),this.recordExportAudit("corrections",e.mode,e.approvedOnly,n,t.length),{filePath:n,count:t.length,mode:e.mode}}exportAnalytics(){let e={generatedAt:
|
|
190
|
+
`:""}`),this.recordExportAudit("corrections",e.mode,e.approvedOnly,n,t.length),{filePath:n,count:t.length,mode:e.mode}}exportAnalytics(){let e={generatedAt:m(),stats:this.getDataStats(),dailyMetrics:this.dailyMetrics(),errorClusters:this.db.prepare("SELECT * FROM v_error_clusters").all(),principleEffectiveness:this.db.prepare("SELECT * FROM v_principle_effectiveness").all(),sampleQueue:this.db.prepare("SELECT * FROM v_sample_queue").all()},t=g.join(this.exportDir,`analytics-${Date.now()}.json`);return w(t,JSON.stringify(e,null,2)),this.recordExportAudit("analytics","raw",!0,t,Array.isArray(e.dailyMetrics)?e.dailyMetrics.length:0),{filePath:t,count:Array.isArray(e.dailyMetrics)?e.dailyMetrics.length:0}}getDataStats(){let e=(n,s)=>{let o=s?`SELECT COUNT(*) as count FROM ${n} WHERE ${s}`:`SELECT COUNT(*) as count FROM ${n}`;return Number(this.db.prepare(o).get().count)},t=this.db.prepare(`
|
|
191
191
|
SELECT MAX(ts) AS ts FROM (
|
|
192
192
|
SELECT MAX(created_at) AS ts FROM assistant_turns
|
|
193
193
|
UNION ALL SELECT MAX(created_at) AS ts FROM user_turns
|
|
194
194
|
UNION ALL SELECT MAX(created_at) AS ts FROM tool_calls
|
|
195
195
|
UNION ALL SELECT MAX(created_at) AS ts FROM pain_events
|
|
196
196
|
)
|
|
197
|
-
`).get();return{dbPath:this.dbPath,dbSizeBytes:
|
|
197
|
+
`).get();return{dbPath:this.dbPath,dbSizeBytes:Ee(this.dbPath),assistantTurns:e("assistant_turns"),userTurns:e("user_turns"),toolCalls:e("tool_calls"),painEvents:e("pain_events"),pendingSamples:e("correction_samples","review_status = 'pending'"),approvedSamples:e("correction_samples","review_status = 'approved'"),blobBytes:this.computeBlobBytes(),lastIngestAt:t.ts??null}}cleanupBlobStorage(){return this.pruneUnreferencedBlobs()}initSchema(){let e=ot(this.db);for(let n of e.warnings)console.info(`[PD:TrajectoryDatabase] schema init warning: ${n}`);let t=this.db.prepare("SELECT version FROM schema_version LIMIT 1").get();this.migrateSchema(t?.version),t?t.version!==1&&this.db.prepare("UPDATE schema_version SET version = ?").run(1):this.db.prepare("INSERT INTO schema_version (version) VALUES (?)").run(1)}importLegacyArtifacts(){this.importLegacySessions(),this.importLegacyEvents(),this.importLegacyEvolution()}migrateSchema(e){this.db.exec(`
|
|
198
198
|
DROP VIEW IF EXISTS v_daily_metrics;
|
|
199
199
|
CREATE VIEW IF NOT EXISTS v_daily_metrics AS
|
|
200
200
|
WITH tool_daily AS (
|
|
@@ -219,13 +219,13 @@ var Oe=(r=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(r,{get:(e,t)=>(
|
|
|
219
219
|
COALESCE(correction_daily.user_corrections, 0) AS user_corrections
|
|
220
220
|
FROM tool_daily
|
|
221
221
|
LEFT JOIN correction_daily ON correction_daily.day = tool_daily.day;
|
|
222
|
-
`)}dailyMetrics(){return this.db.prepare("SELECT * FROM v_daily_metrics ORDER BY day ASC").all()}importLegacySessions(){let e="legacy:sessions";if(this.isImported(e))return;let t=
|
|
223
|
-
`))try{let o=JSON.parse(s);o.type==="pain_signal"&&o.sessionId&&this.recordPainEvent({sessionId:o.sessionId,source:String(o.data?.source??"legacy"),score:Number(o.data?.score??0),reason:typeof o.data?.reason=="string"?o.data.reason:null,severity:typeof o.data?.severity=="string"?o.data.severity:null,origin:typeof o.data?.origin=="string"?o.data.origin:null,confidence:typeof o.data?.confidence=="number"?o.data.confidence:null,createdAt:o.ts}),o.type==="trust_change"&&this.recordTrustChange({sessionId:o.sessionId,previousScore:Number(o.data?.previousScore??0),newScore:Number(o.data?.newScore??0),delta:Number(o.data?.delta??0),reason:String(o.data?.reason??"legacy"),createdAt:o.ts}),o.type==="gate_block"&&this.recordGateBlock({sessionId:o.sessionId,toolName:String(o.data?.toolName??"unknown"),filePath:typeof o.data?.filePath=="string"?o.data.filePath:null,reason:String(o.data?.reason??"legacy"),createdAt:o.ts})}catch{}this.markImported(e)}importLegacyEvolution(){let e="legacy:evolution";if(this.isImported(e))return;let t=
|
|
222
|
+
`)}dailyMetrics(){return this.db.prepare("SELECT * FROM v_daily_metrics ORDER BY day ASC").all()}importLegacySessions(){let e="legacy:sessions";if(this.isImported(e))return;let t=R(this.workspaceDir,"SESSION_DIR");if(E.existsSync(t)){for(let n of E.readdirSync(t).filter(s=>s.endsWith(".json")))try{let s=JSON.parse(E.readFileSync(g.join(t,n),"utf8"));if(s.sessionId){let o=typeof s.lastActivityAt=="number"?new Date(s.lastActivityAt).toISOString():m();this.recordSession({sessionId:s.sessionId,startedAt:o})}}catch{}this.markImported(e)}}importLegacyEvents(){let e="legacy:events";if(this.isImported(e))return;let t=g.join(this.stateDir,"logs","events.jsonl");if(!E.existsSync(t))return;let n=E.readFileSync(t,"utf8").trim();if(!n){this.markImported(e);return}for(let s of n.split(`
|
|
223
|
+
`))try{let o=JSON.parse(s);o.type==="pain_signal"&&o.sessionId&&this.recordPainEvent({sessionId:o.sessionId,source:String(o.data?.source??"legacy"),score:Number(o.data?.score??0),reason:typeof o.data?.reason=="string"?o.data.reason:null,severity:typeof o.data?.severity=="string"?o.data.severity:null,origin:typeof o.data?.origin=="string"?o.data.origin:null,confidence:typeof o.data?.confidence=="number"?o.data.confidence:null,createdAt:o.ts}),o.type==="trust_change"&&this.recordTrustChange({sessionId:o.sessionId,previousScore:Number(o.data?.previousScore??0),newScore:Number(o.data?.newScore??0),delta:Number(o.data?.delta??0),reason:String(o.data?.reason??"legacy"),createdAt:o.ts}),o.type==="gate_block"&&this.recordGateBlock({sessionId:o.sessionId,toolName:String(o.data?.toolName??"unknown"),filePath:typeof o.data?.filePath=="string"?o.data.filePath:null,reason:String(o.data?.reason??"legacy"),createdAt:o.ts})}catch{}this.markImported(e)}importLegacyEvolution(){let e="legacy:evolution";if(this.isImported(e))return;let t=R(this.workspaceDir,"EVOLUTION_STREAM");if(!E.existsSync(t))return;let n=E.readFileSync(t,"utf8").trim();if(!n){this.markImported(e);return}for(let s of n.split(`
|
|
224
224
|
`))try{let o=JSON.parse(s);this.recordPrincipleEvent({principleId:typeof o.data?.principleId=="string"?o.data.principleId:null,eventType:String(o.type??"legacy"),payload:o.data??{},createdAt:o.ts})}catch{}this.markImported(e)}markImported(e){this.withWrite(()=>{this.db.prepare(`
|
|
225
225
|
INSERT INTO ingest_checkpoint (source_key, imported_at)
|
|
226
226
|
VALUES (?, ?)
|
|
227
227
|
ON CONFLICT(source_key) DO UPDATE SET imported_at = excluded.imported_at
|
|
228
|
-
`).run(e,
|
|
228
|
+
`).run(e,m())})}isImported(e){return!!this.db.prepare("SELECT source_key FROM ingest_checkpoint WHERE source_key = ?").get(e)}maybeCreateCorrectionSample(e){if(this.db.prepare(`
|
|
229
229
|
SELECT sample_id FROM correction_samples
|
|
230
230
|
WHERE session_id = ? AND review_status = 'pending'
|
|
231
231
|
ORDER BY created_at DESC
|
|
@@ -248,17 +248,17 @@ var Oe=(r=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(r,{get:(e,t)=>(
|
|
|
248
248
|
WHERE session_id = ?
|
|
249
249
|
ORDER BY id DESC
|
|
250
250
|
LIMIT 5
|
|
251
|
-
`).all(e).filter(f=>f.outcome==="success"),c=i[0]?.id??n.id,a=`sample_${
|
|
251
|
+
`).all(e).filter(f=>f.outcome==="success"),c=i[0]?.id??n.id,a=`sample_${q.createHash("sha256").update(`${e}:${n.id}:${c}`).digest("hex").slice(0,12)}`,d=this.restoreRawText(n.raw_text,n.blob_ref),S=[n.references_assistant_turn_id?35:0,n.correction_cue?20:0,s?20:0,Math.min(i.length,3)*5].reduce((f,ye)=>f+ye,0),p=d||(s?String(s.error_message??s.error_type??s.tool_name):"")||String(n.correction_cue??"user correction");this.withWrite(()=>{this.db.prepare(`
|
|
252
252
|
INSERT OR IGNORE INTO correction_samples (
|
|
253
253
|
sample_id, session_id, bad_assistant_turn_id, user_correction_turn_id,
|
|
254
254
|
recovery_tool_span_json, diff_excerpt, principle_ids_json, quality_score,
|
|
255
255
|
review_status, export_mode, created_at, updated_at
|
|
256
256
|
) VALUES (?, ?, ?, ?, ?, ?, ?, ?, 'pending', 'raw', ?, ?)
|
|
257
|
-
`).run(a,e,Number(n.references_assistant_turn_id),Number(n.id),y(i.map(f=>({id:f.id,toolName:f.tool_name,outcome:f.outcome}))),
|
|
257
|
+
`).run(a,e,Number(n.references_assistant_turn_id),Number(n.id),y(i.map(f=>({id:f.id,toolName:f.tool_name,outcome:f.outcome}))),it(p),"[]",S,m(),m())})}recordExportAudit(e,t,n,s,o){this.withWrite(()=>{this.db.prepare(`
|
|
258
258
|
INSERT INTO exports_audit (export_kind, mode, approved_only, file_path, row_count, created_at)
|
|
259
259
|
VALUES (?, ?, ?, ?, ?, ?)
|
|
260
|
-
`).run(e,t,n?1:0,s,o,
|
|
260
|
+
`).run(e,t,n?1:0,s,o,m())})}storeRawText(e,t){let n=t.length>200?`${t.slice(0,197)}...`:t;if(Buffer.byteLength(t,"utf8")<=this.blobInlineThresholdBytes)return{inlineText:t,blobRef:null,excerpt:n};let o=q.createHash("sha256").update(t).digest("hex"),i=`${e}-${o}.txt`,c=g.join(this.blobDir,i);return E.existsSync(c)||w(c,t),{inlineText:null,blobRef:i,excerpt:n}}restoreRawText(e,t){if(e)return e;if(!t)return"";let n=g.join(this.blobDir,t);return E.existsSync(n)?E.readFileSync(n,"utf8"):""}computeBlobBytes(){return E.existsSync(this.blobDir)?E.readdirSync(this.blobDir).reduce((e,t)=>e+Ee(g.join(this.blobDir,t)),0):0}pruneUnreferencedBlobs(){if(!E.existsSync(this.blobDir))return{removedFiles:0,reclaimedBytes:0};let e=new Set,t=this.db.prepare(`
|
|
261
261
|
SELECT blob_ref FROM assistant_turns WHERE blob_ref IS NOT NULL
|
|
262
262
|
UNION
|
|
263
263
|
SELECT blob_ref FROM user_turns WHERE blob_ref IS NOT NULL
|
|
264
|
-
`).all();for(let i of t)i.blob_ref&&e.add(String(i.blob_ref));let n=Date.now(),s=0,o=0;for(let i of E.readdirSync(this.blobDir)){if(e.has(i))continue;let c=g.join(this.blobDir,i),a;try{a=E.statSync(c)}catch{continue}a.isFile()&&(this.orphanBlobGraceMs>0&&n-a.mtimeMs<this.orphanBlobGraceMs||(o+=a.size,s+=1,E.rmSync(c,{force:!0})))}return{removedFiles:s,reclaimedBytes:o}}withWrite(e){return
|
|
264
|
+
`).all();for(let i of t)i.blob_ref&&e.add(String(i.blob_ref));let n=Date.now(),s=0,o=0;for(let i of E.readdirSync(this.blobDir)){if(e.has(i))continue;let c=g.join(this.blobDir,i),a;try{a=E.statSync(c)}catch{continue}a.isFile()&&(this.orphanBlobGraceMs>0&&n-a.mtimeMs<this.orphanBlobGraceMs||(o+=a.size,s+=1,E.rmSync(c,{force:!0})))}return{removedFiles:s,reclaimedBytes:o}}withWrite(e){return le(this.dbPath,e,{lockSuffix:".trajectory.lock",lockStaleMs:3e4})}},v=class{static instances=new Map;static get(e,t={}){let n=g.resolve(e),s=this.instances.get(n);if(s)return s;let o=new k({workspaceDir:n,...t});return this.instances.set(n,o),o}static dispose(e){let t=g.resolve(e),n=this.instances.get(t);n&&(n.dispose(),this.instances.delete(t))}static clear(){for(let e of this.instances.values())e.dispose();this.instances.clear()}static use(e,t,n={}){let s=g.resolve(e),o=this.instances.get(s);if(o)return t(o);let i=new k({workspaceDir:s,...n});try{return t(i)}finally{i.dispose()}}};var ct=new Set(["__proto__","constructor","prototype"]);function lt(r){return typeof r=="object"&&r!==null&&!Array.isArray(r)}function ut(r){if(!Array.isArray(r))return{valid:!1,errors:["toolSemanticMappings must be an array"]};let e=[],t=new Map;return r.forEach((n,s)=>{if(!lt(n)){e.push(`toolSemanticMappings[${s}] must be a plain object`);return}if(!Object.hasOwn(n,"rawToolName")||typeof n.rawToolName!="string"||n.rawToolName.trim()===""){e.push(`toolSemanticMappings[${s}].rawToolName must be a non-empty string`);return}if(ct.has(n.rawToolName)){e.push(`toolSemanticMappings[${s}].rawToolName must not be a prototype-pollution key`);return}let o=n.canonicalKind;if(!ee(o)){e.push(`toolSemanticMappings[${s}].canonicalKind must be one of ${[...U].join("|")}, got ${String(o)}`);return}let i=t.get(n.rawToolName);if(i!==void 0&&i!==o){e.push(`toolSemanticMappings[${s}]: rawToolName '${n.rawToolName}' declared twice with conflicting kinds (${i} vs ${o})`);return}t.set(n.rawToolName,o)}),{valid:e.length===0,errors:e}}function fe(r){let e,t=new Set,n=[];if(r===void 0)e=C;else{let s=ut(r);if(!s.valid)return{ok:!1,errors:s.errors};let o={...C};for(let i of r)o[i.rawToolName]=i.canonicalKind,t.add(i.rawToolName);n=Object.freeze(r.map(i=>Object.freeze({rawToolName:i.rawToolName,canonicalKind:i.canonicalKind}))),e=Object.freeze(o)}return{ok:!0,registry:{version:1,hasHostLayer:t.size>0,hasHostTool(s){return typeof s!="string"?!1:t.has(s)},hostMappings(){return n},lookup(s){return typeof s!="string"||!Object.hasOwn(e,s)?null:e[s]??null},resolve(s){return this.lookup(s)??"other"}}}}var ge=["read","read_file","read_many_files","image_read","search_file_content","grep","grep_search","list_directory","ls","glob","lsp_hover","lsp_goto_definition","lsp_find_references","web_fetch","web_search","ref_search_documentation","ref_read_url","resolve-library-id","get-library-docs","memory_recall","save_memory","todo_read","todo_write","ask_user","ask_user_question","pd-status","report"],b=["write","edit","apply_patch"],x=["exec"],dt=[...x],D=["sessions_spawn"],_t=[...b],pt=[...b,...x,...D],Et=[...ge],ar=new Set(ge),cr=new Set(b),lr=new Set(dt),ur=new Set(x),dr=new Set(D),_r=new Set(_t),pr=new Set(pt),Er=new Set(Et),mr=new Set([...b]);function V(r,e){return r.map(t=>({rawToolName:t,canonicalKind:e}))}var mt=Object.freeze([...V(x,"execute"),...V(b,"write"),...V(D,"agent")]),z=fe(mt);if(!z.ok)throw new Error(`[PD] OpenClaw tool semantic declaration is invalid: ${z.errors.join("; ")}`);var Se=z.registry;var Tt=new Set(["success","failure","blocked"]);function ft(r){return typeof r=="object"&&r!==null&&!Array.isArray(r)}function gt(r){return typeof r=="string"&&Tt.has(r)}function he(r,e,t){let n=[];for(let s of r){let o=s.toolName;if(typeof o!="string"||o.length===0)return L(`row id=${s.id}: tool_name must be a non-empty string`);let i=s.outcome;if(!gt(i))return L(`row id=${s.id}: outcome "${s.outcome}" is not a valid RuleToolOutcome`);let c=s.paramsJson;if(typeof c!="string")return L(`row id=${s.id}: params_json must be a string`);let a;try{a=JSON.parse(c)}catch{return L(`row id=${s.id}: params_json is not valid JSON`)}if(!ft(a))return L(`row id=${s.id}: params_json must parse to a non-array object`);let d=Se.resolve(o),S=j(a,{isBashTool:d==="execute",isWriteTool:d==="write",toolName:o}),p=P(S,t);n.push({sequenceId:s.id,toolName:o,canonicalKind:d,normalizedPath:p===""?null:p,paramsSummary:a,outcome:i})}return{status:"available",truncated:e,calls:n}}function L(r){return{status:"unavailable",unavailableReason:r,truncated:!1,calls:[]}}var St=3,ht=5,Rt=100,Oe=new Set(["__proto__","constructor","prototype"]);function M(r,e){try{return e()}catch(t){let n=t instanceof Error?t.message:String(t);throw N("evidence_source_error",`[BehaviorExamplePackAssembler] trajectory store ${r} failed (evidence source error, SPEC-PD-IAER-001 \xA76.2): ${n}`)}}function Ot(r){return typeof r=="object"&&r!==null&&!Array.isArray(r)}function yt(r){for(let e of Object.keys(r))if(Oe.has(e))return!1;return!0}var J=class{db;constructor(e){this.db=v.get(e.workspaceDir)}assemble(e){let t=M(`pain lineage read for canonical_pain_id="${e.sourcePainId}"`,()=>this.db.getPainEventByCanonicalId(e.sourcePainId));if(!t)throw N("pain_not_found",`[BehaviorExamplePackAssembler] pain event not found for canonical_pain_id="${e.sourcePainId}" (ERR-069 fail loud)`);bt(e);let n=Re(M(`evidence row read for id=${e.sourceNegativeToolCallId}`,()=>this.db.getRuleHostEvidenceRow(e.sourceNegativeToolCallId)),e.sourceNegativeToolCallId),s=e.positiveToolCallIds.map(p=>Re(M(`evidence row read for id=${p}`,()=>this.db.getRuleHostEvidenceRow(p)),p));for(let p of[n,...s])if(p.sessionId!==t.sessionId)throw N("session_mismatch",`[BehaviorExamplePackAssembler] selected tool call ${p.id} session mismatch; all examples must belong to pain session ${t.sessionId}`);let o=[],i={projectDir:e.projectDir,redactionNotes:o},c=this.buildSelectedCase(n,"negative","block",i),a=s.map(p=>this.buildSelectedCase(p,"positive","allow",i)),d={sourceNegativeCase:c,ownerDesiredOutcome:e.ownerDesiredOutcome,positiveCounterexamples:a,evidenceRefs:[`pain:${t.id}`,`tool_call:${n.id}`,...s.map(p=>`tool_call:${p.id}`)].slice(0,ht),redactionNotes:o},S=H(d);if(!S.valid)throw new Error(`[BehaviorExamplePackAssembler] assembled pack failed validateBehaviorExamplePack: ${S.errors.join("; ")} (ERR-069 fail loud)`);return d}buildSelectedCase(e,t,n,s){let{projectDir:o,redactionNotes:i}=s,c=Nt(e,t,n,o),a=At(c.params,o);i.push(...a.notes);let d=M(`context history read for session=${e.sessionId} before id=${e.id}`,()=>this.db.getRuleHostContextRowsBefore(e.sessionId,e.id,Rt)),S=he(d.rows,d.truncated,o),p=Q(e.toolName,a.redacted,o),f={version:2,history:S,facts:B(S,p.normalizedPath||null,null)};return{...c,params:a.redacted,ruleContext:f}}};function bt(r){if(!Number.isSafeInteger(r.sourceNegativeToolCallId)||r.sourceNegativeToolCallId<=0)throw new Error("[BehaviorExamplePackAssembler] sourceNegativeToolCallId must be a positive integer");if(!Array.isArray(r.positiveToolCallIds)||r.positiveToolCallIds.length===0||r.positiveToolCallIds.length>St)throw new Error("[BehaviorExamplePackAssembler] positiveToolCallIds must contain 1 to at most 3 IDs");let e=[r.sourceNegativeToolCallId,...r.positiveToolCallIds];if(e.some(t=>!Number.isSafeInteger(t)||t<=0)||new Set(e).size!==e.length)throw new Error("[BehaviorExamplePackAssembler] selected tool call IDs must be unique positive integers")}function Re(r,e){if(!r)throw N("tool_call_not_found",`[BehaviorExamplePackAssembler] selected tool call id=${e} not found`);return r}function Nt(r,e,t,n){if(typeof r.toolName!="string"||r.toolName.length===0)throw new Error(`[BehaviorExamplePackAssembler] row id=${r.id}: toolName must be a non-empty string (rc-9 fail loud)`);if(typeof r.paramsJson!="string")throw new Error(`[BehaviorExamplePackAssembler] row id=${r.id}: paramsJson must be a string (rc-9 fail loud)`);let s;try{s=JSON.parse(r.paramsJson)}catch{throw new Error(`[BehaviorExamplePackAssembler] row id=${r.id}: paramsJson is not valid JSON (rc-9 fail loud)`)}if(!Ot(s))throw new Error(`[BehaviorExamplePackAssembler] row id=${r.id}: paramsJson must parse to a non-array object (rc-9 fail loud)`);if(!yt(s))throw new Error(`[BehaviorExamplePackAssembler] row id=${r.id}: paramsJson must not carry prototype-pollution keys (ERR-076, rc-9 fail loud)`);return{caseId:`case-${e}-${r.id}`,kind:e,toolName:r.toolName,params:s,expectedDecision:t}}function At(r,e){let t=[],n={};for(let s of Object.keys(r)){if(Oe.has(s))continue;let o=r[s];if(typeof o!="string"){n[s]=o;continue}if(It(o)&&!o.startsWith(e)){n[s]="<redacted:absolute-path>",t.push(`redacted absolute path in field "${s}" (outside project tree)`);continue}if(xt(o)){n[s]="<redacted:secret>",t.push(`redacted possible secret in field "${s}"`);continue}n[s]=o}return{redacted:n,notes:t}}function It(r){return r.startsWith("/")||/^[A-Za-z]:[\\/]/.test(r)}var vt=[/AKIA[0-9A-Z]{16}/,/[A-Za-z0-9+/]{40,}/];function xt(r){if(r.length<20)return!1;for(let e of vt)if(e.test(r))return!0;return!1}export{J as BehaviorExamplePackAssembler,v as RuleHostEvidenceRegistry};
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
"id": "principles-disciple",
|
|
3
3
|
"name": "Principles Disciple",
|
|
4
4
|
"description": "Principles Disciple is an AI Agent Governance System. Stop correcting the same AI behavior across sessions. Turn repeated Agent corrections into Owner-approved, observable, reversible behavior principles.",
|
|
5
|
-
"version": "2.1.
|
|
5
|
+
"version": "2.1.5",
|
|
6
6
|
"activation": {
|
|
7
7
|
"onStartup": true,
|
|
8
8
|
"onCapabilities": [
|
package/plugin/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "principles-disciple",
|
|
3
|
-
"version": "2.1.
|
|
3
|
+
"version": "2.1.5",
|
|
4
4
|
"description": "Principles Disciple is an AI Agent Governance System. Stop correcting the same AI behavior across sessions. Turn repeated Agent corrections into Owner-approved, observable, reversible behavior principles.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./dist/index.js",
|
|
@@ -5,6 +5,8 @@ export declare const WORKBUDDY_PLUGIN_NAME = "principles-disciple";
|
|
|
5
5
|
export declare const WORKBUDDY_MARKETPLACE_NAME = "principles-disciple-market";
|
|
6
6
|
/** Registry/settings key: "principles-disciple@principles-disciple-market". */
|
|
7
7
|
export declare const WORKBUDDY_PLUGIN_KEY = "principles-disciple@principles-disciple-market";
|
|
8
|
+
/** Engine CLI shipped with WorkBuddy Desktop (probe P01 frozen path). */
|
|
9
|
+
export declare const WORKBUDDY_ENGINE_RELATIVE: string[];
|
|
8
10
|
export interface WorkbuddyCommandResult {
|
|
9
11
|
status: number | null;
|
|
10
12
|
stdout: string;
|
|
@@ -57,13 +59,24 @@ export interface WorkbuddyPaths {
|
|
|
57
59
|
installManifestPath: string;
|
|
58
60
|
}
|
|
59
61
|
export declare function resolveWorkbuddyPaths(homeDir: string): WorkbuddyPaths;
|
|
62
|
+
/**
|
|
63
|
+
* Candidate Program Files roots probed for the WorkBuddy engine, in order:
|
|
64
|
+
* the env-declared Program Files (both variants), the SystemDrive root, then —
|
|
65
|
+
* Windows only — the same directories on each discovered fixed drive.
|
|
66
|
+
*
|
|
67
|
+
* G1 (2026-10-15): a Desktop install outside the SystemDrive's Program Files
|
|
68
|
+
* (e.g. D:\Program Files\WorkBuddy, the machine this gap was proven on)
|
|
69
|
+
* previously resolved to "engine not found", so install skipped its engine
|
|
70
|
+
* verification and detect() reported an absent engine on a real installation.
|
|
71
|
+
*/
|
|
72
|
+
export declare function workbuddyEngineCandidateRoots(env?: Record<string, string | undefined>, fixedDriveLetters?: readonly string[]): string[];
|
|
60
73
|
/**
|
|
61
74
|
* Resolve the WorkBuddy engine CLI path.
|
|
62
75
|
*
|
|
63
76
|
* Order: PD_WORKBUDDY_ENGINE / WB_ENGINE env override (probe convention) →
|
|
64
|
-
* the Desktop install location under Program Files (frozen by probe P01)
|
|
65
|
-
* The engine is NOT exposed on
|
|
66
|
-
* fact, never a guess.
|
|
77
|
+
* the Desktop install location under Program Files (frozen by probe P01),
|
|
78
|
+
* multi-drive per workbuddyEngineCandidateRoots. The engine is NOT exposed on
|
|
79
|
+
* PATH — absence is a detectable, reportable fact, never a guess.
|
|
67
80
|
*/
|
|
68
81
|
export declare function resolveWorkbuddyEnginePath(): string | undefined;
|
|
69
82
|
export type JsonFileRead = {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"workbuddy-host-installer.d.ts","sourceRoot":"","sources":["../../src/installers/workbuddy-host-installer.ts"],"names":[],"mappings":"AAyDA,OAAO,KAAK,EACV,aAAa,EACb,kBAAkB,EAClB,iBAAiB,EACjB,oBAAoB,EACpB,mBAAmB,EACnB,gBAAgB,EACjB,MAAM,uBAAuB,CAAC;AAM/B,yFAAyF;AACzF,eAAO,MAAM,qBAAqB,wBAAwB,CAAC;AAC3D,qFAAqF;AACrF,eAAO,MAAM,0BAA0B,+BAA+B,CAAC;AACvE,+EAA+E;AAC/E,eAAO,MAAM,oBAAoB,mDAA2D,CAAC;
|
|
1
|
+
{"version":3,"file":"workbuddy-host-installer.d.ts","sourceRoot":"","sources":["../../src/installers/workbuddy-host-installer.ts"],"names":[],"mappings":"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"}
|
|
@@ -58,7 +58,7 @@ export const WORKBUDDY_MARKETPLACE_NAME = 'principles-disciple-market';
|
|
|
58
58
|
/** Registry/settings key: "principles-disciple@principles-disciple-market". */
|
|
59
59
|
export const WORKBUDDY_PLUGIN_KEY = `${WORKBUDDY_PLUGIN_NAME}@${WORKBUDDY_MARKETPLACE_NAME}`;
|
|
60
60
|
/** Engine CLI shipped with WorkBuddy Desktop (probe P01 frozen path). */
|
|
61
|
-
const WORKBUDDY_ENGINE_RELATIVE = ['resources', 'app.asar.unpacked', 'cli', 'dist', 'codebuddy-lite-wb.mjs'];
|
|
61
|
+
export const WORKBUDDY_ENGINE_RELATIVE = ['resources', 'app.asar.unpacked', 'cli', 'dist', 'codebuddy-lite-wb.mjs'];
|
|
62
62
|
/** Engine command success markers (frozen by probe P01 regexes). */
|
|
63
63
|
const MARKETPLACE_ADD_OK = /added successfully|already/i;
|
|
64
64
|
const PLUGIN_INSTALL_OK = /Successfully installed/i;
|
|
@@ -96,13 +96,65 @@ export function resolveWorkbuddyPaths(homeDir) {
|
|
|
96
96
|
installManifestPath: layout.manifest,
|
|
97
97
|
};
|
|
98
98
|
}
|
|
99
|
+
/**
|
|
100
|
+
* Enumerate Windows FIXED drives only. Letters can represent network or
|
|
101
|
+
* removable volumes; never treat A-Z as equivalent to fixed media.
|
|
102
|
+
* A failed/unsupported probe falls back to explicit ProgramFiles/SystemDrive
|
|
103
|
+
* paths, not a guess across mapped network drives.
|
|
104
|
+
*/
|
|
105
|
+
function workbuddyFixedDriveLetters() {
|
|
106
|
+
if (process.platform !== 'win32')
|
|
107
|
+
return [];
|
|
108
|
+
const probe = spawnSync('powershell.exe', [
|
|
109
|
+
'-NoProfile', '-NonInteractive', '-Command',
|
|
110
|
+
'[System.IO.DriveInfo]::GetDrives() | Where-Object { $_.DriveType -eq [System.IO.DriveType]::Fixed } | ForEach-Object { $_.Name }',
|
|
111
|
+
], { encoding: 'utf8', windowsHide: true, timeout: 5_000, maxBuffer: 8 * 1024 });
|
|
112
|
+
if (probe.error || probe.status !== 0 || typeof probe.stdout !== 'string')
|
|
113
|
+
return [];
|
|
114
|
+
return probe.stdout.split(/\r?\n/).map((line) => line.trim())
|
|
115
|
+
.filter((root) => /^[A-Za-z]:\\$/.test(root))
|
|
116
|
+
.map((root) => root.slice(0, 2).toUpperCase());
|
|
117
|
+
}
|
|
118
|
+
/**
|
|
119
|
+
* Candidate Program Files roots probed for the WorkBuddy engine, in order:
|
|
120
|
+
* the env-declared Program Files (both variants), the SystemDrive root, then —
|
|
121
|
+
* Windows only — the same directories on each discovered fixed drive.
|
|
122
|
+
*
|
|
123
|
+
* G1 (2026-10-15): a Desktop install outside the SystemDrive's Program Files
|
|
124
|
+
* (e.g. D:\Program Files\WorkBuddy, the machine this gap was proven on)
|
|
125
|
+
* previously resolved to "engine not found", so install skipped its engine
|
|
126
|
+
* verification and detect() reported an absent engine on a real installation.
|
|
127
|
+
*/
|
|
128
|
+
export function workbuddyEngineCandidateRoots(env = process.env, fixedDriveLetters) {
|
|
129
|
+
const roots = [];
|
|
130
|
+
const push = (value) => {
|
|
131
|
+
if (typeof value === 'string' && value.length > 0 && !roots.includes(value))
|
|
132
|
+
roots.push(value);
|
|
133
|
+
};
|
|
134
|
+
push(env.ProgramFiles);
|
|
135
|
+
push(env['ProgramFiles(x86)']);
|
|
136
|
+
const systemDrive = typeof env.SystemDrive === 'string' ? env.SystemDrive : '';
|
|
137
|
+
if (systemDrive.length > 0)
|
|
138
|
+
push(path.join(systemDrive, 'Program Files'));
|
|
139
|
+
if (process.platform === 'win32') {
|
|
140
|
+
for (const drive of fixedDriveLetters ?? workbuddyFixedDriveLetters()) {
|
|
141
|
+
if (!/^[A-Za-z]:$/.test(drive))
|
|
142
|
+
continue;
|
|
143
|
+
if (systemDrive.length > 0 && drive.toLowerCase() === systemDrive.toLowerCase())
|
|
144
|
+
continue;
|
|
145
|
+
push(path.win32.join(drive + path.win32.sep, 'Program Files'));
|
|
146
|
+
push(path.win32.join(drive + path.win32.sep, 'Program Files (x86)'));
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
return roots;
|
|
150
|
+
}
|
|
99
151
|
/**
|
|
100
152
|
* Resolve the WorkBuddy engine CLI path.
|
|
101
153
|
*
|
|
102
154
|
* Order: PD_WORKBUDDY_ENGINE / WB_ENGINE env override (probe convention) →
|
|
103
|
-
* the Desktop install location under Program Files (frozen by probe P01)
|
|
104
|
-
* The engine is NOT exposed on
|
|
105
|
-
* fact, never a guess.
|
|
155
|
+
* the Desktop install location under Program Files (frozen by probe P01),
|
|
156
|
+
* multi-drive per workbuddyEngineCandidateRoots. The engine is NOT exposed on
|
|
157
|
+
* PATH — absence is a detectable, reportable fact, never a guess.
|
|
106
158
|
*/
|
|
107
159
|
export function resolveWorkbuddyEnginePath() {
|
|
108
160
|
for (const envName of ['PD_WORKBUDDY_ENGINE', 'WB_ENGINE']) {
|
|
@@ -110,12 +162,7 @@ export function resolveWorkbuddyEnginePath() {
|
|
|
110
162
|
if (value && value.length > 0 && existsSync(value))
|
|
111
163
|
return value;
|
|
112
164
|
}
|
|
113
|
-
const
|
|
114
|
-
process.env.ProgramFiles,
|
|
115
|
-
process.env['ProgramFiles(x86)'],
|
|
116
|
-
process.env.SystemDrive ? path.join(process.env.SystemDrive, 'Program Files') : undefined,
|
|
117
|
-
].filter((v) => typeof v === 'string' && v.length > 0);
|
|
118
|
-
for (const root of roots) {
|
|
165
|
+
for (const root of workbuddyEngineCandidateRoots()) {
|
|
119
166
|
const candidate = path.join(root, 'WorkBuddy', ...WORKBUDDY_ENGINE_RELATIVE);
|
|
120
167
|
if (existsSync(candidate))
|
|
121
168
|
return candidate;
|