@chude/memory 4.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +294 -0
- package/dist/application/index.d.ts +6 -0
- package/dist/application/services/ambient-context-service.d.ts +90 -0
- package/dist/application/services/backfill-service.d.ts +71 -0
- package/dist/application/services/budget-allocator.d.ts +57 -0
- package/dist/application/services/embedding-service.d.ts +131 -0
- package/dist/application/services/export-service.d.ts +225 -0
- package/dist/application/services/extraction-pipeline.d.ts +50 -0
- package/dist/application/services/friction-service.d.ts +148 -0
- package/dist/application/services/fts-sanitizer.d.ts +25 -0
- package/dist/application/services/index.d.ts +34 -0
- package/dist/application/services/llm-extractor.d.ts +96 -0
- package/dist/application/services/memory-file-sync-service.d.ts +58 -0
- package/dist/application/services/pattern-extractor.d.ts +95 -0
- package/dist/application/services/recovery-service.d.ts +81 -0
- package/dist/application/services/rrf-fusion.d.ts +53 -0
- package/dist/application/services/smart-context-service.d.ts +126 -0
- package/dist/application/services/sync-service.d.ts +157 -0
- package/dist/application/services/temporal-decay.d.ts +62 -0
- package/dist/domain/entities/backfill-state.d.ts +56 -0
- package/dist/domain/entities/entity.d.ts +131 -0
- package/dist/domain/entities/extraction-state.d.ts +128 -0
- package/dist/domain/entities/fact.d.ts +59 -0
- package/dist/domain/entities/friction-entry.d.ts +84 -0
- package/dist/domain/entities/index.d.ts +15 -0
- package/dist/domain/entities/link.d.ts +74 -0
- package/dist/domain/entities/memory-file.d.ts +78 -0
- package/dist/domain/entities/message.d.ts +70 -0
- package/dist/domain/entities/session.d.ts +93 -0
- package/dist/domain/entities/tool-use.d.ts +85 -0
- package/dist/domain/errors/error-codes.d.ts +37 -0
- package/dist/domain/errors/index.d.ts +8 -0
- package/dist/domain/errors/memory-error.d.ts +52 -0
- package/dist/domain/errors/unknown-error.d.ts +9 -0
- package/dist/domain/index.d.ts +11 -0
- package/dist/domain/ports/embedding.d.ts +96 -0
- package/dist/domain/ports/extraction.d.ts +13 -0
- package/dist/domain/ports/index.d.ts +14 -0
- package/dist/domain/ports/redactor.d.ts +17 -0
- package/dist/domain/ports/repositories.d.ts +658 -0
- package/dist/domain/ports/services.d.ts +180 -0
- package/dist/domain/ports/signals.d.ts +82 -0
- package/dist/domain/ports/sources.d.ts +122 -0
- package/dist/domain/ports/types.d.ts +150 -0
- package/dist/domain/services/content-extractor.d.ts +61 -0
- package/dist/domain/services/index.d.ts +8 -0
- package/dist/domain/services/path-decoder.d.ts +56 -0
- package/dist/domain/services/query-parser.d.ts +47 -0
- package/dist/domain/value-objects/embedding-config.d.ts +56 -0
- package/dist/domain/value-objects/embedding-result.d.ts +46 -0
- package/dist/domain/value-objects/index.d.ts +10 -0
- package/dist/domain/value-objects/project-path.d.ts +92 -0
- package/dist/domain/value-objects/search-query.d.ts +30 -0
- package/dist/domain/value-objects/search-result.d.ts +92 -0
- package/dist/index.d.ts +15 -0
- package/dist/index.js +1548 -0
- package/dist/infrastructure/database/connection.d.ts +161 -0
- package/dist/infrastructure/database/event-log.d.ts +22 -0
- package/dist/infrastructure/database/health-checker.d.ts +248 -0
- package/dist/infrastructure/database/index.d.ts +11 -0
- package/dist/infrastructure/database/repositories/backfill-state-repository.d.ts +19 -0
- package/dist/infrastructure/database/repositories/embedding-repository.d.ts +121 -0
- package/dist/infrastructure/database/repositories/entity-repository.d.ts +73 -0
- package/dist/infrastructure/database/repositories/extraction-log-repository.d.ts +17 -0
- package/dist/infrastructure/database/repositories/extraction-state-repository.d.ts +52 -0
- package/dist/infrastructure/database/repositories/fact-repository.d.ts +25 -0
- package/dist/infrastructure/database/repositories/friction-repository.d.ts +41 -0
- package/dist/infrastructure/database/repositories/index.d.ts +17 -0
- package/dist/infrastructure/database/repositories/link-repository.d.ts +64 -0
- package/dist/infrastructure/database/repositories/memory-file-repository.d.ts +28 -0
- package/dist/infrastructure/database/repositories/message-repository.d.ts +87 -0
- package/dist/infrastructure/database/repositories/session-repository.d.ts +125 -0
- package/dist/infrastructure/database/repositories/tool-use-repository.d.ts +72 -0
- package/dist/infrastructure/database/schema.d.ts +203 -0
- package/dist/infrastructure/database/services/context-service.d.ts +93 -0
- package/dist/infrastructure/database/services/hybrid-search-service.d.ts +156 -0
- package/dist/infrastructure/database/services/index.d.ts +10 -0
- package/dist/infrastructure/database/services/search-service.d.ts +57 -0
- package/dist/infrastructure/database/services/stats-service.d.ts +36 -0
- package/dist/infrastructure/embedding/background-embedder.d.ts +125 -0
- package/dist/infrastructure/embedding/embedding-provider-factory.d.ts +44 -0
- package/dist/infrastructure/embedding/index.d.ts +5 -0
- package/dist/infrastructure/embedding/ollama-provider.d.ts +41 -0
- package/dist/infrastructure/embedding/openai-provider.d.ts +38 -0
- package/dist/infrastructure/embedding/transformers-js-provider.d.ts +34 -0
- package/dist/infrastructure/external/index.d.ts +7 -0
- package/dist/infrastructure/external/qmd-runner.d.ts +36 -0
- package/dist/infrastructure/hooks/auto-memory-writer.d.ts +52 -0
- package/dist/infrastructure/hooks/config-manager.d.ts +237 -0
- package/dist/infrastructure/hooks/git-syncer.d.ts +44 -0
- package/dist/infrastructure/hooks/hook-runner.d.ts +126 -0
- package/dist/infrastructure/hooks/index.d.ts +12 -0
- package/dist/infrastructure/hooks/log-writer.d.ts +106 -0
- package/dist/infrastructure/hooks/settings-manager.d.ts +163 -0
- package/dist/infrastructure/hooks/sync-hook-script.d.ts +83 -0
- package/dist/infrastructure/hooks/sync-logger-adapter.d.ts +17 -0
- package/dist/infrastructure/index.d.ts +11 -0
- package/dist/infrastructure/llm/anthropic-extractor.d.ts +20 -0
- package/dist/infrastructure/llm/claude-cli-extractor.d.ts +14 -0
- package/dist/infrastructure/llm/claude-summary-generator.d.ts +14 -0
- package/dist/infrastructure/llm/extraction-helper.d.ts +16 -0
- package/dist/infrastructure/llm/ollama-extractor.d.ts +20 -0
- package/dist/infrastructure/llm/openai-extractor.d.ts +23 -0
- package/dist/infrastructure/migration.d.ts +103 -0
- package/dist/infrastructure/parsers/event-classifier.d.ts +111 -0
- package/dist/infrastructure/parsers/index.d.ts +8 -0
- package/dist/infrastructure/parsers/jsonl-parser.d.ts +25 -0
- package/dist/infrastructure/parsers/timestamp.d.ts +18 -0
- package/dist/infrastructure/paths.d.ts +129 -0
- package/dist/infrastructure/providers/provider-defaults.d.ts +11 -0
- package/dist/infrastructure/providers/provider-registry.d.ts +28 -0
- package/dist/infrastructure/security/pattern-redactor.d.ts +6 -0
- package/dist/infrastructure/signals/adapters.d.ts +27 -0
- package/dist/infrastructure/signals/checkpoint-manager.d.ts +83 -0
- package/dist/infrastructure/signals/index.d.ts +8 -0
- package/dist/infrastructure/signals/signal-handler.d.ts +113 -0
- package/dist/infrastructure/sources/index.d.ts +8 -0
- package/dist/infrastructure/sources/memory-file-scanner.d.ts +23 -0
- package/dist/infrastructure/sources/project-name-resolver.d.ts +67 -0
- package/dist/infrastructure/sources/session-source.d.ts +70 -0
- package/dist/presentation/cli/command-result.d.ts +10 -0
- package/dist/presentation/cli/commands/_helpers/capture-json.d.ts +36 -0
- package/dist/presentation/cli/commands/_helpers/deprecation-warning.d.ts +41 -0
- package/dist/presentation/cli/commands/backfill.d.ts +56 -0
- package/dist/presentation/cli/commands/browse.d.ts +55 -0
- package/dist/presentation/cli/commands/completion.d.ts +61 -0
- package/dist/presentation/cli/commands/context.d.ts +53 -0
- package/dist/presentation/cli/commands/doctor.d.ts +55 -0
- package/dist/presentation/cli/commands/export.d.ts +36 -0
- package/dist/presentation/cli/commands/extract.d.ts +40 -0
- package/dist/presentation/cli/commands/facts.d.ts +17 -0
- package/dist/presentation/cli/commands/friction/dashboard.d.ts +18 -0
- package/dist/presentation/cli/commands/friction/index.d.ts +12 -0
- package/dist/presentation/cli/commands/friction/list.d.ts +12 -0
- package/dist/presentation/cli/commands/friction/log.d.ts +12 -0
- package/dist/presentation/cli/commands/friction/purge.d.ts +12 -0
- package/dist/presentation/cli/commands/friction/resolve.d.ts +12 -0
- package/dist/presentation/cli/commands/friction/types.d.ts +86 -0
- package/dist/presentation/cli/commands/friction/wontfix.d.ts +12 -0
- package/dist/presentation/cli/commands/import.d.ts +38 -0
- package/dist/presentation/cli/commands/index.d.ts +51 -0
- package/dist/presentation/cli/commands/install.d.ts +67 -0
- package/dist/presentation/cli/commands/list.d.ts +61 -0
- package/dist/presentation/cli/commands/migrate.d.ts +36 -0
- package/dist/presentation/cli/commands/purge.d.ts +100 -0
- package/dist/presentation/cli/commands/query.d.ts +51 -0
- package/dist/presentation/cli/commands/related.d.ts +47 -0
- package/dist/presentation/cli/commands/remote.d.ts +36 -0
- package/dist/presentation/cli/commands/search.d.ts +100 -0
- package/dist/presentation/cli/commands/show.d.ts +51 -0
- package/dist/presentation/cli/commands/stats.d.ts +38 -0
- package/dist/presentation/cli/commands/status.d.ts +152 -0
- package/dist/presentation/cli/commands/sync/ambient.d.ts +22 -0
- package/dist/presentation/cli/commands/sync/background.d.ts +23 -0
- package/dist/presentation/cli/commands/sync/embedding-pass.d.ts +32 -0
- package/dist/presentation/cli/commands/sync/helpers.d.ts +25 -0
- package/dist/presentation/cli/commands/sync/index.d.ts +17 -0
- package/dist/presentation/cli/commands/sync/memory-files.d.ts +26 -0
- package/dist/presentation/cli/commands/sync/types.d.ts +163 -0
- package/dist/presentation/cli/commands/uninstall.d.ts +44 -0
- package/dist/presentation/cli/db-startup.d.ts +61 -0
- package/dist/presentation/cli/formatters/ai-formatter.d.ts +38 -0
- package/dist/presentation/cli/formatters/color.d.ts +82 -0
- package/dist/presentation/cli/formatters/context-formatter.d.ts +55 -0
- package/dist/presentation/cli/formatters/dto-helpers.d.ts +176 -0
- package/dist/presentation/cli/formatters/envelope.d.ts +136 -0
- package/dist/presentation/cli/formatters/error-formatter.d.ts +41 -0
- package/dist/presentation/cli/formatters/friction-dashboard.d.ts +46 -0
- package/dist/presentation/cli/formatters/index.d.ts +17 -0
- package/dist/presentation/cli/formatters/list-formatter.d.ts +48 -0
- package/dist/presentation/cli/formatters/output-formatter.d.ts +98 -0
- package/dist/presentation/cli/formatters/related-formatter.d.ts +57 -0
- package/dist/presentation/cli/formatters/show-formatter.d.ts +63 -0
- package/dist/presentation/cli/formatters/stats-formatter.d.ts +54 -0
- package/dist/presentation/cli/formatters/text-width.d.ts +37 -0
- package/dist/presentation/cli/formatters/timestamp-formatter.d.ts +38 -0
- package/dist/presentation/cli/index.d.ts +10 -0
- package/dist/presentation/cli/index.js +1664 -0
- package/dist/presentation/cli/parsers/date-parser.d.ts +28 -0
- package/dist/presentation/cli/parsers/index.d.ts +6 -0
- package/dist/presentation/cli/pickers/index.d.ts +6 -0
- package/dist/presentation/cli/pickers/session-picker.d.ts +59 -0
- package/dist/presentation/cli/progress-reporter.d.ts +199 -0
- package/package.json +94 -0
package/dist/index.js
ADDED
|
@@ -0,0 +1,1548 @@
|
|
|
1
|
+
// @bun
|
|
2
|
+
var T2=Object.create;var{getPrototypeOf:R2,defineProperty:N9,getOwnPropertyNames:F2}=Object;var M2=Object.prototype.hasOwnProperty;var JZ=($,Z,K)=>{K=$!=null?T2(R2($)):{};let X=Z||!$||!$.__esModule?N9(K,"default",{value:$,enumerable:!0}):K;for(let Y of F2($))if(!M2.call(X,Y))N9(X,Y,{get:()=>$[Y],enumerable:!0});return X};var w=($,Z)=>{for(var K in Z)N9($,K,{get:Z[K],enumerable:!0,configurable:!0,set:(X)=>Z[K]=()=>X})};var U=($,Z)=>()=>($&&(Z=$($=0)),Z);var e0=import.meta.require;class e{_id;_type;_name;_confidence;_metadata;_createdAt;constructor($){this._id=$.id,this._type=$.type,this._name=$.name,this._confidence=$.confidence,this._metadata=$.metadata?structuredClone($.metadata):void 0,this._createdAt=$.createdAt?new Date($.createdAt.getTime()):void 0}static create($){if(!$.name||$.name.trim()==="")throw Error("Entity name cannot be empty");if($.confidence<0||$.confidence>1)throw Error("Confidence must be between 0 and 1");if(!j2.includes($.type))throw Error("Invalid entity type");if($.type==="decision"){let Z=$.metadata;if(!Z||!Z.subject||!Z.decision)throw Error("Decision metadata requires subject and decision fields")}return new e($)}get id(){return this._id}get type(){return this._type}get name(){return this._name}get confidence(){return this._confidence}get metadata(){return this._metadata?structuredClone(this._metadata):void 0}get createdAt(){return this._createdAt?new Date(this._createdAt.getTime()):void 0}get isConcept(){return this._type==="concept"}get isFile(){return this._type==="file"}get isDecision(){return this._type==="decision"}get isTerm(){return this._type==="term"}equals($){if(this._id!==void 0&&$._id!==void 0)return this._id===$._id;return this._type===$._type&&this._name===$._name}withId($){return new e({id:$,type:this._type,name:this._name,confidence:this._confidence,metadata:this._metadata,createdAt:this._createdAt})}}var j2;var k$=U(()=>{j2=["concept","file","decision","term"]});class $0{_id;_sessionPath;_startedAt;_status;_completedAt;_messagesExtracted;_errorMessage;_fileMtime;_fileSize;constructor($){this._id=$.id,this._sessionPath=$.sessionPath,this._startedAt=new Date($.startedAt.getTime()),this._status=$.status??"pending",this._completedAt=$.completedAt?new Date($.completedAt.getTime()):void 0,this._messagesExtracted=$.messagesExtracted??0,this._errorMessage=$.errorMessage,this._fileMtime=$.fileMtime?new Date($.fileMtime.getTime()):void 0,this._fileSize=$.fileSize}static create($){if(!$.id||$.id.trim()==="")throw Error("Extraction state ID cannot be empty");if(!$.sessionPath||$.sessionPath.trim()==="")throw Error("Session path cannot be empty");if($.status&&!x2.includes($.status))throw Error("Invalid extraction status");if($.messagesExtracted!==void 0&&$.messagesExtracted<0)throw Error("Messages extracted cannot be negative");if($.fileSize!==void 0&&$.fileSize<0)throw Error("File size cannot be negative");return new $0($)}get id(){return this._id}get sessionPath(){return this._sessionPath}get startedAt(){return new Date(this._startedAt.getTime())}get status(){return this._status}get completedAt(){return this._completedAt?new Date(this._completedAt.getTime()):void 0}get messagesExtracted(){return this._messagesExtracted}get errorMessage(){return this._errorMessage}get fileMtime(){return this._fileMtime?new Date(this._fileMtime.getTime()):void 0}get fileSize(){return this._fileSize}get isPending(){return this._status==="pending"}get isInProgress(){return this._status==="in_progress"}get isComplete(){return this._status==="complete"}get isError(){return this._status==="error"}get durationMs(){if(!this._completedAt)return;return this._completedAt.getTime()-this._startedAt.getTime()}equals($){return this._id===$._id}startProcessing(){return new $0({id:this._id,sessionPath:this._sessionPath,startedAt:this._startedAt,status:"in_progress",messagesExtracted:this._messagesExtracted,fileMtime:this._fileMtime,fileSize:this._fileSize})}complete($){return new $0({id:this._id,sessionPath:this._sessionPath,startedAt:this._startedAt,status:"complete",completedAt:$,messagesExtracted:this._messagesExtracted,fileMtime:this._fileMtime,fileSize:this._fileSize})}fail($){return new $0({id:this._id,sessionPath:this._sessionPath,startedAt:this._startedAt,status:"error",errorMessage:$,messagesExtracted:this._messagesExtracted,fileMtime:this._fileMtime,fileSize:this._fileSize})}incrementMessages($=1){return new $0({id:this._id,sessionPath:this._sessionPath,startedAt:this._startedAt,status:this._status,completedAt:this._completedAt,messagesExtracted:this._messagesExtracted+$,errorMessage:this._errorMessage,fileMtime:this._fileMtime,fileSize:this._fileSize})}withFileMetadata($,Z){if(Z<0)throw Error("File size cannot be negative");return new $0({id:this._id,sessionPath:this._sessionPath,startedAt:this._startedAt,status:this._status,completedAt:this._completedAt,messagesExtracted:this._messagesExtracted,errorMessage:this._errorMessage,fileMtime:$,fileSize:Z})}}var x2;var HZ=U(()=>{x2=["pending","in_progress","complete","error"]});class $${_sourceType;_sourceId;_targetType;_targetId;_relationship;_weight;constructor($){this._sourceType=$.sourceType,this._sourceId=$.sourceId,this._targetType=$.targetType,this._targetId=$.targetId,this._relationship=$.relationship,this._weight=$.weight??1}static create($){if(!$.sourceId||$.sourceId.trim()==="")throw Error("Source ID cannot be empty");if(!$.targetId||$.targetId.trim()==="")throw Error("Target ID cannot be empty");if(!q5.includes($.sourceType))throw Error("Invalid source type");if(!q5.includes($.targetType))throw Error("Invalid target type");if(!P2.includes($.relationship))throw Error("Invalid relationship type");if($.weight!==void 0&&($.weight<0||$.weight>1))throw Error("Weight must be between 0 and 1");return new $$($)}get id(){return`${this._sourceType}:${this._sourceId}->${this._targetType}:${this._targetId}:${this._relationship}`}get sourceType(){return this._sourceType}get sourceId(){return this._sourceId}get targetType(){return this._targetType}get targetId(){return this._targetId}get relationship(){return this._relationship}get weight(){return this._weight}equals($){return this.id===$.id}withWeight($){if($<0||$>1)throw Error("Weight must be between 0 and 1");return new $$({sourceType:this._sourceType,sourceId:this._sourceId,targetType:this._targetType,targetId:this._targetId,relationship:this._relationship,weight:$})}}var q5,P2;var q9=U(()=>{q5=["session","message","topic"],P2=["mentions","related_to","continues"]});class W0{_id;_role;_content;_timestamp;_toolUseIds;constructor($){this._id=$.id,this._role=$.role,this._content=$.content,this._timestamp=new Date($.timestamp.getTime()),this._toolUseIds=Object.freeze([...$.toolUseIds??[]])}static create($){if(!$.id||$.id.trim()==="")throw Error("Message ID cannot be empty");if(!E2.includes($.role))throw Error("Invalid message role");return new W0($)}get id(){return this._id}get role(){return this._role}get content(){return this._content}get timestamp(){return new Date(this._timestamp.getTime())}get toolUses(){return[...this._toolUseIds]}get hasContent(){return this._content.length>0}get hasToolUses(){return this._toolUseIds.length>0}equals($){return this._id===$._id}addToolUse($){return new W0({id:this._id,role:this._role,content:this._content,timestamp:this._timestamp,toolUseIds:[...this._toolUseIds,$]})}}var E2;var S$=U(()=>{E2=["user","assistant"]});class B0{_id;_projectPath;_startTime;_endTime;_messages;_summary;_messageCount;constructor($){this._id=$.id,this._projectPath=$.projectPath,this._startTime=new Date($.startTime.getTime()),this._endTime=$.endTime?new Date($.endTime.getTime()):void 0,this._messages=Object.freeze([...$.messages??[]]),this._summary=$.summary,this._messageCount=$.messageCount}static create($){if(!$.id||$.id.trim()==="")throw Error("Session ID cannot be empty");if($.endTime&&$.endTime<$.startTime)throw Error("End time cannot be before start time");return new B0($)}get id(){return this._id}get projectPath(){return this._projectPath}get startTime(){return new Date(this._startTime.getTime())}get endTime(){return this._endTime?new Date(this._endTime.getTime()):void 0}get messages(){return[...this._messages]}get summary(){return this._summary}get messageCount(){return this._messageCount??this._messages.length}get durationMs(){if(!this._endTime)return;return this._endTime.getTime()-this._startTime.getTime()}equals($){return this._id===$._id}addMessage($){return new B0({id:this._id,projectPath:this._projectPath,startTime:this._startTime,endTime:this._endTime,messages:[...this._messages,$],summary:this._summary})}complete($){if($<this._startTime)throw Error("End time cannot be before start time");return new B0({id:this._id,projectPath:this._projectPath,startTime:this._startTime,endTime:$,messages:[...this._messages],summary:this._summary,messageCount:this._messageCount})}withSummary($){return new B0({id:this._id,projectPath:this._projectPath,startTime:this._startTime,endTime:this._endTime,messages:[...this._messages],summary:$,messageCount:this._messageCount})}}class z0{_id;_name;_input;_timestamp;_status;_result;constructor($){this._id=$.id,this._name=$.name,this._input=structuredClone($.input),this._timestamp=new Date($.timestamp.getTime()),this._status=$.status??"pending",this._result=$.result}static create($){if(!$.id||$.id.trim()==="")throw Error("Tool use ID cannot be empty");if(!$.name||$.name.trim()==="")throw Error("Tool name cannot be empty");if($.status&&!D2.includes($.status))throw Error("Invalid tool use status");return new z0($)}get id(){return this._id}get name(){return this._name}get input(){return structuredClone(this._input)}get timestamp(){return new Date(this._timestamp.getTime())}get status(){return this._status}get result(){return this._result}get isPending(){return this._status==="pending"}get isSuccess(){return this._status==="success"}get isError(){return this._status==="error"}equals($){return this._id===$._id}completeSuccess($){return new z0({id:this._id,name:this._name,input:this._input,timestamp:this._timestamp,status:"success",result:$})}completeError($){return new z0({id:this._id,name:this._name,input:this._input,timestamp:this._timestamp,status:"error",result:$})}}var D2;var VZ=U(()=>{D2=["pending","success","error"]});class m0{_id;_filePath;_fileType;_projectEncoded;_content;_contentHash;_lastIndexedAt;_createdAt;constructor($){this._id=$.id,this._filePath=$.filePath,this._fileType=$.fileType,this._projectEncoded=$.projectEncoded,this._content=$.content,this._contentHash=$.contentHash,this._lastIndexedAt=new Date($.lastIndexedAt.getTime()),this._createdAt=$.createdAt?new Date($.createdAt.getTime()):new Date}static create($){if(!$.filePath||$.filePath.trim()==="")throw Error("File path cannot be empty");if(!$.content||$.content.trim()==="")throw Error("Content cannot be empty");if(!k2.test($.contentHash))throw Error("Content hash must be 64 hexadecimal characters");if(!O5.includes($.fileType))throw Error(`Invalid file type: "${$.fileType}". Must be one of: ${O5.join(", ")}`);return new m0($)}get id(){return this._id}get filePath(){return this._filePath}get fileType(){return this._fileType}get projectEncoded(){return this._projectEncoded}get content(){return this._content}get contentHash(){return this._contentHash}get lastIndexedAt(){return new Date(this._lastIndexedAt.getTime())}get createdAt(){return new Date(this._createdAt.getTime())}}var O5,k2;var WZ=U(()=>{O5=["daily_log","decisions","learnings","user_prefs"],k2=/^[a-f0-9]{64}$/});class x0{_id;_description;_severity;_category;_status;_tool;_tags;_lastReviewedAt;_context;_sourceProject;_loggedAt;_resolvedAt;_resolution;constructor($){this._id=$.id,this._description=$.description.trim(),this._severity=$.severity,this._category=$.category,this._status=$.status,this._tool=$.tool,this._tags=$.tags?[...$.tags]:void 0,this._lastReviewedAt=$.lastReviewedAt?new Date($.lastReviewedAt.getTime()):void 0,this._context=$.context,this._sourceProject=$.sourceProject,this._loggedAt=new Date($.loggedAt.getTime()),this._resolvedAt=$.resolvedAt?new Date($.resolvedAt.getTime()):void 0,this._resolution=$.resolution}static create($){if(!$.description||$.description.trim()==="")throw Error("Description cannot be empty");if(!U5.includes($.severity))throw Error(`Invalid severity: "${$.severity}". Must be one of: ${U5.join(", ")}`);if(!$.category||$.category.trim()==="")throw Error("Category cannot be empty");if(!L5.includes($.status))throw Error(`Invalid status: "${$.status}". Must be one of: ${L5.join(", ")}`);if(!$.tool||$.tool.trim()==="")throw Error("Tool cannot be empty");if($.status==="open"&&$.resolvedAt)throw Error("Open entries cannot have a resolvedAt date");return new x0($)}get id(){return this._id}get description(){return this._description}get severity(){return this._severity}get category(){return this._category}get status(){return this._status}get tool(){return this._tool}get tags(){return this._tags?[...this._tags]:void 0}get lastReviewedAt(){return this._lastReviewedAt?new Date(this._lastReviewedAt.getTime()):void 0}get context(){return this._context}get sourceProject(){return this._sourceProject}get loggedAt(){return new Date(this._loggedAt.getTime())}get resolvedAt(){return this._resolvedAt?new Date(this._resolvedAt.getTime()):void 0}get resolution(){return this._resolution}}var U5,L5;var BZ=U(()=>{U5=["low","medium","high","critical"],L5=["open","resolved","wont-fix"]});class c0{_sessionId;_backfilledAt;_dailyLogPath;_success;_errorMessage;constructor($){this._sessionId=$.sessionId,this._backfilledAt=new Date($.backfilledAt.getTime()),this._dailyLogPath=$.dailyLogPath,this._success=$.success??!0,this._errorMessage=$.errorMessage}static create($){if(!$.sessionId||$.sessionId.trim()==="")throw Error("Session ID cannot be empty");if(!$.dailyLogPath||$.dailyLogPath.trim()==="")throw Error("Daily log path cannot be empty");return new c0($)}get sessionId(){return this._sessionId}get backfilledAt(){return new Date(this._backfilledAt.getTime())}get dailyLogPath(){return this._dailyLogPath}get success(){return this._success}get errorMessage(){return this._errorMessage}get isSuccess(){return this._success}}import{randomUUID as S2}from"crypto";class A0{_id;_uuid;_type;_project;_content;_metadata;_observedAt;_supersededAt;_supersededBy;constructor($){this._id=$.id,this._uuid=$.uuid??S2(),this._type=$.type,this._project=$.project,this._content=$.content,this._metadata=$.metadata?JSON.parse(JSON.stringify($.metadata)):void 0,this._observedAt=new Date($.observedAt.getTime()),this._supersededAt=$.supersededAt?new Date($.supersededAt.getTime()):null,this._supersededBy=$.supersededBy??null}static create($){if(!$.project||$.project.trim()==="")throw Error("Fact project cannot be empty");if(!$.content||$.content.trim()==="")throw Error("Fact content cannot be empty");if(!["decision","learning","preference","friction","observation","supersedence"].includes($.type))throw Error("Invalid fact type");return new A0($)}get id(){return this._id}get uuid(){return this._uuid}get type(){return this._type}get project(){return this._project}get content(){return this._content}get metadata(){return this._metadata?JSON.parse(JSON.stringify(this._metadata)):void 0}get observedAt(){return new Date(this._observedAt.getTime())}get supersededAt(){return this._supersededAt?new Date(this._supersededAt.getTime()):null}get supersededBy(){return this._supersededBy}withId($){return new A0({id:$,uuid:this._uuid,type:this._type,project:this._project,content:this._content,metadata:this._metadata,observedAt:this._observedAt,supersededAt:this._supersededAt,supersededBy:this._supersededBy})}withSuperseded($,Z){return new A0({id:this._id,uuid:this._uuid,type:this._type,project:this._project,content:this._content,metadata:this._metadata,observedAt:this._observedAt,supersededAt:$,supersededBy:Z})}}var v$=()=>{};var I5=U(()=>{k$();HZ();q9();S$();VZ();WZ();BZ();v$()});class zZ{_enabled;_provider;_model;_dimensions;constructor($){this._enabled=$.enabled,this._provider=$.provider,this._model=$.model,this._dimensions=$.dimensions}static create($){let Z=$.provider.trim();if(Z==="")throw Error("Provider cannot be empty");let K=$.model.trim();if(K==="")throw Error("Model cannot be empty");if($.dimensions<=0||!Number.isInteger($.dimensions))throw Error("Dimensions must be a positive integer");return new zZ({enabled:$.enabled,provider:Z,model:K,dimensions:$.dimensions})}static defaults(){return new zZ({enabled:!0,provider:"local",model:"Xenova/all-MiniLM-L6-v2",dimensions:384})}get enabled(){return this._enabled}get provider(){return this._provider}get model(){return this._model}get dimensions(){return this._dimensions}equals($){return this._enabled===$._enabled&&this._provider===$._provider&&this._model===$._model&&this._dimensions===$._dimensions}}class X0{_embedding;_model;_dimensions;constructor($){this._embedding=new Float32Array($.embedding),this._model=$.model,this._dimensions=$.dimensions}static create($){if($.embedding.length===0)throw Error("Embedding cannot be empty");let Z=$.model.trim();if(Z==="")throw Error("Model cannot be empty");if($.dimensions!==$.embedding.length)throw Error(`Dimensions (${$.dimensions}) must match embedding length (${$.embedding.length})`);return new X0({embedding:$.embedding,model:Z,dimensions:$.dimensions})}get embedding(){return new Float32Array(this._embedding)}get model(){return this._model}get dimensions(){return this._dimensions}equals($){if(this._model!==$._model)return!1;if(this._dimensions!==$._dimensions)return!1;for(let Z=0;Z<this._dimensions;Z++)if(this._embedding[Z]!==$._embedding[Z])return!1;return!0}}var T5={};w(T5,{ProjectPath:()=>i});class i{_decoded;_encoded;_projectName;constructor($,Z,K){this._decoded=$,this._encoded=Z,this._projectName=K??this.extractProjectName($)}static fromDecoded($){if(!$||$.trim()==="")throw Error("Path cannot be empty");let Z=i.encode($);return new i($,Z)}static fromEncoded($){if(!$||$.trim()==="")throw Error("Path cannot be empty");let Z=i.decode($);return new i(Z,$)}get decoded(){return this._decoded}get encoded(){return this._encoded}get projectName(){return this._projectName}withProjectName($){return new i(this._decoded,this._encoded,$)}equals($){return this._decoded===$._decoded}static encode($){return $.replace(/:\\/g,"--").replace(/\\/g,"-").replace(/\//g,"-").replace(/ /g,"-")}static decode($){if(/^([A-Za-z])--/.test($))return $.replace(/^([A-Za-z])--/,"$1:\\").replace(/-/g,"\\");else return $.replace(/-/g,"/")}extractProjectName($){let Z=$.replace(/[\\/]+$/,"");if(Z===""&&$.startsWith("/"))return"";if(/^[A-Za-z]:$/.test(Z))return Z;let K=Z.split(/[\\/]/);return K[K.length-1]||""}}class C${_value;constructor($){this._value=$}static from($){let Z=$.trim();if(Z==="")throw Error("Query cannot be empty");return new C$(Z)}get value(){return this._value}equals($){return this._value===$._value}}class Y0{_sessionId;_messageId;_snippet;_score;_timestamp;_role;_source;_rawScores;constructor($){this._sessionId=$.sessionId,this._messageId=$.messageId,this._snippet=$.snippet,this._score=$.score,this._timestamp=new Date($.timestamp.getTime()),this._role=$.role,this._source=$.source,this._rawScores=$.rawScores?{...$.rawScores}:void 0}static create($){if(!$.sessionId||$.sessionId.trim()==="")throw Error("Session ID cannot be empty");if(!$.messageId||$.messageId.trim()==="")throw Error("Message ID cannot be empty");if(!$.snippet||$.snippet.trim()==="")throw Error("Snippet cannot be empty");if($.score<0||$.score>1)throw Error("Score must be between 0 and 1");if(!$.role||$.role.trim()==="")throw Error("Role cannot be empty");return new Y0($)}get sessionId(){return this._sessionId}get messageId(){return this._messageId}get snippet(){return this._snippet}get score(){return this._score}get timestamp(){return new Date(this._timestamp.getTime())}get role(){return this._role}get source(){return this._source}get rawScores(){return this._rawScores?{...this._rawScores}:void 0}equals($){return this._sessionId===$._sessionId&&this._messageId===$._messageId}compareByScore($){return $._score-this._score}}var O9=()=>{};class N0{static extractMessageContent($){let Z=N0.parseJson($);if(!Z)return null;if(!N0.isMessageType(Z.type))return null;let K=Z.type==="human"?"user":"assistant",X=N0.extractTextContent(Z.message?.content);if(!X)return null;return{role:K,content:X}}static extractToolUses($){let Z=N0.parseJson($);if(!Z)return[];let K=Z.message?.content;if(!Array.isArray(K))return[];return K.filter((X)=>X.type==="tool_use").map((X)=>({id:X.id??"",name:X.name??"",input:X.input??{}}))}static extractToolResults($){let Z=N0.parseJson($);if(!Z)return[];let K=Z.message?.content;if(!Array.isArray(K))return[];return K.filter((X)=>X.type==="tool_result").map((X)=>({toolUseId:X.tool_use_id??"",content:X.content??"",isError:X.is_error??!1}))}static isMessageLine($){let Z=N0.parseJson($);if(!Z)return!1;return N0.isMessageType(Z.type)}static extractTimestamp($){let Z=N0.parseJson($);if(!Z||!Z.timestamp)return null;let K=new Date(Z.timestamp);if(isNaN(K.getTime()))return null;return K}static parseJson($){try{return JSON.parse($)}catch{return null}}static isMessageType($){return $==="human"||$==="assistant"}static extractTextContent($){if(!$)return null;if(typeof $==="string")return $;if(Array.isArray($)){let K=$.filter((X)=>X.type==="text"&&X.text).map((X)=>X.text).join(`
|
|
3
|
+
`);return K.length>0?K:null}return null}}class P0{static decodeProjectDirectory($){return i.fromEncoded($)}static isEncodedPath($){if(!$||$.length===0)return!1;if(v2.test($))return!0;if(C2.test($))return!0;return!1}static extractProjectName($){return i.fromEncoded($).projectName}static filterEncodedPaths($){return $.filter((Z)=>P0.isEncodedPath(Z))}static translatePath($,Z=process.platform){if(!$||$.trim()==="")return $;if(Z==="win32"){let K=$.match(/^\/mnt\/([a-zA-Z])([\/]?)(.*)$/);if(K){let X=K[1].toUpperCase(),Y=K[3].replace(/\//g,"\\");return`${X}:\\${Y}`}return $}else{let K=$.match(/^([a-zA-Z]):([\\/]?)(.*)$/);if(K){let X=K[1].toLowerCase(),Y=K[3].replace(/\\/g,"/");return`/mnt/${X}/${Y}`}return $}}static resolveExistingPath($,Z,K=process.platform){if(!$)return $;let X=Z??(()=>!1);if(X($))return $;let Y=P0.translatePath($,K);if(X(Y))return Y;return $}}var v2,C2;var AZ=U(()=>{O9();v2=/^[A-Za-z]--/,C2=/^-[a-z]/i});class U9{static parse($){let Z=$,K={},X=[],Y=[],G=$.replace(w2,(_,J)=>{return Y.push(J.toLowerCase()),""}).trim().split(/\s+/).filter(Boolean);for(let _ of G){let J=_.match(y2);if(J&&J[1]&&J[2]){let H=J[1],V=J[2],B=H.toLowerCase();K[B]=V.toLowerCase()}else{let H=_.toLowerCase().replace(/"/g,"");if(H.length>=2&&!X.includes(H))X.push(H)}}for(let _ of Y)if(!X.includes(_))X.push(_);return{terms:X,filters:K,originalQuery:Z}}static toFts5Query($){if($.terms.length===0)return"";return $.terms.map((K)=>{if(K.includes(" "))return`"${K}"`;return K}).join(" AND ")}static isEmpty($){return $.terms.length===0&&!U9.hasFilters($)}static hasFilters($){return Object.keys($.filters).length>0}}var y2,w2;var R5=U(()=>{y2=/^(project|role|tool):(.+)$/i,w2=/"([^"]+)"/g});var F5=U(()=>{AZ();R5()});var T;var M5=U(()=>{T={DB_CONNECTION_FAILED:"DB_CONNECTION_FAILED",DB_CORRUPTED:"DB_CORRUPTED",DB_LOCKED:"DB_LOCKED",INVALID_SESSION_ID:"INVALID_SESSION_ID",SESSION_NOT_FOUND:"SESSION_NOT_FOUND",SOURCE_INACCESSIBLE:"SOURCE_INACCESSIBLE",DISK_FULL:"DISK_FULL",INVALID_JSON:"INVALID_JSON",UNKNOWN_FORMAT:"UNKNOWN_FORMAT",SYNC_INTERRUPTED:"SYNC_INTERRUPTED",SYNC_FAILED:"SYNC_FAILED",INVALID_ARGUMENT:"INVALID_ARGUMENT",MISSING_ARGUMENT:"MISSING_ARGUMENT",VECTOR_UNAVAILABLE:"VECTOR_UNAVAILABLE",PROVIDER_TIMEOUT:"PROVIDER_TIMEOUT",PROVIDER_CONFIG_INVALID:"PROVIDER_CONFIG_INVALID",EMBEDDING_DIMENSION_MISMATCH:"EMBEDDING_DIMENSION_MISMATCH",MODEL_CORRUPTED:"MODEL_CORRUPTED",NOT_FOUND:"NOT_FOUND",INVALID_STATE:"INVALID_STATE",UNKNOWN:"UNKNOWN"}});var R;var j5=U(()=>{R=class R extends Error{code;context;constructor($,Z,K){super(Z);if(this.name="MemoryError",this.code=$,this.context=K,Error.captureStackTrace)Error.captureStackTrace(this,R)}toJSON(){let $={error:{code:this.code,message:this.message}};if(this.context&&Object.keys(this.context).length>0)$.error.context=this.context;return $}}});function A($){return $ instanceof Error?$.message:String($)}function y$($){return $ instanceof Error?$:Error(A($))}var Q0=U(()=>{M5();j5()});var w$=U(()=>{I5();O9();F5();Q0()});class q0{static async extract($){let{messages:Z}=$;if(Z.length===0)return{topics:[],terms:[],decisions:[],summary:""};return q0.createExtractionPrompt(Z),{topics:[],terms:[],decisions:[],summary:""}}static createExtractionPrompt($){return`Analyze this session and extract:
|
|
4
|
+
|
|
5
|
+
1. TOPICS: Key technical concepts discussed (1-5)
|
|
6
|
+
- Include only significant technical concepts, patterns, or technologies
|
|
7
|
+
- Each topic needs a name and confidence score (0-1)
|
|
8
|
+
|
|
9
|
+
2. TERMS: Domain-specific terminology defined or explained (0-3)
|
|
10
|
+
- Include only terms that were explicitly defined or explained
|
|
11
|
+
- Each term needs a name, definition, and confidence score (0-1)
|
|
12
|
+
|
|
13
|
+
3. DECISIONS: Explicit choices made with rationale (0-3)
|
|
14
|
+
- Include only decisions where a choice was made between alternatives
|
|
15
|
+
- Each decision needs: subject, decision, rejected alternatives, rationale, confidence
|
|
16
|
+
|
|
17
|
+
4. SUMMARY: 1-2 sentence summary of what was accomplished
|
|
18
|
+
|
|
19
|
+
Output as JSON:
|
|
20
|
+
{
|
|
21
|
+
"topics": [{ "name": "...", "confidence": 0.9 }],
|
|
22
|
+
"terms": [{ "name": "...", "definition": "...", "confidence": 0.8 }],
|
|
23
|
+
"decisions": [{
|
|
24
|
+
"subject": "...",
|
|
25
|
+
"decision": "...",
|
|
26
|
+
"rejected": ["..."],
|
|
27
|
+
"rationale": "...",
|
|
28
|
+
"confidence": 0.9
|
|
29
|
+
}],
|
|
30
|
+
"summary": "..."
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
--- SESSION CONTENT ---
|
|
34
|
+
|
|
35
|
+
${$.map((K)=>{return`${K.role==="user"?"[USER]":"[ASSISTANT]"}
|
|
36
|
+
${K.content}`}).join(`
|
|
37
|
+
|
|
38
|
+
`)}
|
|
39
|
+
|
|
40
|
+
--- END SESSION CONTENT ---
|
|
41
|
+
|
|
42
|
+
Extract the entities and summary from the session above. Output only valid JSON.`}static parseExtractionResponse($,Z){let K={topics:[],terms:[],decisions:[],summary:""};if(!$||$.trim()==="")return K;let X=$.trim(),Y=X.match(/```(?:json)?\s*([\s\S]*?)\s*```/);if(Y&&Y[1])X=Y[1].trim();let Q;try{Q=JSON.parse(X)}catch{return K}let G=q0.parseTopics(Q.topics),_=q0.parseTerms(Q.terms),J=q0.parseDecisions(Q.decisions),H=typeof Q.summary==="string"?Q.summary:"";return{topics:G,terms:_,decisions:J,summary:H}}static parseTopics($){if(!$||!Array.isArray($))return[];return $.filter((Z)=>Z!==null&&typeof Z==="object").filter((Z)=>Z.name&&typeof Z.name==="string"&&Z.name.trim()!=="").map((Z)=>{let K=q0.normalizeConfidence(Z.confidence);return e.create({type:"concept",name:Z.name.trim(),confidence:K})})}static parseTerms($){if(!$||!Array.isArray($))return[];return $.filter((Z)=>Z!==null&&typeof Z==="object").filter((Z)=>Z.name&&typeof Z.name==="string"&&Z.name.trim()!=="").map((Z)=>{let K=q0.normalizeConfidence(Z.confidence),X={};if(Z.definition)X.definition=Z.definition;return e.create({type:"term",name:Z.name.trim(),confidence:K,metadata:X})})}static parseDecisions($){if(!$||!Array.isArray($))return[];return $.filter((Z)=>Z!==null&&typeof Z==="object").filter((Z)=>{return Z.subject&&typeof Z.subject==="string"&&Z.subject.trim()!==""&&Z.decision&&typeof Z.decision==="string"&&Z.decision.trim()!==""}).map((Z)=>{let K=q0.normalizeConfidence(Z.confidence),X={subject:Z.subject.trim(),decision:Z.decision.trim(),rejected:Array.isArray(Z.rejected)?Z.rejected:[],rationale:typeof Z.rationale==="string"?Z.rationale:""};return e.create({type:"decision",name:Z.subject.trim(),confidence:K,metadata:X})})}static normalizeConfidence($){if($===void 0||$===null||typeof $!=="number")return 0.5;return Math.max(0,Math.min(1,$))}}var L9=U(()=>{k$()});var D5={};w(D5,{computeModelHash:()=>I9,EmbeddingService:()=>T9});import{createHash as m2}from"crypto";function I9($){let Z=`${$.provider}:${$.model}:${$.dimensions}`;return m2("sha256").update(Z).digest("hex").slice(0,16)}class T9{repository;provider;batchSize;modelHash;modelName;redactor;constructor($){this.repository=$.repository,this.provider=$.provider,this.batchSize=$.config.batchSize,this.modelHash=I9($.config),this.modelName=$.config.model,this.redactor=$.redactor??c2}checkModelState(){let $=this.repository.getStoredModelHash(),Z=this.modelHash,K=this.modelName;if($===null)return{modelChanged:!1,needsReEmbed:!1,currentHash:Z,currentModelName:K};if($===Z)return{modelChanged:!1,needsReEmbed:!1,currentHash:Z,currentModelName:K};let X=this.repository.getStoredModelName()??$;return{modelChanged:!0,needsReEmbed:!0,storedHash:$,currentHash:Z,storedModelName:X,currentModelName:K,embeddedCount:this.repository.getEmbeddedCount()}}async embedUnembedded($={}){let Z=Date.now(),K=0,X=this.repository.getTotalMessageCount()-this.repository.getEmbeddedCount();if(X<=0)return{embedded:0,skipped:0,durationMs:0,rate:0};let Y=this.repository.findUnembedded(this.batchSize);while(Y.length>0){let _=Y.map((V)=>this.redactor.redactText(V.content).text),J=await this.provider.embedBatch(_),H=Y.map((V,B)=>({rowid:V.rowid,embedding:J[B].embedding}));this.repository.storeBatch(H,this.modelHash,this.modelName),K+=Y.length,$.onProgress?.({current:K,total:X}),Y=this.repository.findUnembedded(this.batchSize)}let Q=Date.now()-Z,G=Q>0?K/(Q/1000):0;return{embedded:K,skipped:0,durationMs:Q,rate:G}}async clearAndReembed($={}){return this.repository.clearAllEmbeddings(),this.embedUnembedded($)}}var c2;var R9=U(()=>{c2={redactText:($)=>({text:$,findings:[]}),redactJson:($)=>({value:$,findings:[]})}});function x9($,Z,K){let X=new Map;for(let Q of $){let G=X.get(Q.rowid)??{rowid:Q.rowid,rrfScore:0,normalizedScore:0,sources:[]};G.rrfScore+=1/(60+Q.rank),G.sources.push({source:"fts",rank:Q.rank,rawScore:Q.rawScore}),X.set(Q.rowid,G)}for(let Q of Z){let G=X.get(Q.rowid)??{rowid:Q.rowid,rrfScore:0,normalizedScore:0,sources:[]};G.rrfScore+=1/(60+Q.rank),G.sources.push({source:"vector",rank:Q.rank,rawScore:Q.rawScore}),X.set(Q.rowid,G)}let Y=Array.from(X.values()).sort((Q,G)=>G.rrfScore-Q.rrfScore);if(Y=Y.filter((Q)=>Q.rrfScore>=0.001),Y=Y.slice(0,K),Y.length>0){let Q=Y[0].rrfScore;if(Q>0)for(let G of Y)G.normalizedScore=G.rrfScore/Q}return Y}function u0($){let Z=($.match(/"/g)||[]).length,K=Z>0&&Z%2===0,X;if(K)X=$.replace(/[.:\-()[\]{}^~@/\\]/gu," ").replace(/\s+/g," ").trim();else X=$.replace(/[.:\-()[\]{}^"~@/\\]/gu," ").replace(/\s+/g," ").trim();if(X)return X;let Y=($.match(/"/g)||[]).length,G=Y>0&&Y%2===0?/[.:\-()[\]{}^~@/\\]/gu:/[.:\-()[\]{}^"~@/\\]/gu;return $.replace(G," ").replace(/\s+/g," ").trim()}class S5{sessionRepo;messageRepo;backfillStateRepo;summaryGenerator;dailyLogWriter;constructor($,Z,K,X,Y){this.sessionRepo=$;this.messageRepo=Z;this.backfillStateRepo=K;this.summaryGenerator=X;this.dailyLogWriter=Y}async dryRun($={}){let Z=await this.getUnprocessedSessions($.project);return{unprocessedCount:Z.length,estimatedCost:Z.length*o2}}async backfill($={}){let{batch:Z=50,project:K,onProgress:X}=$,Q=(await this.getUnprocessedSessions(K)).slice(0,Z),G={sessionsProcessed:0,sessionsFailed:0,sessionsSkipped:0,dailyLogsCreated:0,dailyLogsUpdated:0,errors:[]};for(let _=0;_<Q.length;_++){let J=Q[_];if(!J)continue;if(await this.backfillStateRepo.findBySessionId(J.id)){G.sessionsSkipped++,X?.({current:_+1,total:Q.length,sessionId:J.id,action:"skipped"});continue}try{X?.({current:_+1,total:Q.length,sessionId:J.id,action:"processing"});let V=await this.extractContent(J.id),B=J.projectPath.decoded,z=B.split(/[/\\]/).filter(Boolean).pop()??B,W=await this.summaryGenerator.generateSummary(V,J.id,z,J.startTime.toISOString(),J.endTime?.toISOString()??J.startTime.toISOString()),q=`daily/${J.startTime.toISOString().slice(0,10)}.md`;if(await this.dailyLogWriter.writeOrAppend(q,W+`
|
|
43
|
+
|
|
44
|
+
`))G.dailyLogsCreated++;else G.dailyLogsUpdated++;await this.backfillStateRepo.save(c0.create({sessionId:J.id,backfilledAt:new Date,dailyLogPath:q,success:!0})),G.sessionsProcessed++}catch(V){let B=A(V);G.sessionsFailed++,G.errors.push({sessionId:J.id,error:B});let z=J.startTime.toISOString().slice(0,10);await this.backfillStateRepo.save(c0.create({sessionId:J.id,backfilledAt:new Date,dailyLogPath:`daily/${z}.md`,success:!1,errorMessage:B})),X?.({current:_+1,total:Q.length,sessionId:J.id,action:"error"})}}return G}async getUnprocessedSessions($){let Z=await this.sessionRepo.findFiltered({projectFilter:$,limit:1e4}),K=[];for(let X of Z)if(!await this.backfillStateRepo.findBySessionId(X.id))K.push(X);return K.sort((X,Y)=>X.startTime.getTime()-Y.startTime.getTime()),K}async extractContent($){let K=(await this.messageRepo.findBySession($)).filter((Y)=>Y.role==="user"||Y.role==="assistant"),X="";for(let Y of K){let G=`${Y.role==="user"?"User":"Assistant"}: ${Y.content}
|
|
45
|
+
|
|
46
|
+
`;if(X.length+G.length>t2){X+=`... [content truncated]
|
|
47
|
+
`;break}X+=G}return X}}var o2=0.001,t2=16000;var v5=()=>{};function P9($,Z,K=4){if(Z<=0){let H=$.map((B)=>({...B,truncatedContent:B.content,allocated:B.content.length===0?0:Math.ceil(B.content.length/K),truncated:!1})),V=H.reduce((B,z)=>B+z.allocated,0);return{sections:H,totalTokensUsed:V,budgetExceeded:!1}}let X=Z*K,Y=[...$].sort((H,V)=>H.priority-V.priority),Q=X,G=[],_=!1;for(let H of Y){if(H.content.length===0){G.push({...H,truncatedContent:"",allocated:0,truncated:!1});continue}if(Q<=0){G.push({...H,truncatedContent:"",allocated:0,truncated:!0}),_=!0;continue}let V=H.content.length;if(V<=Q){let B=Math.ceil(V/K);G.push({...H,truncatedContent:H.content,allocated:B,truncated:!1}),Q-=V}else{let B=H.content.slice(0,Q),z=Math.ceil(Q/K);G.push({...H,truncatedContent:B,allocated:z,truncated:!0}),Q=0,_=!0}}let J=G.reduce((H,V)=>H+V.allocated,0);return{sections:G,totalTokensUsed:J,budgetExceeded:_}}var C5={};w(C5,{SmartContextService:()=>f$});function e2($){if($.length===0)return 0;return Math.ceil($.length/s2)}function $7($){return`#${$.id} (${$.severity}/${$.category}): ${$.description}`}class f${projectResolver;factRepo;frictionRepo;getSessionSummary;constructor($){if(this.projectResolver=$.projectResolver,this.factRepo=$.factRepo,this.frictionRepo=$.frictionRepo,$.getSessionSummary)this.getSessionSummary=$.getSessionSummary}async getContext($){let Z=this.projectResolver.resolveProjectEncoded($.projectFilter),K=this.projectResolver.resolveProjectName($.projectFilter);if(!Z||!K)return null;let Y=(await this.factRepo.findByProject(K)).filter((W)=>W.supersededAt===null),Q=(W)=>{return W.map((N)=>`- ${N.content}`).join(`
|
|
48
|
+
`)},G=[],_=Y.filter((W)=>W.type==="decision");if(_.length>0)G.push(this.buildSection("decisions","Active Decisions",1,Q(_)));let J=Y.filter((W)=>W.type==="learning");if(J.length>0)G.push(this.buildSection("learnings","Recent Learnings",2,Q(J)));let H=Y.filter((W)=>W.type==="preference");if(H.length>0)G.push(this.buildSection("preferences","User Preferences",3,Q(H)));let V=Y.filter((W)=>W.type==="observation");if(V.length>0)G.push(this.buildSection("observations","Observations",4,Q(V)));if($.crossProject){let N=(await this.factRepo.findAll()).filter((L)=>L.supersededAt===null&&L.project!==K),q=N.filter((L)=>L.type==="preference");if(q.length>0)G.push(this.buildSection("cross_project_preferences","Global/Cross-Project User Preferences",5,Q(q)));let I=N.filter((L)=>L.type==="decision");if(I.length>0)G.push(this.buildSection("cross_project_decisions","Cross-Project Decisions",6,Q(I)));let F=N.filter((L)=>L.type==="learning");if(F.length>0)G.push(this.buildSection("cross_project_learnings","Cross-Project Learnings",7,Q(F)))}let B=await this.buildFrictionContent($.projectFilter);if(B)G.push(this.buildSection("friction","Open Friction",8,B));if(this.getSessionSummary){let W=await this.getSessionSummary($.projectFilter,$.days);if(W)G.push(this.buildSection("session_summary","Session Summary",9,W))}if($.budget&&$.budget>0)return this.applyBudget(K,Z,G,$.budget);let z=G.reduce((W,N)=>W+N.tokenEstimate,0);return{projectName:K,projectEncoded:Z,sections:G,totalTokensEstimate:z,truncated:!1}}buildSection($,Z,K,X){return{key:$,title:Z,priority:K,content:X,truncated:!1,tokenEstimate:e2(X)}}async buildFrictionContent($){let Z=await this.frictionRepo.findOpen();if(Z.length===0)return null;let K=Z.filter((Y)=>Y.description.includes($)||Y.context&&Y.context.includes($));return(K.length>0?K:Z).map($7).join(`
|
|
49
|
+
`)}applyBudget($,Z,K,X){let Y=K.map((_)=>({key:_.key,priority:_.priority,content:_.content})),Q=P9(Y,X),G=Q.sections.map((_)=>{let J=K.find((H)=>H.key===_.key);return{key:_.key,title:J.title,priority:_.priority,content:_.truncatedContent,truncated:_.truncated,tokenEstimate:_.allocated}});return{projectName:$,projectEncoded:Z,sections:G,totalTokensEstimate:Q.totalTokensUsed,truncated:Q.budgetExceeded}}}var s2=4;var LZ=()=>{};var y5={};w(y5,{AmbientContextService:()=>E9});class E9{smartContext;contextWriter;formatter;constructor($,Z,K){this.smartContext=$;this.contextWriter=Z;this.formatter=K}async generateAmbientContext($){let Z=await this.smartContext.getContext({projectFilter:$.projectName,budget:$.budget,crossProject:!0});if(Z===null)return{success:!1,reason:"project-not-found"};if(Z.sections.length===0)return{success:!1,reason:"no-context"};let K=this.formatter.formatSmartContext(Z),X=this.buildSummaryBlock(Z);return await this.contextWriter.writeContextFile($.autoMemoryDir,K),await this.contextWriter.updateMemoryBlock($.autoMemoryDir,X),{success:!0,contextTokens:Z.totalTokensEstimate}}buildSummaryBlock($){let Z=this.countSectionLines($.sections,"decisions"),K=this.countSectionLines($.sections,"learnings"),X=this.countSectionLines($.sections,"friction"),Y=new Date().toISOString().split("T")[0];return["## Cross-Project Context",`Run \`memory context ${$.projectName}\` for full briefing. See [context.md](context.md) for latest snapshot.`,`- ${Z} active decisions, ${K} learnings`,`- Open friction: ${X}`,`- Last synced: ${Y}`].join(`
|
|
50
|
+
`)}countSectionLines($,Z){let K=$.find((X)=>X.key===Z);if(!K||!K.content)return 0;return K.content.split(`
|
|
51
|
+
`).filter((X)=>X.trim().length>0).length}}var b5={};w(b5,{trackDownloadTotal:()=>Y7,isUnicodeSupported:()=>w5,getBarCharacters:()=>IZ,createProgressReporter:()=>C9,createModelDownloadHandler:()=>Q7,createEmbeddingProgressReporter:()=>X7,TtyProgressReporter:()=>k9,TtyEmbeddingProgressReporter:()=>y9,QuietProgressReporter:()=>v9,QuietEmbeddingProgressReporter:()=>b9,PlainProgressReporter:()=>S9,PlainEmbeddingProgressReporter:()=>w9});import D9 from"cli-progress";function w5(){let{env:$}=process;if(process.platform!=="win32")return $.TERM!=="linux";return Boolean($.MSYSTEM)||Boolean($.WT_SESSION)||Boolean($.TERMINUS_SUBLIME)||$.ConEmuTask==="{cmd::Cmder}"||$.TERM_PROGRAM==="vscode"||$.TERM==="xterm-256color"||$.TERM==="alacritty"||$.TERMINAL_EMULATOR==="JetBrains-JediTerm"}function IZ(){return w5()?Z7:K7}class k9{bar;verbose;total=0;currentValue=0;constructor($=!1){this.verbose=$;let Z=IZ();this.bar=new D9.SingleBar({format:"Syncing |{bar}| {percentage}% | {value}/{total} sessions",barCompleteChar:Z.complete,barIncompleteChar:Z.incomplete,hideCursor:!0})}start($){this.total=$,this.currentValue=0,this.bar.start($,0)}update($,Z){if(this.currentValue=$,this.bar.update($),this.verbose)this.bar.stop(),console.log(` Processing: ${Z}`),this.bar.start(this.total,$)}stop(){this.bar.stop()}log($){if(this.verbose)this.bar.stop(),console.log($),this.bar.start(this.total,this.currentValue)}}class S9{verbose;constructor($=!1){this.verbose=$}start($){console.log(`Processing ${$} sessions...`)}update($,Z){if(this.verbose)console.log(` [${$}] Processing: ${Z}`)}stop(){console.log("Done.")}log($){if(this.verbose)console.log($)}}class v9{start($){}update($,Z){}stop(){}log($){}}function C9($){if($.quiet)return new v9;if(!process.stdout.isTTY)return new S9($.verbose);return new k9($.verbose)}class y9{bar;constructor(){let $=IZ();this.bar=new D9.SingleBar({format:"Embedding |{bar}| {percentage}% | {value}/{total} messages | ETA: {eta_formatted}",barCompleteChar:$.complete,barIncompleteChar:$.incomplete,hideCursor:!0,etaBuffer:20})}start($){this.bar.start($,0)}update($){this.bar.update($)}stop(){this.bar.stop()}}class w9{start($){console.log(`Embedding ${$} messages...`)}update($){}stop(){console.log("Done.")}}class b9{start($){}update($){}stop(){}}function X7($){if($.quiet)return new b9;if(!process.stdout.isTTY)return new w9;return new y9}function Y7($,Z){let K=Math.round(Z/1048576);return K>$?K:$}function Q7($){if($.quiet||!process.stdout.isTTY){let Q=!1;return(G)=>{if(!Q&&G.status==="downloading"&&!$.quiet)console.log("Downloading embedding model (one-time setup)..."),Q=!0}}let Z=IZ(),K=new D9.SingleBar({format:"Downloading model |{bar}| {percentage}% | {value}/{total} MB",barCompleteChar:Z.complete,barIncompleteChar:Z.incomplete,hideCursor:!0}),X=!1,Y=0;return(Q)=>{if(Q.status==="downloading"){let G=Math.round(Q.loaded/1048576),_=Math.round(Q.total/1048576);if(_>Y)Y=_;if(!X&&Y>0)K.start(Y,G),X=!0;else if(X){if(_>0&&K.getTotal()!==Y)K.setTotal(Y);K.update(G)}}else if(Q.status==="ready"&&X)K.stop()}}var Z7,K7;var f9=U(()=>{Z7={complete:"\u2588",incomplete:"\u2591"},K7={complete:"#",incomplete:"-"}});function TZ($){try{return $.exec("CREATE VIRTUAL TABLE _fts5_check USING fts5(test)"),$.exec("DROP TABLE _fts5_check"),!0}catch{return!1}}function h9($,Z){let{sqliteVecAvailable:K=!1}=Z??{};if(!TZ($))throw Error("FTS5 extension is not available. Ensure you are using Bun with FTS5 support enabled.");try{let Q=$.prepare("PRAGMA table_info(friction_log)").all();if(!Q.some((_)=>_.name==="tool")&&Q.length>0)$.exec(`
|
|
52
|
+
CREATE TABLE friction_log_new (
|
|
53
|
+
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
|
54
|
+
description TEXT NOT NULL,
|
|
55
|
+
severity TEXT NOT NULL DEFAULT 'medium' CHECK (severity IN ('low', 'medium', 'high', 'critical')),
|
|
56
|
+
category TEXT NOT NULL DEFAULT 'cli',
|
|
57
|
+
tool TEXT NOT NULL DEFAULT 'memory',
|
|
58
|
+
tags TEXT,
|
|
59
|
+
status TEXT NOT NULL DEFAULT 'open' CHECK (status IN ('open', 'resolved', 'wont-fix')),
|
|
60
|
+
context TEXT,
|
|
61
|
+
source_project TEXT,
|
|
62
|
+
logged_at TEXT NOT NULL,
|
|
63
|
+
resolved_at TEXT,
|
|
64
|
+
resolution TEXT,
|
|
65
|
+
last_reviewed_at TEXT
|
|
66
|
+
);
|
|
67
|
+
INSERT INTO friction_log_new (id, description, severity, category, tool, tags, status, context, source_project, logged_at, resolved_at, resolution, last_reviewed_at)
|
|
68
|
+
SELECT id, description, severity, category, 'memory', NULL, status, context, source_project, logged_at, resolved_at, resolution, NULL
|
|
69
|
+
FROM friction_log;
|
|
70
|
+
DROP TABLE friction_log;
|
|
71
|
+
ALTER TABLE friction_log_new RENAME TO friction_log;
|
|
72
|
+
CREATE INDEX IF NOT EXISTS idx_friction_status ON friction_log(status);
|
|
73
|
+
CREATE INDEX IF NOT EXISTS idx_friction_severity ON friction_log(severity);
|
|
74
|
+
CREATE INDEX IF NOT EXISTS idx_friction_category ON friction_log(category);
|
|
75
|
+
CREATE INDEX IF NOT EXISTS idx_friction_tool ON friction_log(tool);
|
|
76
|
+
`)}catch{}for(let Q of f5)$.exec(Q);if(!$.prepare("PRAGMA table_info(embedding_state)").all().some((Q)=>Q.name==="model_name"))$.exec(`
|
|
77
|
+
ALTER TABLE embedding_state ADD COLUMN model_name TEXT NOT NULL DEFAULT '';
|
|
78
|
+
`);if(K)$.exec(`
|
|
79
|
+
CREATE VIRTUAL TABLE IF NOT EXISTS message_embeddings USING vec0(
|
|
80
|
+
embedding float[384]
|
|
81
|
+
);
|
|
82
|
+
`)}var f5;var g9=U(()=>{f5=[`
|
|
83
|
+
CREATE TABLE IF NOT EXISTS sessions (
|
|
84
|
+
id TEXT PRIMARY KEY,
|
|
85
|
+
project_path_encoded TEXT NOT NULL,
|
|
86
|
+
project_path_decoded TEXT NOT NULL,
|
|
87
|
+
project_name TEXT NOT NULL,
|
|
88
|
+
start_time TEXT NOT NULL,
|
|
89
|
+
end_time TEXT,
|
|
90
|
+
message_count INTEGER DEFAULT 0,
|
|
91
|
+
summary TEXT,
|
|
92
|
+
created_at TEXT DEFAULT (datetime('now')),
|
|
93
|
+
updated_at TEXT DEFAULT (datetime('now'))
|
|
94
|
+
);
|
|
95
|
+
CREATE INDEX IF NOT EXISTS idx_sessions_project ON sessions(project_path_encoded);
|
|
96
|
+
CREATE INDEX IF NOT EXISTS idx_sessions_start_time ON sessions(start_time);
|
|
97
|
+
`,`
|
|
98
|
+
CREATE TABLE IF NOT EXISTS messages_meta (
|
|
99
|
+
rowid INTEGER PRIMARY KEY AUTOINCREMENT,
|
|
100
|
+
id TEXT UNIQUE NOT NULL,
|
|
101
|
+
session_id TEXT NOT NULL,
|
|
102
|
+
role TEXT NOT NULL CHECK (role IN ('user', 'assistant')),
|
|
103
|
+
content TEXT NOT NULL,
|
|
104
|
+
timestamp TEXT NOT NULL,
|
|
105
|
+
tool_use_ids TEXT,
|
|
106
|
+
FOREIGN KEY (session_id) REFERENCES sessions(id) ON DELETE CASCADE
|
|
107
|
+
);
|
|
108
|
+
CREATE INDEX IF NOT EXISTS idx_messages_session ON messages_meta(session_id);
|
|
109
|
+
CREATE INDEX IF NOT EXISTS idx_messages_timestamp ON messages_meta(timestamp);
|
|
110
|
+
`,`
|
|
111
|
+
CREATE VIRTUAL TABLE IF NOT EXISTS messages_fts USING fts5(
|
|
112
|
+
content,
|
|
113
|
+
content=messages_meta,
|
|
114
|
+
content_rowid=rowid,
|
|
115
|
+
tokenize='porter unicode61'
|
|
116
|
+
);
|
|
117
|
+
`,`
|
|
118
|
+
CREATE TRIGGER IF NOT EXISTS messages_fts_insert AFTER INSERT ON messages_meta BEGIN
|
|
119
|
+
INSERT INTO messages_fts(rowid, content) VALUES (new.rowid, new.content);
|
|
120
|
+
END;
|
|
121
|
+
|
|
122
|
+
CREATE TRIGGER IF NOT EXISTS messages_fts_delete AFTER DELETE ON messages_meta BEGIN
|
|
123
|
+
INSERT INTO messages_fts(messages_fts, rowid, content) VALUES('delete', old.rowid, old.content);
|
|
124
|
+
END;
|
|
125
|
+
|
|
126
|
+
CREATE TRIGGER IF NOT EXISTS messages_fts_update AFTER UPDATE ON messages_meta BEGIN
|
|
127
|
+
INSERT INTO messages_fts(messages_fts, rowid, content) VALUES('delete', old.rowid, old.content);
|
|
128
|
+
INSERT INTO messages_fts(rowid, content) VALUES (new.rowid, new.content);
|
|
129
|
+
END;
|
|
130
|
+
`,`
|
|
131
|
+
CREATE TABLE IF NOT EXISTS tool_uses (
|
|
132
|
+
id TEXT PRIMARY KEY,
|
|
133
|
+
session_id TEXT NOT NULL,
|
|
134
|
+
name TEXT NOT NULL,
|
|
135
|
+
input TEXT NOT NULL,
|
|
136
|
+
timestamp TEXT NOT NULL,
|
|
137
|
+
status TEXT NOT NULL CHECK (status IN ('pending', 'success', 'error')),
|
|
138
|
+
result TEXT,
|
|
139
|
+
FOREIGN KEY (session_id) REFERENCES sessions(id) ON DELETE CASCADE
|
|
140
|
+
);
|
|
141
|
+
CREATE INDEX IF NOT EXISTS idx_tool_uses_session ON tool_uses(session_id);
|
|
142
|
+
CREATE INDEX IF NOT EXISTS idx_tool_uses_name ON tool_uses(name);
|
|
143
|
+
`,`
|
|
144
|
+
CREATE TABLE IF NOT EXISTS links (
|
|
145
|
+
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
|
146
|
+
source_type TEXT NOT NULL CHECK (source_type IN ('session', 'message', 'topic')),
|
|
147
|
+
source_id TEXT NOT NULL,
|
|
148
|
+
target_type TEXT NOT NULL CHECK (target_type IN ('session', 'message', 'topic')),
|
|
149
|
+
target_id TEXT NOT NULL,
|
|
150
|
+
relationship TEXT NOT NULL CHECK (relationship IN ('mentions', 'related_to', 'continues')),
|
|
151
|
+
weight REAL DEFAULT 1.0 CHECK (weight >= 0 AND weight <= 1),
|
|
152
|
+
UNIQUE(source_type, source_id, target_type, target_id, relationship)
|
|
153
|
+
);
|
|
154
|
+
CREATE INDEX IF NOT EXISTS idx_links_source ON links(source_type, source_id);
|
|
155
|
+
CREATE INDEX IF NOT EXISTS idx_links_target ON links(target_type, target_id);
|
|
156
|
+
`,`
|
|
157
|
+
CREATE TABLE IF NOT EXISTS topics (
|
|
158
|
+
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
|
159
|
+
name TEXT UNIQUE NOT NULL,
|
|
160
|
+
created_at TEXT DEFAULT (datetime('now'))
|
|
161
|
+
);
|
|
162
|
+
CREATE INDEX IF NOT EXISTS idx_topics_name ON topics(name);
|
|
163
|
+
`,`
|
|
164
|
+
CREATE TABLE IF NOT EXISTS extraction_state (
|
|
165
|
+
id TEXT PRIMARY KEY,
|
|
166
|
+
session_path TEXT UNIQUE NOT NULL,
|
|
167
|
+
started_at TEXT NOT NULL,
|
|
168
|
+
status TEXT NOT NULL CHECK (status IN ('pending', 'in_progress', 'complete', 'error')),
|
|
169
|
+
completed_at TEXT,
|
|
170
|
+
messages_extracted INTEGER DEFAULT 0,
|
|
171
|
+
error_message TEXT,
|
|
172
|
+
file_mtime TEXT,
|
|
173
|
+
file_size INTEGER
|
|
174
|
+
);
|
|
175
|
+
CREATE INDEX IF NOT EXISTS idx_extraction_session_path ON extraction_state(session_path);
|
|
176
|
+
CREATE INDEX IF NOT EXISTS idx_extraction_status ON extraction_state(status);
|
|
177
|
+
`,`
|
|
178
|
+
CREATE TABLE IF NOT EXISTS entities (
|
|
179
|
+
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
|
180
|
+
type TEXT NOT NULL CHECK (type IN ('concept', 'file', 'decision', 'term')),
|
|
181
|
+
name TEXT NOT NULL,
|
|
182
|
+
metadata TEXT,
|
|
183
|
+
confidence REAL DEFAULT 1.0 CHECK (confidence >= 0 AND confidence <= 1),
|
|
184
|
+
created_at TEXT DEFAULT (datetime('now')),
|
|
185
|
+
UNIQUE(type, name)
|
|
186
|
+
);
|
|
187
|
+
CREATE INDEX IF NOT EXISTS idx_entities_type ON entities(type);
|
|
188
|
+
CREATE INDEX IF NOT EXISTS idx_entities_name ON entities(name);
|
|
189
|
+
`,`
|
|
190
|
+
CREATE TABLE IF NOT EXISTS session_entities (
|
|
191
|
+
session_id TEXT NOT NULL,
|
|
192
|
+
entity_id INTEGER NOT NULL,
|
|
193
|
+
frequency INTEGER DEFAULT 1,
|
|
194
|
+
FOREIGN KEY (session_id) REFERENCES sessions(id) ON DELETE CASCADE,
|
|
195
|
+
FOREIGN KEY (entity_id) REFERENCES entities(id) ON DELETE CASCADE,
|
|
196
|
+
PRIMARY KEY (session_id, entity_id)
|
|
197
|
+
);
|
|
198
|
+
`,`
|
|
199
|
+
CREATE TABLE IF NOT EXISTS entity_links (
|
|
200
|
+
source_id INTEGER NOT NULL,
|
|
201
|
+
target_id INTEGER NOT NULL,
|
|
202
|
+
relationship TEXT NOT NULL CHECK (relationship IN ('related', 'implies', 'contradicts')),
|
|
203
|
+
weight REAL DEFAULT 1.0 CHECK (weight >= 0 AND weight <= 1),
|
|
204
|
+
FOREIGN KEY (source_id) REFERENCES entities(id) ON DELETE CASCADE,
|
|
205
|
+
FOREIGN KEY (target_id) REFERENCES entities(id) ON DELETE CASCADE,
|
|
206
|
+
PRIMARY KEY (source_id, target_id, relationship)
|
|
207
|
+
);
|
|
208
|
+
`,`
|
|
209
|
+
CREATE VIRTUAL TABLE IF NOT EXISTS sessions_fts USING fts5(
|
|
210
|
+
session_id,
|
|
211
|
+
summary,
|
|
212
|
+
tokenize='porter unicode61'
|
|
213
|
+
);
|
|
214
|
+
`,`
|
|
215
|
+
CREATE TRIGGER IF NOT EXISTS sessions_fts_update AFTER UPDATE OF summary ON sessions
|
|
216
|
+
WHEN new.summary IS NOT NULL AND new.summary != ''
|
|
217
|
+
BEGIN
|
|
218
|
+
DELETE FROM sessions_fts WHERE session_id = old.id;
|
|
219
|
+
INSERT INTO sessions_fts(session_id, summary) VALUES (new.id, new.summary);
|
|
220
|
+
END;
|
|
221
|
+
|
|
222
|
+
CREATE TRIGGER IF NOT EXISTS sessions_fts_delete AFTER DELETE ON sessions BEGIN
|
|
223
|
+
DELETE FROM sessions_fts WHERE session_id = old.id;
|
|
224
|
+
END;
|
|
225
|
+
`,`
|
|
226
|
+
CREATE TABLE IF NOT EXISTS embedding_state (
|
|
227
|
+
message_id INTEGER PRIMARY KEY,
|
|
228
|
+
embedded_at TEXT NOT NULL,
|
|
229
|
+
model_hash TEXT NOT NULL,
|
|
230
|
+
FOREIGN KEY (message_id) REFERENCES messages_meta(rowid) ON DELETE CASCADE
|
|
231
|
+
);
|
|
232
|
+
CREATE INDEX IF NOT EXISTS idx_embedding_state_model ON embedding_state(model_hash);
|
|
233
|
+
`,`
|
|
234
|
+
CREATE TABLE IF NOT EXISTS memory_files (
|
|
235
|
+
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
|
236
|
+
file_path TEXT UNIQUE NOT NULL,
|
|
237
|
+
file_type TEXT NOT NULL CHECK (file_type IN ('daily_log', 'decisions', 'learnings', 'user_prefs')),
|
|
238
|
+
project_encoded TEXT,
|
|
239
|
+
content TEXT NOT NULL,
|
|
240
|
+
content_hash TEXT NOT NULL,
|
|
241
|
+
last_indexed_at TEXT NOT NULL,
|
|
242
|
+
created_at TEXT DEFAULT (datetime('now'))
|
|
243
|
+
);
|
|
244
|
+
CREATE INDEX IF NOT EXISTS idx_memory_files_type ON memory_files(file_type);
|
|
245
|
+
CREATE INDEX IF NOT EXISTS idx_memory_files_project ON memory_files(project_encoded);
|
|
246
|
+
`,`
|
|
247
|
+
CREATE VIRTUAL TABLE IF NOT EXISTS memory_files_fts USING fts5(
|
|
248
|
+
content,
|
|
249
|
+
content=memory_files,
|
|
250
|
+
content_rowid=id,
|
|
251
|
+
tokenize='porter unicode61'
|
|
252
|
+
);
|
|
253
|
+
`,`
|
|
254
|
+
CREATE TRIGGER IF NOT EXISTS memory_files_fts_insert AFTER INSERT ON memory_files BEGIN
|
|
255
|
+
INSERT INTO memory_files_fts(rowid, content) VALUES (new.id, new.content);
|
|
256
|
+
END;
|
|
257
|
+
|
|
258
|
+
CREATE TRIGGER IF NOT EXISTS memory_files_fts_delete AFTER DELETE ON memory_files BEGIN
|
|
259
|
+
INSERT INTO memory_files_fts(memory_files_fts, rowid, content) VALUES('delete', old.id, old.content);
|
|
260
|
+
END;
|
|
261
|
+
|
|
262
|
+
CREATE TRIGGER IF NOT EXISTS memory_files_fts_update AFTER UPDATE ON memory_files BEGIN
|
|
263
|
+
INSERT INTO memory_files_fts(memory_files_fts, rowid, content) VALUES('delete', old.id, old.content);
|
|
264
|
+
INSERT INTO memory_files_fts(rowid, content) VALUES (new.id, new.content);
|
|
265
|
+
END;
|
|
266
|
+
`,`
|
|
267
|
+
CREATE TABLE IF NOT EXISTS friction_log (
|
|
268
|
+
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
|
269
|
+
description TEXT NOT NULL,
|
|
270
|
+
severity TEXT NOT NULL DEFAULT 'medium' CHECK (severity IN ('low', 'medium', 'high', 'critical')),
|
|
271
|
+
category TEXT NOT NULL DEFAULT 'cli',
|
|
272
|
+
tool TEXT NOT NULL DEFAULT 'memory',
|
|
273
|
+
tags TEXT,
|
|
274
|
+
status TEXT NOT NULL DEFAULT 'open' CHECK (status IN ('open', 'resolved', 'wont-fix')),
|
|
275
|
+
context TEXT,
|
|
276
|
+
source_project TEXT,
|
|
277
|
+
logged_at TEXT NOT NULL,
|
|
278
|
+
resolved_at TEXT,
|
|
279
|
+
resolution TEXT,
|
|
280
|
+
last_reviewed_at TEXT
|
|
281
|
+
);
|
|
282
|
+
CREATE INDEX IF NOT EXISTS idx_friction_status ON friction_log(status);
|
|
283
|
+
CREATE INDEX IF NOT EXISTS idx_friction_severity ON friction_log(severity);
|
|
284
|
+
CREATE INDEX IF NOT EXISTS idx_friction_category ON friction_log(category);
|
|
285
|
+
CREATE INDEX IF NOT EXISTS idx_friction_tool ON friction_log(tool);
|
|
286
|
+
`,`
|
|
287
|
+
CREATE TABLE IF NOT EXISTS backfill_state (
|
|
288
|
+
session_id TEXT PRIMARY KEY,
|
|
289
|
+
backfilled_at TEXT NOT NULL,
|
|
290
|
+
daily_log_path TEXT NOT NULL,
|
|
291
|
+
success INTEGER DEFAULT 1,
|
|
292
|
+
error_message TEXT
|
|
293
|
+
);
|
|
294
|
+
`,`
|
|
295
|
+
CREATE TABLE IF NOT EXISTS facts (
|
|
296
|
+
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
|
297
|
+
uuid TEXT UNIQUE NOT NULL,
|
|
298
|
+
type TEXT NOT NULL CHECK (type IN ('decision', 'learning', 'preference', 'friction', 'observation', 'supersedence')),
|
|
299
|
+
project TEXT NOT NULL,
|
|
300
|
+
content TEXT NOT NULL,
|
|
301
|
+
metadata TEXT,
|
|
302
|
+
observed_at TEXT NOT NULL,
|
|
303
|
+
superseded_at TEXT,
|
|
304
|
+
superseded_by TEXT,
|
|
305
|
+
created_at TEXT DEFAULT (datetime('now')),
|
|
306
|
+
updated_at TEXT DEFAULT (datetime('now'))
|
|
307
|
+
);
|
|
308
|
+
CREATE INDEX IF NOT EXISTS idx_facts_uuid ON facts(uuid);
|
|
309
|
+
CREATE INDEX IF NOT EXISTS idx_facts_project ON facts(project);
|
|
310
|
+
CREATE INDEX IF NOT EXISTS idx_facts_type ON facts(type);
|
|
311
|
+
`,`
|
|
312
|
+
CREATE VIRTUAL TABLE IF NOT EXISTS facts_fts USING fts5(
|
|
313
|
+
content,
|
|
314
|
+
content=facts,
|
|
315
|
+
content_rowid=id,
|
|
316
|
+
tokenize='porter unicode61'
|
|
317
|
+
);
|
|
318
|
+
`,`
|
|
319
|
+
CREATE TRIGGER IF NOT EXISTS facts_fts_insert AFTER INSERT ON facts BEGIN
|
|
320
|
+
INSERT INTO facts_fts(rowid, content) VALUES (new.id, new.content);
|
|
321
|
+
END;
|
|
322
|
+
|
|
323
|
+
CREATE TRIGGER IF NOT EXISTS facts_fts_delete AFTER DELETE ON facts BEGIN
|
|
324
|
+
INSERT INTO facts_fts(facts_fts, rowid, content) VALUES('delete', old.id, old.content);
|
|
325
|
+
END;
|
|
326
|
+
|
|
327
|
+
CREATE TRIGGER IF NOT EXISTS facts_fts_update AFTER UPDATE ON facts BEGIN
|
|
328
|
+
INSERT INTO facts_fts(facts_fts, rowid, content) VALUES('delete', old.id, old.content);
|
|
329
|
+
INSERT INTO facts_fts(rowid, content) VALUES (new.id, new.content);
|
|
330
|
+
END;
|
|
331
|
+
`,`
|
|
332
|
+
CREATE TABLE IF NOT EXISTS extraction_log (
|
|
333
|
+
session_id TEXT PRIMARY KEY,
|
|
334
|
+
mode TEXT NOT NULL,
|
|
335
|
+
facts_added INTEGER DEFAULT 0,
|
|
336
|
+
facts_updated INTEGER DEFAULT 0,
|
|
337
|
+
facts_superseded INTEGER DEFAULT 0,
|
|
338
|
+
facts_skipped INTEGER DEFAULT 0,
|
|
339
|
+
provider TEXT NOT NULL,
|
|
340
|
+
model TEXT NOT NULL,
|
|
341
|
+
tokens_consumed INTEGER DEFAULT 0,
|
|
342
|
+
extracted_at TEXT NOT NULL
|
|
343
|
+
);
|
|
344
|
+
`]});import{existsSync as h5,readdirSync as G7}from"fs";import{homedir as FZ}from"os";import{join as l}from"path";function K$(){let $=process.env.XDG_CONFIG_HOME;if($)return l($,RZ);return l(FZ(),".config",RZ)}function t(){let $=process.env.XDG_DATA_HOME;if($)return l($,RZ);return l(FZ(),".local","share",RZ)}function g5(){return l(FZ(),".memory-nexus")}function MZ(){let $=process.env.MEMORY_HOME;if($)return $;return l(FZ(),".memory")}function m9(){return l(K$(),"config.json")}function c9(){return l(t(),"memory.db")}function O0(){return l(t(),"logs")}function u9(){return l(t(),"hooks")}function d9(){return l(t(),"backups")}function p9(){return l(t(),"sync-checkpoint.json")}function jZ(){return l(t(),"events")}function m5($){return l(jZ(),`events-${$}.jsonl`)}function xZ($){let Z=$??jZ();if(!h5(Z))return[];let K=G7(Z),X=[],Y=l(Z,"events.jsonl");if(h5(Y))X.push(Y);for(let Q of K)if(Q.startsWith("events-")&&Q.endsWith(".jsonl"))X.push(l(Z,Q));return X}var RZ="memory";var p=U(()=>{if(process.platform==="win32"&&!process.env.HOME)process.env.HOME=process.env.USERPROFILE});import{Database as _7}from"bun:sqlite";import{existsSync as J7,mkdirSync as H7}from"fs";import{dirname as c5}from"path";function V7($){try{return e0("sqlite-vec").load($),!0}catch{return!1}}function E(){return c9()}function v($){let{path:Z,create:K=!0,applySchema:X=!0,walMode:Y=!0,cacheSize:Q=-64000,busyTimeout:G=5000}=$,_=Z!==":memory:",J=_&&J7(Z),H=$.quickCheck??(_&&J);if(_)try{H7(c5(Z),{recursive:!0})}catch(z){let W=A(z);throw new R(T.DB_CONNECTION_FAILED,`Failed to create database directory: ${W}`,{path:c5(Z)})}let V;try{V=new _7(Z,{create:K})}catch(z){let W=A(z),N=z.code;throw new R(T.DB_CONNECTION_FAILED,`Failed to connect to database: ${W}`,{path:Z,...N?{errno:N}:{}})}let B=(z)=>{V.close();let W=A(z);if(W.includes("not a database")||W.includes("SQLITE_NOTADB"))throw new R(T.DB_CORRUPTED,"Database file is corrupted or not a valid SQLite database",{path:Z});throw new R(T.DB_CONNECTION_FAILED,`Failed to initialize database: ${W}`,{path:Z})};try{V.exec("PRAGMA foreign_keys = ON;");let z=!1;if(Y&&_){V.exec("PRAGMA journal_mode = WAL;");let q=V.query("PRAGMA journal_mode;").get();if(z=q.journal_mode==="wal",!z)console.warn(`Warning: WAL mode not enabled. Current mode: ${q.journal_mode}`)}V.exec(`PRAGMA busy_timeout = ${G};`),V.exec("PRAGMA synchronous = NORMAL;"),V.exec(`PRAGMA cache_size = ${Q};`),V.exec("PRAGMA temp_store = MEMORY;");let W=TZ(V);if(!W){let q=V.query("SELECT sqlite_version() as version").get();throw V.close(),new R(T.DB_CONNECTION_FAILED,"FTS5 is not available. memory requires FTS5 for full-text search.",{sqliteVersion:q?.version??"unknown"})}if(H){let q=V.query("PRAGMA quick_check(1);").get();if(q?.quick_check!=="ok")throw V.close(),new R(T.DB_CORRUPTED,"Database integrity check failed",{path:Z,checkResult:q?.quick_check??"unknown"})}let N=V7(V);if(X)h9(V,{sqliteVecAvailable:N});return{db:V,walEnabled:z,fts5Available:W,sqliteVecAvailable:N}}catch(z){if(z instanceof R)throw z;throw B(z)}}function D($){try{$.exec("PRAGMA wal_checkpoint(TRUNCATE);")}catch{}try{$.exec("PRAGMA journal_mode = DELETE;")}catch{}$.close()}function l9($){return $.query("PRAGMA wal_checkpoint(TRUNCATE);").get()??{busy:0,log:0,checkpointed:0}}var n9=U(()=>{g9();w$();p()});class g{db;findByIdStmt;findByProjectStmt;findRecentStmt;insertStmt;deleteStmt;updateSummaryStmt;updateProjectNameStmt;findDistinctEncodedPathsStmt;constructor($){this.db=$,this.findByIdStmt=$.prepare(`
|
|
345
|
+
SELECT id, project_path_encoded, project_path_decoded, project_name,
|
|
346
|
+
start_time, end_time, message_count, summary
|
|
347
|
+
FROM sessions
|
|
348
|
+
WHERE id = $id
|
|
349
|
+
`),this.findByProjectStmt=$.prepare(`
|
|
350
|
+
SELECT id, project_path_encoded, project_path_decoded, project_name,
|
|
351
|
+
start_time, end_time, message_count, summary
|
|
352
|
+
FROM sessions
|
|
353
|
+
WHERE project_path_encoded = $projectPath
|
|
354
|
+
ORDER BY start_time DESC
|
|
355
|
+
`),this.findRecentStmt=$.prepare(`
|
|
356
|
+
SELECT id, project_path_encoded, project_path_decoded, project_name,
|
|
357
|
+
start_time, end_time, message_count, summary
|
|
358
|
+
FROM sessions
|
|
359
|
+
ORDER BY start_time DESC
|
|
360
|
+
LIMIT $limit
|
|
361
|
+
`),this.insertStmt=$.prepare(`
|
|
362
|
+
INSERT OR IGNORE INTO sessions
|
|
363
|
+
(id, project_path_encoded, project_path_decoded, project_name,
|
|
364
|
+
start_time, end_time, message_count)
|
|
365
|
+
VALUES
|
|
366
|
+
($id, $projectPathEncoded, $projectPathDecoded, $projectName,
|
|
367
|
+
$startTime, $endTime, $messageCount)
|
|
368
|
+
`),this.deleteStmt=$.prepare(`
|
|
369
|
+
DELETE FROM sessions WHERE id = $id
|
|
370
|
+
`),this.updateSummaryStmt=$.prepare(`
|
|
371
|
+
UPDATE sessions SET summary = $summary, updated_at = datetime('now')
|
|
372
|
+
WHERE id = $id
|
|
373
|
+
`),this.updateProjectNameStmt=$.prepare(`
|
|
374
|
+
UPDATE sessions SET project_name = $projectName, updated_at = datetime('now')
|
|
375
|
+
WHERE project_path_encoded = $encodedPath
|
|
376
|
+
`),this.findDistinctEncodedPathsStmt=$.prepare(`
|
|
377
|
+
SELECT DISTINCT project_path_encoded FROM sessions
|
|
378
|
+
ORDER BY project_path_encoded
|
|
379
|
+
`)}rowToSession($){let Z=i.fromDecoded($.project_path_decoded);return B0.create({id:$.id,projectPath:Z,startTime:new Date($.start_time),endTime:$.end_time?new Date($.end_time):void 0,summary:$.summary??void 0,messageCount:$.message_count})}async findById($){let Z=this.findByIdStmt.get({$id:$});if(!Z)return null;return this.rowToSession(Z)}async findByProject($){return this.findByProjectStmt.all({$projectPath:$.encoded}).map((K)=>this.rowToSession(K))}async findRecent($){return this.findRecentStmt.all({$limit:$}).map((K)=>this.rowToSession(K))}async save($){this.insertStmt.run({$id:$.id,$projectPathEncoded:$.projectPath.encoded,$projectPathDecoded:$.projectPath.decoded,$projectName:$.projectPath.projectName,$startTime:$.startTime.toISOString(),$endTime:$.endTime?.toISOString()??null,$messageCount:$.messages.length})}async saveMany($){this.db.transaction(()=>{for(let K of $)this.insertStmt.run({$id:K.id,$projectPathEncoded:K.projectPath.encoded,$projectPathDecoded:K.projectPath.decoded,$projectName:K.projectPath.projectName,$startTime:K.startTime.toISOString(),$endTime:K.endTime?.toISOString()??null,$messageCount:K.messages.length})}).immediate()}async delete($){this.deleteStmt.run({$id:$})}async updateSummary($,Z){this.updateSummaryStmt.run({$id:$,$summary:Z})}async findOlderThan($){return this.db.prepare(`
|
|
380
|
+
SELECT id, project_path_encoded, project_path_decoded, project_name,
|
|
381
|
+
start_time, end_time, message_count, summary
|
|
382
|
+
FROM sessions
|
|
383
|
+
WHERE updated_at < $cutoffDate
|
|
384
|
+
ORDER BY updated_at ASC
|
|
385
|
+
`).all({$cutoffDate:$.toISOString()}).map((Y)=>this.rowToSession(Y))}async countOlderThan($){return this.db.prepare(`
|
|
386
|
+
SELECT COUNT(*) as count
|
|
387
|
+
FROM sessions
|
|
388
|
+
WHERE updated_at < $cutoffDate
|
|
389
|
+
`).get({$cutoffDate:$.toISOString()}).count}async deleteOlderThan($){let Z=await this.countOlderThan($),K=`
|
|
390
|
+
DELETE FROM sessions
|
|
391
|
+
WHERE updated_at < $cutoffDate
|
|
392
|
+
`;return this.db.prepare(`
|
|
393
|
+
DELETE FROM sessions
|
|
394
|
+
WHERE updated_at < $cutoffDate
|
|
395
|
+
`).run({$cutoffDate:$.toISOString()}),Z}async updateProjectName($,Z){let X=this.db.prepare("SELECT COUNT(*) as count FROM sessions WHERE project_path_encoded = $encodedPath").get({$encodedPath:$}).count;if(X>0)this.updateProjectNameStmt.run({$encodedPath:$,$projectName:Z});return X}async findDistinctEncodedPaths(){return this.findDistinctEncodedPathsStmt.all().map((Z)=>Z.project_path_encoded)}async findFiltered($){let Z=[],K={};if($.projectFilter)Z.push("project_name LIKE $projectFilter"),K.$projectFilter=`%${$.projectFilter}%`;if($.sinceDate)Z.push("start_time >= $sinceDate"),K.$sinceDate=$.sinceDate.toISOString();if($.beforeDate)Z.push("start_time <= $beforeDate"),K.$beforeDate=$.beforeDate.toISOString();let X=Z.length>0?`WHERE ${Z.join(" AND ")}`:"",Y=$.limit??20;K.$limit=Y;let Q=`
|
|
396
|
+
SELECT id, project_path_encoded, project_path_decoded, project_name,
|
|
397
|
+
start_time, end_time, message_count, summary
|
|
398
|
+
FROM sessions
|
|
399
|
+
${X}
|
|
400
|
+
ORDER BY start_time DESC
|
|
401
|
+
LIMIT $limit
|
|
402
|
+
`;return this.db.prepare(Q).all(K).map((J)=>this.rowToSession(J))}async searchSummaries($,Z=20){let K=u0($);if(!K)return[];let X=`
|
|
403
|
+
SELECT s.id, s.project_path_encoded, s.project_path_decoded, s.project_name,
|
|
404
|
+
s.start_time, s.end_time, s.message_count, s.summary
|
|
405
|
+
FROM sessions s
|
|
406
|
+
JOIN sessions_fts f ON f.session_id = s.id
|
|
407
|
+
WHERE sessions_fts MATCH $query
|
|
408
|
+
ORDER BY rank
|
|
409
|
+
LIMIT $limit
|
|
410
|
+
`;return this.db.prepare(X).all({$query:K,$limit:Z}).map((G)=>this.rowToSession(G))}}var E0=()=>{};class T0{db;findByIdStmt;findBySessionStmt;existsStmt;insertStmt;constructor($){this.db=$,this.findByIdStmt=$.prepare(`SELECT id, session_id, role, content, timestamp, tool_use_ids
|
|
411
|
+
FROM messages_meta
|
|
412
|
+
WHERE id = ?`),this.findBySessionStmt=$.prepare(`SELECT id, session_id, role, content, timestamp, tool_use_ids
|
|
413
|
+
FROM messages_meta
|
|
414
|
+
WHERE session_id = ?
|
|
415
|
+
ORDER BY timestamp ASC`),this.existsStmt=$.prepare("SELECT id FROM messages_meta WHERE id = ?"),this.insertStmt=$.prepare(`INSERT OR IGNORE INTO messages_meta (id, session_id, role, content, timestamp, tool_use_ids)
|
|
416
|
+
VALUES ($id, $session_id, $role, $content, $timestamp, $tool_use_ids)`)}async findById($){let Z=this.findByIdStmt.get($);if(!Z)return null;return this.rowToMessage(Z)}async findBySession($){return this.findBySessionStmt.all($).map((K)=>this.rowToMessage(K))}async save($,Z){this.insertStmt.run({$id:$.id,$session_id:Z,$role:$.role,$content:$.content,$timestamp:$.timestamp.toISOString(),$tool_use_ids:$.toolUses.length>0?JSON.stringify($.toolUses):null})}async saveMany($,Z){let X={inserted:0,skipped:0,errors:[]};for(let Y=0;Y<$.length;Y+=100){let Q=$.slice(Y,Y+100);this.db.transaction((_)=>{for(let{message:J,sessionId:H}of _)try{if(this.existsStmt.get(J.id)){X.skipped++;continue}this.insertStmt.run({$id:J.id,$session_id:H,$role:J.role,$content:J.content,$timestamp:J.timestamp.toISOString(),$tool_use_ids:J.toolUses.length>0?JSON.stringify(J.toolUses):null}),X.inserted++}catch(V){X.skipped++,X.errors.push({id:J.id,reason:A(V)})}}).immediate(Q),Z?.onProgress?.({inserted:X.inserted,total:$.length})}return X}rowToMessage($){let Z=$.tool_use_ids?JSON.parse($.tool_use_ids):void 0;return W0.create({id:$.id,role:$.role,content:$.content,timestamp:new Date($.timestamp),toolUseIds:Z})}}var h$=U(()=>{S$()});class d0{findByIdStmt;findBySessionPathStmt;findPendingStmt;saveStmt;constructor($){this.findByIdStmt=$.prepare(`
|
|
417
|
+
SELECT id, session_path, started_at, status, completed_at,
|
|
418
|
+
messages_extracted, error_message, file_mtime, file_size
|
|
419
|
+
FROM extraction_state
|
|
420
|
+
WHERE id = $id
|
|
421
|
+
`),this.findBySessionPathStmt=$.prepare(`
|
|
422
|
+
SELECT id, session_path, started_at, status, completed_at,
|
|
423
|
+
messages_extracted, error_message, file_mtime, file_size
|
|
424
|
+
FROM extraction_state
|
|
425
|
+
WHERE session_path = $sessionPath
|
|
426
|
+
`),this.findPendingStmt=$.prepare(`
|
|
427
|
+
SELECT id, session_path, started_at, status, completed_at,
|
|
428
|
+
messages_extracted, error_message, file_mtime, file_size
|
|
429
|
+
FROM extraction_state
|
|
430
|
+
WHERE status IN ('pending', 'in_progress')
|
|
431
|
+
ORDER BY started_at ASC
|
|
432
|
+
`),this.saveStmt=$.prepare(`
|
|
433
|
+
INSERT OR REPLACE INTO extraction_state
|
|
434
|
+
(id, session_path, started_at, status, completed_at,
|
|
435
|
+
messages_extracted, error_message, file_mtime, file_size)
|
|
436
|
+
VALUES
|
|
437
|
+
($id, $sessionPath, $startedAt, $status, $completedAt,
|
|
438
|
+
$messagesExtracted, $errorMessage, $fileMtime, $fileSize)
|
|
439
|
+
`)}rowToExtractionState($){return $0.create({id:$.id,sessionPath:$.session_path,startedAt:new Date($.started_at),status:$.status,completedAt:$.completed_at?new Date($.completed_at):void 0,messagesExtracted:$.messages_extracted,errorMessage:$.error_message??void 0,fileMtime:$.file_mtime?new Date($.file_mtime):void 0,fileSize:$.file_size??void 0})}async findById($){let Z=this.findByIdStmt.get({$id:$});if(!Z)return null;return this.rowToExtractionState(Z)}async findBySessionPath($){let Z=this.findBySessionPathStmt.get({$sessionPath:$});if(!Z)return null;return this.rowToExtractionState(Z)}async findPending(){return this.findPendingStmt.all().map((Z)=>this.rowToExtractionState(Z))}async save($){this.saveStmt.run({$id:$.id,$sessionPath:$.sessionPath,$startedAt:$.startedAt.toISOString(),$status:$.status,$completedAt:$.completedAt?.toISOString()??null,$messagesExtracted:$.messagesExtracted,$errorMessage:$.errorMessage??null,$fileMtime:$.fileMtime?.toISOString()??null,$fileSize:$.fileSize??null})}}var u5=U(()=>{HZ()});class p0{db;findByIdStmt;findBySessionStmt;insertStmt;constructor($){this.db=$,this.findByIdStmt=$.prepare(`SELECT id, session_id, name, input, timestamp, status, result
|
|
440
|
+
FROM tool_uses
|
|
441
|
+
WHERE id = ?`),this.findBySessionStmt=$.prepare(`SELECT id, session_id, name, input, timestamp, status, result
|
|
442
|
+
FROM tool_uses
|
|
443
|
+
WHERE session_id = ?
|
|
444
|
+
ORDER BY timestamp ASC`),this.insertStmt=$.prepare(`INSERT OR IGNORE INTO tool_uses
|
|
445
|
+
(id, session_id, name, input, timestamp, status, result)
|
|
446
|
+
VALUES ($id, $session_id, $name, $input, $timestamp, $status, $result)`)}async findById($){let Z=this.findByIdStmt.get($);if(!Z)return null;return this.rowToEntity(Z)}async findBySession($){return this.findBySessionStmt.all($).map((K)=>this.rowToEntity(K))}async save($,Z){this.insertStmt.run({$id:$.id,$session_id:Z,$name:$.name,$input:JSON.stringify($.input),$timestamp:$.timestamp.toISOString(),$status:$.status,$result:$.result??null})}async saveMany($,Z){let X={inserted:0,skipped:0,errors:[]};for(let Y=0;Y<$.length;Y+=100){let Q=$.slice(Y,Y+100);this.db.transaction((_)=>{for(let{toolUse:J,sessionId:H}of _)try{if(this.insertStmt.run({$id:J.id,$session_id:H,$name:J.name,$input:JSON.stringify(J.input),$timestamp:J.timestamp.toISOString(),$status:J.status,$result:J.result??null}).changes>0)X.inserted++;else X.skipped++}catch(V){X.skipped++,X.errors.push({id:J.id,reason:A(V)})}}).immediate(Q),Z?.onProgress?.({inserted:X.inserted,total:$.length})}return X}rowToEntity($){return z0.create({id:$.id,name:$.name,input:JSON.parse($.input),timestamp:new Date($.timestamp),status:$.status,result:$.result??void 0})}}var a9=U(()=>{VZ()});class g${db;findBySourceStmt;findByTargetStmt;insertStmt;constructor($){this.db=$,this.findBySourceStmt=$.prepare(`
|
|
447
|
+
SELECT source_type, source_id, target_type, target_id, relationship, weight
|
|
448
|
+
FROM links
|
|
449
|
+
WHERE source_type = $sourceType AND source_id = $sourceId
|
|
450
|
+
`),this.findByTargetStmt=$.prepare(`
|
|
451
|
+
SELECT source_type, source_id, target_type, target_id, relationship, weight
|
|
452
|
+
FROM links
|
|
453
|
+
WHERE target_type = $targetType AND target_id = $targetId
|
|
454
|
+
`),this.insertStmt=$.prepare(`
|
|
455
|
+
INSERT OR REPLACE INTO links
|
|
456
|
+
(source_type, source_id, target_type, target_id, relationship, weight)
|
|
457
|
+
VALUES
|
|
458
|
+
($sourceType, $sourceId, $targetType, $targetId, $relationship, $weight)
|
|
459
|
+
`)}rowToLink($){return $$.create({sourceType:$.source_type,sourceId:$.source_id,targetType:$.target_type,targetId:$.target_id,relationship:$.relationship,weight:$.weight})}async findBySource($,Z){return this.findBySourceStmt.all({$sourceType:$,$sourceId:Z}).map((X)=>this.rowToLink(X))}async findByTarget($,Z){return this.findByTargetStmt.all({$targetType:$,$targetId:Z}).map((X)=>this.rowToLink(X))}async findRelated($,Z,K=2){return(await this.findRelatedWithHops($,Z,K)).map((Y)=>Y.link)}async findRelatedWithHops($,Z,K=2){return this.db.prepare(`
|
|
460
|
+
WITH RECURSIVE related(
|
|
461
|
+
source_type, source_id, target_type, target_id,
|
|
462
|
+
relationship, weight, hop, path
|
|
463
|
+
) AS (
|
|
464
|
+
-- Base case: direct connections (1-hop)
|
|
465
|
+
SELECT
|
|
466
|
+
source_type, source_id, target_type, target_id,
|
|
467
|
+
relationship, weight, 1 as hop,
|
|
468
|
+
source_type || ':' || source_id || '->' || target_type || ':' || target_id as path
|
|
469
|
+
FROM links
|
|
470
|
+
WHERE source_type = $entityType AND source_id = $entityId
|
|
471
|
+
|
|
472
|
+
UNION ALL
|
|
473
|
+
|
|
474
|
+
-- Recursive case: next level connections
|
|
475
|
+
SELECT
|
|
476
|
+
l.source_type, l.source_id, l.target_type, l.target_id,
|
|
477
|
+
l.relationship, l.weight * r.weight, r.hop + 1,
|
|
478
|
+
r.path || '->' || l.target_type || ':' || l.target_id
|
|
479
|
+
FROM links l
|
|
480
|
+
JOIN related r ON l.source_type = r.target_type AND l.source_id = r.target_id
|
|
481
|
+
WHERE r.hop < $maxHops
|
|
482
|
+
-- Prevent cycles: don't revisit nodes in current path
|
|
483
|
+
AND r.path NOT LIKE '%' || l.target_type || ':' || l.target_id || '%'
|
|
484
|
+
)
|
|
485
|
+
SELECT DISTINCT source_type, source_id, target_type, target_id, relationship, weight, hop
|
|
486
|
+
FROM related
|
|
487
|
+
ORDER BY hop ASC, weight DESC
|
|
488
|
+
`).all({$entityType:$,$entityId:Z,$maxHops:K}).map((G)=>({link:this.rowToLink(G),hop:G.hop}))}async save($){this.insertStmt.run({$sourceType:$.sourceType,$sourceId:$.sourceId,$targetType:$.targetType,$targetId:$.targetId,$relationship:$.relationship,$weight:$.weight})}async saveMany($){this.db.transaction(()=>{for(let K of $)this.insertStmt.run({$sourceType:K.sourceType,$sourceId:K.sourceId,$targetType:K.targetType,$targetId:K.targetId,$relationship:K.relationship,$weight:K.weight})}).immediate()}}var d5=U(()=>{q9()});var i9=U(()=>{k$()});var p5={};w(p5,{EmbeddingRepository:()=>D0});class D0{db;constructor($){this.db=$}findUnembedded($){return this.db.prepare(`
|
|
489
|
+
SELECT m.rowid AS rowid, m.content AS content
|
|
490
|
+
FROM messages_meta m
|
|
491
|
+
LEFT JOIN embedding_state es ON m.rowid = es.message_id
|
|
492
|
+
WHERE es.message_id IS NULL
|
|
493
|
+
ORDER BY m.rowid ASC
|
|
494
|
+
LIMIT ?
|
|
495
|
+
`).all($)}storeBatch($,Z,K){let X=this.db.prepare("INSERT INTO message_embeddings(rowid, embedding) VALUES (?, vec_f32(?))"),Y=this.db.prepare("INSERT INTO embedding_state(message_id, embedded_at, model_hash, model_name) VALUES (?, ?, ?, ?)");this.db.transaction((G)=>{let _=new Date().toISOString();for(let J of G)X.run(J.rowid,J.embedding),Y.run(J.rowid,_,Z,K)})($)}getStoredModelHash(){return this.db.prepare("SELECT DISTINCT model_hash FROM embedding_state LIMIT 1").get()?.model_hash??null}getStoredModelName(){return this.db.prepare("SELECT DISTINCT model_name FROM embedding_state WHERE model_name != '' LIMIT 1").get()?.model_name??null}clearAllEmbeddings(){this.db.exec("DELETE FROM message_embeddings"),this.db.exec("DELETE FROM embedding_state")}getEmbeddedCount(){return this.db.prepare("SELECT COUNT(*) as count FROM embedding_state").get()?.count??0}getTotalMessageCount(){return this.db.prepare("SELECT COUNT(*) as count FROM messages_meta").get()?.count??0}vectorKnnSearch($,Z){if(Z<=0)return[];return this.db.prepare(`
|
|
496
|
+
SELECT rowid, distance
|
|
497
|
+
FROM message_embeddings
|
|
498
|
+
WHERE embedding MATCH ?
|
|
499
|
+
ORDER BY distance
|
|
500
|
+
LIMIT ?
|
|
501
|
+
`).all($,Z)}getStoredEmbeddingDimensions(){let $=this.db.prepare("SELECT COUNT(*) as count FROM message_embeddings").get();if(!$||$.count===0)return null;let Z=this.db.prepare("SELECT embedding FROM message_embeddings LIMIT 1").get();if(!Z||!Z.embedding)return null;return Z.embedding.byteLength/4}recreateVecTable($){this.db.exec("DROP TABLE IF EXISTS message_embeddings"),this.db.exec(`CREATE VIRTUAL TABLE message_embeddings USING vec0(
|
|
502
|
+
embedding float[${$}]
|
|
503
|
+
)`),this.db.exec("DELETE FROM embedding_state")}}class PZ{db;constructor($){this.db=$}async findByPath($){let Z=this.db.prepare("SELECT * FROM memory_files WHERE file_path = ?").get($);return Z?this.toEntity(Z):null}async findByType($){return this.db.prepare("SELECT * FROM memory_files WHERE file_type = ? ORDER BY last_indexed_at DESC").all($).map((K)=>this.toEntity(K))}async findByProject($){return this.db.prepare("SELECT * FROM memory_files WHERE project_encoded = ? ORDER BY file_path").all($).map((K)=>this.toEntity(K))}async save($){this.db.prepare(l5).run($.filePath,$.fileType,$.projectEncoded??null,$.content,$.contentHash,$.lastIndexedAt.toISOString())}async saveMany($){let Z=this.db.prepare(l5);this.db.transaction(()=>{for(let X of $)Z.run(X.filePath,X.fileType,X.projectEncoded??null,X.content,X.contentHash,X.lastIndexedAt.toISOString())})()}async searchContent($,Z=20){let K=u0($);if(!K)return[];return this.db.prepare(`
|
|
504
|
+
SELECT m.* FROM memory_files m
|
|
505
|
+
JOIN memory_files_fts f ON f.rowid = m.id
|
|
506
|
+
WHERE memory_files_fts MATCH ?
|
|
507
|
+
ORDER BY rank
|
|
508
|
+
LIMIT ?
|
|
509
|
+
`).all(K,Z).map((Y)=>this.toEntity(Y))}async findCrossProjectLearnings($,Z=20){if($)return this.db.prepare(`SELECT * FROM memory_files
|
|
510
|
+
WHERE file_type = 'learnings'
|
|
511
|
+
AND content LIKE '%Applies to: cross-project%'
|
|
512
|
+
AND (project_encoded IS NULL OR project_encoded != ?)
|
|
513
|
+
ORDER BY last_indexed_at DESC
|
|
514
|
+
LIMIT ?`).all($,Z).map((Y)=>this.toEntity(Y));return this.db.prepare(`SELECT * FROM memory_files
|
|
515
|
+
WHERE file_type = 'learnings'
|
|
516
|
+
AND content LIKE '%Applies to: cross-project%'
|
|
517
|
+
ORDER BY last_indexed_at DESC
|
|
518
|
+
LIMIT ?`).all(Z).map((X)=>this.toEntity(X))}toEntity($){return m0.create({id:$.id,filePath:$.file_path,fileType:$.file_type,projectEncoded:$.project_encoded??void 0,content:$.content,contentHash:$.content_hash,lastIndexedAt:new Date($.last_indexed_at),createdAt:new Date($.created_at)})}}var l5=`
|
|
519
|
+
INSERT INTO memory_files (file_path, file_type, project_encoded, content, content_hash, last_indexed_at)
|
|
520
|
+
VALUES (?, ?, ?, ?, ?, ?)
|
|
521
|
+
ON CONFLICT(file_path) DO UPDATE SET
|
|
522
|
+
file_type = excluded.file_type,
|
|
523
|
+
project_encoded = excluded.project_encoded,
|
|
524
|
+
content = excluded.content,
|
|
525
|
+
content_hash = excluded.content_hash,
|
|
526
|
+
last_indexed_at = excluded.last_indexed_at
|
|
527
|
+
`;var r9=U(()=>{WZ()});var n5={};w(n5,{SqliteFrictionRepository:()=>k0});class k0{db;constructor($){this.db=$}async save($){let Z=this.db.prepare(`
|
|
528
|
+
INSERT INTO friction_log (description, severity, category, tool, tags, status, context, source_project, logged_at, resolved_at, resolution, last_reviewed_at)
|
|
529
|
+
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)
|
|
530
|
+
`).run($.description,$.severity,$.category,$.tool,$.tags?JSON.stringify($.tags):null,$.status,$.context??null,$.sourceProject??null,$.loggedAt.toISOString(),$.resolvedAt?.toISOString()??null,$.resolution??null,$.lastReviewedAt?.toISOString()??null);return x0.create({id:Number(Z.lastInsertRowid),description:$.description,severity:$.severity,category:$.category,status:$.status,tool:$.tool,tags:$.tags,lastReviewedAt:$.lastReviewedAt,context:$.context,sourceProject:$.sourceProject,loggedAt:$.loggedAt,resolvedAt:$.resolvedAt,resolution:$.resolution})}async findById($){let Z=this.db.prepare("SELECT * FROM friction_log WHERE id = ?").get($);return Z?this.toEntity(Z):null}async findOpen(){return this.db.prepare("SELECT * FROM friction_log WHERE status = 'open' ORDER BY logged_at DESC").all().map((Z)=>this.toEntity(Z))}async findAll($){let Z=[],K=[];if($?.status)Z.push("status = ?"),K.push($.status);if($?.category)Z.push("category = ?"),K.push($.category);if($?.tool)Z.push("tool = ?"),K.push($.tool);if($?.sourceProject)Z.push("source_project = ?"),K.push($.sourceProject);let X=Z.length>0?`WHERE ${Z.join(" AND ")}`:"",Y=$?.limit??100;K.push(Y);let Q=`SELECT * FROM friction_log ${X} ORDER BY logged_at DESC LIMIT ?`;return this.db.prepare(Q).all(...K).map((_)=>this.toEntity(_))}async resolve($,Z){if(this.db.prepare("UPDATE friction_log SET status = 'resolved', resolution = ?, resolved_at = ? WHERE id = ?").run(Z,new Date().toISOString(),$).changes===0)throw Error(`Friction entry with id ${$} not found`)}async updateStatus($,Z){if(this.db.prepare("UPDATE friction_log SET status = ? WHERE id = ?").run(Z,$).changes===0)throw Error(`Friction entry with id ${$} not found`)}async getStats(){let $=this.db.prepare(`
|
|
531
|
+
SELECT
|
|
532
|
+
COUNT(*) as total,
|
|
533
|
+
COALESCE(SUM(CASE WHEN status = 'open' THEN 1 ELSE 0 END), 0) as open_count,
|
|
534
|
+
COALESCE(SUM(CASE WHEN status = 'resolved' THEN 1 ELSE 0 END), 0) as resolved_count,
|
|
535
|
+
COALESCE(SUM(CASE WHEN status = 'wont-fix' THEN 1 ELSE 0 END), 0) as wont_fix_count,
|
|
536
|
+
AVG(CASE WHEN resolved_at IS NOT NULL
|
|
537
|
+
THEN julianday(resolved_at) - julianday(logged_at) END) as avg_resolve_days
|
|
538
|
+
FROM friction_log
|
|
539
|
+
`).get(),Z=this.db.prepare("SELECT severity, COUNT(*) as count FROM friction_log GROUP BY severity").all(),K={low:0,medium:0,high:0,critical:0};for(let H of Z)K[H.severity]=H.count;let X=this.db.prepare("SELECT category, COUNT(*) as count FROM friction_log GROUP BY category").all(),Y={};for(let H of X)Y[H.category]=H.count;let Q=this.db.prepare("SELECT tool, COUNT(*) as count FROM friction_log GROUP BY tool").all(),G={};for(let H of Q)G[H.tool]=H.count;let _=this.db.prepare(`
|
|
540
|
+
SELECT id, description,
|
|
541
|
+
julianday('now') - julianday(logged_at) as days_open
|
|
542
|
+
FROM friction_log
|
|
543
|
+
WHERE status = 'open'
|
|
544
|
+
ORDER BY logged_at ASC
|
|
545
|
+
LIMIT 1
|
|
546
|
+
`).get(),J=_?{id:_.id,description:_.description,daysOpen:Math.floor(_.days_open)}:null;return{total:$.total,open:$.open_count,resolved:$.resolved_count,wontFix:$.wont_fix_count,bySeverity:K,byCategory:Y,byTool:G,meanTimeToResolve:$.avg_resolve_days??null,oldestOpen:J}}async getWeeklyTrends($){let Z=[],K=new Date;for(let _=$-1;_>=0;_--){let J=new Date(K);J.setDate(J.getDate()-_*7);let H=J.getFullYear(),V=new Date(H,0,1),B=Math.ceil((J.getTime()-V.getTime())/86400000),z=Math.ceil((B+V.getDay())/7),W=`${H}-W${String(z).padStart(2,"0")}`;Z.push(W)}let X=this.db.prepare(`
|
|
547
|
+
SELECT strftime('%Y-W', logged_at) || printf('%02d', CAST(strftime('%W', logged_at) AS INTEGER)) as week,
|
|
548
|
+
COUNT(*) as count
|
|
549
|
+
FROM friction_log
|
|
550
|
+
WHERE logged_at >= ?
|
|
551
|
+
GROUP BY week
|
|
552
|
+
`).all(new Date(K.getTime()-$*7*86400000).toISOString()),Y=new Map(X.map((_)=>[_.week,_.count])),Q=this.db.prepare(`
|
|
553
|
+
SELECT strftime('%Y-W', resolved_at) || printf('%02d', CAST(strftime('%W', resolved_at) AS INTEGER)) as week,
|
|
554
|
+
COUNT(*) as count
|
|
555
|
+
FROM friction_log
|
|
556
|
+
WHERE resolved_at IS NOT NULL AND resolved_at >= ?
|
|
557
|
+
GROUP BY week
|
|
558
|
+
`).all(new Date(K.getTime()-$*7*86400000).toISOString()),G=new Map(Q.map((_)=>[_.week,_.count]));return Z.map((_)=>({week:_,newCount:Y.get(_)??0,resolvedCount:G.get(_)??0}))}async markReviewed($,Z){this.db.prepare("UPDATE friction_log SET last_reviewed_at = ? WHERE tool = ? AND status = 'open'").run(Z.toISOString(),$)}async findPatterns($){let Z=this.db.prepare(`
|
|
559
|
+
SELECT tool, category, COUNT(*) as count
|
|
560
|
+
FROM friction_log
|
|
561
|
+
WHERE status = 'open'
|
|
562
|
+
GROUP BY tool, category
|
|
563
|
+
HAVING COUNT(*) >= ?
|
|
564
|
+
ORDER BY count DESC
|
|
565
|
+
`).all($),K=[];for(let X of Z){let Y=this.db.prepare("SELECT * FROM friction_log WHERE tool = ? AND category = ? AND status = 'open'").all(X.tool,X.category);K.push({tool:X.tool,category:X.category,count:X.count,entries:Y.map((Q)=>this.toEntity(Q))})}return K}async deleteByPattern($){return this.db.prepare("DELETE FROM friction_log WHERE description LIKE $pattern").run({$pattern:$}),this.db.query("SELECT changes() as count").get().count}toEntity($){return x0.create({id:$.id,description:$.description,severity:$.severity,category:$.category,status:$.status,tool:$.tool,tags:$.tags?JSON.parse($.tags):void 0,lastReviewedAt:$.last_reviewed_at?new Date($.last_reviewed_at):void 0,context:$.context??void 0,sourceProject:$.source_project??void 0,loggedAt:new Date($.logged_at),resolvedAt:$.resolved_at?new Date($.resolved_at):void 0,resolution:$.resolution??void 0})}}var EZ=U(()=>{BZ()});var a5=()=>{};var i5={};w(i5,{SqliteFactRepository:()=>l0});class l0{db;constructor($){this.db=$}async findById($){let Z=this.db.prepare("SELECT * FROM facts WHERE id = ?").get($);if(!Z)return null;return this.toEntity(Z)}async findByUuid($){let Z=this.db.prepare("SELECT * FROM facts WHERE uuid = ?").get($);if(!Z)return null;return this.toEntity(Z)}async findByProject($){return this.db.prepare("SELECT * FROM facts WHERE project = ? ORDER BY observed_at DESC").all($).map((K)=>this.toEntity(K))}async findRecent($){return this.db.prepare("SELECT * FROM facts ORDER BY observed_at DESC LIMIT ?").all($).map((K)=>this.toEntity(K))}async save($){let Z=$.metadata?JSON.stringify($.metadata):null,K=await this.findByUuid($.uuid);if(K)return this.db.prepare(`
|
|
566
|
+
UPDATE facts
|
|
567
|
+
SET type = ?, project = ?, content = ?, metadata = ?, observed_at = ?, superseded_at = ?, superseded_by = ?, updated_at = datetime('now')
|
|
568
|
+
WHERE uuid = ?
|
|
569
|
+
`).run($.type,$.project,$.content,Z,$.observedAt.toISOString(),$.supersededAt?$.supersededAt.toISOString():null,$.supersededBy,$.uuid),$.withId(K.id);else{let X=this.db.prepare(`
|
|
570
|
+
INSERT INTO facts (
|
|
571
|
+
uuid, type, project, content, metadata, observed_at, superseded_at, superseded_by
|
|
572
|
+
) VALUES (?, ?, ?, ?, ?, ?, ?, ?)
|
|
573
|
+
`).run($.uuid,$.type,$.project,$.content,Z,$.observedAt.toISOString(),$.supersededAt?$.supersededAt.toISOString():null,$.supersededBy);return $.withId(Number(X.lastInsertRowid))}}async saveMany($){let Z=[];return this.db.transaction(()=>{for(let X of $){let Y=X.metadata?JSON.stringify(X.metadata):null,Q=this.db.prepare("SELECT id FROM facts WHERE uuid = ?").get(X.uuid);if(Q)this.db.prepare(`
|
|
574
|
+
UPDATE facts
|
|
575
|
+
SET type = ?, project = ?, content = ?, metadata = ?, observed_at = ?, superseded_at = ?, superseded_by = ?, updated_at = datetime('now')
|
|
576
|
+
WHERE uuid = ?
|
|
577
|
+
`).run(X.type,X.project,X.content,Y,X.observedAt.toISOString(),X.supersededAt?X.supersededAt.toISOString():null,X.supersededBy,X.uuid),Z.push(X.withId(Q.id));else{let G=this.db.prepare(`
|
|
578
|
+
INSERT INTO facts (
|
|
579
|
+
uuid, type, project, content, metadata, observed_at, superseded_at, superseded_by
|
|
580
|
+
) VALUES (?, ?, ?, ?, ?, ?, ?, ?)
|
|
581
|
+
`).run(X.uuid,X.type,X.project,X.content,Y,X.observedAt.toISOString(),X.supersededAt?X.supersededAt.toISOString():null,X.supersededBy);Z.push(X.withId(Number(G.lastInsertRowid)))}}})(),Z}async search($,Z=20){return this.db.prepare(`
|
|
582
|
+
SELECT f.* FROM facts f
|
|
583
|
+
JOIN facts_fts fts ON f.id = fts.rowid
|
|
584
|
+
WHERE facts_fts MATCH ?
|
|
585
|
+
ORDER BY f.observed_at DESC
|
|
586
|
+
LIMIT ?
|
|
587
|
+
`).all($,Z).map((X)=>this.toEntity(X))}async superseded($,Z,K){this.db.prepare("UPDATE facts SET superseded_at = ?, superseded_by = ?, updated_at = datetime('now') WHERE uuid = ?").run(Z.toISOString(),K,$)}async supersede($,Z,K){await this.superseded($,Z,K)}async findAll(){return this.db.prepare("SELECT * FROM facts ORDER BY observed_at DESC").all().map((Z)=>this.toEntity(Z))}async clearAll(){this.db.exec("DELETE FROM facts;")}toEntity($){return A0.create({id:$.id,uuid:$.uuid,type:$.type,project:$.project,content:$.content,metadata:$.metadata?JSON.parse($.metadata):void 0,observedAt:new Date($.observed_at),supersededAt:$.superseded_at?new Date($.superseded_at):null,supersededBy:$.superseded_by??null})}}var X$=U(()=>{v$()});var o9=U(()=>{E0();h$();u5();a9();d5();i9();r9();EZ();a5();X$()});class m${db;constructor($){this.db=$}async search($,Z){let K=Z?.limit??20,X=u0($.value);if(!X)return[];let{sql:Y,params:Q}=this.buildSearchQuery(X,K,Z),_=this.db.prepare(Y).all(...Q);if(_.length===0)return[];return this.normalizeBm25Scores(_).map((H)=>Y0.create({sessionId:H.session_id,messageId:H.id,snippet:H.snippet,score:H.normalizedScore,timestamp:new Date(H.timestamp),role:H.role}))}buildSearchQuery($,Z,K){let X=[$],Y=["messages_fts MATCH ?"],Q=`
|
|
588
|
+
FROM messages_fts f
|
|
589
|
+
JOIN messages_meta m ON f.rowid = m.rowid
|
|
590
|
+
`;if(K?.projectFilter)Q+=`
|
|
591
|
+
JOIN sessions s ON m.session_id = s.id
|
|
592
|
+
`,Y.push("LOWER(s.project_name) LIKE LOWER(?)"),X.push(`%${K.projectFilter}%`);if(K?.roleFilter)if(Array.isArray(K.roleFilter)){let _=K.roleFilter.map(()=>"?").join(", ");Y.push(`m.role IN (${_})`),X.push(...K.roleFilter)}else Y.push("m.role = ?"),X.push(K.roleFilter);if(K?.sessionFilter)Y.push("m.session_id = ?"),X.push(K.sessionFilter);if(K?.sinceDate)Y.push("m.timestamp >= ?"),X.push(K.sinceDate.toISOString());if(K?.beforeDate)Y.push("m.timestamp <= ?"),X.push(K.beforeDate.toISOString());return X.push(Z),{sql:`
|
|
593
|
+
SELECT
|
|
594
|
+
m.id,
|
|
595
|
+
m.session_id,
|
|
596
|
+
m.role,
|
|
597
|
+
m.content,
|
|
598
|
+
m.timestamp,
|
|
599
|
+
bm25(messages_fts) as score,
|
|
600
|
+
snippet(messages_fts, 0, '<mark>', '</mark>', '...', 64) as snippet
|
|
601
|
+
${Q}
|
|
602
|
+
WHERE ${Y.join(" AND ")}
|
|
603
|
+
ORDER BY score
|
|
604
|
+
LIMIT ?
|
|
605
|
+
`,params:X}}normalizeBm25Scores($){if($.length===0)return[];let Z=$[0];if($.length===1&&Z)return[{...Z,normalizedScore:1}];let K=$.map((G)=>G.score),X=Math.min(...K),Y=Math.max(...K);if(X===Y)return $.map((G)=>({...G,normalizedScore:1}));let Q=Y-X;return $.map((G)=>({...G,normalizedScore:(Y-G.score)/Q}))}}var r5=()=>{};class c${db;fts5Service;embeddingRepo;providerFactory;config;sqliteVecAvailable;lastSearchMeta=null;constructor($){this.db=$.db,this.fts5Service=$.fts5Service,this.embeddingRepo=$.embeddingRepo,this.providerFactory=$.providerFactory,this.config=$.config,this.sqliteVecAvailable=$.sqliteVecAvailable}getLastSearchMeta(){return this.lastSearchMeta}async search($,Z){let K=performance.now(),X=this.embeddingRepo.getEmbeddedCount(),Y=this.embeddingRepo.getTotalMessageCount(),Q=Y>0?X/Y:0,G=this.sqliteVecAvailable&&X>0,_={fts:!0,vector:G,hybrid:G},J=this.resolveMode(Z?.mode,X),H=!1,V,B;try{switch(J.effectiveMode){case"fts":B=await this.ftsSearch($,Z);break;case"vector":B=await this.vectorSearch($,Z);break;case"hybrid":{let I=await this.hybridSearch($,Z);if(B=I.results,I.degraded)H=!0,V=I.degradationReason}break}}catch(I){if(J.effectiveMode!=="vector"&&!(I instanceof R))B=await this.ftsSearch($,Z),H=!0,V="provider_failure";else throw I}B=this.applyDecayToResults(B,Z);let z=J.degraded||H,W=V??(J.degraded?J.reason:void 0),N=z&&!J.degraded?"fts":J.effectiveMode,q=performance.now()-K;return this.lastSearchMeta={mode:N,modeReason:z?W??J.reason:J.reason,degraded:z,degradationReason:z?W:void 0,embeddingCoverage:Q,capabilities:_,timingMs:q},B}resolveMode($,Z=0){let K=this.config.search?.defaultMode??"auto",X=$??K;if(X==="fts")return{effectiveMode:"fts",degraded:!1,reason:"explicit"};if(X==="vector"){if(!this.sqliteVecAvailable)throw new R(T.VECTOR_UNAVAILABLE,"Vector search requires sqlite-vec extension",{suggestion:"Run 'memory doctor' to check extension status"});if(Z===0)throw new R(T.VECTOR_UNAVAILABLE,"No embeddings found in database",{suggestion:"Run 'memory sync --embed' to generate embeddings"});return{effectiveMode:"vector",degraded:!1,reason:"explicit"}}if(X==="hybrid"){if(!this.sqliteVecAvailable||Z===0)return{effectiveMode:"fts",degraded:!0,reason:!this.sqliteVecAvailable?"sqlite_vec_unavailable":"no_embeddings"};return{effectiveMode:"hybrid",degraded:!1,reason:"explicit"}}if(!this.sqliteVecAvailable||Z===0)return{effectiveMode:"fts",degraded:!1,reason:"no_embeddings"};return{effectiveMode:"hybrid",degraded:!1,reason:"auto_hybrid"}}applyDecayToResults($,Z){if(!(this.config.search?.temporalDecay?.enabled!==!1&&!Z?.noDecay)||$.length===0)return $;let X=this.config.search?.temporalDecay?.halfLifeDays??30,Q=new Date().getTime(),G=86400000,_=$.map((J)=>{let H=(Q-J.timestamp.getTime())/G,V=Math.pow(0.5,H/X),B=Math.max(0,Math.min(1,J.score*V));return{result:J,decayedScore:B}});return _.sort((J,H)=>H.decayedScore-J.decayedScore),_.map(({result:J,decayedScore:H})=>Y0.create({sessionId:J.sessionId,messageId:J.messageId,snippet:J.snippet,score:H,timestamp:J.timestamp,role:J.role,source:J.source,rawScores:J.rawScores}))}async ftsSearch($,Z){return(await this.fts5Service.search($,Z)).map((X)=>Y0.create({sessionId:X.sessionId,messageId:X.messageId,snippet:X.snippet,score:X.score,timestamp:X.timestamp,role:X.role,source:"fts",rawScores:{bm25:X.score}}))}async getProvider($){try{let Z=this.providerFactory.createFromConfig(this.config);if(!Z){if($)throw new R(T.VECTOR_UNAVAILABLE,"Embedding provider is disabled in configuration");return null}if(!Z.isReady())await Z.initialize();return Z}catch(Z){if($){if(Z instanceof R)throw Z;throw new R(T.VECTOR_UNAVAILABLE,`Embedding provider failed to initialize: ${A(Z)}`)}return null}}async embedQuery($,Z){return(await Z.embed($)).embedding}checkDimensionMismatch($){if(this.embeddingRepo.getEmbeddedCount()===0)return null;let K=this.getStoredEmbeddingDimensions();if(K===null)return null;let X=$.dimensions;if(X!==K)return`dimension_mismatch (stored: ${K}, provider: ${X})`;return null}getStoredEmbeddingDimensions(){try{let $=this.db.prepare("SELECT embedding FROM message_embeddings LIMIT 1").get();if(!$||!$.embedding)return null;let Z=$.embedding;if(Z instanceof Float32Array)return Z.length;if(Z instanceof ArrayBuffer||Z.byteLength!==void 0)return Z.byteLength/4;return null}catch{return null}}async vectorSearch($,Z){let K=await this.getProvider(!0);if(!K)throw new R(T.VECTOR_UNAVAILABLE,"Embedding provider unavailable");let X=this.checkDimensionMismatch(K);if(X)throw new R(T.EMBEDDING_DIMENSION_MISMATCH,`Cannot run vector search: ${X}`);let Y=await this.embedQuery($.value,K),Q=Z?.limit??20,G=Q*o5,_=this.embeddingRepo.vectorKnnSearch(Y,G);if(_.length===0)return[];let J=_.map((B)=>B.rowid),H=this.hydrateByRowids(J),V=[];for(let B=0;B<_.length&&V.length<Q;B++){let z=_[B];if(!z)continue;let W=H.get(z.rowid);if(!W)continue;if(!this.passesFilters(W,Z))continue;let N=this.vectorSnippet(W.content),q=Math.max(0,Math.min(1,1-z.distance/2));V.push(Y0.create({sessionId:W.session_id,messageId:W.id,snippet:N,score:q,timestamp:new Date(W.timestamp),role:W.role,source:"vector",rawScores:{cosine:z.distance}}))}return V}async hybridSearch($,Z){let K=Z?.limit??20,X=K*o5,Y={...Z,limit:X},Q=await this.fts5Service.search($,Y),G=[],_=null,J=!1,H;try{if(_=await this.getProvider(!1),_){let O=this.checkDimensionMismatch(_);if(O)_=null,J=!0,H=O;else{let M=await this.embedQuery($.value,_);G=this.embeddingRepo.vectorKnnSearch(M,X)}}else J=!0,H="provider_unavailable"}catch(O){G=[],J=!0,H=`provider_failure: ${A(O)}`}if(G.length===0&&Q.length>0)return{results:Q.map((M)=>Y0.create({sessionId:M.sessionId,messageId:M.messageId,snippet:M.snippet,score:M.score,timestamp:M.timestamp,role:M.role,source:"fts",rawScores:{bm25:M.score}})).slice(0,K),degraded:J,degradationReason:H};if(Q.length===0&&G.length===0)return{results:[],degraded:J,degradationReason:H};let V=this.buildFtsRowidMap(Q),B=Q.map((O,M)=>({rowid:V.get(O.messageId)??0,rank:M+1,source:"fts",rawScore:O.score})),z=G.map((O,M)=>({rowid:O.rowid,rank:M+1,source:"vector",rawScore:O.distance})),W=x9(B,z,K);if(W.length===0)return{results:[],degraded:J,degradationReason:H};let N=W.map((O)=>O.rowid),q=this.hydrateByRowids(N),I=new Map;for(let O of W){let M=O.sources.some((y)=>y.source==="fts"),x=O.sources.some((y)=>y.source==="vector");if(M&&x)I.set(O.rowid,"both");else if(M)I.set(O.rowid,"fts");else I.set(O.rowid,"vector")}let F=W.map((O)=>({...O,score:O.normalizedScore})),L=[];for(let O of F){let M=q.get(O.rowid);if(!M)continue;if(!this.passesFilters(M,Z))continue;let x=I.get(O.rowid)??"fts",y=Q.find((V0)=>V0.messageId===M.id),J0=y?y.snippet:this.vectorSnippet(M.content),g0=Math.max(0,Math.min(1,O.score)),H0={rrf:O.rrfScore};for(let V0 of O.sources){if(V0.source==="fts")H0.bm25=V0.rawScore;if(V0.source==="vector")H0.cosine=V0.rawScore}L.push(Y0.create({sessionId:M.session_id,messageId:M.id,snippet:J0,score:g0,timestamp:new Date(M.timestamp),role:M.role,source:x,rawScores:H0}))}return{results:L,degraded:J,degradationReason:H}}buildFtsRowidMap($){if($.length===0)return new Map;let Z=$.map((Y)=>Y.messageId),K=Z.map(()=>"?").join(","),X=this.db.prepare(`SELECT rowid, id FROM messages_meta WHERE id IN (${K})`).all(...Z);return new Map(X.map((Y)=>[Y.id,Y.rowid]))}hydrateByRowids($){if($.length===0)return new Map;let Z=$.map(()=>"?").join(","),K=this.db.prepare(`SELECT rowid, id, session_id, content, timestamp, role
|
|
606
|
+
FROM messages_meta
|
|
607
|
+
WHERE rowid IN (${Z})`).all(...$);return new Map(K.map((X)=>[X.rowid,X]))}vectorSnippet($){if($.length<=200)return $;return $.slice(0,200)+"..."}passesFilters($,Z){if(!Z)return!0;if(Z.projectFilter){let K=this.db.prepare("SELECT project_name FROM sessions WHERE id = ?").get($.session_id);if(!K||!K.project_name.toLowerCase().includes(Z.projectFilter.toLowerCase()))return!1}if(Z.roleFilter){if(Array.isArray(Z.roleFilter)){if(!Z.roleFilter.includes($.role))return!1}else if($.role!==Z.roleFilter)return!1}if(Z.sessionFilter&&$.session_id!==Z.sessionFilter)return!1;if(Z.sinceDate){if(new Date($.timestamp)<Z.sinceDate)return!1}if(Z.beforeDate){if(new Date($.timestamp)>Z.beforeDate)return!1}return!0}}var o5=4;var t5=U(()=>{w$()});class Y${db;constructor($){this.db=$}async getStats($=10){let Z=this.db.prepare(`
|
|
608
|
+
SELECT page_size * page_count as size
|
|
609
|
+
FROM pragma_page_count(), pragma_page_size()
|
|
610
|
+
`).get(),K=this.db.prepare(`
|
|
611
|
+
SELECT
|
|
612
|
+
s.project_name as projectName,
|
|
613
|
+
COUNT(DISTINCT s.id) as sessionCount,
|
|
614
|
+
COUNT(m.id) as messageCount
|
|
615
|
+
FROM sessions s
|
|
616
|
+
LEFT JOIN messages_meta m ON m.session_id = s.id
|
|
617
|
+
GROUP BY s.project_name
|
|
618
|
+
ORDER BY sessionCount DESC
|
|
619
|
+
LIMIT ?
|
|
620
|
+
`).all($),X=K.reduce((G,_)=>G+_.sessionCount,0),Y=K.reduce((G,_)=>G+_.messageCount,0),Q=this.db.prepare("SELECT COUNT(*) as totalToolUses FROM tool_uses").get();return{totalSessions:X,totalMessages:Y,totalToolUses:Q?.totalToolUses??0,databaseSizeBytes:Z?.size??0,projectBreakdown:K.map((G)=>({projectName:G.projectName,sessionCount:G.sessionCount,messageCount:G.messageCount}))}}}var s5={};w(s5,{SqliteProjectResolver:()=>G$,SqliteContextService:()=>Q$});class Q${db;constructor($){this.db=$}async getProjectContext($,Z={}){let K=Z.topicsLimit??10,X=Z.toolsLimit??10,Y;if(Z.days){let I=new Date,F=new Date(I.getFullYear(),I.getMonth(),I.getDate());Y=new Date(F.getTime()-(Z.days-1)*24*60*60*1000)}let Q=this.db.prepare(`SELECT DISTINCT project_name, project_path_decoded, project_path_encoded
|
|
621
|
+
FROM sessions
|
|
622
|
+
WHERE LOWER(project_name) = LOWER(?)
|
|
623
|
+
LIMIT 1`).get($)??this.db.prepare(`SELECT project_name, project_path_decoded, project_path_encoded
|
|
624
|
+
FROM sessions
|
|
625
|
+
WHERE project_name LIKE '%' || ? || '%'
|
|
626
|
+
GROUP BY project_name
|
|
627
|
+
ORDER BY COUNT(*) DESC
|
|
628
|
+
LIMIT 1`).get($);if(!Q)return null;let G=Q.project_path_encoded,J=`
|
|
629
|
+
SELECT
|
|
630
|
+
COUNT(DISTINCT s.id) as sessionCount,
|
|
631
|
+
MAX(s.start_time) as lastActivity,
|
|
632
|
+
COUNT(CASE WHEN m.role = 'user' THEN 1 END) as userMessages,
|
|
633
|
+
COUNT(CASE WHEN m.role = 'assistant' THEN 1 END) as assistantMessages
|
|
634
|
+
FROM sessions s
|
|
635
|
+
LEFT JOIN messages_meta m ON m.session_id = s.id
|
|
636
|
+
WHERE s.project_path_encoded = ?
|
|
637
|
+
${Y?"AND s.start_time >= ?":""}
|
|
638
|
+
`,H=Y?this.db.prepare(J).get(G,Y.toISOString()):this.db.prepare(J).get(G);if(!H||H.sessionCount===0)return null;let B=`
|
|
639
|
+
SELECT t.name, COUNT(*) as count
|
|
640
|
+
FROM tool_uses t
|
|
641
|
+
JOIN sessions s ON t.session_id = s.id
|
|
642
|
+
WHERE s.project_path_encoded = ?
|
|
643
|
+
${Y?"AND t.timestamp >= ?":""}
|
|
644
|
+
GROUP BY t.name
|
|
645
|
+
ORDER BY count DESC
|
|
646
|
+
LIMIT ?
|
|
647
|
+
`,z=Y?this.db.prepare(B).all(G,Y.toISOString(),X):this.db.prepare(B).all(G,X),N=`
|
|
648
|
+
SELECT DISTINCT l.target_id as topic
|
|
649
|
+
FROM links l
|
|
650
|
+
${Y?`JOIN sessions s ON l.source_type = 'session' AND l.source_id = s.id
|
|
651
|
+
WHERE s.project_path_encoded = ?
|
|
652
|
+
AND l.target_type = 'topic'
|
|
653
|
+
AND s.start_time >= ?`:`JOIN sessions s ON l.source_type = 'session' AND l.source_id = s.id
|
|
654
|
+
WHERE s.project_path_encoded = ?
|
|
655
|
+
AND l.target_type = 'topic'`}
|
|
656
|
+
ORDER BY l.weight DESC
|
|
657
|
+
LIMIT ?
|
|
658
|
+
`,q=Y?this.db.prepare(N).all(G,Y.toISOString(),K):this.db.prepare(N).all(G,K);return{projectName:Q.project_name,projectPathDecoded:Q.project_path_decoded,sessionCount:H.sessionCount,totalMessages:H.userMessages+H.assistantMessages,userMessages:H.userMessages,assistantMessages:H.assistantMessages,recentTopics:q.map((I)=>I.topic),recentToolUses:z.map((I)=>({name:I.name,count:I.count})),lastActivity:H.lastActivity?new Date(H.lastActivity):null}}}class G${db;constructor($){this.db=$}resolveProjectEncoded($){let Z=this.db.prepare(`SELECT DISTINCT project_path_encoded
|
|
659
|
+
FROM sessions
|
|
660
|
+
WHERE LOWER(project_name) = LOWER(?)
|
|
661
|
+
LIMIT 1`).get($);if(Z)return Z.project_path_encoded;return this.db.prepare(`SELECT project_path_encoded
|
|
662
|
+
FROM sessions
|
|
663
|
+
WHERE project_name LIKE '%' || ? || '%'
|
|
664
|
+
GROUP BY project_path_encoded
|
|
665
|
+
ORDER BY COUNT(*) DESC
|
|
666
|
+
LIMIT 1`).get($)?.project_path_encoded??null}resolveProjectName($){let Z=this.db.prepare(`SELECT DISTINCT project_name
|
|
667
|
+
FROM sessions
|
|
668
|
+
WHERE LOWER(project_name) = LOWER(?)
|
|
669
|
+
LIMIT 1`).get($);if(Z)return Z.project_name;return this.db.prepare(`SELECT project_name
|
|
670
|
+
FROM sessions
|
|
671
|
+
WHERE project_name LIKE '%' || ? || '%'
|
|
672
|
+
GROUP BY project_name
|
|
673
|
+
ORDER BY COUNT(*) DESC
|
|
674
|
+
LIMIT 1`).get($)?.project_name??null}}var e5=U(()=>{r5();t5()});var G0,_$;var t9=U(()=>{G0={local:{model:"Xenova/all-MiniLM-L6-v2",dimensions:384},openai:{model:"text-embedding-3-small",dimensions:1536},ollama:{model:"nomic-embed-text",dimensions:768},"openai-compatible":{model:"text-embedding-3-small",dimensions:1536}},_$={anthropic:"claude-3-5-sonnet-20241022",openai:"gpt-4o",ollama:"llama3","claude-cli":"claude-cli-print","openai-compatible":"gpt-4o"}});var K4={};w(K4,{saveConfig:()=>S0,resolveProviderDefaults:()=>Y1,resolveEmbeddingApiKey:()=>d$,loadConfig:()=>m,getConfigPath:()=>kZ,getConfigDir:()=>n0,PROVIDER_DEFAULTS:()=>X1,DEFAULT_SEARCH_CONFIG:()=>DZ,DEFAULT_REMOTE_SYNC_CONFIG:()=>$4,DEFAULT_LEGACY_MEMORY_FILES_CONFIG:()=>Z4,DEFAULT_EMBEDDING_CONFIG:()=>J$,DEFAULT_CONFIG:()=>u$,DEFAULT_AMBIENT_CONTEXT_CONFIG:()=>e9});import{randomUUID as s9}from"crypto";import{existsSync as $1,mkdirSync as A7,readFileSync as Z1,writeFileSync as N7}from"fs";import{dirname as K1}from"path";function Y1($,Z){let K=$.provider;if(K==="local"||!Z)return $;let X=X1[K],Y={...$};if(!("model"in Z))Y.model=X?.model??$.model;if(!("dimensions"in Z))Y.dimensions=X?.dimensions??$.dimensions;return Y}function d$($,Z){let K=[$.apiKeyEnv,...Z].filter((Y)=>Boolean(Y));for(let Y of K){let Q=process.env[Y];if(Q){let G={apiKey:Q,source:"environment",envVar:Y,deprecatedPlaintext:!1};if($.apiKeyRef)G.ref=$.apiKeyRef;return G}}if($.apiKey){let Y={apiKey:$.apiKey,source:"plaintext-config",deprecatedPlaintext:!0};if($.apiKeyRef)Y.ref=$.apiKeyRef;return Y}let X={source:"missing",deprecatedPlaintext:!1};if($.apiKeyRef)X.ref=$.apiKeyRef;return X}function n0($){if($!==void 0)return K1($);return K$()}function kZ($){if($!==void 0)return $;return m9()}function m($){let Z=kZ($);if(!$1(Z)){let K=process.env.MEMORY_TEST_MACHINE_ID??s9(),X={...u$,machineId:K};try{S0(X,$)}catch{}return X}try{let K=Z1(Z,"utf-8"),X=JSON.parse(K),Y=X.machineId,Q=!1;if(!Y)Y=process.env.MEMORY_TEST_MACHINE_ID??s9(),Q=!0;let G=X.embedding,_={...J$,...G??{}},J={...$4,...X.remoteSync??{}},H={...Z4,...X.legacyMemoryFiles??{}},V={...u$,...X,machineId:Y,remoteSync:J,legacyMemoryFiles:H,embedding:Y1(_,G),search:{...DZ,...X.search??{},temporalDecay:{...DZ.temporalDecay,...X.search?.temporalDecay??{}}},ambientContext:{...e9,...X.ambientContext??{}}};if(Q)try{S0(V,$)}catch{}return V}catch{console.warn("Invalid config.json, using defaults");let K=process.env.MEMORY_TEST_MACHINE_ID??s9();return{...u$,machineId:K}}}function S0($,Z){let K=kZ(Z),X=K1(K);A7(X,{recursive:!0});let Y={};if($1(K))try{let G=Z1(K,"utf-8");Y=JSON.parse(G)}catch{}let Q={...Y,...$};N7(K,JSON.stringify(Q,null,2)+`
|
|
675
|
+
`)}var DZ,e9,$4,Z4,X1,J$,u$;var Z0=U(()=>{p();t9();DZ={defaultMode:"auto",temporalDecay:{enabled:!0,halfLifeDays:30}},e9={enabled:!0,budget:800},$4={enabled:!1,autoPush:!0,autoPull:!0},Z4={enabled:!1},X1={...G0};J$={enabled:!0,provider:"local",model:"Xenova/all-MiniLM-L6-v2",dimensions:384,batchSize:100},u$={autoSync:!0,recoveryOnStartup:!0,syncOnCompaction:!0,timeout:5000,logLevel:"info",logRetentionDays:7,showFailures:!1,embedding:J$,search:DZ,ambientContext:e9,machineId:"",remoteSync:$4,legacyMemoryFiles:Z4}});import{appendFileSync as MG,existsSync as q7,mkdirSync as jG,readFileSync as O7,renameSync as xG,statSync as PG}from"fs";import{dirname as U7,join as L7}from"path";function H$($){if($!==void 0)return U7($);return O0()}function Q1($){if($!==void 0)return $;return L7(O0(),"sync.log")}function V$($=100,Z){let K=Q1(Z);if(!q7(K))return[];try{let Y=O7(K,"utf-8").split(`
|
|
676
|
+
`).filter((G)=>G.trim()!==""),Q=[];for(let G of Y)try{let _=JSON.parse(G);Q.push(_)}catch{continue}return Q.slice(-$)}catch{return[]}}var SZ=U(()=>{p()});var X4=U(()=>{p();L9();i9();h$()});var _1=U(()=>{Z0();SZ();X4()});var J1=U(()=>{SZ()});import{copyFileSync as H1,existsSync as p$,mkdirSync as Y4,readFileSync as T7,writeFileSync as V1}from"fs";import{dirname as Q4,join as G4}from"path";import{homedir as R7}from"os";function W$($){return $?.settingsPath??G4(R7(),".claude","settings.json")}function vZ($){return $?.backupPath??G4(d9(),"settings.json.backup")}function a0($){return $?.hookScriptPath??G4(u9(),"sync-hook.js")}function B$($){let Z=W$($);if(!p$(Z))return{};try{let K=T7(Z,"utf-8");return JSON.parse(K)}catch{return{}}}function W1($){let Z=W$($),K=vZ($);if(!p$(Z))return!1;return Y4(Q4(K),{recursive:!0}),H1(Z,K),!0}function _4($){let Z=W$($),K=vZ($);if(!p$(K))return!1;return Y4(Q4(Z),{recursive:!0}),H1(K,Z),!0}function a$($){let Z=W$($),K=a0($);W1($);let X=B$($),Y=`bun run "${K.replace(/\\/g,"/")}"`;if(X.hooks=X.hooks??{},X.hooks.SessionEnd?.some((G)=>G.hooks.some((_)=>_.command.includes(l$)||_.command.includes(n$))))return{success:!0,message:"Hooks already installed"};return X.hooks.SessionEnd=X.hooks.SessionEnd??[],X.hooks.SessionEnd.push({hooks:[{type:"command",command:Y,timeout:5}]}),X.hooks.PreCompact=X.hooks.PreCompact??[],X.hooks.PreCompact.push({matcher:"auto",hooks:[{type:"command",command:Y,timeout:5}]}),Y4(Q4(Z),{recursive:!0}),V1(Z,JSON.stringify(X,null,2)+`
|
|
677
|
+
`),{success:!0,message:"Hooks installed successfully"}}function i$($){let Z=W$($),K=B$($);if(!K.hooks)return{success:!0,message:"No hooks to uninstall"};if(K.hooks.SessionEnd){if(K.hooks.SessionEnd=K.hooks.SessionEnd.filter((X)=>!X.hooks.some((Y)=>Y.command.includes(l$)||Y.command.includes(n$))),K.hooks.SessionEnd.length===0)delete K.hooks.SessionEnd}if(K.hooks.PreCompact){if(K.hooks.PreCompact=K.hooks.PreCompact.filter((X)=>!X.hooks.some((Y)=>Y.command.includes(l$)||Y.command.includes(n$))),K.hooks.PreCompact.length===0)delete K.hooks.PreCompact}if(Object.keys(K.hooks).length===0)delete K.hooks;return V1(Z,JSON.stringify(K,null,2)+`
|
|
678
|
+
`),{success:!0,message:"Hooks uninstalled successfully"}}function R0($){let Z=B$($),K=a0($),X=vZ($);return{sessionEnd:Z.hooks?.SessionEnd?.some((Y)=>Y.hooks.some((Q)=>Q.command.includes(l$)||Q.command.includes(n$)))??!1,preCompact:Z.hooks?.PreCompact?.some((Y)=>Y.hooks.some((Q)=>Q.command.includes(l$)||Q.command.includes(n$)))??!1,hookScriptExists:p$(K),backupExists:p$(X)}}var l$="memory",n$="memory-nexus";var J4=U(()=>{p()});var z$=U(()=>{Z0();SZ();X4();_1();J1();J4()});class H4{name="transformers-js";model;dimensions;_pipeline=null;constructor($){this.model=$?.model??"Xenova/all-MiniLM-L6-v2",this.dimensions=$?.dimensions??384}async initialize($){if(this._pipeline)return;let{pipeline:Z,env:K}=await import("@huggingface/transformers");K.allowLocalModels=!1;let X={dtype:"q8"};if($)X.progress_callback=(Y)=>{$({status:Y.status==="ready"?"ready":"downloading",file:Y.file??"",loaded:Y.loaded??0,total:Y.total??0})};try{this._pipeline=await Z("feature-extraction",this.model,X)}catch(Y){if(console.warn(`Native ONNX runtime failed: ${A(Y)}`),console.warn("Falling back to WASM backend (slower but universal)"),K.backends?.onnx?.wasm)K.backends.onnx.wasm.numThreads=1;try{this._pipeline=await Z("feature-extraction",this.model,{dtype:"q8",device:"wasm"})}catch(Q){throw Error(`Embedding initialization failed. Native: ${A(Y)}. WASM: ${A(Q)}`)}}}async embed($){if(!this._pipeline)throw Error("Provider not initialized. Call initialize() before embed().");let Z=await this._pipeline($,{pooling:"mean",normalize:!0}),K=new Float32Array(Z.tolist()[0]);return X0.create({embedding:K,model:this.model,dimensions:this.dimensions})}async embedBatch($){let Z=[];for(let K of $)Z.push(await this.embed(K));return Z}isReady(){return this._pipeline!==null}async dispose(){this._pipeline=null}}var B1=()=>{};class CZ{name;model;dimensions;apiKey;baseUrl;_ready=!1;constructor($){this.apiKey=$.apiKey,this.name=$.providerId??"openai",this.model=$.model??"text-embedding-3-small",this.dimensions=$.dimensions??1536,this.baseUrl=$.baseUrl??"https://api.openai.com/v1"}async initialize($){this._ready=!0}async embed($){if(!this._ready)throw Error("Provider not initialized. Call initialize() before embed().");let Z=await fetch(`${this.baseUrl}/embeddings`,{method:"POST",headers:{"Content-Type":"application/json",Authorization:`Bearer ${this.apiKey}`},body:JSON.stringify({model:this.model,input:$,dimensions:this.dimensions})});if(!Z.ok){let Q=await Z.text();throw Error(`OpenAI API error ${Z.status}: ${Q}`)}let X=(await Z.json()).data?.[0];if(!X)throw Error("OpenAI returned empty embeddings response");let Y=new Float32Array(X.embedding);return X0.create({embedding:Y,model:this.model,dimensions:this.dimensions})}async embedBatch($){if(!this._ready)throw Error("Provider not initialized. Call initialize() before embed().");let Z=await fetch(`${this.baseUrl}/embeddings`,{method:"POST",headers:{"Content-Type":"application/json",Authorization:`Bearer ${this.apiKey}`},body:JSON.stringify({model:this.model,input:$,dimensions:this.dimensions})});if(!Z.ok){let Y=await Z.text();throw Error(`OpenAI API error ${Z.status}: ${Y}`)}return[...(await Z.json()).data].sort((Y,Q)=>Y.index-Q.index).map((Y)=>X0.create({embedding:new Float32Array(Y.embedding),model:this.model,dimensions:this.dimensions}))}isReady(){return this._ready}async dispose(){this._ready=!1}}var z1=()=>{};class V4{name="ollama";model;dimensions;baseUrl;_ready=!1;constructor($){this.model=$?.model??"nomic-embed-text",this.dimensions=$?.dimensions??768,this.baseUrl=$?.baseUrl??"http://localhost:11434"}async initialize($){let Z;try{Z=await fetch(`${this.baseUrl}/api/tags`,{method:"GET"})}catch(K){let X=A(K);throw Error(`Cannot reach Ollama server at ${this.baseUrl}. Ensure Ollama is running: ollama serve (${X})`)}if(!Z.ok)throw Error(`Ollama server returned ${Z.status} from ${this.baseUrl}/api/tags`);this._ready=!0}async embed($){if(!this._ready)throw Error("Provider not initialized. Call initialize() before embed().");let Z=await fetch(`${this.baseUrl}/api/embed`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({model:this.model,input:$})});if(!Z.ok){let Q=await Z.text();this.throwWithHint(Z.status,Q)}let X=(await Z.json()).embeddings?.[0];if(!X)throw Error("Ollama returned empty embeddings response");let Y=new Float32Array(X);return X0.create({embedding:Y,model:this.model,dimensions:this.dimensions})}async embedBatch($){if(!this._ready)throw Error("Provider not initialized. Call initialize() before embed().");let Z=await fetch(`${this.baseUrl}/api/embed`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({model:this.model,input:$})});if(!Z.ok){let X=await Z.text();this.throwWithHint(Z.status,X)}return(await Z.json()).embeddings.map((X)=>X0.create({embedding:new Float32Array(X),model:this.model,dimensions:this.dimensions}))}isReady(){return this._ready}async dispose(){this._ready=!1}throwWithHint($,Z){if($===404||Z.includes("not found"))throw Error(`Ollama error ${$}: ${Z}. Model '${this.model}' not found. Run: ollama pull ${this.model}`);throw Error(`Ollama error ${$}: ${Z}`)}}var A1=()=>{};function v0($){return["You are an expert developer assistant. Analyze the following conversation transcript between a user and an AI coding assistant.","Your task is to extract a structured JSON list of key facts that occurred during this conversation.","","Specifically, you should identify and classify facts into these categories:",'1. "decision": Key architectural choices, technology selections, conventions, or design decisions made.','2. "learning": Lessons learned, discoveries about tools, APIs, bugs found, environment specific issues, or workarounds.','3. "preference": User guidelines, rules, stylistic/operational preferences, or explicit constraints.','4. "friction": Pain points, slow processes, build issues, sync locks, file system access issues, command timeouts, or system bottlenecks.','5. "observation": Key metrics, observed state, runtime configurations, or general context findings.',"","For each fact, assign a confidence score between 0.0 and 1.0 based on how explicitly and clearly it was stated or agreed upon in the transcript.",'Provide optional structured "metadata" for additional context (e.g. rationale, severity, file path, system version, etc.).',"","CRITICAL: Your output MUST be a valid JSON array of objects. Do not include any explanation, markdown formatting outside of a JSON code block, or preambles. Output ONLY the JSON.","","Format:","["," {",' "type": "decision" | "learning" | "preference" | "friction" | "observation",',' "content": "Description of the fact",',' "metadata": { "key": "value" },',' "confidence": 0.95'," }","]","","Transcript:",$.map((K)=>`[${K.timestamp.toISOString()}] ${K.role.toUpperCase()}: ${K.content}`).join(`
|
|
679
|
+
|
|
680
|
+
`)].join(`
|
|
681
|
+
`)}function C0($){let Z=$.trim(),K=Z.match(/\[\s*\{[\s\S]*\}\s*\]/),X=K?K[0]:Z;try{let Y=JSON.parse(X);if(!Array.isArray(Y))return[];let Q=[];for(let G of Y){if(typeof G.content!=="string"||G.content.trim()==="")continue;let J=["decision","learning","preference","friction","observation"].includes(G.type)?G.type:"observation",H=typeof G.confidence==="number"?Math.max(0,Math.min(1,G.confidence)):0.8;Q.push({type:J,content:G.content.trim(),metadata:G.metadata&&typeof G.metadata==="object"?G.metadata:void 0,confidence:H})}return Q}catch(Y){return console.error("Failed to parse LLM facts JSON response:",Y),[]}}import F7 from"@anthropic-ai/sdk";class W4{providerId="anthropic";modelName;anthropic;constructor($){this.modelName=$.model??"claude-3-5-sonnet-20241022",this.anthropic=new F7({apiKey:$.apiKey})}async extract($){if($.length===0)return[];let Z=v0($);try{let X=(await this.anthropic.messages.create({model:this.modelName,max_tokens:4000,messages:[{role:"user",content:Z}]})).content[0],Y=X&&"text"in X?X.text:"";return C0(Y)}catch(K){throw console.error("Anthropic fact extraction API failed:",K),Error(`Anthropic API error: ${K.message}`)}}}var N1=()=>{};import{spawn as M7}from"child_process";class B4{providerId="claude-cli";modelName="claude-cli-print";async extract($){if($.length===0)return[];let Z=v0($);return new Promise((K,X)=>{let Y={...process.env};delete Y.CLAUDECODE;let Q=M7("claude",["-p","--output-format","text"],{env:Y,stdio:["pipe","pipe","pipe"]}),G="",_="";Q.stdout.on("data",(J)=>{G+=J.toString()}),Q.stderr.on("data",(J)=>{_+=J.toString()}),Q.on("error",(J)=>{X(Error(`Failed to spawn claude -p: ${J.message}`))}),Q.on("close",(J)=>{if(J===0)K(C0(G));else X(Error(`claude -p exited with code ${J}: ${_.trim()}`))}),Q.stdin.write(Z),Q.stdin.end()})}}var q1=()=>{};class z4{providerId="ollama";modelName;baseUrl;constructor($){this.baseUrl=$.baseUrl??"http://localhost:11434",this.modelName=$.model??"llama3"}async extract($){if($.length===0)return[];let Z=v0($);try{let K=`${this.baseUrl}/api/generate`,X=await fetch(K,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({model:this.modelName,prompt:Z,stream:!1,options:{temperature:0.1}})});if(!X.ok){let G=await X.text();throw Error(`HTTP ${X.status}: ${G}`)}let Q=(await X.json())?.response??"";return C0(Q)}catch(K){throw console.error("Ollama fact extraction API failed:",K),Error(`Ollama API error: ${K.message}`)}}}var O1=()=>{};class yZ{providerId;modelName;apiKey;baseUrl;constructor($){this.apiKey=$.apiKey,this.providerId=$.providerId??"openai",this.modelName=$.model??"gpt-4o",this.baseUrl=$.baseUrl??"https://api.openai.com/v1"}async extract($){if($.length===0)return[];let Z=v0($);try{let K=await fetch(`${this.baseUrl}/chat/completions`,{method:"POST",headers:{"Content-Type":"application/json",Authorization:`Bearer ${this.apiKey}`},body:JSON.stringify({model:this.modelName,messages:[{role:"user",content:Z}],temperature:0.1})});if(!K.ok){let Q=await K.text();throw Error(`HTTP ${K.status}: ${Q}`)}let Y=(await K.json())?.choices?.[0]?.message?.content??"";return C0(Y)}catch(K){throw console.error("OpenAI fact extraction API failed:",K),Error(`OpenAI API error: ${K.message}`)}}}var U1=()=>{};function A$($){return{ready:!0,readyReason:$}}function t$($){return{ready:!1,readyReason:$}}function r$($,Z,K){let X=d$($,Z);if(X.source==="missing")return t$(X.ref?"API key reference configured but not available at runtime; run through a secret injector or set embedding.apiKeyEnv":K);if(X.deprecatedPlaintext)return A$("Using deprecated plaintext config; prefer environment injection or embedding.apiKeyEnv");return A$()}function o$($,Z,K){let X=d$($,Z);if(!X.apiKey)throw Error(`${K} API key is required. Set ${Z.join(" or ")} or configure embedding.apiKeyEnv for runtime injection. apiKeyRef is an opaque reference and is not resolved by memory-nexus.`);return X.apiKey}function L1($,Z){if(!$.baseUrl)throw Error(`openai-compatible ${Z} provider requires embedding.baseUrl`);return $.baseUrl}function j7(){return I1.map(($)=>$.id)}function x7(){return T1.map(($)=>$.id)}function M1($){return`Unsupported embedding provider: "${$}". Supported: ${j7().join(", ")}`}function P7($){return`Unsupported extraction provider: "${$}". Supported: ${x7().join(", ")}`}function j1($){let Z=R1.get($.provider);if(!Z)return t$(M1($.provider));return Z.checkReadiness($)}function x1($){let Z=R1.get($.provider);if(!Z)throw Error(M1($.provider));return Z.create($)}function A4($,Z=process.env){let K=Z.LLM_PROVIDER?.trim();if(K)return K;let X=$.embedding?.provider??"claude-cli";return X==="local"?"claude-cli":X}function P1($,Z,K=process.env){let X=F1.get(Z);if(!X)return"";return K.LLM_MODEL?.trim()||X.defaultModel}function E1($,Z=A4($)){let K=F1.get(Z);if(!K)return t$(P7(Z));return K.checkReadiness($.embedding)}var I1,T1,R1,F1;var wZ=U(()=>{Z0();B1();z1();A1();N1();q1();O1();U1();t9();I1=[{id:"local",defaultModel:G0.local.model,defaultDimensions:G0.local.dimensions,checkReadiness:()=>A$(),create:($)=>new H4({model:$.model,dimensions:$.dimensions})},{id:"openai",defaultModel:G0.openai.model,defaultDimensions:G0.openai.dimensions,checkReadiness:($)=>r$($,["OPENAI_API_KEY"],"API key not available at runtime; set OPENAI_API_KEY or embedding.apiKeyEnv"),create:($)=>new CZ({apiKey:o$($,["OPENAI_API_KEY"],"OpenAI embedding"),model:$.model,dimensions:$.dimensions,baseUrl:$.baseUrl})},{id:"ollama",defaultModel:G0.ollama.model,defaultDimensions:G0.ollama.dimensions,checkReadiness:()=>A$("Server reachability verified at sync time"),create:($)=>new V4({model:$.model,dimensions:$.dimensions,baseUrl:$.baseUrl})},{id:"openai-compatible",defaultModel:G0["openai-compatible"].model,defaultDimensions:G0["openai-compatible"].dimensions,checkReadiness:($)=>{if(!$.baseUrl)return t$("openai-compatible embedding provider requires embedding.baseUrl");return r$($,[],"API key not available at runtime; set embedding.apiKeyEnv for openai-compatible")},create:($)=>new CZ({apiKey:o$($,[],"openai-compatible embedding"),model:$.model,dimensions:$.dimensions,baseUrl:L1($,"embedding"),providerId:"openai-compatible"})}],T1=[{id:"anthropic",defaultModel:_$.anthropic,checkReadiness:($)=>r$($,["ANTHROPIC_API_KEY"],"API key not available at runtime; set ANTHROPIC_API_KEY or embedding.apiKeyEnv"),create:($,Z)=>new W4({apiKey:o$($,["ANTHROPIC_API_KEY"],"Anthropic extraction"),model:Z})},{id:"openai",defaultModel:_$.openai,checkReadiness:($)=>r$($,["OPENAI_API_KEY"],"API key not available at runtime; set OPENAI_API_KEY or embedding.apiKeyEnv"),create:($,Z)=>new yZ({apiKey:o$($,["OPENAI_API_KEY"],"OpenAI extraction"),model:Z})},{id:"ollama",defaultModel:_$.ollama,checkReadiness:()=>A$(),create:($,Z)=>new z4({baseUrl:$.baseUrl,model:Z})},{id:"claude-cli",defaultModel:_$["claude-cli"],checkReadiness:()=>A$(),create:()=>new B4},{id:"openai-compatible",defaultModel:_$["openai-compatible"],checkReadiness:($)=>{if(!$.baseUrl)return t$("openai-compatible extraction provider requires embedding.baseUrl");return r$($,[],"API key not available at runtime; set embedding.apiKeyEnv for openai-compatible")},create:($,Z)=>new yZ({apiKey:o$($,[],"openai-compatible extraction"),model:Z,baseUrl:L1($,"extraction"),providerId:"openai-compatible"})}],R1=new Map(I1.map(($)=>[$.id,$])),F1=new Map(T1.map(($)=>[$.id,$]))});import{Database as q4}from"bun:sqlite";import{accessSync as D1,constants as k1,existsSync as O4,statSync as E7}from"fs";import{homedir as D7}from"os";import{join as N4}from"path";function v1($){try{return $.query("PRAGMA quick_check(1);").get()?.quick_check==="ok"?"ok":"corrupted"}catch{return"corrupted"}}function s$($){if(!O4($))return{readable:!1,writable:!1};let Z=!1,K=!1;try{D1($,k1.R_OK),Z=!0}catch{}try{D1($,k1.W_OK),K=!0}catch{}return{readable:Z,writable:K}}function C1($,Z,K,X){let Y=X??R0(K),Q=m(Z),_=V$(1,$)[0];return{installed:Y.sessionEnd&&Y.preCompact,enabled:Q.autoSync,lastRun:_?new Date(_.timestamp):null}}function y1($){let Z=[];try{let K=m($);if(typeof K.autoSync!=="boolean")Z.push("autoSync is not a boolean");if(typeof K.recoveryOnStartup!=="boolean")Z.push("recoveryOnStartup is not a boolean");if(typeof K.syncOnCompaction!=="boolean")Z.push("syncOnCompaction is not a boolean");if(typeof K.timeout!=="number"||!Number.isFinite(K.timeout)||K.timeout<0)Z.push("timeout is not a valid positive number");if(!S1.includes(K.logLevel))Z.push(`logLevel "${K.logLevel}" is not valid (expected: ${S1.join(", ")})`);if(typeof K.logRetentionDays!=="number"||!Number.isFinite(K.logRetentionDays)||K.logRetentionDays<0)Z.push("logRetentionDays is not a valid positive number");if(typeof K.showFailures!=="boolean")Z.push("showFailures is not a boolean");return{valid:Z.length===0,issues:Z}}catch(K){let X=A(K);return Z.push(`Failed to load config: ${X}`),{valid:!1,issues:Z}}}function w1(){try{let $=e0("sqlite-vec"),Z=new q4(":memory:");try{return $.load(Z),{available:!0,version:Z.query("SELECT vec_version()").get()["vec_version()"]}}finally{Z.close()}}catch{return{available:!1,version:null}}}function b1($){let K=m($).embedding,X=j1(K);return{configured:!0,provider:K.provider,model:K.model,dimensions:K.dimensions,enabled:K.enabled,ready:X.ready,readyReason:X.readyReason}}function k7($){let Z=m($),K=A4(Z),X=E1(Z,K);return{provider:K,model:P1(Z,K),ready:X.ready,readyReason:X.readyReason}}function U4($){let Z=$?.dbPath??E(),K=v7(Z),X=$?.configDir??n0(),Y=$?.logsDir??H$(),Q=$?.sourceDir??N4(D7(),".claude","projects"),G=$?.logsDir?N4($.logsDir,"sync.log"):void 0,_=$?.configDir?N4($.configDir,"config.json"):void 0,J=s$(X),H=s$(Y),V=s$(Q),B={configDir:J.readable&&J.writable,logsDir:H.readable&&H.writable,sourceDir:V.readable},z=C1(G,_,$?.hookOverrides,$?.preCalculatedHookStatus),W=y1(_),N=m(_),q=b1(_),I=w1(),F=S7(Z,I,N),L=k7(_);return{database:K,permissions:B,hooks:z,config:W,embedding:q,sqliteVec:I,searchCapability:F,llmExtraction:L}}function S7($,Z,K){let X=0,Y=0;try{if(O4($)){let G=new q4($,{create:!1,readonly:!0});try{X=G.query("SELECT COUNT(*) as count FROM embedding_state").get()?.count??0,Y=G.query("SELECT COUNT(*) as count FROM messages_meta").get()?.count??0}finally{G.close()}}}catch{}let Q=Y>0?Math.round(X/Y*100):0;return{fts5:!0,sqliteVec:Z.available,embeddedCount:X,totalMessages:Y,coveragePercent:Q,defaultMode:K.search?.defaultMode??"auto",vectorReady:Z.available&&X>0}}function v7($){if(!O4($))return{exists:!1,readable:!1,writable:!1,integrity:"unknown",size:0};let K=s$($),X=0;try{X=E7($).size}catch{}let Y="unknown";if(K.readable)try{let Q=new q4($,{create:!1,readonly:!0});try{Y=v1(Q)}finally{Q.close()}}catch{Y="corrupted"}return{exists:!0,readable:K.readable,writable:K.writable,integrity:Y,size:X}}var S1;var f1=U(()=>{n9();z$();wZ();S1=["debug","info","warn","error"]});var u=U(()=>{g9();n9();o9();e5();f1()});import{readdir as L4,stat as e$}from"fs/promises";import{join as $Z}from"path";import{homedir as C7}from"os";class y0{claudeProjectsDir;resolver;constructor($){this.claudeProjectsDir=$?.claudeDir??$Z(C7(),".claude","projects"),this.resolver=$?.projectNameResolver}async discoverSessions(){let $=[];try{await e$(this.claudeProjectsDir)}catch{return $}let Z;try{Z=await L4(this.claudeProjectsDir)}catch{return $}for(let K of Z){let X=$Z(this.claudeProjectsDir,K);try{if(!(await e$(X)).isDirectory())continue}catch{continue}let Y;try{if(Y=i.fromEncoded(K),this.resolver){let Q=this.resolver.resolveFromEncodedPath(K);if(Q!==Y.projectName)Y=Y.withProjectName(Q)}}catch{continue}await this.scanProjectDirectory(X,Y,$)}return $}async getSessionFile($){return(await this.discoverSessions()).find((X)=>X.id===$)?.path??null}async scanProjectDirectory($,Z,K){let X;try{X=await L4($)}catch{return}for(let Y of X){let Q=$Z($,Y);try{let G=await e$(Q);if(G.isFile()&&Y.endsWith(".jsonl")){let _=Y.slice(0,-6);K.push({id:_,path:Q,projectPath:Z,modifiedTime:G.mtime,size:G.size})}else if(G.isDirectory())await this.scanSubagentsDirectory(Q,Z,K)}catch{continue}}}async scanSubagentsDirectory($,Z,K){let X=$Z($,"subagents");try{if(!(await e$(X)).isDirectory())return}catch{return}let Y;try{Y=await L4(X)}catch{return}for(let Q of Y){if(!Q.endsWith(".jsonl"))continue;let G=$Z(X,Q);try{let _=await e$(G);if(_.isFile()){let J=Q.slice(0,-6);K.push({id:J,path:G,projectPath:Z,modifiedTime:_.mtime,size:_.size})}}catch{continue}}}}var h1=()=>{};import{readdirSync as y7,statSync as w7}from"fs";function b7($){return $.replace(/ /g,"-").replace(/-/g,"-")}class bZ{rootDir;cache=new Map;dirCache=new Map;constructor($){this.rootDir=$}resolveFromEncodedPath($){let Z=/^[A-Za-z]--/,K=$;if(Z.test(K))K=K.slice(3);else if(K.startsWith("-"))K=K.slice(1);return this.resolveProjectName(K)}resolveProjectName($){let Z=this.cache.get($);if(Z!==void 0)return Z;let K=this.walkAndResolve(this.rootDir,$);return this.cache.set($,K),K}walkAndResolve($,Z){if(Z==="")return"";let K=this.listSubdirectories($),X=[];for(let Q of K){let G=b7(Q);X.push({name:Q,encoded:G})}X.sort((Q,G)=>G.encoded.length-Q.encoded.length);for(let Q of X){if(Z===Q.encoded)return Q.name;if(Z.startsWith(Q.encoded+"-")){let G=Z.slice(Q.encoded.length+1),_=`${$}/${Q.name}`,J=this.walkAndResolve(_,G);if(J!==this.fallbackLastSegment(G))return J;return J}}let Y=this.probeHiddenDirectories($,Z);if(Y!==void 0)return Y;return this.fallbackLastSegment(Z)}probeHiddenDirectories($,Z){let K=Z.split("-");for(let X=1;X<K.length;X++){let Y=K.slice(0,X).join("-"),Q=`${$}/${Y}`;if(this.isDirectory(Q)){let G=K.slice(X).join("-");if(G==="")return Y;let _=this.walkAndResolve(Q,G);if(_!==this.fallbackLastSegment(G))return _}}return}isDirectory($){try{return w7($).isDirectory()}catch{return!1}}listSubdirectories($){let Z=this.dirCache.get($);if(Z!==void 0)return Z;try{let X=y7($,{withFileTypes:!0}).filter((Y)=>Y.isDirectory()).map((Y)=>Y.name);return this.dirCache.set($,X),X}catch{return this.dirCache.set($,[]),[]}}fallbackLastSegment($){let Z=$.split("-");return Z[Z.length-1]??""}}var g1=()=>{};import{readdir as f7,readFile as h7,stat as g7}from"fs/promises";import{join as m7,relative as c7}from"path";import{createHash as u7}from"crypto";class fZ{async discoverFiles(){let $=MZ();try{await g7($)}catch{return[]}let Z=[];return await this.scanDirectory($,$,Z),Z}async scanDirectory($,Z,K){let X;try{X=await f7($,{withFileTypes:!0})}catch{return}for(let Y of X){let Q=m7($,Y.name);if(Y.isDirectory())await this.scanDirectory(Q,Z,K);else if(Y.isFile()&&Y.name.endsWith(".md")){let G=c7(Z,Q).split("\\").join("/"),_=this.classifyFileType(G);if(!_)continue;let J=await h7(Q,"utf8"),H=u7("sha256").update(J,"utf8").digest("hex"),V=this.extractProjectEncoded(G);K.push({filePath:G,absolutePath:Q,fileType:_,projectEncoded:V,contentHash:H,content:J})}}}classifyFileType($){if($.startsWith("daily/"))return"daily_log";if($.endsWith("DECISIONS.md"))return"decisions";if($.endsWith("LEARNINGS.md"))return"learnings";if($.endsWith("USER-PREFS.md"))return"user_prefs";return null}extractProjectEncoded($){return $.match(/^projects\/([^/]+)\//)?.[1]??void 0}}var m1=U(()=>{p()});var ZZ=U(()=>{h1();g1();m1()});function _0($,Z){let K=Z??new Date,X=$.getTime()-K.getTime(),Y=Math.abs(X);if(Y<3600000){let G=Math.round(X/60000);return KZ.format(G,"minute")}if(Y<86400000){let G=Math.round(X/3600000);return KZ.format(G,"hour")}if(Y<604800000){let G=Math.round(X/86400000);return KZ.format(G,"day")}if(Y<2592000000){let G=Math.round(X/604800000);return KZ.format(G,"week")}let Q=Math.round(X/2592000000);return KZ.format(Q,"month")}function i0($){let Z=$.getFullYear(),K=String($.getMonth()+1).padStart(2,"0"),X=String($.getDate()).padStart(2,"0"),Y=String($.getHours()).padStart(2,"0"),Q=String($.getMinutes()).padStart(2,"0");return`${Z}-${K}-${X} ${Y}:${Q}`}function U0($,Z){let K=_0($,Z),X=i0($);return`${K} (${X})`}var KZ;var w0=U(()=>{KZ=new Intl.RelativeTimeFormat("en",{numeric:"auto",style:"long"})});function k($){let Z=$?.noColor??!!process.env.NO_COLOR,K=$?.forceColor??!!process.env.FORCE_COLOR,X=$?.isTTY??process.stdout.isTTY===!0;if(Z)return!1;if(K)return!0;return X}function O$($,Z,K){if(!K)return $;return`\x1B[${Z}m${$}\x1B[0m`}function r($,Z){return O$($,"1",Z??k())}function P($,Z){return O$($,"2",Z??k())}function b($,Z){return O$($,"32",Z??k())}function f($,Z){return O$($,"31",Z??k())}function d($,Z){return O$($,"33",Z??k())}function s1($,Z){return O$($,"36",Z??k())}import e1 from"string-width";function R4($){return e1($)}function F4($,Z){if(Z<=0)return"";if(R4($)<=Z)return $;let K="...",X=3;if(Z<=X)return".".repeat(Z);let Y=Z-X,Q="",G=0;for(let _ of $){let J=e1(_);if(G+J>Y)break;Q+=_,G+=J}return Q+K}function dZ($,Z){let K=R4($);if(K>=Z)return $;return $+" ".repeat(Z-K)}function M4(){return process.stdout.columns||80}function j4($,Z,K=20){let X=M4(),Y=R4(Z),Q=X-Y;return F4($,Q>K?Q:K)}var x4=()=>{};function pZ($,Z={}){let K=Y3($.snippet),X=$.snippet.replace(/<\/?mark>/g,""),Y={sessionId:$.sessionId,messageId:$.messageId,role:$.role,score:$.score,timestamp:$.timestamp.toISOString(),snippet:X};if(Z.includeSearchMetaFields){if(Z.rank!==void 0)Y.rank=Z.rank;let Q=$.rawScores;if(Q)Y.raw_scores=Q;if($.source)Y.source=$.source;if(K.length>0)Y.highlights=K}return Y}function $3($){let Z={score:$.score,file:$.file,title:$.title};if($.docid!==void 0)Z.docid=$.docid;if($.context!==void 0)Z.context=$.context;if($.snippet!==void 0)Z.snippet=$.snippet;return Z}function lZ($){let Z={id:$.id,project:$.projectPath.projectName,projectPath:$.projectPath.decoded,startTime:$.startTime.toISOString()};if($.endTime)Z.endTime=$.endTime.toISOString();if($.messageCount!==void 0)Z.messageCount=$.messageCount;if($.summary!==void 0)Z.summary=$.summary;return Z}function Z3($){return{session:lZ($.session),messages:$.messages.map(G6),toolUses:Array.from($.toolUses.values()).map(_6)}}function G6($){return{id:$.id,role:$.role,timestamp:$.timestamp.toISOString(),content:$.content}}function _6($){let Z={id:$.id,name:$.name,status:$.status,input:$.input};if($.result!==void 0)Z.result=$.result;return Z}function K3($){return{session:lZ($.session),weight:$.weight,hops:$.hops}}function P4($){let Z={totalSessions:$.totalSessions,totalMessages:$.totalMessages,totalToolUses:$.totalToolUses,databaseSizeBytes:$.databaseSizeBytes,projectBreakdown:$.projectBreakdown.map((K)=>({projectName:K.projectName,sessionCount:K.sessionCount,messageCount:K.messageCount}))};if($.hooks)Z.hooks={installed:$.hooks.installed,autoSync:$.hooks.autoSync,pendingSessions:$.hooks.pendingSessions};return Z}function X3($){return{projectName:$.projectName,projectPathDecoded:$.projectPathDecoded,sessionCount:$.sessionCount,totalMessages:$.totalMessages,userMessages:$.userMessages,assistantMessages:$.assistantMessages,recentTopics:[...$.recentTopics],recentToolUses:$.recentToolUses.map((Z)=>({name:Z.name,count:Z.count})),lastActivity:$.lastActivity?$.lastActivity.toISOString():null}}var b0=U(()=>{nZ()});function E4($,Z){switch($){case"json":return new J3;case"quiet":return new H3;case"verbose":return new V3(Z);case"brief":return new _3;default:return new G3(Z)}}function Y3($){let Z=[],K=0,X=0;while(X<$.length)if($.startsWith("<mark>",X)){X+=6;let Y=$.indexOf("</mark>",X);if(Y===-1)break;Z.push({offset:K,length:Y-X}),K+=Y-X,X=Y+7}else K++,X++;return Z}function Q3($,Z){if(!Z)return $.replace(/<mark>/g,"*").replace(/<\/mark>/g,"*");return $.replace(/<mark>/g,"\x1B[1;36m").replace(/<\/mark>/g,"\x1B[0m")}class G3{useColor;constructor($){this.useColor=$}formatResults($,Z){let K=Z?.contextBudget??U$;if($.length===0)return`No results found for: ${Z?.query??"query"}`;let X=`Found ${$.length} result(s):
|
|
682
|
+
|
|
683
|
+
`;for(let Y=0;Y<$.length;Y++){let Q=$[Y];if(!Q)continue;let G=this.formatResult(Q,Y+1);if(X.length+G.length>K){X+=`
|
|
684
|
+
(Output truncated - ${U$.toLocaleString()} char limit)
|
|
685
|
+
`;break}X+=G}return X}formatResult($,Z){let K=($.score*100).toFixed(0),X=$.sessionId.substring(0,16),Y=U0($.timestamp),Q=Q3($.snippet,this.useColor),G=$.role.charAt(0).toUpperCase()+$.role.slice(1),_=j4(Q," ");return`${Z}. [${K}%] [${G}] ${X}...
|
|
686
|
+
${Y}
|
|
687
|
+
${_}
|
|
688
|
+
|
|
689
|
+
`}formatError($){return`Error: ${A($)}`}formatSummary($){let Z=`Found ${$.found} results (showing ${$.shown})`;if($.truncated)Z+=" - truncated";return Z}}class _3{formatResults($,Z){if($.length===0)return`No results for "${Z?.query??""}"`;return $.map((K)=>{let X=K.snippet.replace(/<\/?mark>/g,"").replace(/\s+/g," ").trim().slice(0,80),Y=Math.round(K.score*100);return`${K.sessionId} [${Y}%] ${X}`}).join(`
|
|
690
|
+
`)}formatError($){return`Error: ${A($)}`}formatSummary($){return""}}class J3{formatResults($,Z){let K=Z?.contextBudget??U$,X=$.map((Q,G)=>pZ(Q,{rank:G+1,includeSearchMetaFields:!!Z?.searchMeta}));if(Z?.searchMeta){let Q={query:Z.query??"",mode:Z.searchMeta.mode,mode_reason:Z.searchMeta.modeReason,total_results:$.length,embedding_coverage:Z.searchMeta.embeddingCoverage,degraded:Z.searchMeta.degraded,capabilities:Z.searchMeta.capabilities,timing_ms:Z.searchMeta.timingMs};if(Z.searchMeta.degradationReason)Q.degradation_reason=Z.searchMeta.degradationReason;return JSON.stringify({meta:Q,results:X},null,2)}let Y=JSON.stringify(X,null,2);if(Y.length>K){let Q=X.length;while(Q>0){let G=X.slice(0,Q);if(Y=JSON.stringify(G,null,2),Y.length<=K)break;Q--}}return Y}formatError($){let Z=A($);return JSON.stringify({error:Z})}formatSummary($){return""}}class H3{formatResults($,Z){if($.length===0)return"";let K=M4();return $.map((X)=>{let Y=X.sessionId.substring(0,16),Q=X.snippet.replace(/<mark>/g,"*").replace(/<\/mark>/g,"*"),G=`${Y} ${Q}`;return F4(G,K)}).join(`
|
|
691
|
+
`)}formatError($){return`Error: ${A($)}`}formatSummary($){return""}}class V3{useColor;constructor($){this.useColor=$}formatResults($,Z){let K=Z?.contextBudget??U$;if($.length===0)return`No results found for: ${Z?.query??"query"}`;let X="";if(Z?.searchMeta){if(X+=`Mode: ${Z.searchMeta.mode}`,Z.searchMeta.degraded)X+=` (degraded: ${Z.searchMeta.degradationReason??"unknown"})`;X+=`
|
|
692
|
+
`}if(Z?.executionDetails){let Y=Z.executionDetails;if(X+=`=== Execution Details ===
|
|
693
|
+
`,Y.timeMs!==void 0)X+=`Time: ${Y.timeMs}ms
|
|
694
|
+
`;if(Y.ftsQuery)X+=`FTS5 Query: ${Y.ftsQuery}
|
|
695
|
+
`;if(Y.filtersApplied&&Y.filtersApplied.length>0)X+=`Filters: ${Y.filtersApplied.join(", ")}
|
|
696
|
+
`;X+=`
|
|
697
|
+
`}X+=`Found ${$.length} result(s):
|
|
698
|
+
|
|
699
|
+
`;for(let Y=0;Y<$.length;Y++){let Q=$[Y];if(!Q)continue;let G=this.formatResult(Q,Y+1,!!Z?.searchMeta);if(X.length+G.length>K){X+=`
|
|
700
|
+
(Output truncated - ${U$.toLocaleString()} char limit)
|
|
701
|
+
`;break}X+=G}return X}formatResult($,Z,K){let X=($.score*100).toFixed(0),Y=U0($.timestamp),Q=Q3($.snippet,this.useColor),G=$.role.charAt(0).toUpperCase()+$.role.slice(1),_=j4(Q," "),J=`${Z}. [${X}%] [${G}] ${$.sessionId}
|
|
702
|
+
${Y}
|
|
703
|
+
${_}
|
|
704
|
+
`;if(K&&$.rawScores){let H=[];if($.rawScores.bm25!==void 0)H.push(`bm25: ${$.rawScores.bm25}`);if($.rawScores.cosine!==void 0)H.push(`cosine: ${$.rawScores.cosine}`);if($.rawScores.rrf!==void 0)H.push(`rrf: ${$.rawScores.rrf}`);if(H.length>0)J+=` Scores: ${H.join(", ")}
|
|
705
|
+
`;if($.source)J+=` Source: ${$.source}
|
|
706
|
+
`}return J+=`
|
|
707
|
+
`,J}formatError($){let Z=A($),K=$ instanceof Error?$.stack:"";return`Error: ${Z}
|
|
708
|
+
${K??""}`}formatSummary($){let Z=`=== Summary ===
|
|
709
|
+
Found ${$.found} results (showing ${$.shown})`;if($.truncated)Z+=" - truncated due to context budget";return Z}}var U$=50000;var nZ=U(()=>{w0();x4();b0()});function D4($,Z){switch($){case"json":return new z3;case"quiet":return new A3;case"verbose":return new N3(Z);case"brief":return new B3;default:return new W3(Z)}}function aZ($,Z,K){return $===1?Z:K}class W3{useColor;constructor($){this.useColor=$}formatSessions($,Z){let K=$.length,X=`Sessions (${K} ${aZ(K,"result","results")}):
|
|
710
|
+
|
|
711
|
+
`;for(let Y of $)X+=this.formatSession(Y);return X}formatSession($){let Z=$.id.substring(0,8),K=$.projectPath.projectName,X=_0($.startTime),Y=$.messageCount,Q=`${Y} ${aZ(Y,"message","messages")}`,G=dZ(Z,10),_=dZ(K,20),J=dZ(X,18);return` ${G}${_}${J}${P(Q,this.useColor)}
|
|
712
|
+
`}formatError($){return`Error: ${A($)}`}formatEmpty(){return"No sessions found. Run 'memory sync' to import sessions."}}class B3{formatSessions($,Z){if($.length===0)return this.formatEmpty();return $.map((K)=>{let X=K.id.substring(0,8),Y=K.projectPath.projectName,Q=K.messageCount,G=_0(K.startTime);return`${X} ${Y} ${Q} ${G}`}).join(`
|
|
713
|
+
`)}formatError($){return`Error: ${A($)}`}formatEmpty(){return"No sessions found."}}class z3{formatSessions($,Z){let K=$.map((X)=>({id:X.id,projectPath:X.projectPath.decoded,projectName:X.projectPath.projectName,startTime:X.startTime.toISOString(),endTime:X.endTime?.toISOString()??null,messageCount:X.messageCount}));return JSON.stringify(K,null,2)}formatError($){let Z=A($);return JSON.stringify({error:Z})}formatEmpty(){return"[]"}}class A3{formatSessions($,Z){if($.length===0)return"";return $.map((K)=>K.id).join(`
|
|
714
|
+
`)}formatError($){return`Error: ${A($)}`}formatEmpty(){return""}}class N3{useColor;constructor($){this.useColor=$}formatSessions($,Z){let K="";if(Z){if(K+=`=== Execution Details ===
|
|
715
|
+
`,Z.executionTimeMs!==void 0)K+=`Time: ${Z.executionTimeMs}ms
|
|
716
|
+
`;if(Z.filtersApplied&&Z.filtersApplied.length>0)K+=`Filters: ${Z.filtersApplied.join(", ")}
|
|
717
|
+
`;K+=`
|
|
718
|
+
`}let X=$.length;K+=`Sessions (${X} ${aZ(X,"result","results")}):
|
|
719
|
+
|
|
720
|
+
`;for(let Y of $)K+=this.formatSession(Y);return K}formatSession($){let Z=$.projectPath.projectName,K=$.projectPath.decoded,X=U0($.startTime),Y=$.messageCount,Q=`${Y} ${aZ(Y,"message","messages")}`,G=` ${$.id}
|
|
721
|
+
`;return G+=` Project: ${Z} (${K})
|
|
722
|
+
`,G+=` Started: ${X}
|
|
723
|
+
`,G+=` ${P(Q,this.useColor)}
|
|
724
|
+
|
|
725
|
+
`,G}formatError($){let Z=A($),K=$ instanceof Error?$.stack:"";return`Error: ${Z}
|
|
726
|
+
${K??""}`}formatEmpty(){return"No sessions found. Run 'memory sync' to import sessions."}}var k4=U(()=>{w0();x4()});function S4($){if($<1024)return`${$} B`;else if($<1048576)return`${($/1024).toFixed(1)} KB`;else if($<1073741824)return`${($/1048576).toFixed(1)} MB`;else return`${($/1073741824).toFixed(1)} GB`}function o($){return new Intl.NumberFormat("en-US").format($)}function v4($,Z){switch($){case"json":return new U3;case"quiet":return new L3;case"verbose":return new I3(Z);case"brief":return new q3;default:return new O3(Z)}}class q3{formatStats($,Z){return[`${o($.totalSessions)} sessions`,`${o($.totalMessages)} messages`,`${o($.totalToolUses)} tool uses`,`${o($.projectBreakdown.length)} projects`,`${S4($.databaseSizeBytes)}`].join(`
|
|
727
|
+
`)}formatError($){return`Error: ${A($)}`}formatEmpty(){return`0 sessions
|
|
728
|
+
0 messages
|
|
729
|
+
0 tool uses
|
|
730
|
+
0 projects
|
|
731
|
+
0 B`}}class O3{constructor($){}formatStats($,Z){let K="";if(K+=`=== Database Statistics ===
|
|
732
|
+
|
|
733
|
+
`,K+=`Totals:
|
|
734
|
+
`,K+=` Sessions: ${o($.totalSessions)}
|
|
735
|
+
`,K+=` Messages: ${o($.totalMessages)}
|
|
736
|
+
`,K+=` Tool Uses: ${o($.totalToolUses)}
|
|
737
|
+
`,K+=` Size: ${S4($.databaseSizeBytes)}
|
|
738
|
+
`,$.projectBreakdown.length>0){K+=`
|
|
739
|
+
Projects:
|
|
740
|
+
`;for(let X of $.projectBreakdown)K+=` ${X.projectName}
|
|
741
|
+
`,K+=` Sessions: ${o(X.sessionCount)}`,K+=`, Messages: ${o(X.messageCount)}
|
|
742
|
+
`}if($.hooks){if(K+=`
|
|
743
|
+
Hooks:
|
|
744
|
+
`,K+=` Installed: ${$.hooks.installed?"yes":"no"}
|
|
745
|
+
`,K+=` Auto-sync: ${$.hooks.autoSync?"enabled":"disabled"}
|
|
746
|
+
`,K+=` Pending sessions: ${$.hooks.pendingSessions}
|
|
747
|
+
`,!$.hooks.installed)K+=`
|
|
748
|
+
Run 'aidev memory install' to enable automatic sync
|
|
749
|
+
`}return K}formatError($){return`Error: ${A($)}`}formatEmpty(){return"No sessions synced. Run 'memory sync' to import data."}}class U3{formatStats($,Z){let K={totalSessions:$.totalSessions,totalMessages:$.totalMessages,totalToolUses:$.totalToolUses,databaseSizeBytes:$.databaseSizeBytes,projectBreakdown:$.projectBreakdown.map((X)=>({projectName:X.projectName,sessionCount:X.sessionCount,messageCount:X.messageCount}))};if(Z?.executionTimeMs!==void 0)K.executionTimeMs=Z.executionTimeMs;if($.hooks)K.hooks={installed:$.hooks.installed,autoSync:$.hooks.autoSync,pendingSessions:$.hooks.pendingSessions};return JSON.stringify(K,null,2)}formatError($){let Z=A($);return JSON.stringify({error:Z})}formatEmpty(){return JSON.stringify({totalSessions:0,totalMessages:0,totalToolUses:0,databaseSizeBytes:0,projectBreakdown:[],empty:!0,message:"No sessions synced. Run 'memory sync' to import data."})}}class L3{formatStats($,Z){return[`Sessions: ${$.totalSessions}`,`Messages: ${$.totalMessages}`,`Tool uses: ${$.totalToolUses}`,`Size: ${$.databaseSizeBytes}`].join(`
|
|
750
|
+
`)}formatError($){return`Error: ${A($)}`}formatEmpty(){return`Sessions: 0
|
|
751
|
+
Messages: 0
|
|
752
|
+
Tool uses: 0
|
|
753
|
+
Size: 0`}}class I3{constructor($){}formatStats($,Z){let K="";if(Z?.executionTimeMs!==void 0)K+=`=== Execution Details ===
|
|
754
|
+
`,K+=`Time: ${Z.executionTimeMs}ms
|
|
755
|
+
|
|
756
|
+
`;if(K+=`=== Database Statistics ===
|
|
757
|
+
|
|
758
|
+
`,K+=`Totals:
|
|
759
|
+
`,K+=` Sessions: ${o($.totalSessions)}
|
|
760
|
+
`,K+=` Messages: ${o($.totalMessages)}
|
|
761
|
+
`,K+=` Tool Uses: ${o($.totalToolUses)}
|
|
762
|
+
`,K+=` Size: ${S4($.databaseSizeBytes)} (${o($.databaseSizeBytes)} bytes)
|
|
763
|
+
`,$.projectBreakdown.length>0){K+=`
|
|
764
|
+
Projects (${$.projectBreakdown.length}):
|
|
765
|
+
`;for(let X of $.projectBreakdown){let Y=X.sessionCount>0?(X.messageCount/X.sessionCount).toFixed(1):"0";K+=` ${X.projectName}
|
|
766
|
+
`,K+=` Sessions: ${o(X.sessionCount)}`,K+=`, Messages: ${o(X.messageCount)}`,K+=` (avg ${Y}/session)
|
|
767
|
+
`}}if($.hooks){if(K+=`
|
|
768
|
+
Hooks:
|
|
769
|
+
`,K+=` Installed: ${$.hooks.installed?"yes":"no"}
|
|
770
|
+
`,K+=` Auto-sync: ${$.hooks.autoSync?"enabled":"disabled"}
|
|
771
|
+
`,K+=` Pending sessions: ${$.hooks.pendingSessions}
|
|
772
|
+
`,!$.hooks.installed)K+=`
|
|
773
|
+
Run 'aidev memory install' to enable automatic sync
|
|
774
|
+
`}return K}formatError($){let Z=A($),K=$ instanceof Error?$.stack:"";return`Error: ${Z}
|
|
775
|
+
${K??""}`}formatEmpty(){return"No sessions synced. Run 'memory sync' to import data."}}var C4=()=>{};function T3($){return $.replace(J6,"")}function a($){return T3($).replace(/\n{3,}/g,`
|
|
776
|
+
|
|
777
|
+
`).trim()}var J6;var F0=U(()=>{J6=/\x1b\[[0-9;]*[a-zA-Z]|\x1b\].*?\x07|\x1b\(B/g});var x3={};w(x3,{createContextFormatter:()=>iZ});function iZ($,Z){switch($){case"json":return new R3;case"quiet":return new F3;case"verbose":return new M3(Z);case"detailed":return new w4(Z);case"ai":return new j3;case"brief":case"default":default:return new y4(Z)}}function f0($){return new Intl.NumberFormat("en-US").format($)}function H6($,Z=3){if($.length===0)return"";let K=$.slice(0,Z),X=$.length-Z,Y=K.map((Q)=>`${Q.name} (${Q.count})`).join(", ");if(X>0)return`${Y} (+${X} more)`;return Y}function V6($,Z=3){if($.length===0)return"";let K=$.slice(0,Z),X=$.length-Z,Y=K.join(", ");if(X>0)return`${Y} (+${X} more)`;return Y}class y4{useColor;constructor($){this.useColor=$}formatContext($,Z){let K="";K+=r(`${$.projectName} Context`,this.useColor)+`
|
|
778
|
+
`;let X=$.lastActivity?_0($.lastActivity):"never";K+=`Sessions: ${f0($.sessionCount)} | `,K+=`Messages: ${f0($.totalMessages)} | `,K+=`Last active: ${X}
|
|
779
|
+
`;let Y=V6($.recentTopics);if(Y)K+=`Topics: ${Y}
|
|
780
|
+
`;let Q=H6($.recentToolUses);if(Q)K+=`Tools: ${Q}
|
|
781
|
+
`;return K}formatError($){return`Error: ${A($)}`}formatEmpty($){return`No sessions found for project matching '${$}'`}formatNoTopics(){return P("No topics extracted yet",this.useColor)}}class w4{useColor;constructor($){this.useColor=$}formatContext($,Z){let K="";if(K+=r(`${$.projectName} Context`,this.useColor)+`
|
|
782
|
+
`,K+="=".repeat(40)+`
|
|
783
|
+
|
|
784
|
+
`,K+=`Project: ${$.projectPathDecoded}
|
|
785
|
+
`,K+=`Sessions: ${f0($.sessionCount)}
|
|
786
|
+
`,K+=`Messages: ${f0($.totalMessages)}`,K+=` (user: ${f0($.userMessages)}, assistant: ${f0($.assistantMessages)})
|
|
787
|
+
`,$.lastActivity)K+=`Last active: ${U0($.lastActivity)}
|
|
788
|
+
`;else K+=`Last active: never
|
|
789
|
+
`;if(K+=`
|
|
790
|
+
Topics:
|
|
791
|
+
`,$.recentTopics.length>0)for(let X of $.recentTopics)K+=` - ${X}
|
|
792
|
+
`;else K+=P(` (no topics extracted yet)
|
|
793
|
+
`,this.useColor);if(K+=`
|
|
794
|
+
Tool Usage:
|
|
795
|
+
`,$.recentToolUses.length>0)for(let X of $.recentToolUses)K+=` - ${X.name}: ${f0(X.count)} times
|
|
796
|
+
`;else K+=P(` (no tool usage recorded)
|
|
797
|
+
`,this.useColor);return K}formatError($){return`Error: ${A($)}`}formatEmpty($){return`No sessions found for project matching '${$}'`}formatNoTopics(){return P("(no topics extracted yet)",this.useColor)}}class R3{formatContext($,Z){let K={projectName:$.projectName,projectPath:$.projectPathDecoded,sessionCount:$.sessionCount,totalMessages:$.totalMessages,userMessages:$.userMessages,assistantMessages:$.assistantMessages,lastActivity:$.lastActivity?.toISOString()??null,topics:$.recentTopics,toolUsage:$.recentToolUses};return JSON.stringify(K,null,2)}formatError($){let Z=A($);return JSON.stringify({error:Z})}formatEmpty($){return JSON.stringify({error:`No sessions found for project matching '${$}'`})}formatNoTopics(){return JSON.stringify({topics:[]})}}class F3{formatContext($,Z){return`${$.projectName}: ${$.sessionCount} sessions, ${f0($.totalMessages)} messages`}formatError($){return`Error: ${A($)}`}formatEmpty($){return""}formatNoTopics(){return""}}class M3{detailed;constructor($){this.detailed=new w4($)}formatContext($,Z){let K="";if(Z){if(K+=`=== Execution Details ===
|
|
798
|
+
`,Z.executionTimeMs!==void 0)K+=`Time: ${Z.executionTimeMs}ms
|
|
799
|
+
`;if(Z.filtersApplied&&Z.filtersApplied.length>0)K+=`Filters: ${Z.filtersApplied.join(", ")}
|
|
800
|
+
`;K+=`
|
|
801
|
+
`}return K+=this.detailed.formatContext($,Z),K}formatError($){let Z=A($),K=$ instanceof Error?$.stack:"";return`Error: ${Z}
|
|
802
|
+
${K??""}`}formatEmpty($){return`No sessions found for project matching '${$}'`}formatNoTopics(){return this.detailed.formatNoTopics()}}class j3{formatContext($,Z){let K=new y4(!1);return a(K.formatContext($,Z))}formatSmartContext($){let Z=[];for(let X of $.sections){if(X.content.trim()==="")continue;let Y=`### ${X.title}
|
|
803
|
+
${X.content}`;if(X.truncated)Y+=`
|
|
804
|
+
[truncated]`;Z.push(Y)}let K=`## ${$.projectName} context
|
|
805
|
+
|
|
806
|
+
`+Z.join(`
|
|
807
|
+
|
|
808
|
+
---
|
|
809
|
+
|
|
810
|
+
`);if($.truncated)K+=`
|
|
811
|
+
|
|
812
|
+
(budget: ~${$.totalTokensEstimate} tokens)`;return K.trim()}formatError($){return`Error: ${A($)}`}formatEmpty($){return`No sessions found for project matching '${$}'`}formatNoTopics(){return"No topics extracted yet"}}var rZ=U(()=>{w0();F0()});function b4($,Z){switch($){case"json":return new D3;case"quiet":return new k3;case"verbose":return new S3(Z);case"detailed":return new f4(Z);case"brief":case"default":default:return new E3(Z)}}function P3($,Z){let K=`${Math.round($*100)}%`;if(!Z)return K;if($>0.75)return b(K,Z);if($>=0.5)return d(K,Z);return K}function W6($){return $===1?"1 hop":`${$} hops`}function B6($){return`${$===1?"1":`${$}`} (${$===1?"direct":"indirect"})`}class E3{useColor;constructor($){this.useColor=$}formatRelated($,Z){if($.length===0)return"";let X=`Related to session ${Z?.sourceId??"unknown"}...
|
|
813
|
+
`;return $.forEach((Y,Q)=>{let G=Y.session.projectPath.projectName,_=_0(Y.session.startTime),J=P3(Y.weight,this.useColor),H=W6(Y.hops);X+=`${Q+1}. ${G} (${J}) - ${_} [${H}]
|
|
814
|
+
`}),X}formatError($){return`Error: ${A($)}`}formatEmpty($){return`No relationships found for '${$}'`}formatNoLinks(){return"No relationships extracted yet. Run 'memory sync' to extract session data."}}class f4{useColor;constructor($){this.useColor=$}formatRelated($,Z){if($.length===0)return"";let X=`Related to session ${Z?.sourceId??"unknown"}...
|
|
815
|
+
`;return X+="=".repeat(40)+`
|
|
816
|
+
|
|
817
|
+
`,$.forEach((Y,Q)=>{let G=Y.session,_=G.projectPath.projectName,J=G.projectPath.decoded,H=P3(Y.weight,this.useColor),V=B6(Y.hops),B=U0(G.startTime),z=G.messages.length;X+=`${Q+1}. ${_}
|
|
818
|
+
`,X+=` Weight: ${H} | Hops: ${V}
|
|
819
|
+
`,X+=` Path: ${J}
|
|
820
|
+
`,X+=` Last active: ${B}
|
|
821
|
+
`,X+=` Messages: ${z}
|
|
822
|
+
|
|
823
|
+
`}),X}formatError($){return`Error: ${A($)}`}formatEmpty($){return`No relationships found for '${$}'`}formatNoLinks(){return"No relationships extracted yet. Run 'memory sync' to extract session data."}}class D3{formatRelated($,Z){let X={sourceId:Z?.sourceId??"unknown",related:$.map((Y)=>({sessionId:Y.session.id,projectName:Y.session.projectPath.projectName,weight:Y.weight,hops:Y.hops,lastActivity:Y.session.startTime.toISOString(),messageCount:Y.session.messages.length}))};return JSON.stringify(X,null,2)}formatError($){let Z=A($);return JSON.stringify({error:Z})}formatEmpty($){return JSON.stringify({error:`No relationships found for '${$}'`})}formatNoLinks(){return JSON.stringify({error:"No relationships extracted yet"})}}class k3{formatRelated($,Z){if($.length===0)return"";return $.map((K)=>K.session.id).join(`
|
|
824
|
+
`)}formatError($){return`Error: ${A($)}`}formatEmpty($){return""}formatNoLinks(){return""}}class S3{detailed;constructor($){this.detailed=new f4($)}formatRelated($,Z){let K="";if(Z?.executionTimeMs!==void 0)K+=`=== Execution Details ===
|
|
825
|
+
`,K+=`Time: ${Z.executionTimeMs}ms
|
|
826
|
+
`,K+=`
|
|
827
|
+
`;return K+=this.detailed.formatRelated($,Z),K}formatError($){let Z=A($),K=$ instanceof Error?$.stack:"";return`Error: ${Z}
|
|
828
|
+
${K??""}`}formatEmpty($){return this.detailed.formatEmpty($)}formatNoLinks(){return this.detailed.formatNoLinks()}}var h4=U(()=>{w0()});function tZ($,Z){switch($){case"json":return new w3;case"quiet":return new b3;case"verbose":return new f3(Z);case"tools":return new oZ(Z);case"brief":return new C3;default:return new y3(Z)}}function g4($){let Z=$.replace(/\\/g,"/").split("/");return Z[Z.length-1]||$}function v3($){switch($.name){case"Read":{let Z=$.input.file_path,K=$.result?$.result.split(`
|
|
829
|
+
`).length:0;return`${g4(Z)} -> ${K} lines`}case"Write":{let Z=$.input.file_path;return g4(Z)}case"Edit":{let Z=$.input.file_path;return`${g4(Z)} edited`}case"Bash":{if(!$.isSuccess)return"FAILED";let Z=$.input.command.substring(0,20);return Z.length<$.input.command.length?`${Z}...`:Z}case"Glob":return`${$.result?.split(`
|
|
830
|
+
`).filter(Boolean).length??0} files`;case"Grep":return $.isSuccess?"matches":"no matches";default:return $.status}}function z6($){let Z=Math.floor($/3600000),K=Math.floor($%3600000/60000);if(Z>0)return`${Z}h ${K}m`;if(K>0)return`${K}m`;return"< 1m"}function m4($,Z){let{session:K,messages:X,toolUses:Y}=$,Q=[];Q.push(`Session: ${K.id}`),Q.push(`Project: ${K.projectPath.projectName}`);let G=i0(K.startTime),_=K.endTime?i0(K.endTime):"ongoing";if(Q.push(`Date: ${G} - ${_}`),K.durationMs!==void 0)Q.push(`Duration: ${z6(K.durationMs)}`);else Q.push("Duration: ongoing");let J=Y.size;return Q.push(`Messages: ${X.length} | Tools: ${J}`),Q.push("---"),Q.join(`
|
|
831
|
+
`)}function c4($,Z,K,X){let Y=$.role==="user"?r("[USER]",K):r("[ASSISTANT]",K),Q=i0($.timestamp),G=`${Y} ${P(Q,K)}
|
|
832
|
+
`;if(G+=$.content,X&&$.role==="assistant"&&$.hasToolUses){let _=[];for(let J of $.toolUses){let H=Z.get(J);if(H)_.push(`[${H.name}: ${v3(H)}]`)}if(_.length>0)G+=`
|
|
833
|
+
${_.join(" ")}`}return G}class C3{formatSession($,Z){let{session:K,messages:X}=$,Y=i0(K.startTime);return`${K.id} | ${K.projectPath.projectName} | ${X.length} messages | ${Y}`}formatError($){return`Error: ${A($)}`}formatNotFound($){return`Session not found: ${$}`}}class y3{useColor;constructor($){this.useColor=$}formatSession($,Z){let K=[];K.push(m4($,this.useColor)),K.push("");for(let X of $.messages)K.push(c4(X,$.toolUses,this.useColor,!0)),K.push("");return K.join(`
|
|
834
|
+
`)}formatError($){return`Error: ${A($)}`}formatNotFound($){return`Session not found: ${$}`}}class w3{formatSession($,Z){let{session:K,messages:X,toolUses:Y}=$,Q={session:{id:K.id,projectPath:K.projectPath.decoded,projectName:K.projectPath.projectName,startTime:K.startTime.toISOString(),endTime:K.endTime?.toISOString()??null,durationMs:K.durationMs??null},messages:X.map((G)=>({id:G.id,role:G.role,content:G.content,timestamp:G.timestamp.toISOString(),toolUseIds:G.toolUses})),toolUses:Object.fromEntries(Array.from(Y.entries()).map(([G,_])=>[G,{id:_.id,name:_.name,input:_.input,timestamp:_.timestamp.toISOString(),status:_.status,result:_.result??null}]))};return JSON.stringify(Q,null,2)}formatError($){let Z=A($);return JSON.stringify({error:Z})}formatNotFound($){return JSON.stringify({error:`Session not found: ${$}`})}}class b3{formatSession($,Z){let K=[];for(let X of $.messages){let Y=X.role==="user"?"U:":"A:";K.push(`${Y} ${X.content}`)}return K.join(`
|
|
835
|
+
`)}formatError($){return`Error: ${A($)}`}formatNotFound($){return`Session not found: ${$}`}}class f3{useColor;constructor($){this.useColor=$}formatSession($,Z){let K=[];if(Z?.executionTimeMs!==void 0)K.push("=== Execution Details ==="),K.push(`Time: ${Z.executionTimeMs}ms`),K.push("");K.push(m4($,this.useColor)),K.push("");for(let X of $.messages){if(K.push(c4(X,$.toolUses,this.useColor,!0)),X.role==="assistant"&&X.hasToolUses)for(let Y of X.toolUses){let Q=$.toolUses.get(Y);if(Q){if(K.push(""),K.push(` [TOOL: ${Q.name}]`),K.push(` Input: ${JSON.stringify(Q.input)}`),Q.result)K.push(` Result: ${Q.result}`);K.push(` Status: ${Q.status}`)}}K.push("")}return K.join(`
|
|
836
|
+
`)}formatError($){let Z=A($),K=$ instanceof Error?$.stack:"";return`Error: ${Z}
|
|
837
|
+
${K??""}`}formatNotFound($){return`Session not found: ${$}`}}class oZ{useColor;static RESULT_TRUNCATE_LENGTH=500;constructor($){this.useColor=$}formatSession($,Z){let K=[];K.push(m4($,this.useColor)),K.push("");for(let X of $.messages){if(K.push(c4(X,$.toolUses,this.useColor,!1)),X.role==="assistant"&&X.hasToolUses)for(let Y of X.toolUses){let Q=$.toolUses.get(Y);if(Q){if(K.push(""),K.push(` [TOOL: ${Q.name}]`),K.push(` Input: ${JSON.stringify(Q.input)}`),Q.result){let G=Q.result.length>oZ.RESULT_TRUNCATE_LENGTH?Q.result.substring(0,oZ.RESULT_TRUNCATE_LENGTH)+"...":Q.result;K.push(` Result: ${G}`)}K.push(` Status: ${Q.status}`)}}K.push("")}return K.join(`
|
|
838
|
+
`)}formatError($){return`Error: ${A($)}`}formatNotFound($){return`Session not found: ${$}`}}var u4=U(()=>{w0()});function h3($){switch($){case T.DB_CONNECTION_FAILED:return"Check database file permissions";case T.DB_CORRUPTED:return"Run 'memory doctor' to diagnose or recreate database";case T.DB_LOCKED:return"Wait and retry, or check for other running processes";case T.INVALID_SESSION_ID:return"Check session ID format (expected UUID)";case T.SESSION_NOT_FOUND:return"Run 'memory list' to see available sessions";case T.SOURCE_INACCESSIBLE:return"Check that ~/.claude/projects exists and is readable";case T.DISK_FULL:return"Free up disk space and retry";case T.INVALID_JSON:return"Check file for JSON syntax errors";case T.UNKNOWN_FORMAT:return"File may be incompatible with current version";case T.SYNC_INTERRUPTED:return"Run 'memory sync' again to resume";case T.SYNC_FAILED:return`Check logs at ${O0()} for details`;case T.INVALID_ARGUMENT:return"Run command with --help to see valid options";case T.MISSING_ARGUMENT:return"Run command with --help to see required arguments";case T.VECTOR_UNAVAILABLE:return"Run 'memory sync --embed' to generate embeddings, or use '--mode fts' for keyword-only search";case T.PROVIDER_TIMEOUT:return"Check network connection or switch to local provider in config";case T.PROVIDER_CONFIG_INVALID:return"Check embedding config in ~/.config/memory/config.json";case T.EMBEDDING_DIMENSION_MISMATCH:return"Run 'memory sync --embed' to re-embed with the current model";case T.MODEL_CORRUPTED:return"Delete cached model files and run 'memory sync --embed' to re-download";case T.NOT_FOUND:return"Check the ID and try again";case T.INVALID_STATE:return"The entity is not in a valid state for this operation";case T.UNKNOWN:default:return null}}function A6($,Z){if(typeof Z==="string"||typeof Z==="number")return` ${$}: ${Z}`;return` ${$}: ${JSON.stringify(Z)}`}function c($,Z={}){let K=Z.useColor??k(),X=[];if($ instanceof R){let Y=f(`Error [${$.code}]:`,K);if(X.push(`${Y} ${$.message}`),$.context&&Object.keys($.context).length>0)for(let[G,_]of Object.entries($.context))X.push(A6(G,_));let Q=h3($.code);if(Q)X.push(""),X.push(`Suggestion: ${Q}`)}else{let Y=f("Error:",K);X.push(`${Y} ${$.message}`)}if(Z.verbose&&$.stack)X.push(""),X.push("Stack trace:"),X.push($.stack);return X.join(`
|
|
839
|
+
`)}function r0($){if($ instanceof R)return JSON.stringify($.toJSON());let Z={error:{code:"UNKNOWN",message:$.message}};return JSON.stringify(Z)}var M0=U(()=>{w$();p()});function g3($){return{schema_version:"1",command:$.command,kind:$.kind,...$.scope!==void 0?{scope:$.scope}:{},...$.meta!==void 0?{meta:$.meta}:{},data:$.data}}function m3($){return{schema_version:"1",command:$.command,error:{code:$.code,message:$.message,...$.context!==void 0?{context:$.context}:{}}}}function s($){let Z=process.env.MEMORY_JSON_COMMAND_OVERRIDE||$.command;console.log(JSON.stringify(g3({...$,command:Z}),null,2))}function S($){let Z=process.env.MEMORY_JSON_COMMAND_OVERRIDE||$.command;console.log(JSON.stringify(m3({...$,command:Z}),null,2))}var L0=()=>{};var eZ={};w(eZ,{writeLock:()=>p3,spawnBackgroundEmbedding:()=>M6,removeLock:()=>sZ,readLock:()=>a4,isProcessAlive:()=>i4,isBackgroundEmbedding:()=>x6,cleanupLock:()=>j6,acquireLock:()=>l3});import{spawn as L6}from"child_process";import{existsSync as I6,readFileSync as T6,writeFileSync as R6,unlinkSync as F6,mkdirSync as u3,openSync as c3}from"fs";import{join as d3}from"path";function n4($){return d3($??t(),"embedding.lock")}function p3($,Z){let K=n4(Z),X=Z??t();u3(X,{recursive:!0}),R6(K,JSON.stringify($))}function a4($){let Z=n4($);if(!I6(Z))return null;try{return JSON.parse(T6(Z,"utf-8"))}catch{return null}}function sZ($){let Z=n4($);try{F6(Z)}catch{}}function i4($){try{return process.kill($,0),!0}catch{return!1}}function l3($,Z,K){let X=a4(K);if(X){if(i4(X.pid))return{acquired:!1,existingPid:X.pid,startedAt:X.startedAt};sZ(K)}return p3({pid:$,startedAt:new Date().toISOString(),totalMessages:Z},K),{acquired:!0,staleRemoved:X!==null}}function M6($){let{dataDir:Z,logDir:K,command:X=process.execPath}=$??{},Y=a4(Z);if(Y&&i4(Y.pid))return{started:!1,reason:"already_running",pid:Y.pid};if(Y)sZ(Z);let Q=K??O0();u3(Q,{recursive:!0});let G=d3(Q,"sync.log"),_=c3(G,"a"),J=c3(G,"a"),V=[process.argv[1]??"","sync","--embed","--quiet"],B=L6(X,V,{detached:!0,stdio:["ignore",_,J],env:{...process.env,MEMORY_EMBED_BACKGROUND:"1"}});if(B.unref(),B.pid===void 0)return{started:!1,reason:"spawn_failed"};let z=l3(B.pid,0,Z);if(!z.acquired)return{started:!1,reason:"already_running",pid:z.existingPid};return{started:!0,pid:B.pid}}function j6($){sZ($)}function x6(){return process.env.MEMORY_EMBED_BACKGROUND==="1"}var $9=U(()=>{p()});var n3={};w(n3,{EmbeddingProviderFactory:()=>Z9});import{createHash as E6}from"crypto";class Z9{cache=new Map;cacheKey($){let Z=$.apiKey?E6("sha256").update($.apiKey).digest("hex").slice(0,16):"";return[$.provider,$.model,String($.dimensions),$.baseUrl??"",$.apiKeyEnv??"",$.apiKeyRef??"",Z].join(":")}create($){let Z=this.cacheKey($),K=this.cache.get(Z);if(K)return K;let X=x1($);return this.cache.set(Z,X),X}createFromConfig($){let Z=$.embedding??J$;if(!Z.enabled)return null;return this.create(Z)}async dispose(){for(let $ of this.cache.values())await $.dispose();this.cache.clear()}}var o4=U(()=>{Z0();wZ()});var e3={};w(e3,{PatternRedactor:()=>o0});class o0{redactText($){let Z=$,K=[];for(let X of D6)Z=Z.replace(X.pattern,(Y)=>{let Q=`[REDACTED:${X.kind}]`;return K.push({kind:X.kind,placeholder:Q}),`${X.preservePrefix?.(Y)??""}${Q}`});return{text:Z,findings:K}}redactJson($){let Z=[];return{value:this.redactUnknown($,Z,new WeakSet),findings:Z}}redactUnknown($,Z,K){if(typeof $==="string"){let X=this.redactText($);return Z.push(...X.findings),X.text}if(Array.isArray($))return $.map((X)=>this.redactUnknown(X,Z,K));if($&&typeof $==="object"){if(K.has($))return"[REDACTED:circular]";K.add($);let X={};for(let[Y,Q]of Object.entries($))X[Y]=this.redactUnknown(Q,Z,K);return X}return $}}var D6;var XZ=U(()=>{D6=[{kind:"private_key",pattern:/-----BEGIN [A-Z ]*PRIVATE KEY-----[\s\S]*?-----END [A-Z ]*PRIVATE KEY-----/g},{kind:"api_key",pattern:/\bsk-ant-[A-Za-z0-9_-]{20,}\b/g},{kind:"api_key",pattern:/\bsk-[A-Za-z0-9_-]{20,}\b/g},{kind:"api_key",pattern:/\bgh[pousr]_[A-Za-z0-9_]{20,}\b/g},{kind:"aws_access_key",pattern:/\b(A3T[A-Z0-9]|AKIA|ASIA)[A-Z0-9]{16}\b/g},{kind:"jwt",pattern:/\beyJ[A-Za-z0-9_-]+\.[A-Za-z0-9_-]+\.[A-Za-z0-9_-]+\b/g},{kind:"bearer_token",pattern:/\bBearer\s+[A-Za-z0-9._~+/=-]{16,}/g,preservePrefix:()=>"Bearer "},{kind:"env_secret",pattern:/\b([A-Z][A-Z0-9_]*(?:KEY|TOKEN|SECRET|PASSWORD|PASS|CREDENTIAL)[A-Z0-9_]*)\s*=\s*(?:"[^"]+"|'[^']+'|[^\s]+)/g,preservePrefix:($)=>`${$.split("=")[0].trim()}=`}]});var _8={};w(_8,{mergeMemoryBlock:()=>Q8,AutoMemoryWriter:()=>G8});import{existsSync as k6,mkdirSync as X8,readFileSync as S6,writeFileSync as e4}from"fs";import{join as Y8}from"path";function Q8($,Z){let K=`${$5}
|
|
840
|
+
${Z}
|
|
841
|
+
${K9}
|
|
842
|
+
`;if($.length===0)return K;let X=$.indexOf($5),Y=$.indexOf(K9);if(X!==-1&&Y!==-1){let G=$.substring(0,X),_=$.substring(Y+K9.length);return`${G}${K}${_}`}let Q=$.endsWith(`
|
|
843
|
+
`)?`
|
|
844
|
+
`:`
|
|
845
|
+
|
|
846
|
+
`;return`${$}${Q}${K}`}class G8{async writeContextFile($,Z){X8($,{recursive:!0}),e4(Y8($,"context.md"),Z,"utf-8")}async updateMemoryBlock($,Z){X8($,{recursive:!0});let K=Y8($,"MEMORY.md"),X=`${$5}
|
|
847
|
+
${Z}
|
|
848
|
+
${K9}
|
|
849
|
+
`;if(!k6(K)){e4(K,X,"utf-8");return}let Y=S6(K,"utf-8"),Q=Q8(Y,Z);e4(K,Q,"utf-8")}}var $5="<!-- memory-cli:start -->",K9="<!-- memory-cli:end -->";var J8=()=>{};var B8={};w(B8,{runGit:()=>W8,GitSyncer:()=>K5});import{readFileSync as v6,existsSync as C6}from"fs";import{join as H8}from"path";var{spawn:y6}=globalThis.Bun;async function W8($,Z,K=process.env){let X=y6(["git",...$],{cwd:Z,stdout:"pipe",stderr:"pipe",env:K}),Y=await new Response(X.stdout).text(),Q=await new Response(X.stderr).text(),G=await X.exited;return{success:G===0,stdout:Y.trim(),stderr:Q.trim(),exitCode:G}}function V8($,Z){let K={};for(let X of $)if(Z.existsSync(X))try{let Y=Z.readFileSync(X,"utf-8");K[X]=Bun.hash(Y).toString()}catch{K[X]="error"}return K}class K5{eventsDir;deps;constructor($,Z={}){this.eventsDir=$??jZ(),this.deps={runGit:W8,existsSync:C6,readFileSync:v6,getAllLogFiles:xZ,now:()=>new Date,...Z}}async isGitRepo(){let $=H8(this.eventsDir,".git");return this.deps.existsSync($)}async initRepo(){if(!(await this.deps.runGit(["init"],this.eventsDir)).success)return!1;let Z=await this.deps.runGit(["config","user.name"],this.eventsDir);if(!Z.success||!Z.stdout)await this.deps.runGit(["config","user.name","Memory Nexus"],this.eventsDir),await this.deps.runGit(["config","user.email","sync@memory-nexus.local"],this.eventsDir);return await this.deps.runGit(["checkout","-b","main"],this.eventsDir),!0}async configureRemote($){if(!$.trim())return!1;return await this.deps.runGit(["remote","remove","origin"],this.eventsDir),(await this.deps.runGit(["remote","add","origin",$],this.eventsDir)).success}async removeRemote(){let $=await this.deps.runGit(["remote","remove","origin"],this.eventsDir);return $.success||$.stderr.includes("No such remote")}async getRemoteUrl(){let $=await this.deps.runGit(["remote","get-url","origin"],this.eventsDir);return $.success?$.stdout:null}async sync($,Z,K=!0,X=!0){try{if(!await this.isGitRepo()){if(!await this.initRepo())return{success:!1,rebuildNeeded:!1,error:"Failed to initialize Git repository in events directory"}}if(await this.getRemoteUrl()!==Z){if(!await this.configureRemote(Z))return{success:!1,rebuildNeeded:!1,error:"Failed to configure Git remote repository URL"}}let G=this.deps.getAllLogFiles(this.eventsDir),_=V8(G,this.deps),J=`events-${$}.jsonl`,H=H8(this.eventsDir,J);if(this.deps.existsSync(H))await this.deps.runGit(["add",J],this.eventsDir),await this.deps.runGit(["commit","-m",`sync: ${$} observed at ${this.deps.now().toISOString()}`],this.eventsDir);let V=!0;if(K){if(await this.deps.runGit(["fetch","origin"],this.eventsDir),(await this.deps.runGit(["rev-parse","--verify","origin/main"],this.eventsDir)).success){let q=await this.deps.runGit(["pull","--rebase","origin","main"],this.eventsDir);if(!q.success)return V=!1,await this.deps.runGit(["rebase","--abort"],this.eventsDir),{success:!1,rebuildNeeded:!1,error:`Git pull failed: ${q.stderr}`}}}if(X&&V){let N=await this.deps.runGit(["push","-u","origin","main"],this.eventsDir);if(!N.success)return{success:!1,rebuildNeeded:!1,error:`Git push failed: ${N.stderr}`}}let B=this.deps.getAllLogFiles(this.eventsDir),z=V8(B,this.deps),W=!1;if(G.length!==B.length)W=!0;else for(let N of B)if(_[N]!==z[N]){W=!0;break}return{success:!0,rebuildNeeded:W}}catch(Y){return{success:!1,rebuildNeeded:!1,error:A(Y)}}}}var X5=U(()=>{p()});var U8={};w(U8,{rebuildProjections:()=>O8,readEvents:()=>q8,appendEvent:()=>N8});import{appendFile as w6,mkdir as b6}from"fs/promises";import{dirname as f6}from"path";import{existsSync as h6,createReadStream as g6}from"fs";import*as A8 from"readline";async function N8($,Z){let K=Z;if(!K){let Q=m();K=m5(Q.machineId)}let X=f6(K);await b6(X,{recursive:!0});let Y={id:$.id,uuid:$.uuid,type:$.type,project:$.project,content:$.content,metadata:$.metadata,observedAt:$.observedAt.toISOString(),supersededAt:$.supersededAt?$.supersededAt.toISOString():null,supersededBy:$.supersededBy,version:1};await w6(K,JSON.stringify(Y)+`
|
|
850
|
+
`,"utf-8")}async function*q8($,Z){if($){yield*z8($);return}let K=xZ(Z),X=[];for(let Y of K)for await(let Q of z8(Y))X.push(Q);X.sort((Y,Q)=>{let G=Y.observedAt.getTime()-Q.observedAt.getTime();if(G!==0)return G;return Y.uuid.localeCompare(Q.uuid)});for(let Y of X)yield Y}async function*z8($){if(!h6($))return;let Z=g6($,"utf-8"),K=A8.createInterface({input:Z,crlfDelay:1/0});for await(let X of K){if(!X.trim())continue;try{let Y=JSON.parse(X),Q=A0.create({uuid:Y.uuid,type:Y.type,project:Y.project,content:Y.content,metadata:Y.metadata,observedAt:new Date(Y.observedAt),supersededAt:Y.supersededAt?new Date(Y.supersededAt):null,supersededBy:Y.supersededBy??null});yield Y.id!==void 0?Q.withId(Y.id):Q}catch(Y){console.error("Skipping malformed event log line:",Y)}}}async function O8($,Z,K){let X=[];for await(let Q of q8(Z,K))X.push(Q);$.transaction(()=>{$.run("DELETE FROM facts;");let Q=$.prepare(`
|
|
851
|
+
INSERT INTO facts (
|
|
852
|
+
uuid, type, project, content, metadata, observed_at, superseded_at, superseded_by
|
|
853
|
+
) VALUES (?, ?, ?, ?, ?, ?, ?, ?)
|
|
854
|
+
`);for(let G of X)if(Q.run(G.uuid,G.type,G.project,G.content,G.metadata?JSON.stringify(G.metadata):null,G.observedAt.toISOString(),G.supersededAt?G.supersededAt.toISOString():null,G.supersededBy),G.type==="supersedence"){let _=G.metadata?.superseded_uuid,J=G.metadata?.superseded_by_uuid;if(_&&J)$.prepare(`
|
|
855
|
+
UPDATE facts
|
|
856
|
+
SET superseded_at = ?, superseded_by = ?, updated_at = datetime('now')
|
|
857
|
+
WHERE uuid = ?
|
|
858
|
+
`).run(G.observedAt.toISOString(),J,_)}})()}var Y5=U(()=>{v$();p();Z0()});import*as I8 from"chrono-node";function L$($,Z){if(!$||$.trim()==="")throw new I0("Invalid date format: ''. Examples: 'yesterday', '2 weeks ago', '2026-01-15'");let K=Z??new Date,X=I8.parseDate($,K);if(!X)throw new I0(`Invalid date format: '${$}'. Examples: 'yesterday', '2 weeks ago', '2026-01-15'`);let Y=new Date(X.getFullYear(),X.getMonth(),X.getDate()),Q=new Date(K.getFullYear(),K.getMonth(),K.getDate());if(Y>Q)throw new I0(`Future dates not allowed: '${$}'. Examples: 'yesterday', '2 weeks ago', '2026-01-15'`);return X}var I0;var Q5=U(()=>{I0=class I0 extends Error{constructor($){super($);this.name="DateParseError"}}});function K0($){if($.json)return;let Z=`${$.command}:--format=${$.alias}`;if(T8.has(Z))return;T8.add(Z),console.error(`warning: --format ${$.alias} is deprecated and will be removed in the next minor release. ${$.replacement}`)}var T8;var t0=U(()=>{T8=new Set});import{spawn as l6,execSync as X9}from"child_process";class Y9{search($){return new Promise((Z,K)=>{let X=l6("qmd",["search",$,"--json"],{stdio:["pipe","pipe","pipe"]}),Y="",Q="";X.stdout.on("data",(G)=>{Y+=G.toString()}),X.stderr.on("data",(G)=>{Q+=G.toString()}),X.on("error",(G)=>{K(Error(`Failed to spawn qmd: ${G.message}`))}),X.on("close",(G)=>{if(G===0)try{let _=JSON.parse(Y);Z(_)}catch{K(Error(`Failed to parse qmd output: ${Y.slice(0,200)}`))}else K(Error(`qmd exited with code ${G}: ${Q.trim()}`))})})}isAvailable(){try{return X9("which qmd",{stdio:"ignore"}),!0}catch{return!1}}getHealthInfo(){try{return{available:!0,path:X9("which qmd",{encoding:"utf-8"}).trim()}}catch{return{available:!1,path:null}}}}function G5(){try{return X9("which qmd",{stdio:"ignore"}),!0}catch{return!1}}function Q9(){try{return{available:!0,path:X9("which qmd",{encoding:"utf-8"}).trim()}}catch{return{available:!1,path:null}}}var R8=()=>{};var G9=U(()=>{R8()});var j8={};w(j8,{runShowInternal:()=>i6,executeShowCommand:()=>I$,createShowCommand:()=>M8});import{Command as n6,Option as _5}from"commander";function M8(){return new n6("show").description("Show session details").argument("<session-id>","Session ID to display").option("--json","Output as JSON").addOption(new _5("--format <type>","Output format: brief (single-line summary) or ai (AI-optimized text). 'default' accepted as deprecated alias.").choices(["brief","ai","default"])).addOption(new _5("-v, --verbose","Show detailed output").conflicts("quiet")).addOption(new _5("-q, --quiet","Minimal output (message content only)").conflicts("verbose")).option("--tools","Show detailed tool inputs and outputs").action(async($,Z)=>{let K=await I$($,Z);process.exitCode=K.exitCode})}function F8($){if($.json)return"json";if($.tools)return"tools";if($.quiet)return"quiet";if($.verbose)return"verbose";if($.format==="brief")return"brief";return"default"}async function a6($,Z,K){let X=await $.findById(Z);if(X)return X;let Q=K.prepare("SELECT id FROM sessions WHERE id LIKE ? ORDER BY start_time DESC LIMIT 1").get(`${Z}%`);if(Q)return $.findById(Q.id);return null}async function I$($,Z,K={}){let{executeQueryCommand:X}=await Promise.resolve().then(() => (s0(),T$));process.env.MEMORY_JSON_COMMAND_OVERRIDE="show";try{return await X($,{...Z,kind:"session",dbPath:K.dbPath})}finally{delete process.env.MEMORY_JSON_COMMAND_OVERRIDE}}async function i6($,Z,K={}){let X=performance.now();if(Z.format==="default")K0({command:"show",alias:"default",replacement:"Omit --format for default behavior, or use --format brief / --format ai.",json:Z.json});let Y=K.dbPath??E(),{db:Q}=v({path:Y});try{let G=new g(Q),_=new T0(Q),J=new p0(Q),H=await a6(G,$,Q);if(!H){if(Z.json)S({command:"show",code:"NOT_FOUND",message:`Session not found: ${$}`,context:{session_id:$}});else{let L=F8(Z),O=tZ(L,k());console.log(O.formatNotFound($))}return{exitCode:1}}let V=await _.findBySession(H.id),B=await J.findBySession(H.id),z=new Map;for(let L of B)z.set(L.id,L);let W={session:H,messages:V,toolUses:z};if(Z.json){let L=performance.now();return s({command:"show",kind:"session",data:Z3(W),meta:{session_id:H.id,message_count:V.length,timing_ms:Math.round(L-X)}}),{exitCode:0}}let N=F8(Z),q=tZ(N,k()),I=performance.now(),F=q.formatSession(W,{executionTimeMs:Math.round(I-X)});if(Z.format==="ai")F=a(F);return console.log(F),{exitCode:0}}catch(G){let _=G instanceof R?G:new R(T.DB_CONNECTION_FAILED,A(G));if(Z.json)S({command:"show",code:_.code,message:_.message,..._.context!==void 0?{context:_.context}:{}});else console.error(c(_));return{exitCode:1}}finally{D(Q)}}var _9=U(()=>{Q0();E0();h$();a9();u();u4();F0();M0();L0();b0();t0()});var P8={};w(P8,{runListInternal:()=>o6,executeListCommand:()=>J9,createListCommand:()=>x8});import{Command as r6,Option as R$}from"commander";function x8(){return new r6("list").description("List sessions").option("-l, --limit <count>","Maximum sessions to return","20").option("-p, --project <name>","Filter by project name").addOption(new R$("--since <date>","Sessions after date (e.g., 'yesterday', '2 weeks ago')").conflicts("days")).addOption(new R$("--before <date>","Sessions before date").conflicts("days")).addOption(new R$("--days <n>","Sessions from last N days (includes today)").argParser(($)=>{let Z=parseInt($,10);if(isNaN(Z)||Z<1)throw Error("Days must be a positive number");return Z}).conflicts(["since","before"])).option("--json","Output as JSON").addOption(new R$("--format <type>","Output format: brief (single-line per session) or ai (AI-optimized text). 'default' accepted as deprecated alias.").choices(["brief","ai","default"])).addOption(new R$("-v, --verbose","Show detailed output").conflicts("quiet")).addOption(new R$("-q, --quiet","Minimal output (session IDs only)").conflicts("verbose")).action(async($)=>{let Z=await J9($);process.exitCode=Z.exitCode})}async function J9($,Z={}){let{executeQueryCommand:K}=await Promise.resolve().then(() => (s0(),T$)),X=$.project?"project":"global";process.env.MEMORY_JSON_COMMAND_OVERRIDE="list";try{return await K(void 0,{...$,kind:"session",scope:X,dbPath:Z.dbPath})}finally{delete process.env.MEMORY_JSON_COMMAND_OVERRIDE}}async function o6($,Z={}){let K=performance.now();if($.format==="default")K0({command:"list",alias:"default",replacement:"Omit --format for default behavior, or use --format brief / --format ai.",json:$.json});let X=Z.dbPath??E(),Y=parseInt($.limit??"20",10);if(isNaN(Y)||Y<1){if($.json)S({command:"list",code:"INVALID_ARGUMENT",message:"Limit must be a positive number"});else console.error("Error: Limit must be a positive number");return{exitCode:1}}let Q,G;if($.days){let J=new Date,H=new Date(J.getFullYear(),J.getMonth(),J.getDate());Q=new Date(H.getTime()-($.days-1)*24*60*60*1000)}else{if($.since)try{Q=L$($.since)}catch(J){if(J instanceof I0){if($.json)S({command:"list",code:"INVALID_ARGUMENT",message:J.message,context:{flag:"since",value:$.since}});else console.error(`Error: ${J.message}`);return{exitCode:1}}throw J}if($.before)try{G=L$($.before)}catch(J){if(J instanceof I0){if($.json)S({command:"list",code:"INVALID_ARGUMENT",message:J.message,context:{flag:"before",value:$.before}});else console.error(`Error: ${J.message}`);return{exitCode:1}}throw J}}let{db:_}=v({path:X});try{let J=new g(_),H={limit:Y,projectFilter:$.project,sinceDate:Q,beforeDate:G},V=await J.findFiltered(H),B=t6($);if($.json){let L=performance.now(),O=V.map(lZ);return s({command:"list",kind:"session",data:O,meta:{filters_applied:B,count:O.length,timing_ms:Math.round(L-K)}}),{exitCode:0}}let z="default";if($.quiet)z="quiet";else if($.verbose)z="verbose";else if($.format==="brief")z="brief";let W=k(),N=D4(z,W);if(V.length===0)return console.log(N.formatEmpty()),{exitCode:0};let q=performance.now(),I={executionTimeMs:Math.round(q-K),filtersApplied:B},F=N.formatSessions(V,I);if($.format==="ai")F=a(F);return console.log(F),{exitCode:0}}catch(J){let H=J instanceof R?J:new R(T.DB_CONNECTION_FAILED,A(J));if($.json)S({command:"list",code:H.code,message:H.message,...H.context!==void 0?{context:H.context}:{}});else console.error(c(H));return{exitCode:1}}finally{D(_)}}function t6($){let Z=[];if($.limit)Z.push(`limit: ${$.limit}`);if($.project)Z.push(`project: ${$.project}`);if($.days)Z.push(`days: ${$.days}`);if($.since)Z.push(`since: ${$.since}`);if($.before)Z.push(`before: ${$.before}`);return Z}var J5=U(()=>{E0();Q0();u();k4();F0();Q5();M0();L0();b0();t0()});import{copyFileSync as mW,cpSync as cW,existsSync as H5,mkdirSync as uW,readdirSync as dW,renameSync as pW,rmSync as lW,statSync as nW,unlinkSync as aW}from"fs";function E8(){let $=H5(g5()),Z=H5(K$())||H5(t()),K;if(!$&&!Z)K="not-needed";else if($&&!Z)K="pending";else if(!$&&Z)K="complete";else K="partial";return{legacyExists:$,newExists:Z,status:K}}var D8=U(()=>{p();J4()});var V5={};w(V5,{gatherStatus:()=>C8,formatTimeAgo:()=>b8,formatStatusOutput:()=>w8,executeStatusCommand:()=>h0,createStatusCommand:()=>v8,attemptFixes:()=>y8});import{Command as s6,Option as e6}from"commander";import{existsSync as $K,mkdirSync as k8}from"fs";import{dirname as S8}from"path";function v8(){return new s6("status").description("Show system status, health, and statistics").option("--db","Show database health and diagnostic info").option("--hooks","Show Git hook status").option("--embedding","Show background embedding process status").option("--config","Show config validation status").option("--stats","Show database statistics").option("--all","Show all status and health sections").option("--fix","Attempt to fix common issues automatically").option("--projects <count>","Number of projects to show in stats breakdown","10").addOption(new e6("--format <type>","Output format for stats: brief or ai").choices(["brief","ai","default"])).option("-v, --verbose","Show detailed output with timing").option("-q, --quiet","Minimal output").option("--json","Output as JSON").action(async($)=>{let Z=await h0($);process.exitCode=Z.exitCode})}async function C8($={}){let Z=R0($.hookOverrides),K=m($.configPath),X=V$(1,$.logPath),Y=$.dbPath??E(),G=$K(Y)||$.stats,_=0,J,H=0,V=0,B=U4({dbPath:Y,configDir:$.configPath?S8($.configPath):void 0,logsDir:$.logPath?S8($.logPath):void 0,hookOverrides:$.hookOverrides,preCalculatedHookStatus:Z});if(G)try{let{db:F}=v({path:Y});try{let L=new y0,O=new d0(F),M=await L.discoverSessions();for(let g0 of M){let H0=await O.findBySessionPath(g0.path);if(!H0||H0.status!=="complete")_++}let x=new Y$(F),y=$.projects??10;J=await x.getStats(y);let J0=new D0(F);H=J0.getEmbeddedCount(),V=J0.getTotalMessageCount()}finally{D(F)}}catch{}let z={active:!1};try{let{readLock:F,isProcessAlive:L}=await Promise.resolve().then(() => ($9(),eZ)),O=F();if(O&&L(O.pid))z={active:!0,pid:O.pid,startedAt:O.startedAt,embeddedCount:H,totalMessages:V}}catch{}let W=E8(),N=Q9(),q;if(J)q={...J,hooks:{installed:Z.sessionEnd&&Z.preCompact,autoSync:K.autoSync,pendingSessions:_}};let I=[];if($.fix)I=y8(B,k());return{hooks:Z,config:ZK(K),lastSync:X.length>0?X[0]?.timestamp??null:null,pendingSessions:_,recentLogs:V$(100,$.logPath).length,embedding:z,health:B,stats:q,migration:W,qmd:N,fixes:I}}function ZK($){let Z={...$.embedding};if(Z.apiKey)Z.apiKey="[REDACTED:api_key]";return{...$,embedding:Z}}async function h0($,Z={}){let K=performance.now();if($.format==="default")K0({command:"status",alias:"default",replacement:"Omit --format for default behavior, or use --format brief / --format ai.",json:$.json});let Y=$.stats&&!$.db&&!$.hooks&&!$.config&&!$.embedding&&!$.all?"stats":"status",Q=parseInt($.projects??"10",10);if(isNaN(Q)||Q<1){if($.json)S({command:Y,code:"INVALID_ARGUMENT",message:"Projects count must be a positive number"});else console.error("Error: Projects count must be a positive number");return{exitCode:1}}let _=await(Z.gatherStatus??C8)({dbPath:Z.dbPath,logPath:Z.logPath,configPath:Z.configPath,hookOverrides:Z.hookOverrides,fix:$.fix,projects:Q,stats:$.stats||$.all}),J=0;if($.db||$.all||$.fix)J=WK(_.health);else if($.stats)J=_.stats?0:1;else J=0;if($.json){if($.stats&&!$.db&&!$.hooks&&!$.config&&!$.embedding&&!$.all){if(!_.stats)return S({command:"stats",code:"DB_CONNECTION_FAILED",message:"Database stats could not be gathered"}),{exitCode:1};return s({command:"stats",kind:"stats",data:P4(_.stats),meta:{generated_at:new Date().toISOString(),timing_ms:Math.round(performance.now()-K)}}),{exitCode:0}}let W={hooks:_.hooks,config:_.config,lastSync:_.lastSync,pendingSessions:_.pendingSessions,recentLogs:_.recentLogs,embedding:_.embedding,health:{..._.health,hooks:{..._.health.hooks,lastRun:_.health.hooks.lastRun?.toISOString()??null}},stats:_.stats?P4(_.stats):void 0,migration:_.migration,qmd:_.qmd,fixes:_.fixes};return console.log(JSON.stringify(W,null,2)),{exitCode:J}}let V=k();if(!($.db||$.hooks||$.embedding||$.config||$.stats||$.all)){if(w8(_),$.fix&&_.fixes.length>0){console.log(`
|
|
859
|
+
Applied fixes:`);for(let W of _.fixes)console.log(W)}return{exitCode:0}}let z=[];if($.hooks||$.all)z.push(XK(_,V));if($.config||$.all)z.push(YK(_,V));if($.db||$.all)z.push(QK(_,V));if($.embedding||$.all)z.push(GK(_,V)),z.push(_K(_,V));if($.stats||$.all)if(!_.stats)z.push(f("Database statistics are not available.",V));else{let W="default";if($.quiet)W="quiet";else if($.verbose)W="verbose";else if($.format==="brief")W="brief";let N=v4(W,V);if(_.stats.totalSessions===0)z.push(N.formatEmpty());else{let q=N.formatStats(_.stats,{executionTimeMs:Math.round(performance.now()-K)});if($.format==="ai")q=a(q);z.push(q)}}if(console.log(z.join(`
|
|
860
|
+
|
|
861
|
+
`)),$.all||$.db){if(_.migration.status==="pending")console.log(""),console.log(d("Legacy data found at ~/.memory-nexus/. Run any memory command to auto-migrate.",V));else if(_.migration.status==="partial")console.log(""),console.log(d("Partial migration detected. Some data in ~/.memory-nexus/ and some in new paths. Re-run migration or check manually.",V))}if($.fix)if(console.log(""),console.log("Attempting fixes..."),_.fixes.length===0)console.log(P("No automatic fixes available.",V));else for(let W of _.fixes)console.log(W);return{exitCode:J}}function KK($){let K=Date.now()-$.getTime(),X=Math.floor(K/1000),Y=Math.floor(X/60),Q=Math.floor(Y/60),G=Math.floor(Q/24);if(G>0)return`${G} day${G>1?"s":""} ago`;if(Q>0)return`${Q} hour${Q>1?"s":""} ago`;if(Y>0)return`${Y} minute${Y>1?"s":""} ago`;return"just now"}function XK($,Z){let K=[];if(K.push("Hooks"),K.push(` ${h($.health.hooks.installed,Z)} Installed: ${$.health.hooks.installed?"yes":"no"}`),K.push(` ${h($.health.hooks.enabled,Z)} Enabled (autoSync): ${$.health.hooks.enabled?"yes":"no"}`),$.health.hooks.lastRun)K.push(` ${P(`Last run: ${KK($.health.hooks.lastRun)}`,Z)}`);else K.push(` ${P("Last run: never",Z)}`);return K.join(`
|
|
862
|
+
`)}function YK($,Z){let K=[];if(K.push("Configuration"),$.health.config.valid)K.push(` ${h(!0,Z)} Valid`);else{K.push(` ${h(!1,Z)} Invalid`);for(let X of $.health.config.issues)K.push(` ${f("-",Z)} ${X}`)}return K.join(`
|
|
863
|
+
`)}function QK($,Z){let K=[];K.push("Database");let X=E();if($.health.database.exists)K.push(` ${h($.health.database.exists,Z)} Exists: ${X}`),K.push(` ${h($.health.database.readable,Z)} Readable`),K.push(` ${h($.health.database.writable,Z)} Writable`),K.push(` ${h($.health.database.integrity==="ok",Z)} Integrity: ${HK($.health.database.integrity,Z)}`),K.push(` ${P(`Size: ${JK($.health.database.size)}`,Z)}`);else K.push(` ${h(!1,Z)} Database not found: ${X}`),K.push(` ${P("Run 'memory sync' to create database",Z)}`);if($.health.sqliteVec.available)K.push(` ${h(!0,Z)} sqlite-vec: v${$.health.sqliteVec.version}`);else K.push(` ${h(!1,Z)} sqlite-vec: not available`);if(K.push(""),K.push("Permissions"),K.push(` ${h($.health.permissions.configDir,Z)} Config directory: ${n0()}`),K.push(` ${h($.health.permissions.logsDir,Z)} Logs directory: ${H$()}`),K.push(` ${h($.health.permissions.sourceDir,Z)} Source directory: ~/.claude/projects`),K.push(""),K.push("Search Capability"),K.push(` ${h($.health.searchCapability.fts5,Z)} FTS5: available`),K.push(` ${h($.health.searchCapability.sqliteVec,Z)} sqlite-vec: ${$.health.searchCapability.sqliteVec?"available":"not available"}`),K.push(` ${P(`Embeddings: ${$.health.searchCapability.embeddedCount}/${$.health.searchCapability.totalMessages} (${$.health.searchCapability.coveragePercent}%)`,Z)}`),K.push(` ${P(`Default mode: ${$.health.searchCapability.defaultMode}`,Z)}`),K.push(` ${h($.health.searchCapability.vectorReady,Z)} Vector search: ${$.health.searchCapability.vectorReady?"ready":"not ready"}`),K.push(""),K.push("Optional Tools"),$.qmd.available)K.push(` ${P("[INFO]",Z)} qmd: installed at ${$.qmd.path} (enables --files search)`);else K.push(` ${P("[INFO]",Z)} qmd: not found (optional -- install with: bun add -g @tobilu/qmd)`);return K.join(`
|
|
864
|
+
`)}function GK($,Z){let K=[];if(K.push("Embeddings"),K.push(` ${h($.health.embedding.enabled,Z)} Enabled: ${$.health.embedding.enabled?"yes":"no"}`),K.push(` ${P(`Provider: ${$.health.embedding.provider}`,Z)}`),K.push(` ${P(`Model: ${$.health.embedding.model}`,Z)}`),K.push(` ${P(`Dimensions: ${$.health.embedding.dimensions}`,Z)}`),K.push(` ${h($.health.embedding.ready,Z)} Ready: ${$.health.embedding.ready?"yes":"no"}`),$.health.embedding.readyReason)if($.health.embedding.ready)K.push(` ${P(`Note: ${$.health.embedding.readyReason}`,Z)}`);else K.push(` ${f(`Reason: ${$.health.embedding.readyReason}`,Z)}`);return K.join(`
|
|
865
|
+
`)}function _K($,Z){let K=[];if(K.push("LLM Fact Extraction"),K.push(` ${h($.health.llmExtraction.ready,Z)} Ready: ${$.health.llmExtraction.ready?"yes":"no"}`),K.push(` ${P(`Provider: ${$.health.llmExtraction.provider}`,Z)}`),K.push(` ${P(`Model: ${$.health.llmExtraction.model}`,Z)}`),$.health.llmExtraction.readyReason)if($.health.llmExtraction.ready)K.push(` ${P(`Note: ${$.health.llmExtraction.readyReason}`,Z)}`);else K.push(` ${f(`Reason: ${$.health.llmExtraction.readyReason}`,Z)}`);return K.join(`
|
|
866
|
+
`)}function h($,Z){if($)return b("[OK]",Z);return f("[FAIL]",Z)}function JK($){if($===0)return"0 B";let Z=["B","KB","MB","GB"],K=1024,X=Math.floor(Math.log($)/Math.log(K));return`${($/Math.pow(K,X)).toFixed(X>0?1:0)} ${Z[X]}`}function HK($,Z){switch($){case"ok":return b("ok",Z);case"corrupted":return f("CORRUPTED",Z);default:return d("unknown",Z)}}function VK($){let Z=0;if(!$.database.readable)Z++;if(!$.database.writable)Z++;if(!$.permissions.configDir)Z++;if(!$.permissions.logsDir)Z++;if(!$.permissions.sourceDir)Z++;return Z+=$.config.issues.length,Z}function WK($){if(!$.database.exists||$.database.integrity==="corrupted")return 2;if(VK($)>0||!$.searchCapability.vectorReady)return 1;return 0}function y8($,Z){let K=[];if(!$.permissions.configDir){let X=n0();try{k8(X,{recursive:!0}),K.push(b(`Created config directory: ${X}`,Z))}catch(Y){let Q=A(Y);K.push(f(`Failed to create config directory: ${Q}`,Z))}}if(!$.permissions.logsDir){let X=H$();try{k8(X,{recursive:!0}),K.push(b(`Created logs directory: ${X}`,Z))}catch(Y){let Q=A(Y);K.push(f(`Failed to create logs directory: ${Q}`,Z))}}if($.database.integrity==="corrupted")K.push(d("Database corruption detected. Consider:",Z)),K.push(" 1. Backup your database file"),K.push(` 2. Delete the database: rm ${E()}`),K.push(" 3. Re-sync: memory sync");if(!$.hooks.installed)K.push(d("Hooks not installed. Run 'memory install' to enable automatic sync.",Z));return K}function w8($){if(console.log("Memory Status"),console.log(`=============
|
|
867
|
+
`),console.log("Hooks:"),console.log(` SessionEnd: ${$.hooks.sessionEnd?"installed":"not installed"}`),console.log(` PreCompact: ${$.hooks.preCompact?"installed":"not installed"}`),console.log(` Hook script: ${$.hooks.hookScriptExists?"present":"missing"}`),console.log(` Backup: ${$.hooks.backupExists?"available":"none"}`),console.log(""),console.log("Configuration:"),console.log(` autoSync: ${$.config.autoSync}`),console.log(` syncOnCompaction: ${$.config.syncOnCompaction}`),console.log(` recoveryOnStartup: ${$.config.recoveryOnStartup}`),console.log(` timeout: ${$.config.timeout}ms`),console.log(` logLevel: ${$.config.logLevel}`),console.log(` showFailures: ${$.config.showFailures}`),console.log(""),console.log("Activity:"),console.log(` Last sync: ${$.lastSync??"never"}`),console.log(` Pending sessions: ${$.pendingSessions}`),console.log(` Recent log entries: ${$.recentLogs}`),console.log(""),console.log("Embedding:"),$.embedding.active){let Z=$.embedding.startedAt?b8($.embedding.startedAt):"unknown",K=$.embedding.embeddedCount!==void 0&&$.embedding.totalMessages!==void 0?`, ${$.embedding.embeddedCount}/${$.embedding.totalMessages} messages`:"";console.log(` Status: active (PID ${$.embedding.pid}${K}, started ${Z})`)}else console.log(" Status: idle");if(!$.hooks.sessionEnd||!$.hooks.preCompact)console.log(`
|
|
868
|
+
Recommendation: Run 'memory install' to enable automatic sync.`);if($.pendingSessions>0)console.log(`
|
|
869
|
+
Note: ${$.pendingSessions} session(s) pending sync. Run 'memory sync' to sync now.`)}function b8($){let Z=Date.now()-new Date($).getTime(),K=Math.floor(Z/60000);if(K<1)return"just now";if(K<60)return`${K} min ago`;let X=Math.floor(K/60);if(X<24)return`${X}h ago`;return`${Math.floor(X/24)}d ago`}var F$=U(()=>{z$();u();ZZ();D8();G9();C4();F0();t0();L0();b0()});var h8={};w(h8,{executeStatsCommand:()=>H9,createStatsCommand:()=>f8});import{Command as BK,Option as W5}from"commander";function f8(){return new BK("stats").description("Show database statistics").option("--json","Output as JSON").addOption(new W5("--format <type>","Output format: brief (top-line counters) or ai (AI-optimized text). 'default' accepted as deprecated alias.").choices(["brief","ai","default"])).addOption(new W5("-v, --verbose","Show detailed output with timing").conflicts("quiet")).addOption(new W5("-q, --quiet","Minimal output").conflicts("verbose")).option("--projects <count>","Number of projects to show in breakdown","10").action(async($)=>{let Z=await H9($);process.exitCode=Z.exitCode})}async function H9($,Z={}){return h0({stats:!0,projects:$.projects,format:$.format,verbose:$.verbose,quiet:$.quiet,json:$.json},{dbPath:Z.dbPath})}var B5=U(()=>{F$()});var u8={};w(u8,{runContextInternal:()=>NK,executeContextCommand:()=>M$,createContextCommand:()=>c8});import*as g8 from"fs";import*as m8 from"os";import{join as zK}from"path";import{Command as AK,Option as YZ}from"commander";function c8(){return new AK("context").description("Show aggregated context for a project").argument("<project>","Project name or substring to filter by").addOption(new YZ("--days <n>","Sessions from last N days (includes today)").argParser(($)=>{let Z=parseInt($,10);if(isNaN(Z)||Z<1)throw Error("Days must be a positive number");return Z})).addOption(new YZ("--format <type>","Output format: brief, ai. 'detailed' accepted as deprecated alias.").choices(["brief","ai","detailed"])).addOption(new YZ("--budget <tokens>","Maximum token budget for context").argParser(($)=>{let Z=parseInt($,10);if(isNaN(Z)||Z<1)throw Error("Budget must be a positive number");return Z})).option("--cross-project","Include cross-project learnings and decisions").option("--json","Output as JSON").addOption(new YZ("-v, --verbose","Show detailed output with timing").conflicts("quiet")).addOption(new YZ("-q, --quiet","Minimal output").conflicts("verbose")).action(async($,Z)=>{let K=await M$($,Z);process.exitCode=K.exitCode})}async function M$($,Z){let{executeQueryCommand:K}=await Promise.resolve().then(() => (s0(),T$));process.env.MEMORY_JSON_COMMAND_OVERRIDE="context";try{return await K($,{...Z,kind:"context",scope:"project"})}finally{delete process.env.MEMORY_JSON_COMMAND_OVERRIDE}}async function NK($,Z,K){if(Z.format==="detailed")K0({command:"context",alias:"detailed",replacement:"Use --format brief or --format ai.",json:Z.json});let X=zK(m8.homedir(),".memory");if(g8.existsSync(X)&&!Z.quiet&&!Z.json)console.error("[DEPRECATION WARNING] Legacy memory directory ~/.memory/ is deprecated. Your knowledge and decisions are now stored safely in the SQLite database.");let Y=K?.dbPath??Z.dbPath??E(),{db:Q}=v({path:Y});try{return await qK(Q,$,Z)}catch(G){let _=G instanceof R?G:new R(T.DB_CONNECTION_FAILED,A(G));if(Z.json)S({command:"context",code:_.code,message:_.message,..._.context!==void 0?{context:_.context}:{}});else console.error(c(_));return{exitCode:1}}finally{D(Q)}}async function qK($,Z,K){let X=new G$($),Y=new l0($),Q=new k0($),G=new Q$($),J=await new f$({projectResolver:X,factRepo:Y,frictionRepo:Q,getSessionSummary:async(z,W)=>{let N=await G.getProjectContext(z,{days:W});if(!N)return null;return`Sessions: ${N.sessionCount} | Messages: ${N.totalMessages} | Last active: ${N.lastActivity?.toISOString()??"never"}`}}).getContext({projectFilter:Z,budget:K.budget,days:K.days,crossProject:K.crossProject});if(K.json){if(!J)return S({command:"context",code:"NOT_FOUND",message:`Project not found: ${Z}`,context:{project:Z}}),{exitCode:1};let z=await G.getProjectContext(Z,{days:K.days});return s({command:"context",kind:"context",data:z?X3(z):null,meta:{project:Z,days:K.days,budget:K.budget,cross_project:!!K.crossProject,mode:"smart",sections:J.sections.map((W)=>({key:W.key,title:W.title}))}}),{exitCode:0}}let H=K.format==="ai"?"ai":K.verbose?"verbose":K.quiet?"quiet":K.format==="detailed"?"detailed":"brief",V=k(),B=iZ(H,V);if(!J){let z=B.formatEmpty(Z);if(H!=="quiet"||z)console.error(z);return{exitCode:1}}if(B.formatSmartContext){let z=B.formatSmartContext(J);console.log(z)}else{let z=J.sections.find((W)=>W.key==="session_summary");if(z)console.log(z.content);else{let W=J.sections.map((N)=>`${N.title}:
|
|
870
|
+
${N.content}`).join(`
|
|
871
|
+
|
|
872
|
+
`);console.log(W)}}return{exitCode:0}}var V9=U(()=>{Q0();X$();EZ();u();LZ();rZ();M0();L0();b0();t0()});var p8={};w(p8,{runRelatedInternal:()=>UK,executeRelatedCommand:()=>x$,createRelatedCommand:()=>d8});import{Command as OK,Option as j$}from"commander";function d8(){return new OK("related").description("Find sessions related through shared topics/entities").argument("<id>","Session ID, message ID, or topic name").addOption(new j$("--limit <n>","Maximum results").argParser(($)=>{let Z=parseInt($,10);if(isNaN(Z)||Z<1)throw Error("Limit must be a positive number");return Z}).default(10)).addOption(new j$("--hops <n>","Traversal depth (1-3)").argParser(($)=>{let Z=parseInt($,10);if(isNaN(Z)||Z<1||Z>3)throw Error("Hops must be 1, 2, or 3");return Z}).default(2)).addOption(new j$("--type <type>","Entity type of the ID").choices(["session","message","topic"]).default("session")).addOption(new j$("--format <type>","Output format: brief, ai. 'detailed' accepted as deprecated alias.").choices(["brief","ai","detailed"])).option("--json","Output as JSON").addOption(new j$("-v, --verbose","Show detailed output with timing").conflicts("quiet")).addOption(new j$("-q, --quiet","Minimal output (session IDs only)").conflicts("verbose")).action(async($,Z)=>{let K=await x$($,Z);process.exitCode=K.exitCode})}async function x$($,Z){let{executeQueryCommand:K}=await Promise.resolve().then(() => (s0(),T$));process.env.MEMORY_JSON_COMMAND_OVERRIDE="related";try{return await K($,{...Z,kind:"related"})}finally{delete process.env.MEMORY_JSON_COMMAND_OVERRIDE}}async function UK($,Z,K){let X=performance.now();if(Z.format==="detailed")K0({command:"related",alias:"detailed",replacement:"Use --format brief or --format ai.",json:Z.json});let Y=K?.dbPath??Z.dbPath??E(),{db:Q}=v({path:Y});try{let G=new g$(Q),_=new g(Q),J=Z.type??"session",H=await G.findRelatedWithHops(J,$,Z.hops??2),V="brief";if(Z.json)V="json";else if(Z.verbose)V="verbose";else if(Z.quiet)V="quiet";else if(Z.format==="detailed")V="detailed";let B=k(),z=b4(V,B);if(H.length===0){let O=await G.findBySource(J,$),M=await G.findByTarget(J,$);if(O.length===0&&M.length===0){if(Z.json)S({command:"related",code:"NOT_FOUND",message:`No related items found for ${$}`,context:{source_id:$,source_type:J}});else{let x=z.formatEmpty($);if(V!=="quiet"||x)console.error(x)}return{exitCode:1}}}let W=new Map;for(let{link:O,hop:M}of H)if(O.targetType==="session"){let x=W.get(O.targetId);if(!x||O.weight>x.weight)W.set(O.targetId,{weight:O.weight,hops:M})}W.delete($);let N=Array.from(W.entries()).sort((O,M)=>M[1].weight-O[1].weight||O[1].hops-M[1].hops).slice(0,Z.limit??10),q=[];for(let[O,{weight:M,hops:x}]of N){let y=await _.findById(O);if(y)q.push({session:y,weight:M,hops:x})}if(q.length===0){if(Z.json)S({command:"related",code:"NOT_FOUND",message:`No related items found for ${$}`,context:{source_id:$,source_type:J}});else{let O=z.formatEmpty($);if(V!=="quiet"||O)console.error(O)}return{exitCode:1}}if(Z.json){let O=performance.now();return s({command:"related",kind:"related",data:q.map(K3),meta:{source_id:$,source_type:J,count:q.length,timing_ms:Math.round(O-X)}}),{exitCode:0}}let I=performance.now(),F={sourceId:$,executionTimeMs:Math.round(I-X)},L=z.formatRelated(q,F);if(Z.format==="ai")L=a(L);return console.log(L),{exitCode:0}}catch(G){let _=G instanceof R?G:new R(T.DB_CONNECTION_FAILED,A(G));if(Z.json)S({command:"related",code:_.code,message:_.message,..._.context!==void 0?{context:_.context}:{}});else console.error(c(_));return{exitCode:1}}finally{D(Q)}}var W9=U(()=>{Q0();o9();u();h4();F0();M0();L0();b0();t0()});var T$={};w(T$,{executeQueryCommand:()=>B9,createQueryCommand:()=>l8});import{Command as LK,Option as P$}from"commander";function l8(){return new LK("query").argument("[argument]","Query argument (search query text, session ID, or project name depending on kind)").description("Execute unified query across sessions, files, stats, or context").addOption(new P$("--scope <scope>","Query scope: global or project").choices(["global","project"])).option("-p, --project <name>","Filter by project name").addOption(new P$("--kind <kind>","Resource kind to query").choices(["message","session","file","stats","context","related"]).default("message")).addOption(new P$("--mode <mode>","Search mode: auto, fts, vector, hybrid").choices(["auto","fts","vector","hybrid"])).option("-l, --limit <count>","Maximum results to return").addOption(new P$("--format <type>","Output format: brief or ai").choices(["brief","ai","default"])).option("--json","Output results as JSON envelope").option("--days <count>","Filter results from last N days",($)=>{let Z=parseInt($,10);if(isNaN(Z)||Z<1)throw Error("Days must be a positive number");return Z}).option("--projects <count>","Number of projects to show in stats breakdown","10").addOption(new P$("-v, --verbose","Show detailed output with execution info").conflicts("quiet")).addOption(new P$("-q, --quiet","Suppress headers and decorations").conflicts("verbose")).action(async($,Z)=>{let K=await B9($,Z);process.exitCode=K.exitCode})}async function B9($,Z){let K=Z.kind??"message",X=Z.project||(Z.scope==="project"?$:void 0),Y=!process.env.MEMORY_JSON_COMMAND_OVERRIDE;if(Y)process.env.MEMORY_JSON_COMMAND_OVERRIDE="query";try{let Q=Z;switch(K){case"message":{let{runSearchInternal:G}=await Promise.resolve().then(() => (QZ(),z5));return await G($||"",{...Z,project:X,files:!1})}case"file":{let{runSearchInternal:G}=await Promise.resolve().then(() => (QZ(),z5));return await G($||"",{...Z,project:X,files:!0})}case"session":if($){let{runShowInternal:G}=await Promise.resolve().then(() => (_9(),j8));return await G($,{json:Q.json,verbose:Q.verbose,quiet:Q.quiet,tools:Q.tools,format:Q.format},{dbPath:Z.dbPath})}else{let{runListInternal:G}=await Promise.resolve().then(() => (J5(),P8));return await G({limit:Z.limit,project:X,since:Q.since,before:Q.before,days:Z.days,json:Z.json,verbose:Z.verbose,quiet:Z.quiet,format:Z.format},{dbPath:Z.dbPath})}case"stats":{let{executeStatsCommand:G}=await Promise.resolve().then(() => (B5(),h8));return await G({json:Z.json,verbose:Z.verbose,quiet:Z.quiet,projects:Z.projects,format:Z.format},{dbPath:Z.dbPath})}case"context":{let G=X||$;if(!G){if(Z.json)S({command:"query",code:"INVALID_ARGUMENT",message:"Project name is required for context query"});else console.error("Error: Project name is required for context query");return{exitCode:1}}let{runContextInternal:_}=await Promise.resolve().then(() => (V9(),u8));return await _(G,{json:Z.json,verbose:Z.verbose,quiet:Z.quiet,days:Z.days,format:Q.format,budget:Q.budget,crossProject:Q.crossProject},{dbPath:Z.dbPath})}case"related":{if(!$){if(Z.json)S({command:"query",code:"INVALID_ARGUMENT",message:"Source session ID is required for related query"});else console.error("Error: Source session ID is required for related query");return{exitCode:1}}let{runRelatedInternal:G}=await Promise.resolve().then(() => (W9(),p8));return await G($,{limit:Q.limit,json:Z.json,verbose:Z.verbose,quiet:Z.quiet,format:Q.format,type:Q.type,hops:Q.hops,dbPath:Z.dbPath},{dbPath:Z.dbPath})}default:{if(Z.json)S({command:"query",code:"INVALID_ARGUMENT",message:`Unsupported kind: ${K}`});else console.error(`Error: Unsupported kind: ${K}`);return{exitCode:1}}}}finally{if(Y)delete process.env.MEMORY_JSON_COMMAND_OVERRIDE}}var s0=U(()=>{L0()});var z5={};w(z5,{runSearchInternal:()=>TK,resolveSearchMode:()=>n8,filterCaseSensitive:()=>i8,executeSearchCommand:()=>E$,createSearchCommand:()=>a8});import{Command as IK,Option as j0}from"commander";function n8($){if($.vector===!1)return"fts";if(!$.mode||$.mode==="auto")return;return $.mode}function a8(){return new IK("search").argument("<query>","Search query text").description("Search across all sessions (keyword, semantic, or hybrid)").option("-l, --limit <count>","Maximum results to return","10").option("-p, --project <name>","Filter by project name").option("-s, --session <id>","Filter by session ID").option("--role <roles>","Filter by role: user, assistant, or both (comma-separated)").addOption(new j0("--since <date>","Results after date (e.g., 'yesterday', '2 weeks ago')").conflicts("days")).addOption(new j0("--before <date>","Results before date").conflicts("days")).addOption(new j0("--days <n>","Results from last N days (includes today)").argParser(($)=>{let Z=parseInt($,10);if(isNaN(Z)||Z<1)throw Error("Days must be a positive number");return Z}).conflicts(["since","before"])).option("--json","Output results as JSON").option("-i, --ignore-case","Case-insensitive search (default)").option("-c, --case-sensitive","Case-sensitive search").addOption(new j0("--mode <mode>","Search mode: auto, fts, vector, hybrid").choices(["auto","fts","vector","hybrid"]).default("auto")).addOption(new j0("--no-vector","Disable vector search (same as --mode fts)")).addOption(new j0("--no-decay","Disable temporal decay scoring")).option("--files","Search markdown files via qmd (requires qmd installed)").addOption(new j0("--format <type>","Output format: brief (single-line per record) or ai (AI-optimized text). 'default' accepted as deprecated alias.").choices(["brief","ai","default"])).addOption(new j0("-v, --verbose","Show detailed output with execution info").conflicts("quiet")).addOption(new j0("-q, --quiet","Suppress headers and decorations").conflicts("verbose")).action(async($,Z)=>{let K=await E$($,Z);process.exitCode=K.exitCode})}async function E$($,Z){let{executeQueryCommand:K}=await Promise.resolve().then(() => (s0(),T$)),X=Z.files?"file":"message",Y=Z.project?"project":"global";process.env.MEMORY_JSON_COMMAND_OVERRIDE="search";try{return await K($,{...Z,kind:X,scope:Y})}finally{delete process.env.MEMORY_JSON_COMMAND_OVERRIDE}}async function TK($,Z){let K=performance.now();if(Z.format==="default")K0({command:"search",alias:"default",replacement:"Omit --format for default behavior, or use --format brief / --format ai.",json:Z.json});let X;try{X=C$.from($)}catch(J){if(Z.json)S({command:"search",code:"INVALID_QUERY",message:"Query cannot be empty"});else console.error("Error: Query cannot be empty");return{exitCode:1}}if(Z.files)return RK($,Z);let Y=Z.dbPath??E(),{db:Q,sqliteVecAvailable:G}=v({path:Y}),_=new Z9;try{let J=m(),H=new m$(Q),V=new D0(Q),B=new c$({db:Q,fts5Service:H,embeddingRepo:V,providerFactory:_,config:J,sqliteVecAvailable:G}),z=parseInt(Z.limit??"10",10);if(isNaN(z)||z<1){if(Z.json)S({command:"search",code:"INVALID_ARGUMENT",message:"Limit must be a positive number"});else console.error("Error: Limit must be a positive number");return{exitCode:1}}let W;if(Z.role){let C=Z.role.split(",").map((D$)=>D$.trim().toLowerCase());if(C.length===1)W=C[0];else W=C}let N,q;if(Z.days){let C=new Date,D$=new Date(C.getFullYear(),C.getMonth(),C.getDate());N=new Date(D$.getTime()-(Z.days-1)*24*60*60*1000)}else{if(Z.since)try{N=L$(Z.since)}catch(C){if(C instanceof I0){if(Z.json)S({command:"search",code:"INVALID_ARGUMENT",message:C.message,context:{flag:"since",value:Z.since}});else console.error(`Error: ${C.message}`);return{exitCode:1}}throw C}if(Z.before)try{q=L$(Z.before)}catch(C){if(C instanceof I0){if(Z.json)S({command:"search",code:"INVALID_ARGUMENT",message:C.message,context:{flag:"before",value:Z.before}});else console.error(`Error: ${C.message}`);return{exitCode:1}}throw C}}let I=n8(Z),L={limit:Z.caseSensitive?z*2:z,projectFilter:Z.project,roleFilter:W,sinceDate:N,beforeDate:q,sessionFilter:Z.session,mode:I,noDecay:Z.decay===!1},O=await B.search(X,L),M=!1;if(Z.caseSensitive&&O.length>0){let C=O.length;O=i8(O,$,z),M=C>O.length||O.length<z}else O=O.slice(0,z);let x=B.getLastSearchMeta(),y="default";if(Z.json)y="json";else if(Z.quiet)y="quiet";else if(Z.verbose)y="verbose";else if(Z.format==="brief")y="brief";let J0=k(),g0=E4(y,J0),H0=performance.now(),V0={query:$,executionDetails:{timeMs:Math.round(H0-K),ftsQuery:$,filtersApplied:MK(Z,M)},searchMeta:x??void 0},L2=Math.round(performance.now()-K),I2=()=>{let C={query:$,total_results:O.length,timing_ms:L2};if(x){if(C.mode=x.mode,C.mode_reason=x.modeReason,C.embedding_coverage=x.embeddingCoverage,C.degraded=x.degraded,x.degradationReason)C.degradation_reason=x.degradationReason}return C};if(Z.json){if(s({command:"search",kind:"message",data:O.map((C,D$)=>pZ(C,{rank:D$+1,includeSearchMetaFields:!!x})),meta:I2()}),x&&x.embeddingCoverage===0&&!J.search?.hintShown)console.error("Tip: run 'memory sync --embed' to enable semantic search"),S0({search:{...J.search,hintShown:!0}});return{exitCode:0}}if(O.length===0&&x?.mode==="vector")return console.log(`No semantic matches for "${$}"`),{exitCode:0};let A9=g0.formatResults(O,V0);if(Z.format==="ai")A9=a(A9);if(console.log(A9),x&&x.embeddingCoverage===0&&!J.search?.hintShown)console.error("Tip: run 'memory sync --embed' to enable semantic search"),S0({search:{...J.search,hintShown:!0}});return{exitCode:0}}catch(J){let H=J instanceof R?J:new R(T.DB_CONNECTION_FAILED,A(J));if(Z.json)S({command:"search",code:H.code,message:H.message,...H.context!==void 0?{context:H.context}:{}});else console.error(c(H));return{exitCode:1}}finally{await _.dispose(),D(Q)}}async function RK($,Z){if(!G5()){if(Z.json)S({command:"search",code:"QMD_UNAVAILABLE",message:"qmd is required for --files search. Install: bun add -g @tobilu/qmd"});else console.error("Error: qmd is required for --files search. Install: bun add -g @tobilu/qmd");return{exitCode:1}}try{let X=await new Y9().search($);if(Z.json)return s({command:"search",kind:"file",data:X.map($3),meta:{query:$,files:!0,total_results:X.length}}),{exitCode:0};if(X.length===0){let G=`No file results for "${$}"`;return console.log(Z.format==="ai"?G:G),{exitCode:0}}let Y=k(),Q=FK(X,Y);if(Z.format==="ai")Q=a(Q);return console.log(Q),{exitCode:0}}catch(K){let X=A(K);if(Z.json)S({command:"search",code:"QMD_FAILED",message:`qmd search failed: ${X}`});else console.error(`Error: qmd search failed: ${X}`);return{exitCode:1}}}function FK($,Z){let K=[];K.push(`File results: ${$.length} match${$.length!==1?"es":""}`),K.push("");for(let X of $){let Y=X.file.replace(/^qmd:\/\//,"");K.push(` ${b(X.title,Z)}`),K.push(` ${P(`${Y} (score: ${X.score})`,Z)}`);let Q=X.snippet||X.context;if(Q)K.push(` ${Q}`);K.push("")}return K.join(`
|
|
873
|
+
`)}function MK($,Z){let K=[];if($.limit)K.push(`limit: ${$.limit}`);if($.project)K.push(`project: ${$.project}`);if($.session)K.push(`session: ${$.session}`);if($.role)K.push(`role: ${$.role}`);if($.days)K.push(`days: ${$.days}`);if($.since)K.push(`since: ${$.since}`);if($.before)K.push(`before: ${$.before}`);if($.caseSensitive)K.push("case-sensitive");if(Z)K.push("case-sensitive filter applied");if($.mode&&$.mode!=="auto")K.push(`mode: ${$.mode}`);if($.vector===!1)K.push("no-vector");if($.decay===!1)K.push("no-decay");return K}function i8($,Z,K){return $.filter((Y)=>{return Y.snippet.replace(/<\/?mark>/g,"").includes(Z)}).slice(0,K)}var QZ=U(()=>{Q0();u();o4();Z0();nZ();F0();Q5();M0();L0();b0();t0();G9()});w$();S$();VZ();HZ();Q0();var b2={redactText:($)=>({text:$,findings:[]}),redactJson:($)=>({value:$,findings:[]})};class NZ{sessionSource;eventParser;sessionRepo;messageRepo;toolUseRepo;extractionStateRepo;db;abortSignal;checkpointManager;redactor;constructor($,Z,K,X,Y,Q,G,_,J,H=b2){this.sessionSource=$;this.eventParser=Z;this.sessionRepo=K;this.messageRepo=X;this.toolUseRepo=Y;this.extractionStateRepo=Q;this.db=G;this.abortSignal=_;this.checkpointManager=J;this.redactor=H}async sync($={}){let Z=Date.now(),K=$.checkpointEnabled!==!1,X={success:!0,sessionsDiscovered:0,sessionsProcessed:0,sessionsSkipped:0,messagesInserted:0,toolUsesInserted:0,errors:[],durationMs:0,aborted:!1},Y=null,Q=new Set;if(K){if(Y=this.checkpointManager.load(),Y){X.recoveredFromCheckpoint=Y.completedSessions;for(let V of Y.completedSessionIds)Q.add(V)}}$.onProgress?.({current:0,total:0,sessionId:"",phase:"discovering"});let G;try{G=await this.sessionSource.discoverSessions()}catch(V){throw new R(T.SOURCE_INACCESSIBLE,"Failed to discover sessions",{reason:A(V)})}X.sessionsDiscovered=G.length;let _=await this.filterSessions(G,$);if(Q.size>0){let V=_.length;_=_.filter((B)=>!Q.has(B.id)),X.sessionsSkipped+=V-_.length}if(X.sessionsSkipped=X.sessionsDiscovered-_.length-Q.size,X.sessionsSkipped<0)X.sessionsSkipped=X.sessionsDiscovered-_.length;let J=_.length+Q.size,H=Y??{startedAt:new Date().toISOString(),totalSessions:J,completedSessions:Q.size,completedSessionIds:[...Q],lastCompletedAt:null};for(let V=0;V<_.length;V++){if(this.abortSignal.shouldAbort()){if(X.aborted=!0,K)this.checkpointManager.save(H);break}let B=_[V];if(!B)continue;$.onProgress?.({current:V+1+Q.size,total:J,sessionId:B.id,phase:"extracting"});try{let z=await this.extractSession(B);if(X.sessionsProcessed++,X.messagesInserted+=z.messages,X.toolUsesInserted+=z.toolUses,K)H.completedSessions++,H.completedSessionIds.push(B.id),H.lastCompletedAt=new Date().toISOString(),this.checkpointManager.save(H);$.onSessionComplete?.(B.id)}catch(z){let W=this.wrapError(z,B.path);X.errors.push({sessionPath:B.path,error:W.message}),X.success=!1}}if(K&&!X.aborted&&X.success)this.checkpointManager.clear();return $.onProgress?.({current:J,total:J,sessionId:"",phase:"complete"}),X.durationMs=Date.now()-Z,X}async fixProjectNames($){let Z=await this.sessionRepo.findDistinctEncodedPaths(),K=0;for(let X of Z){let Y=$.resolveFromEncodedPath(X),Q=await this.sessionRepo.updateProjectName(X,Y);K+=Q}return K}wrapError($,Z){if($ instanceof R)return $;let K=A($);if(K.includes("ENOENT")||K.includes("no such file"))return new R(T.SOURCE_INACCESSIBLE,`Cannot access session file: ${K}`,{path:Z});if(K.includes("JSON")||K.includes("parse"))return new R(T.INVALID_JSON,`Failed to parse session file: ${K}`,{path:Z});if(K.includes("locked")||K.includes("SQLITE_BUSY"))return new R(T.DB_LOCKED,`Database is locked: ${K}`,{path:Z});if(K.includes("database")||K.includes("SQLITE"))return new R(T.DB_CONNECTION_FAILED,`Database error: ${K}`,{path:Z});return new R(T.SYNC_FAILED,K,{path:Z})}async filterSessions($,Z){let K=$;if(Z.projectFilter)K=K.filter((Y)=>Y.projectPath.decoded.includes(Z.projectFilter));if(Z.sessionFilter)K=K.filter((Y)=>Y.id===Z.sessionFilter);let X=[];for(let Y of K){let Q=await this.extractionStateRepo.findBySessionPath(Y.path);if(this.needsExtraction(Y,Q,Z.force??!1))X.push(Y)}return X}needsExtraction($,Z,K){if(K)return!0;if(!Z)return!0;if(Z.status!=="complete")return!0;let{fileMtime:X,fileSize:Y}=Z;if(!X||Y===void 0||Y===null)return!0;return $.modifiedTime.getTime()!==X.getTime()||$.size!==Y}async extractSession($){let Z=crypto.randomUUID(),K=$0.create({id:Z,sessionPath:$.path,startedAt:new Date,status:"pending"}).withFileMetadata($.modifiedTime,$.size);try{let X=[];for await(let V of this.eventParser.parse($.path))X.push(V);let{messages:Y,toolUses:Q,firstTimestamp:G,lastTimestamp:_}=this.extractEntities(X),J=B0.create({id:$.id,projectPath:$.projectPath,startTime:G??new Date,endTime:_,messageCount:Y.length});return this.db.transaction(()=>{if(this.sessionRepo.save(J),Y.length>0)this.messageRepo.saveMany(Y.map((B)=>({message:B,sessionId:$.id})));if(Q.length>0)this.toolUseRepo.saveMany(Q.map((B)=>({toolUse:B,sessionId:$.id})));let V=K.startProcessing().incrementMessages(Y.length).complete(new Date);this.extractionStateRepo.save(V)}).immediate(),{messages:Y.length,toolUses:Q.length}}catch(X){let Y=K.fail(A(X));throw await this.extractionStateRepo.save(Y),X}}extractEntities($){let Z=[],K=[],X=new Map,Y,Q;for(let G of $){if(G.type==="skipped")continue;if("data"in G&&G.data.timestamp){let _=new Date(G.data.timestamp);if(!Y||_<Y)Y=_;if(!Q||_>Q)Q=_}switch(G.type){case"user":{let _=W0.create({id:G.data.uuid,role:"user",content:this.redactor.redactText(G.data.message.content).text,timestamp:new Date(G.data.timestamp)});Z.push(_);break}case"assistant":{let _=G.data.message.content.filter((B)=>B.type==="text").map((B)=>B.text).join(`
|
|
874
|
+
`),J=this.redactor.redactText(_).text,H=G.data.message.content.filter((B)=>B.type==="tool_use").map((B)=>B.id);for(let B of G.data.message.content)if(B.type==="tool_use"){let z=z0.create({id:B.id,name:B.name,input:this.redactor.redactJson(B.input).value,timestamp:new Date(G.data.timestamp),status:"pending"});X.set(B.id,z)}let V=W0.create({id:G.data.uuid,role:"assistant",content:J,timestamp:new Date(G.data.timestamp),toolUseIds:H});Z.push(V);break}case"tool_use":{let _=z0.create({id:G.data.uuid,name:G.data.name,input:this.redactor.redactJson(G.data.input).value,timestamp:new Date(G.data.timestamp),status:"pending"});X.set(G.data.uuid,_);break}case"tool_result":{let _=X.get(G.data.toolUseId);if(_){let J=G.data.isError?_.completeError(this.redactor.redactText(G.data.content).text):_.completeSuccess(this.redactor.redactText(G.data.content).text);X.set(G.data.toolUseId,J)}break}case"summary":case"system":break}}return K.push(...X.values()),{messages:Z,toolUses:K,firstTimestamp:Y,lastTimestamp:Q}}}class x5{sessionSource;extractionStateRepo;syncService;syncLogger;recoveryEnabled;constructor($,Z,K,X,Y){this.sessionSource=$;this.extractionStateRepo=Z;this.syncService=K;this.syncLogger=X;this.recoveryEnabled=Y}async recover($={}){if(!this.recoveryEnabled&&!$.dryRun)return{pendingSessions:[],syncedSessions:0,errors:[],skipped:!0};let Z=await this.sessionSource.discoverSessions(),K=[];for(let G of Z){let _=await this.extractionStateRepo.findBySessionPath(G.path);if(!_||_.status!=="complete")K.push(G.path)}if(this.syncLogger.log({level:"info",message:`Recovery scan found ${K.length} pending sessions`}),$.dryRun)return{pendingSessions:K,syncedSessions:0,errors:[],skipped:!1};let X=$.maxSessions?K.slice(0,$.maxSessions):K,Y=0,Q=[];for(let G of X)try{let _=P5(G);await this.syncService.sync({sessionFilter:_}),Y++,this.syncLogger.log({level:"info",message:`Recovery synced session ${_}`,sessionId:_})}catch(_){let J=A(_);Q.push({sessionPath:G,error:J}),this.syncLogger.log({level:"error",message:`Recovery failed for ${G}: ${J}`,error:J})}return{pendingSessions:K,syncedSessions:Y,errors:Q,skipped:!1}}async getPendingCount(){let $=await this.sessionSource.discoverSessions(),Z=0;for(let K of $){let X=await this.extractionStateRepo.findBySessionPath(K.path);if(!X||X.status!=="complete")Z++}return Z}}function P5($){let Z=$.split(/[/\\]/);return Z[Z.length-1].replace(/\.jsonl$/,"")}k$();var f2=["Read","Write","Edit","NotebookEdit"],h2=["Glob","Grep"],g2=["Write","Edit","NotebookEdit"];class E5{static extractFilePaths($){let Z=new Set;for(let K of $){let X=K.input;if(f2.includes(K.name)){let Y=X.file_path;if(Y)Z.add(Y)}if(h2.includes(K.name)){let Y=X.path;if(Y)Z.add(Y)}if(K.name==="Glob"&&K.result){let Y=K.result.split(`
|
|
875
|
+
`);for(let Q of Y){let G=Q.trim();if(G)Z.add(G)}}}return Array.from(Z)}static extractFileModifications($){let Z=[];for(let K of $){if(!g2.includes(K.name))continue;if(K.status!=="success")continue;let X=K.input.file_path;if(X)Z.push({path:X,operation:K.name,timestamp:K.timestamp})}return Z}static extractToolStats($){let Z=new Map;for(let K of $){let X=Z.get(K.name);if(X){if(X.count++,K.status==="success")X.successCount++;else if(K.status==="error")X.errorCount++}else Z.set(K.name,{count:1,successCount:K.status==="success"?1:0,errorCount:K.status==="error"?1:0})}return Array.from(Z.entries()).map(([K,X])=>({name:K,...X}))}static extractToolNames($){let Z=new Set;for(let K of $)Z.add(K.name);return Array.from(Z)}static toFileEntities($){return $.map((Z)=>e.create({type:"file",name:Z,confidence:1}))}static toFileModificationEntities($){return $.map((Z)=>{let K={operation:Z.operation.toLowerCase()};return e.create({type:"file",name:Z.path,confidence:1,metadata:K})})}}L9();R9();import{existsSync as u2}from"fs";var k5={redactText:($)=>({text:$,findings:[]}),redactJson:($)=>({value:$,findings:[]})};function Z$($,Z){return $.redactText(Z).text}function b$($,Z){return Z===null?null:Z$($,Z)}async function F9($,Z,K={}){let X=K.includeSensitive?k5:K.redactor??k5,Y=$.query(`SELECT id, project_path_encoded as projectPathEncoded,
|
|
876
|
+
project_path_decoded as projectPathDecoded,
|
|
877
|
+
project_name as projectName,
|
|
878
|
+
start_time as startTime, end_time as endTime,
|
|
879
|
+
message_count as messageCount, summary
|
|
880
|
+
FROM sessions`).all().map((q)=>({...q,summary:b$(X,q.summary)})),Q=$.query(`SELECT id, session_id as sessionId, role, content, timestamp,
|
|
881
|
+
tool_use_ids as toolUseIds
|
|
882
|
+
FROM messages_meta`).all().map((q)=>({...q,content:Z$(X,q.content)})),G=$.query(`SELECT id, session_id as sessionId, name, input, timestamp, status, result
|
|
883
|
+
FROM tool_uses`).all().map((q)=>({...q,input:Z$(X,q.input),result:b$(X,q.result)})),_=$.query(`SELECT id, type, name, metadata, confidence
|
|
884
|
+
FROM entities`).all().map((q)=>({...q,name:Z$(X,q.name),metadata:b$(X,q.metadata)})),J=$.query(`SELECT source_type as sourceType, source_id as sourceId,
|
|
885
|
+
target_type as targetType, target_id as targetId,
|
|
886
|
+
relationship, weight
|
|
887
|
+
FROM links`).all(),H=$.query(`SELECT session_id as sessionId, entity_id as entityId, frequency
|
|
888
|
+
FROM session_entities`).all(),V=$.query(`SELECT source_id as sourceId, target_id as targetId, relationship, weight
|
|
889
|
+
FROM entity_links`).all(),B=$.query(`SELECT id, session_path as sessionPath, started_at as startedAt,
|
|
890
|
+
status, completed_at as completedAt,
|
|
891
|
+
messages_extracted as messagesExtracted,
|
|
892
|
+
error_message as errorMessage,
|
|
893
|
+
file_mtime as fileMtime, file_size as fileSize
|
|
894
|
+
FROM extraction_state`).all().map((q)=>({...q,sessionPath:Z$(X,q.sessionPath),errorMessage:b$(X,q.errorMessage)})),z=$.query(`SELECT uuid, type, project, content, metadata,
|
|
895
|
+
observed_at as observedAt, superseded_at as supersededAt,
|
|
896
|
+
superseded_by as supersededBy
|
|
897
|
+
FROM facts`).all().map((q)=>({...q,content:Z$(X,q.content),metadata:b$(X,q.metadata)})),W={version:"1.0",exportedAt:new Date().toISOString(),stats:{sessions:Y.length,messages:Q.length,toolUses:G.length,entities:_.length,links:J.length,sessionEntities:H.length,entityLinks:V.length,extractionStates:B.length,facts:z.length},sessions:Y,messages:Q,toolUses:G,entities:_,links:J,sessionEntities:H,entityLinks:V,extractionStates:B,facts:z},N=JSON.stringify(W,null,2);return await Bun.write(Z,N),{sessions:Y.length,messages:Q.length,toolUses:G.length,entities:_.length,links:J.length,bytes:N.length,facts:z.length}}async function qZ($){if(!u2($))return{valid:!1,error:"File does not exist"};try{let K=await Bun.file($).text(),X=JSON.parse(K);if(!X.version||typeof X.version!=="string")return{valid:!1,error:"Missing or invalid version field"};let Y=["sessions","messages","toolUses","entities","links"];for(let Q of Y)if(!Array.isArray(X[Q]))return{valid:!1,error:`Missing or invalid ${Q} array`};if(!X.stats||typeof X.stats!=="object")return{valid:!1,error:"Missing or invalid stats object"};return{valid:!0,version:X.version}}catch(Z){return{valid:!1,error:`Failed to parse file: ${A(Z)}`}}}async function M9($,Z,K={}){let X=await qZ(Z);if(!X.valid)throw Error(`Invalid export file: ${X.error}`);let Q=await Bun.file(Z).text(),G=JSON.parse(Q);if(K.clearExisting)d2($);return $.transaction(()=>{let J=$.prepare(`
|
|
898
|
+
INSERT OR IGNORE INTO sessions
|
|
899
|
+
(id, project_path_encoded, project_path_decoded, project_name,
|
|
900
|
+
start_time, end_time, message_count, summary)
|
|
901
|
+
VALUES (?, ?, ?, ?, ?, ?, ?, ?)
|
|
902
|
+
`);for(let W of G.sessions)J.run(W.id,W.projectPathEncoded,W.projectPathDecoded,W.projectName,W.startTime,W.endTime,W.messageCount,W.summary);let H=$.prepare(`
|
|
903
|
+
INSERT OR IGNORE INTO messages_meta
|
|
904
|
+
(id, session_id, role, content, timestamp, tool_use_ids)
|
|
905
|
+
VALUES (?, ?, ?, ?, ?, ?)
|
|
906
|
+
`);for(let W of G.messages)H.run(W.id,W.sessionId,W.role,W.content,W.timestamp,W.toolUseIds);let V=$.prepare(`
|
|
907
|
+
INSERT OR IGNORE INTO tool_uses
|
|
908
|
+
(id, session_id, name, input, timestamp, status, result)
|
|
909
|
+
VALUES (?, ?, ?, ?, ?, ?, ?)
|
|
910
|
+
`);for(let W of G.toolUses)V.run(W.id,W.sessionId,W.name,W.input,W.timestamp,W.status,W.result);let B=$.prepare(`
|
|
911
|
+
INSERT OR IGNORE INTO entities
|
|
912
|
+
(id, type, name, metadata, confidence)
|
|
913
|
+
VALUES (?, ?, ?, ?, ?)
|
|
914
|
+
`);for(let W of G.entities)B.run(W.id,W.type,W.name,W.metadata,W.confidence);let z=$.prepare(`
|
|
915
|
+
INSERT OR IGNORE INTO links
|
|
916
|
+
(source_type, source_id, target_type, target_id, relationship, weight)
|
|
917
|
+
VALUES (?, ?, ?, ?, ?, ?)
|
|
918
|
+
`);for(let W of G.links)z.run(W.sourceType,W.sourceId,W.targetType,W.targetId,W.relationship,W.weight);if(G.sessionEntities&&G.sessionEntities.length>0){let W=$.prepare(`
|
|
919
|
+
INSERT OR IGNORE INTO session_entities
|
|
920
|
+
(session_id, entity_id, frequency)
|
|
921
|
+
VALUES (?, ?, ?)
|
|
922
|
+
`);for(let N of G.sessionEntities)W.run(N.sessionId,N.entityId,N.frequency)}if(G.entityLinks&&G.entityLinks.length>0){let W=$.prepare(`
|
|
923
|
+
INSERT OR IGNORE INTO entity_links
|
|
924
|
+
(source_id, target_id, relationship, weight)
|
|
925
|
+
VALUES (?, ?, ?, ?)
|
|
926
|
+
`);for(let N of G.entityLinks)W.run(N.sourceId,N.targetId,N.relationship,N.weight)}if(G.extractionStates&&G.extractionStates.length>0){let W=$.prepare(`
|
|
927
|
+
INSERT OR IGNORE INTO extraction_state
|
|
928
|
+
(id, session_path, started_at, status, completed_at,
|
|
929
|
+
messages_extracted, error_message, file_mtime, file_size)
|
|
930
|
+
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)
|
|
931
|
+
`);for(let N of G.extractionStates)W.run(N.id,N.sessionPath,N.startedAt,N.status,N.completedAt,N.messagesExtracted,N.errorMessage,N.fileMtime,N.fileSize)}if(G.facts&&G.facts.length>0){let W=$.prepare(`
|
|
932
|
+
INSERT OR IGNORE INTO facts
|
|
933
|
+
(uuid, type, project, content, metadata, observed_at, superseded_at, superseded_by)
|
|
934
|
+
VALUES (?, ?, ?, ?, ?, ?, ?, ?)
|
|
935
|
+
`);for(let N of G.facts)W.run(N.uuid,N.type,N.project,N.content,N.metadata,N.observedAt,N.supersededAt,N.supersededBy)}return{sessions:G.sessions.length,messages:G.messages.length,toolUses:G.toolUses.length,entities:G.entities.length,links:G.links.length,facts:G.facts?G.facts.length:0}}).immediate()}function d2($){$.exec("PRAGMA foreign_keys = OFF;");try{$.exec("DELETE FROM session_entities;"),$.exec("DELETE FROM entity_links;"),$.exec("DELETE FROM links;"),$.exec("DELETE FROM messages_meta;"),$.exec("DELETE FROM sessions_fts;"),$.exec("DELETE FROM facts;"),$.exec("DELETE FROM tool_uses;"),$.exec("DELETE FROM sessions;"),$.exec("DELETE FROM entities;"),$.exec("DELETE FROM extraction_state;"),$.exec("DELETE FROM topics;")}finally{$.exec("PRAGMA foreign_keys = ON;")}}function j9($){return($.query(`SELECT (SELECT COUNT(*) FROM sessions) +
|
|
936
|
+
(SELECT COUNT(*) FROM messages_meta) as count`).get()?.count??0)>0}function p2($,Z,K=30,X=new Date){let Y=X.getTime(),Q=86400000;return $.map((_)=>{let J=Z.get(_.rowid);if(!J)return{..._,decayedScore:_.score};let H=(Y-J.getTime())/86400000,V=Math.pow(0.5,H/K);return{..._,decayedScore:_.score*V}}).sort((_,J)=>J.decayedScore-_.decayedScore)}var l2=["decisions","learnings","user_prefs"];function n2($,Z,K,X=30,Y=new Date){let Q=Y.getTime(),G=86400000;return $.map((J)=>{if(K.has(J.rowid))return{...J,decayedScore:J.score};let H=Z.get(J.rowid);if(!H)return{...J,decayedScore:J.score};let V=(Q-H.getTime())/86400000,B=Math.pow(0.5,V/X);return{...J,decayedScore:J.score*B}}).sort((J,H)=>H.decayedScore-J.decayedScore)}WZ();class OZ{repository;scanner;constructor($,Z){this.repository=$;this.scanner=Z}async syncMemoryFiles($={}){let Z={filesIndexed:0,filesSkipped:0,errors:[]},K;try{K=await this.scanner.discoverFiles()}catch(X){return Z.errors.push({filePath:"~/.memory/",error:A(X)}),Z}for(let X=0;X<K.length;X++){let Y=K[X];if(!Y)continue;try{let Q=await this.repository.findByPath(Y.filePath);if(Q&&Q.contentHash===Y.contentHash){Z.filesSkipped++,$.onProgress?.({current:X+1,total:K.length,filePath:Y.filePath,action:"skipped"});continue}let G=m0.create({filePath:Y.filePath,fileType:Y.fileType,projectEncoded:Y.projectEncoded,content:Y.content,contentHash:Y.contentHash,lastIndexedAt:new Date});await this.repository.save(G),Z.filesIndexed++,$.onProgress?.({current:X+1,total:K.length,filePath:Y.filePath,action:"indexing"})}catch(Q){Z.errors.push({filePath:Y.filePath,error:A(Q)})}}return Z}}BZ();Q0();import{existsSync as a2,readFileSync as i2,unlinkSync as r2}from"fs";class UZ{repository;constructor($){this.repository=$}async log($){let Z=x0.create({description:$.description,severity:$.severity??"medium",category:$.category??"cli",tool:$.tool??"memory",status:"open",context:$.context,sourceProject:$.sourceProject,loggedAt:$.loggedAt??new Date});return this.repository.save(Z)}async list($){if($?.all||$?.tool||$?.category||$?.sourceProject)return this.repository.findAll({status:$?.all?$.status:"open",category:$?.category,tool:$?.tool,sourceProject:$?.sourceProject,limit:$?.limit});return this.repository.findOpen()}async resolve($,Z){let K=await this.repository.findById($);if(!K)throw new R(T.NOT_FOUND,`Friction entry #${$} not found`,{id:$});if(K.status!=="open")throw new R(T.INVALID_STATE,`Friction entry #${$} is already ${K.status}`,{id:$,currentStatus:K.status});await this.repository.resolve($,Z)}async wontFix($,Z){let K=await this.repository.findById($);if(!K)throw new R(T.NOT_FOUND,`Friction entry #${$} not found`,{id:$});if(K.status!=="open")throw new R(T.INVALID_STATE,`Friction entry #${$} is already ${K.status}`,{id:$,currentStatus:K.status});await this.repository.resolve($,Z),await this.repository.updateStatus($,"wont-fix")}async getStats(){return this.repository.getStats()}async getWeeklyTrends($=4){return this.repository.getWeeklyTrends($)}async ingestFallbackFile($){if(!a2($))return 0;let K=i2($,"utf-8").split(`
|
|
937
|
+
`).filter(Boolean),X=0;for(let Y of K)try{let Q=JSON.parse(Y);await this.log({description:Q.description,severity:Q.severity??"medium",category:Q.category??"cli",tool:Q.tool??"unknown",context:Q.context,sourceProject:Q.project,loggedAt:Q.date?new Date(Q.date+"T00:00:00Z"):new Date}),X++}catch{process.stderr.write(`Warning: skipping malformed friction entry in ${$}
|
|
938
|
+
`)}try{r2($)}catch{process.stderr.write(`Warning: could not delete ${$} (entries already ingested)
|
|
939
|
+
`)}return X}async detectPatterns($=3){return this.repository.findPatterns($)}async markReviewed($){await this.repository.markReviewed($,new Date)}async purge($){return this.repository.deleteByPattern($)}}v5();LZ();import{Command as gV,Option as mV}from"commander";f9();u();ZZ();import{createReadStream as o7}from"fs";import{createInterface as t7}from"readline";function N$($){if(typeof $==="string"){if(/^\d{4}-\d{2}-\d{2}T/.test($))return $;let Z=new Date($);if(!isNaN(Z.getTime()))return Z.toISOString()}if(typeof $==="number"&&!isNaN($)){let Z=$>1000000000000?$:$*1000,K=new Date(Z);if(!isNaN(K.getTime()))return K.toISOString()}if($ instanceof Date&&!isNaN($.getTime()))return $.toISOString();return new Date().toISOString()}var d7=new Set(["progress","agent_progress","bash_progress","mcp_progress","hook_progress","base64","image","file-history-snapshot","waiting_for_task","create","update","queue-operation"]);function c1($){if(typeof $!=="object"||$===null)return!1;return typeof $.type==="string"}function I4($){if(!c1($))return{type:"skipped",reason:"Invalid event structure"};let Z=$.type;if(d7.has(Z))return{type:"skipped",reason:`Event type "${Z}" not extracted`};switch(Z){case"user":return p7($);case"assistant":return n7($);case"summary":return i7($);case"system":return r7($);default:return{type:"skipped",reason:`Event type "${Z}" not classified`}}}function p7($){if(!$.uuid||!$.timestamp||!$.message)return{type:"skipped",reason:"User event missing required fields"};let Z={uuid:$.uuid,message:{content:l7($.message.content)},timestamp:N$($.timestamp)};if($.cwd)Z.cwd=$.cwd;if($.gitBranch)Z.gitBranch=$.gitBranch;return{type:"user",data:Z}}function l7($){if(typeof $==="string")return $;if(Array.isArray($))return $.filter((K)=>K.type==="tool_result").map((K)=>{if(typeof K.content==="string")return K.content;return JSON.stringify(K.content)}).join(`
|
|
940
|
+
`);return""}function n7($){if(!$.uuid||!$.timestamp||!$.message)return{type:"skipped",reason:"Assistant event missing required fields"};let Z=a7($.message.content||[]),K={uuid:$.uuid,message:{content:Z},timestamp:N$($.timestamp)};if($.message.model)K.message.model=$.message.model;if($.message.usage)K.usage={inputTokens:$.message.usage.input_tokens,outputTokens:$.message.usage.output_tokens};return{type:"assistant",data:K}}function a7($){if(!Array.isArray($))return[];return $.filter((Z)=>{return Z.type!=="thinking"}).map((Z)=>{if(Z.type==="text")return{type:"text",text:Z.text};if(Z.type==="tool_use")return{type:"tool_use",id:Z.id,name:Z.name,input:Z.input};return{type:"text",text:""}})}function i7($){if(!$.summary)return{type:"skipped",reason:"Summary event missing summary field"};let Z={content:$.summary,timestamp:N$($.timestamp)};if($.leafUuid)Z.leafUuid=$.leafUuid;return{type:"summary",data:Z}}function r7($){if(!$.subtype)return{type:"skipped",reason:"System event missing subtype field"};return{type:"system",data:{subtype:$.subtype,data:$.durationMs??$.data??null,timestamp:N$($.timestamp)}}}class hZ{async*parse($){let Z=o7($,{encoding:"utf8"}),K=t7({input:Z,crlfDelay:1/0}),X=0;for await(let Y of K){X++;let Q=Y.trim();if(Q===""){yield{type:"skipped",reason:`Empty line at ${X}`};continue}try{let G=JSON.parse(Q);yield I4(G)}catch(G){let _=A(G);yield{type:"skipped",reason:`Malformed JSON at line ${X}: ${_}`}}}}}p();import{existsSync as T4,mkdirSync as s7,readFileSync as e7,unlinkSync as $6,writeFileSync as Z6}from"fs";import{dirname as K6}from"path";function gZ($){return $??p9()}function u1($,Z){let K=gZ(Z),X=K6(K);try{s7(X,{recursive:!0}),Z6(K,JSON.stringify($,null,2)+`
|
|
941
|
+
`)}catch(Y){console.warn("Failed to save checkpoint:",Y.message)}}function q$($){let Z=gZ($);if(!T4(Z))return null;try{let K=e7(Z,"utf-8"),X=JSON.parse(K);if(typeof X.startedAt!=="string"||typeof X.totalSessions!=="number"||typeof X.completedSessions!=="number"||!Array.isArray(X.completedSessionIds))return console.warn("Invalid checkpoint format, ignoring"),null;return X}catch{return console.warn("Invalid checkpoint JSON, ignoring"),null}}function d1($){let Z=gZ($);if(T4(Z))try{$6(Z)}catch(K){console.warn("Failed to clear checkpoint:",K.message)}}function p1($){return T4(gZ($))}import*as n1 from"readline";var n={isShuttingDown:!1,interruptCount:0,cleanupFunctions:[],handlersRegistered:!1,ttyOverride:null,exitOverride:null};function X6(){if(n.ttyOverride!==null)return n.ttyOverride;return process.stdin.isTTY??!1}function mZ($){if(n.exitOverride!==null){n.exitOverride($);return}process.exit($)}async function a1(){for(let $ of n.cleanupFunctions)try{await $()}catch(Z){console.warn("Cleanup error:",Z.message)}}async function Y6(){let $=n1.createInterface({input:process.stdin,output:process.stdout});return new Promise((Z)=>{let K=()=>{console.log(`
|
|
942
|
+
Interrupt received. Choose action:`),console.log(" 1) Abort immediately"),console.log(" 2) Abort after current session (saves progress)"),console.log(" 3) Cancel abort (continue)"),$.question("> ",(X)=>{let Y=parseInt(X.trim(),10);if(Y===1||Y===2||Y===3)$.close(),Z(Y);else console.log("Invalid choice. Enter 1, 2, or 3."),K()})};K()})}async function Q6($){switch($){case 1:console.log("Aborting immediately..."),await a1(),mZ(130);break;case 2:console.log("Will abort after current session..."),n.isShuttingDown=!0;break;case 3:console.log("Continuing..."),n.interruptCount=0;break}}async function l1(){if(n.interruptCount++,n.interruptCount>=2){console.log(`
|
|
943
|
+
Force exiting...`),await a1(),mZ(130);return}if(X6()){let $=await Y6();await Q6($)}else console.log(`
|
|
944
|
+
Interrupt received, shutting down after current operation...`),n.isShuttingDown=!0}function i1(){if(n.handlersRegistered)return;process.on("SIGINT",()=>{l1().catch(($)=>{console.error("Signal handler error:",$),mZ(1)})}),process.on("SIGTERM",()=>{l1().catch(($)=>{console.error("Signal handler error:",$),mZ(1)})}),n.handlersRegistered=!0}function r1(){return n.isShuttingDown}function o1($){n.cleanupFunctions.push($)}function t1($){let Z=n.cleanupFunctions.indexOf($);if(Z!==-1)n.cleanupFunctions.splice(Z,1)}class cZ{shouldAbort(){return r1()}}class uZ{path;constructor($){this.path=$}load(){return q$(this.path)}save($){u1($,this.path)}clear(){d1(this.path)}}w0();nZ();k4();C4();rZ();h4();u4();M0();import{readFileSync as N6}from"fs";import{resolve as q6}from"path";function p4($,Z,K,X,Y){if($.total===0)return"No friction entries logged yet.";let Q=[];Q.push(r("Friction Dashboard",X)),Q.push("=================="),Q.push(""),Q.push(r(" Overview",X)),Q.push(" --------"),Q.push(` Total: ${$.total} Open: ${d(String($.open),X)} Resolved: ${b(String($.resolved),X)} Won't Fix: ${$.wontFix}`),Q.push("");let G=$.meanTimeToResolve!==null?`MTTR: ${$.meanTimeToResolve.toFixed(1)} days`:"MTTR: N/A";if($.oldestOpen)Q.push(` ${G} Oldest Open: #${$.oldestOpen.id} (${$.oldestOpen.daysOpen} days)`);else Q.push(` ${G}`);Q.push(""),Q.push(r(" By Severity",X)),Q.push(" -----------");let _=["critical","high","medium","low"],J=Math.max(..._.map((H)=>$.bySeverity[H]),1);for(let H of _){let V=$.bySeverity[H],B=Math.round(V/J*20),z="=".repeat(B)+" ".repeat(20-B),W=H.padEnd(10),N=H==="critical"||H==="high"?f(W,X):H==="medium"?d(W,X):b(W,X);Q.push(` ${N}[${z}] ${V}`)}Q.push(""),Q.push(r(" By Category",X)),Q.push(" -----------");for(let[H,V]of Object.entries($.byCategory))Q.push(` ${s1(H.padEnd(14),X)}${V}`);if(Q.push(""),$.byTool&&Object.keys($.byTool).length>0){Q.push(r(" By Tool",X)),Q.push(" -------");for(let[H,V]of Object.entries($.byTool)){let B="=".repeat(Math.min(V,40));Q.push(` ${H.padEnd(15)} ${B} ${V}`)}Q.push("")}if(Y&&Y.length>0){Q.push(r(" Pattern Alerts",X)),Q.push(" --------------");for(let H of Y)Q.push(` [!] Pattern detected: ${H.count} open entries for ${H.tool}/${H.category}`);Q.push("")}if(Z.length===0)Q.push(" No trend data available.");else{Q.push(r(" Trends",X)),Q.push(" ------"),Q.push(` ${"Week".padEnd(12)}${"New".padEnd(6)}Resolved`);for(let H of Z)Q.push(` ${P(H.week.padEnd(12),X)}${String(H.newCount).padEnd(6)}${H.resolvedCount}`)}return Q.join(`
|
|
945
|
+
`)}function O6(){let $=q6(import.meta.dirname,"../../../../node_modules/chart.js/dist/chart.umd.js");return N6($,"utf-8")}function U6($){return $.map((Z)=>({id:Z.id,severity:Z.severity,category:Z.category,description:Z.description,daysOpen:Math.floor((Date.now()-Z.loggedAt.getTime())/86400000)}))}function l4($,Z,K,X){let Y=O6(),Q=U6(K),G=$.meanTimeToResolve!==null?`${$.meanTimeToResolve.toFixed(1)} days`:"N/A",_=Q.map((J)=>`<tr>
|
|
946
|
+
<td>${J.id??"-"}</td>
|
|
947
|
+
<td class="severity-${J.severity}">${J.severity}</td>
|
|
948
|
+
<td>${J.category}</td>
|
|
949
|
+
<td>${d4(J.description)}</td>
|
|
950
|
+
<td>${J.daysOpen}d</td>
|
|
951
|
+
</tr>`).join(`
|
|
952
|
+
`);return`<!DOCTYPE html>
|
|
953
|
+
<html lang="en">
|
|
954
|
+
<head>
|
|
955
|
+
<meta charset="UTF-8">
|
|
956
|
+
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
957
|
+
<title>Friction Dashboard</title>
|
|
958
|
+
<style>
|
|
959
|
+
body { background: #1a1a2e; color: #e0e0e0; font-family: system-ui, -apple-system, sans-serif; margin: 0; padding: 24px; }
|
|
960
|
+
h1 { color: #e0e0e0; border-bottom: 1px solid #333; padding-bottom: 12px; }
|
|
961
|
+
h2 { color: #e0e0e0; margin-top: 32px; }
|
|
962
|
+
.stats-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(150px, 1fr)); gap: 16px; margin: 24px 0; }
|
|
963
|
+
.stat-card { background: #16213e; border-radius: 8px; padding: 16px; text-align: center; }
|
|
964
|
+
.stat-value { font-size: 2em; font-weight: bold; }
|
|
965
|
+
.stat-label { color: #888; font-size: 0.9em; }
|
|
966
|
+
.chart-container { background: #16213e; border-radius: 8px; padding: 16px; margin: 24px 0; }
|
|
967
|
+
canvas { max-height: 300px; }
|
|
968
|
+
table { width: 100%; border-collapse: collapse; margin: 24px 0; }
|
|
969
|
+
th, td { text-align: left; padding: 8px 12px; border-bottom: 1px solid #333; }
|
|
970
|
+
th { color: #888; font-weight: 600; }
|
|
971
|
+
.severity-critical { color: #ff4444; }
|
|
972
|
+
.severity-high { color: #ff8800; }
|
|
973
|
+
.severity-medium { color: #ffcc00; }
|
|
974
|
+
.severity-low { color: #44bb44; }
|
|
975
|
+
.open { color: #ffcc00; }
|
|
976
|
+
.resolved { color: #44bb44; }
|
|
977
|
+
.generated { color: #666; font-size: 0.8em; margin-top: 48px; text-align: center; }
|
|
978
|
+
</style>
|
|
979
|
+
<script>${Y}</script>
|
|
980
|
+
</head>
|
|
981
|
+
<body>
|
|
982
|
+
<h1>Friction Dashboard</h1>
|
|
983
|
+
|
|
984
|
+
<div class="stats-grid">
|
|
985
|
+
<div class="stat-card">
|
|
986
|
+
<div class="stat-value">${$.total}</div>
|
|
987
|
+
<div class="stat-label">Total</div>
|
|
988
|
+
</div>
|
|
989
|
+
<div class="stat-card">
|
|
990
|
+
<div class="stat-value open">${$.open}</div>
|
|
991
|
+
<div class="stat-label">Open</div>
|
|
992
|
+
</div>
|
|
993
|
+
<div class="stat-card">
|
|
994
|
+
<div class="stat-value resolved">${$.resolved}</div>
|
|
995
|
+
<div class="stat-label">Resolved</div>
|
|
996
|
+
</div>
|
|
997
|
+
<div class="stat-card">
|
|
998
|
+
<div class="stat-value">${$.wontFix}</div>
|
|
999
|
+
<div class="stat-label">Won't Fix</div>
|
|
1000
|
+
</div>
|
|
1001
|
+
<div class="stat-card">
|
|
1002
|
+
<div class="stat-value">${G}</div>
|
|
1003
|
+
<div class="stat-label">MTTR</div>
|
|
1004
|
+
</div>
|
|
1005
|
+
</div>
|
|
1006
|
+
|
|
1007
|
+
<div class="chart-container">
|
|
1008
|
+
<canvas id="overTimeChart"></canvas>
|
|
1009
|
+
</div>
|
|
1010
|
+
|
|
1011
|
+
<div class="chart-container">
|
|
1012
|
+
<canvas id="byCategoryChart"></canvas>
|
|
1013
|
+
</div>
|
|
1014
|
+
|
|
1015
|
+
<div class="chart-container">
|
|
1016
|
+
<canvas id="bySeverityChart"></canvas>
|
|
1017
|
+
</div>
|
|
1018
|
+
|
|
1019
|
+
<div class="chart-container">
|
|
1020
|
+
<canvas id="resolutionTrendChart"></canvas>
|
|
1021
|
+
</div>
|
|
1022
|
+
|
|
1023
|
+
<div class="chart-container">
|
|
1024
|
+
<canvas id="byToolChart"></canvas>
|
|
1025
|
+
</div>
|
|
1026
|
+
|
|
1027
|
+
${X&&X.length>0?` <div class="alerts">
|
|
1028
|
+
<h2>Pattern Alerts</h2>
|
|
1029
|
+
<ul>
|
|
1030
|
+
${X.map((J)=>`<li>Pattern detected: ${J.count} open entries for ${d4(J.tool)}/${d4(J.category)}</li>`).join(`
|
|
1031
|
+
`)}
|
|
1032
|
+
</ul>
|
|
1033
|
+
</div>`:""}
|
|
1034
|
+
|
|
1035
|
+
<h2>Open Items</h2>
|
|
1036
|
+
<table id="openItemsTable">
|
|
1037
|
+
<thead>
|
|
1038
|
+
<tr><th>ID</th><th>Severity</th><th>Category</th><th>Description</th><th>Age</th></tr>
|
|
1039
|
+
</thead>
|
|
1040
|
+
<tbody>
|
|
1041
|
+
${_||'<tr><td colspan="5">No open items</td></tr>'}
|
|
1042
|
+
</tbody>
|
|
1043
|
+
</table>
|
|
1044
|
+
|
|
1045
|
+
<div class="generated">Generated ${new Date().toISOString().split("T")[0]}</div>
|
|
1046
|
+
|
|
1047
|
+
<script>
|
|
1048
|
+
const stats = ${JSON.stringify($)};
|
|
1049
|
+
const trends = ${JSON.stringify(Z)};
|
|
1050
|
+
const openItems = ${JSON.stringify(Q)};
|
|
1051
|
+
|
|
1052
|
+
const chartDefaults = {
|
|
1053
|
+
color: '#e0e0e0',
|
|
1054
|
+
borderColor: '#333',
|
|
1055
|
+
};
|
|
1056
|
+
Chart.defaults.color = '#e0e0e0';
|
|
1057
|
+
Chart.defaults.borderColor = '#333';
|
|
1058
|
+
|
|
1059
|
+
// Chart 1: Friction Over Time (line)
|
|
1060
|
+
if (trends.length > 0) {
|
|
1061
|
+
new Chart(document.getElementById('overTimeChart'), {
|
|
1062
|
+
type: 'line',
|
|
1063
|
+
data: {
|
|
1064
|
+
labels: trends.map(t => t.week),
|
|
1065
|
+
datasets: [
|
|
1066
|
+
{ label: 'New', data: trends.map(t => t.newCount), borderColor: '#ff4444', backgroundColor: 'rgba(255,68,68,0.1)', fill: true, tension: 0.3 },
|
|
1067
|
+
{ label: 'Resolved', data: trends.map(t => t.resolvedCount), borderColor: '#44bb44', backgroundColor: 'rgba(68,187,68,0.1)', fill: true, tension: 0.3 }
|
|
1068
|
+
]
|
|
1069
|
+
},
|
|
1070
|
+
options: { responsive: true, plugins: { title: { display: true, text: 'Friction Over Time', color: '#e0e0e0' } }, scales: { x: { ticks: { color: '#888' }, grid: { color: '#333' } }, y: { ticks: { color: '#888' }, grid: { color: '#333' }, beginAtZero: true } } }
|
|
1071
|
+
});
|
|
1072
|
+
}
|
|
1073
|
+
|
|
1074
|
+
// Chart 2: By Category (doughnut)
|
|
1075
|
+
new Chart(document.getElementById('byCategoryChart'), {
|
|
1076
|
+
type: 'doughnut',
|
|
1077
|
+
data: {
|
|
1078
|
+
labels: Object.keys(stats.byCategory),
|
|
1079
|
+
datasets: [{
|
|
1080
|
+
data: Object.values(stats.byCategory),
|
|
1081
|
+
backgroundColor: ['#ff6384', '#36a2eb', '#ffce56', '#4bc0c0', '#9966ff', '#ff9f40']
|
|
1082
|
+
}]
|
|
1083
|
+
},
|
|
1084
|
+
options: { responsive: true, plugins: { title: { display: true, text: 'By Category', color: '#e0e0e0' }, legend: { labels: { color: '#e0e0e0' } } } }
|
|
1085
|
+
});
|
|
1086
|
+
|
|
1087
|
+
// Chart 3: By Severity (horizontal bar)
|
|
1088
|
+
new Chart(document.getElementById('bySeverityChart'), {
|
|
1089
|
+
type: 'bar',
|
|
1090
|
+
data: {
|
|
1091
|
+
labels: ['Critical', 'High', 'Medium', 'Low'],
|
|
1092
|
+
datasets: [{
|
|
1093
|
+
label: 'Count',
|
|
1094
|
+
data: [stats.bySeverity.critical, stats.bySeverity.high, stats.bySeverity.medium, stats.bySeverity.low],
|
|
1095
|
+
backgroundColor: ['#ff4444', '#ff8800', '#ffcc00', '#44bb44']
|
|
1096
|
+
}]
|
|
1097
|
+
},
|
|
1098
|
+
options: { indexAxis: 'y', responsive: true, plugins: { title: { display: true, text: 'By Severity', color: '#e0e0e0' }, legend: { display: false } }, scales: { x: { ticks: { color: '#888' }, grid: { color: '#333' }, beginAtZero: true }, y: { ticks: { color: '#888' }, grid: { color: '#333' } } } }
|
|
1099
|
+
});
|
|
1100
|
+
|
|
1101
|
+
// Chart 4: By Tool (doughnut)
|
|
1102
|
+
if (stats.byTool && Object.keys(stats.byTool).length > 0) {
|
|
1103
|
+
new Chart(document.getElementById('byToolChart'), {
|
|
1104
|
+
type: 'doughnut',
|
|
1105
|
+
data: {
|
|
1106
|
+
labels: Object.keys(stats.byTool),
|
|
1107
|
+
datasets: [{
|
|
1108
|
+
data: Object.values(stats.byTool),
|
|
1109
|
+
backgroundColor: ['#ff6384', '#36a2eb', '#ffce56', '#4bc0c0', '#9966ff', '#ff9f40', '#c9cbcf']
|
|
1110
|
+
}]
|
|
1111
|
+
},
|
|
1112
|
+
options: { responsive: true, plugins: { title: { display: true, text: 'By Tool', color: '#e0e0e0' }, legend: { labels: { color: '#e0e0e0' } } } }
|
|
1113
|
+
});
|
|
1114
|
+
}
|
|
1115
|
+
|
|
1116
|
+
// Chart 5: Resolution Trend (grouped bar)
|
|
1117
|
+
if (trends.length > 0) {
|
|
1118
|
+
new Chart(document.getElementById('resolutionTrendChart'), {
|
|
1119
|
+
type: 'bar',
|
|
1120
|
+
data: {
|
|
1121
|
+
labels: trends.map(t => t.week),
|
|
1122
|
+
datasets: [
|
|
1123
|
+
{ label: 'New', data: trends.map(t => t.newCount), backgroundColor: '#ff4444' },
|
|
1124
|
+
{ label: 'Resolved', data: trends.map(t => t.resolvedCount), backgroundColor: '#44bb44' }
|
|
1125
|
+
]
|
|
1126
|
+
},
|
|
1127
|
+
options: { responsive: true, plugins: { title: { display: true, text: 'Resolution Trend', color: '#e0e0e0' }, legend: { labels: { color: '#e0e0e0' } } }, scales: { x: { ticks: { color: '#888' }, grid: { color: '#333' } }, y: { ticks: { color: '#888' }, grid: { color: '#333' }, beginAtZero: true } } }
|
|
1128
|
+
});
|
|
1129
|
+
}
|
|
1130
|
+
</script>
|
|
1131
|
+
</body>
|
|
1132
|
+
</html>`}function d4($){return $.replace(/&/g,"&").replace(/</g,"<").replace(/>/g,">").replace(/"/g,""").replace(/'/g,"'")}F0();L0();async function r4($,Z){if(!$.embed)return console.log("--background requires --embed flag"),console.log(" Usage: memory sync --embed --background"),{exitCode:0};let{spawnBackgroundEmbedding:K,readLock:X,isProcessAlive:Y}=Z??await P6(),Q=X();if(Q&&Y(Q.pid))return console.log(`Embedding already in progress (PID ${Q.pid}). Use 'memory status' to check progress.`),{exitCode:0};let G=K();if(G.started)console.log(`Background embedding started (PID ${G.pid}). Use 'memory status' to check progress.`);else return console.error(`Failed to start background embedding: ${G.reason}`),{exitCode:1};return{exitCode:0}}async function P6(){let $=await Promise.resolve().then(() => ($9(),eZ));return{spawnBackgroundEmbedding:$.spawnBackgroundEmbedding,readLock:$.readLock,isProcessAlive:$.isProcessAlive}}ZZ();async function a3(){let{EmbeddingProviderFactory:$}=await Promise.resolve().then(() => (o4(),n3));return new $}async function i3(){let{loadConfig:$}=await Promise.resolve().then(() => (Z0(),K4));return $()}async function r3($){let{EmbeddingRepository:Z}=await Promise.resolve().then(() => p5);return new Z($)}async function o3($){let Z=new y0;try{let K=await Z.discoverSessions(),X=K;if($.project)X=X.filter((_)=>_.projectPath.decoded.includes($.project));if($.session)X=X.filter((_)=>_.id===$.session);let Y=q$(),Q=new Set(Y?.completedSessionIds??[]),G=X.filter((_)=>!Q.has(_.id));if($.json){let _={dryRun:!0,discovered:K.length,filtered:X.length,toProcess:G.length,recoveredFromCheckpoint:Y?.completedSessions??0,sessions:G.map((J)=>({id:J.id,project:J.projectPath.decoded,size:J.size,modified:J.modifiedTime.toISOString()}))};console.log(JSON.stringify(_,null,2))}else{if(console.log(`Dry run - no changes will be made
|
|
1133
|
+
`),console.log(`Discovered: ${K.length} sessions`),console.log(`After filter: ${X.length} sessions`),Y)console.log(`Checkpoint: ${Y.completedSessions} already done`);if(console.log(`To process: ${G.length} sessions
|
|
1134
|
+
`),G.length>0){console.log("Sessions to sync:");for(let _ of G.slice(0,20)){let J=_.projectPath.decoded.split(/[/\\]/).pop()??"unknown";console.log(` ${_.id.slice(0,16)}... ${J}`)}if(G.length>20)console.log(` ... and ${G.length-20} more`)}}return{exitCode:0}}catch(K){return t4(K,$),{exitCode:1}}}function t4($,Z){let K=y$($);if(Z.json)console.error(r0(K));else console.error(c(K,{verbose:!!Z.verbose}))}function t3($,Z,K){let X=Date.now()-Z;if(K.json){let Y={success:$.success,aborted:$.aborted??!1,duration:X,discovered:$.sessionsDiscovered,processed:$.sessionsProcessed,skipped:$.sessionsSkipped,messages:$.messagesInserted,toolUses:$.toolUsesInserted,recoveredFromCheckpoint:$.recoveredFromCheckpoint,errors:$.errors};console.log(JSON.stringify(Y,null,2));return}if(K.quiet)return;if($.aborted)console.log(`
|
|
1135
|
+
Sync aborted (progress saved)`);else console.log(`
|
|
1136
|
+
Sync complete in ${X}ms`);if(console.log(` Discovered: ${$.sessionsDiscovered}`),console.log(` Processed: ${$.sessionsProcessed}`),console.log(` Skipped: ${$.sessionsSkipped}`),console.log(` Messages: ${$.messagesInserted}`),console.log(` Tool uses: ${$.toolUsesInserted}`),$.recoveredFromCheckpoint)console.log(` Recovered: ${$.recoveredFromCheckpoint} from checkpoint`);if($.errors.length>0){console.log(`
|
|
1137
|
+
Errors (${$.errors.length}):`);for(let Y of $.errors)console.log(` ${Y.sessionPath}: ${Y.error}`)}}function s3(){let $=process.platform==="win32"?"C:\\":"/";return new bZ($)}async function s4($,Z,K={}){let X=K.factory??await a3(),Y=K.config??await i3(),Q=X.createFromConfig(Y);if(!Q){if(!Z.quiet)console.error("Embedding is disabled in configuration. Enable it in ~/.config/memory/config.json");return}let G=K.repositoryOverride??await r3($),{EmbeddingService:_}=await Promise.resolve().then(() => (R9(),D5)),{PatternRedactor:J}=await Promise.resolve().then(() => (XZ(),e3)),{createEmbeddingProgressReporter:H,createModelDownloadHandler:V}=await Promise.resolve().then(() => (f9(),b5)),B=new _({repository:G,provider:Q,config:Y.embedding,redactor:new J}),z=B.checkModelState();if(z.modelChanged&&z.needsReEmbed){if(!await $8(z,Z)){await X.dispose();return}let F=G.getStoredEmbeddingDimensions(),L=Y.embedding.dimensions;if(F!==null&&F!==L){if(!Z.quiet)console.log(`Recreating embedding table for ${L}-dimensional vectors...`);G.recreateVecTable(L)}if(!Z.quiet)console.log("Clearing existing embeddings for re-embedding...")}let W=V({quiet:!!Z.quiet});await Q.initialize(W);let N=G.getTotalMessageCount()-G.getEmbeddedCount();if(N===0){if(!Z.quiet)console.log(`
|
|
1138
|
+
All messages already embedded.`);await X.dispose();return}let q=H({quiet:!!Z.quiet});q.start(N);try{let I;if(z.modelChanged&&z.needsReEmbed)I=await B.clearAndReembed({onProgress:(F)=>q.update(F.current)});else I=await B.embedUnembedded({onProgress:(F)=>q.update(F.current)});if(q.stop(),!Z.quiet){let F=Math.max(1,Math.round(I.durationMs/1000)),L=I.rate.toFixed(1);console.log(`
|
|
1139
|
+
Embedded ${I.embedded} messages in ${F}s (${L} msg/s)`)}}catch(I){q.stop();let F=G.getEmbeddedCount(),L=G.getTotalMessageCount();if(!Z.quiet)console.error(`
|
|
1140
|
+
Embedding failed at ${F}/${L} messages. Run memory sync --embed to resume from where it stopped.`);throw I}finally{await X.dispose()}}async function $8($,Z){let K=$.embeddedCount??0,X=$.storedModelName??$.storedHash??"unknown",Y=$.currentModelName;if(Z.force)return!0;if(!process.stdin.isTTY||Z.quiet)return console.error(`Model changed from ${X} to ${Y}. Skipping re-embedding in non-interactive mode. Run 'memory sync --embed' interactively to re-embed.`),!1;let G=(await import("readline")).createInterface({input:process.stdin,output:process.stdout});return new Promise((_)=>{G.question(`Model changed from ${X} to ${Y}. Re-embed all ${K} messages? [y/N] `,(J)=>{G.close(),_(J.trim().toLowerCase()==="y")})})}r9();ZZ();async function Z8($,Z){try{let K=new PZ($),X=new fZ,Q=await new OZ(K,X).syncMemoryFiles();if(Q.filesIndexed>0||Q.filesSkipped>0||Q.errors.length>0)return Q;return null}catch(K){if(!Z.quiet)console.error(` Memory files: error (${A(K)})`);return null}}function K8($,Z){if(Z.json){let K={memoryFiles:{indexed:$.filesIndexed,skipped:$.filesSkipped,errors:$.errors}};console.log(JSON.stringify(K,null,2));return}if(Z.quiet)return;if(console.log(` Memory files: ${$.filesIndexed} indexed, ${$.filesSkipped} skipped`),$.errors.length>0)for(let K of $.errors)console.log(` Error: ${K.filePath}: ${K.error}`)}async function Z5($,Z,K){try{let X,Y,Q,G;if(K){if(X=K.loadConfig(),!X.ambientContext.enabled)return;Y=K.resolveAutoMemoryDir(),Q=K.resolveProjectName(),G=K.createAmbientService()}else{let{loadConfig:J}=await Promise.resolve().then(() => (Z0(),K4));if(X=J(),!X.ambientContext.enabled)return;let H=process.cwd(),{ProjectPath:V}=await Promise.resolve().then(() => T5),B=V.fromDecoded(H),z=B.encoded;Q=B.projectName;let{homedir:W}=await import("os"),{join:N}=await import("path");Y=N(W(),".claude","projects",z,"memory");let{SqliteProjectResolver:q}=await Promise.resolve().then(() => s5),{SqliteFactRepository:I}=await Promise.resolve().then(() => (X$(),i5)),{SqliteFrictionRepository:F}=await Promise.resolve().then(() => (EZ(),n5)),{AutoMemoryWriter:L}=await Promise.resolve().then(() => (J8(),_8)),{SmartContextService:O}=await Promise.resolve().then(() => (LZ(),C5)),{AmbientContextService:M}=await Promise.resolve().then(() => y5),{createContextFormatter:x}=await Promise.resolve().then(() => (rZ(),x3)),y=new q($),J0=new I($),g0=new F($),H0=x("ai",!1),V0=new O({projectResolver:y,factRepo:J0,frictionRepo:g0});G=new M(V0,new L,H0)}let _=await G.generateAmbientContext({projectName:Q,autoMemoryDir:Y,budget:X.ambientContext.budget});if(_.success&&!Z.quiet)console.log(` Ambient context: updated (~${_.contextTokens} tokens)`);else if(!_.success&&!Z.quiet)console.log(` Ambient context: skipped (${_.reason})`)}catch(X){if(!Z.quiet)console.error(` Ambient context: error (${A(X)})`)}}Z0();XZ();function m6({db:$,resolver:Z}){let K=new y0({projectNameResolver:Z}),X=new hZ,Y=new g($),Q=new T0($),G=new p0($),_=new d0($),J=new NZ(K,X,Y,Q,G,_,$,new cZ,new uZ,new o0);return{fixProjectNames:(H)=>J.fixProjectNames(H),sync:(H)=>J.sync(H)}}async function c6($){await(await p6())($)}function u6($){return{handleBackgroundMode:r4,setupSignalHandlers:i1,hasCheckpoint:p1,loadCheckpoint:q$,createProgressReporter:C9,getDefaultDbPath:E,executeDryRun:o3,handleError:t4,reportResults:t3,createDriveResolver:s3,initializeDatabase:v,closeDatabase:D,bulkOperationCheckpoint:l9,registerCleanup:o1,unregisterCleanup:t1,createSyncService:m6,loadConfig:m,createGitSyncer:d6,rebuildProjections:c6,experimentalRemoteSync:process.env.MEMORY_EXPERIMENTAL_REMOTE_SYNC==="1",runMemoryFileSync:Z8,reportMemoryFileResults:K8,runAmbientContextGeneration:Z5,runEmbeddingPass:s4,...$}}async function L8($,Z={}){let K=u6(Z);if($.background)return await K.handleBackgroundMode($);K.setupSignalHandlers();let X=Date.now(),Y=K.createProgressReporter($);if(!$.quiet&&K.hasCheckpoint()){let J=K.loadCheckpoint();if(J)console.log(`Resuming from previous interrupted sync (${J.completedSessions}/${J.totalSessions} sessions done)`)}let Q=K.getDefaultDbPath();if($.dryRun)return await K.executeDryRun($);let G;try{G=K.initializeDatabase({path:Q}).db}catch(J){return K.handleError(J,$),{exitCode:1}}let _=async()=>{K.closeDatabase(G)};K.registerCleanup(_);try{let J=K.createDriveResolver(),H=K.createSyncService({db:G,resolver:J});if($.fixNames){Y.log("Fixing project names...");let L=await H.fixProjectNames(J);if(!$.quiet)console.log(`Fixed project names: ${L} sessions updated`)}let V={force:$.force,projectFilter:$.project,sessionFilter:$.session,checkpointEnabled:!0,onProgress:(L)=>{if(L.phase==="discovering")Y.log("Discovering sessions...");else if(L.phase==="extracting"){if(L.current===1)Y.start(L.total);Y.update(L.current,L.sessionId)}}},B=await H.sync(V);K.bulkOperationCheckpoint(G),Y.stop(),K.reportResults(B,X,$);let z=K.loadConfig(),W=z.remoteSync?.repositoryUrl,N=z.remoteSync?.enabled===!0&&typeof W==="string"&&W.trim().length>0,q=K.experimentalRemoteSync;if(N&&q){if(!$.quiet)console.log("Synchronizing events with remote Git repository...");try{let O=await(await K.createGitSyncer()).sync(z.machineId,W,z.remoteSync.autoPull,z.remoteSync.autoPush);if(O.success){if(O.rebuildNeeded){if(!$.quiet)console.log("Remote events pulled. Rebuilding database projections...");await K.rebuildProjections(G)}else if(!$.quiet)console.log("Git events are already up to date.")}else console.error(`Warning: Remote synchronization failed: ${O.error}`)}catch(L){console.error(`Warning: Remote synchronization failed to execute: ${A(L)}`)}}else if(N&&!$.quiet)console.warn("Remote synchronization is configured but disabled until Phase 38 readiness. Set MEMORY_EXPERIMENTAL_REMOTE_SYNC=1 only for explicit prototype testing.");if($.includeMemoryFiles===!0||z.legacyMemoryFiles?.enabled===!0||process.env.MEMORY_LEGACY_MEMORY_FILES==="1"){let L=await K.runMemoryFileSync(G,$);if(L)K.reportMemoryFileResults(L,$)}else if($.verbose&&!$.quiet)console.log(" Memory files: skipped (legacy opt-in disabled)");if(!$.dryRun)await K.runAmbientContextGeneration(G,$);let F=B.errors.length>0||B.aborted?1:0;if($.embed&&!$.dryRun){let L=process.env.MEMORY_EMBED_BACKGROUND==="1";try{await K.runEmbeddingPass(G,$)}catch(O){if($.json)console.error(r0(y$(O)));else if(!$.quiet)console.error(c(y$(O),{verbose:$.verbose}));return{exitCode:1}}finally{if(L)if(K.removeBackgroundLock)K.removeBackgroundLock();else{let{removeLock:O}=await Promise.resolve().then(() => ($9(),eZ));O()}}}return{exitCode:F}}catch(J){return Y.stop(),K.handleError(J,$),{exitCode:1}}finally{K.unregisterCleanup(_),K.closeDatabase(G)}}async function d6(){let{GitSyncer:$}=await Promise.resolve().then(() => (X5(),B8));return new $}async function p6(){let{rebuildProjections:$}=await Promise.resolve().then(() => (Y5(),U8));return $}QZ();J5();B5();V9();W9();_9();Q0();import{Command as Bz}from"commander";w0();import jK from"@inquirer/search";import xK from"@inquirer/select";import PK from"fuzzy";var r8=null,EK=null,DK=null;function o8(){if(r8!==null)return r8;return process.stdout.isTTY===!0}function t8(){return o8()}async function s8($){if(!o8())throw Error("Interactive picker requires TTY. Use --session <id> instead.");let{sessionRepo:Z,limit:K=100}=$,Y=(await Z.findFiltered({limit:K})).map((V)=>({value:V.id,name:`${V.projectPath.projectName} (${_0(V.startTime)})`,description:`${V.id.substring(0,8)}... | ${V.messages.length} messages`})),_=await(EK??jK)({message:"Search sessions (type to filter):",source:async(V,{signal:B})=>{if(B.aborted)return[];if(!V)return Y;return PK.filter(V,Y,{extract:(W)=>`${W.name} ${W.description}`}).map((W)=>W.original)},pageSize:10}),H=await(DK??xK)({message:"Action:",choices:[{value:"show",name:"Show session details"},{value:"search",name:"Search within session"},{value:"context",name:"Get project context"},{value:"related",name:"Find related sessions"},{value:"cancel",name:"Cancel"}]});if(H==="cancel")return null;return{sessionId:_,action:H}}E0();_9();QZ();V9();W9();u();M0();function kK($){return{dbPath:E(),show:I$,search:E$,context:M$,related:x$,...$}}async function e8($,Z={}){if(!t8())return console.error("Error: Interactive mode requires a terminal."),console.error("Use specific commands instead:"),console.error(" memory list - List sessions"),console.error(" memory show <id> - Show session details"),console.error(" memory search <q> - Search sessions"),{exitCode:1};let K=kK(Z),X={limit:"100",...$},Y=parseInt(X.limit,10),Q=K.dbPath,{db:G}=v({path:Q});try{let _=new g(G),J=await s8({sessionRepo:_,limit:Y});if(!J)return D(G),{exitCode:0};switch(D(G),J.action){case"show":await K.show(J.sessionId,{});break;case"search":await K.search("*",{session:J.sessionId});break;case"context":{let{db:H}=v({path:Q}),B=await new g(H).findById(J.sessionId);if(D(H),B)await K.context(B.projectPath.projectName,{});break}case"related":await K.related(J.sessionId,{});break}return{exitCode:0}}catch(_){let J=_ instanceof R?_:new R(T.DB_CONNECTION_FAILED,A(_));console.error(c(J));try{D(G)}catch{}return{exitCode:1}}}s0();Z0();X5();import{Command as jz}from"commander";z$();import{Command as Sz}from"commander";import{copyFileSync as SK,existsSync as $2,mkdirSync as vK}from"fs";import{dirname as CK,join as A5}from"path";async function Z2($,Z={}){let K=R0(Z.hookOverrides);if(K.sessionEnd&&K.preCompact&&!$.force)return console.log("Hooks are already installed."),console.log("Use --force to reinstall."),{exitCode:0};let X=a0(Z.hookOverrides);vK(CK(X),{recursive:!0});let Y=wK(Z.hookScriptSourceOverride);if(!Y)return console.error("Error: Hook script not found. Run 'bun run build:hook' first."),{exitCode:1};SK(Y,X),console.log(`Copied hook script to ${X}`);let Q=a$(Z.hookOverrides);if(console.log(Q.message),Q.success)console.log(`
|
|
1141
|
+
Hook installation complete!`),console.log("Sessions will now sync automatically when they end."),console.log(`
|
|
1142
|
+
To check status: memory status`),console.log("To uninstall: memory uninstall"),yK(Z.hookOverrides);else return{exitCode:1};return{exitCode:0}}function yK($){let Z=B$($);if(!Z.hooks)return;let K="memory-nexus",X=!1;for(let Y of Object.values(Z.hooks)){if(!Array.isArray(Y))continue;for(let Q of Y){if(!Q?.hooks)continue;for(let G of Q.hooks)if(G.command?.includes(K)){X=!0;break}if(X)break}if(X)break}if(X)console.error(`
|
|
1143
|
+
Warning: Stale memory-nexus hook references detected in settings.json.`),console.error("Run 'memory uninstall' then 'memory install' to clean up.")}function wK($){if($!==void 0)return $2($)?$:null;let Z=A5(import.meta.dir,"../../../../dist/sync-hook.js"),K=A5(process.cwd(),"dist/sync-hook.js"),X=A5(process.cwd(),"dist","sync-hook.js");return[Z,K,X].find((Q)=>$2(Q))??null}z$();import{Command as fz}from"commander";import{existsSync as bK,unlinkSync as fK}from"fs";async function K2($,Z={}){let K=R0(Z.hookOverrides);if(!K.sessionEnd&&!K.preCompact)return console.log("Hooks are not installed."),{exitCode:0};if($.restore&&K.backupExists){if(_4(Z.hookOverrides))console.log("Restored settings.json from backup.")}else{let Y=i$(Z.hookOverrides);console.log(Y.message)}let X=a0(Z.hookOverrides);if(bK(X))fK(X),console.log("Removed hook script.");return console.log(`
|
|
1144
|
+
Hooks uninstalled successfully.`),console.log("Sessions will no longer sync automatically."),console.log("Manual sync still available: memory sync"),{exitCode:0}}F$();import{Command as uz}from"commander";F$();p();u();AZ();E0();u();p();G9();import{existsSync as N5,readFileSync as hK,unlinkSync as gK}from"fs";import{join as mK}from"path";function cK($){let Z=0;if(!$.database.exists)Z++;if($.database.exists&&!$.database.readable)Z++;if($.database.exists&&!$.database.writable)Z++;if($.database.integrity==="corrupted")Z++;if(!$.permissions.configDir)Z++;if(!$.permissions.logsDir)Z++;if(!$.permissions.sourceDir)Z++;if(Z+=$.config.issues.length,$.llmExtraction&&!$.llmExtraction.ready)Z++;return Z}async function X2($,Z={}){if($.portability)return dK($,Z);if($.json){let X=await(Z.gatherStatus??(await Promise.resolve().then(() => (F$(),V5))).gatherStatus)({dbPath:Z.healthOverrides?.dbPath,logPath:Z.healthOverrides?.logsDir?z9(Z.healthOverrides.logsDir,"sync.log"):void 0,configPath:Z.healthOverrides?.configDir?z9(Z.healthOverrides.configDir,"config.json"):void 0,hookOverrides:Z.healthOverrides?.hookOverrides,fix:$.fix,stats:!1}),Y={database:X.health.database,permissions:X.health.permissions,hooks:{...X.health.hooks,lastRun:X.health.hooks.lastRun?.toISOString()??null},config:X.health.config,embedding:X.health.embedding,sqliteVec:X.health.sqliteVec,searchCapability:X.health.searchCapability,llmExtraction:X.health.llmExtraction,migration:X.migration,qmd:X.qmd};console.log(JSON.stringify(Y,null,2));let Q=0;if(!X.health.database.exists||X.health.database.integrity==="corrupted")Q=2;else if(cK(X.health)>0||!X.health.searchCapability.vectorReady)Q=1;return{exitCode:Q}}return h0({db:!0,hooks:!0,config:!0,embedding:!0,all:!0,fix:$.fix,json:$.json},{dbPath:Z.healthOverrides?.dbPath,logPath:Z.healthOverrides?.logsDir?z9(Z.healthOverrides.logsDir,"sync.log"):void 0,configPath:Z.healthOverrides?.configDir?z9(Z.healthOverrides.configDir,"config.json"):void 0,hookOverrides:Z.healthOverrides?.hookOverrides})}function uK($,Z=process.platform){if(Z==="win32")return $.includes("/")&&($.startsWith("/home")||$.startsWith("/mnt")||$.startsWith("/var")||$.startsWith("/usr")||$.startsWith("/"));return $.includes("\\")||/^[a-zA-Z]:/.test($)}async function dK($,Z={}){let K=N5,X=Z.healthOverrides?.dbPath??E(),Y=Z.healthOverrides?.sourceDir??t(),Q=$.json?!1:k(),G,_=[],J=[],H=[];if(!N5(X)){if($.json)console.log(JSON.stringify({error:"Database does not exist. Run 'memory sync' first."},null,2));else console.error(f("Error: Database does not exist. Run 'memory sync' first.",Q));return{exitCode:1}}try{G=v({path:X}).db;let M=await new g(G).findFiltered({limit:1e5});for(let x of M){let y=x.projectPath.decoded;if(uK(y)&&!_.includes(y))_.push(y);let J0=P0.resolveExistingPath(y,K);if(!K(J0)){if(!J.includes(y))J.push(y)}}}catch(L){let O=A(L);if($.json)console.log(JSON.stringify({error:`Portability scan failed: ${O}`},null,2));else console.error(f(`Portability scan failed: ${O}`,Q));return{exitCode:2}}finally{if(G)D(G)}let V=mK(Y,"embedding.lock"),B=!1,z=!1;if(N5(V)){B=!0;try{let L=hK(V,"utf-8"),O=JSON.parse(L);if(O.pid)process.kill(O.pid,0);else z=!0}catch(L){z=!0}}if(B&&z){if(H.push(V),$.fix)try{gK(V)}catch(L){}}let N=await(Z.gatherStatus??(await Promise.resolve().then(() => (F$(),V5))).gatherStatus)({dbPath:X,fix:!1,stats:!1}),q=N.health.sqliteVec.available,I=N.health.sqliteVec.version;if($.json)return console.log(JSON.stringify({portability:{mixedDialectPaths:_,orphanedPaths:J,staleLocks:H,sqliteVecAvailable:q,sqliteVecVersion:I,fixedStaleLocks:$.fix&&H.length>0}},null,2)),{exitCode:J.length>0||_.length>0||H.length>0&&!$.fix||!q?1:0};if(console.log("Portability & Migration Diagnostics"),console.log("=================================="),console.log(""),_.length===0)console.log(` ${b("[OK]",Q)} Path Dialects: No mixed path slashes/drive dialects detected.`);else{console.log(` ${d("[WARN]",Q)} Path Dialects: ${_.length} mixed slash/drive formats detected.`);for(let L of _)console.log(` - ${L}`)}if(J.length===0)console.log(` ${b("[OK]",Q)} Orphaned Workspaces: All session folders exist physically on disk.`);else{console.log(` ${d("[WARN]",Q)} Orphaned Workspaces: ${J.length} project folder(s) not found on active filesystem.`);for(let L of J)console.log(` - ${L}`)}if(H.length===0)console.log(` ${b("[OK]",Q)} Active Locks: No stale sync/embedding lock files detected.`);else if($.fix)console.log(` ${b("[FIXED]",Q)} Active Locks: Cleaned up ${H.length} stale lock file(s).`);else{console.log(` ${d("[WARN]",Q)} Active Locks: ${H.length} stale sync/embedding lock file(s) found.`);for(let L of H)console.log(` - ${L}`)}if(q)console.log(` ${b("[OK]",Q)} sqlite-vec: Loadable (v${I}) for active architecture.`);else console.log(` ${f("[FAIL]",Q)} sqlite-vec: Not loadable on this system architecture.`);if(console.log(""),J.length>0)console.log("\uD83D\uDCA1 [TIP] Orphaned project paths detected. You can safely prune these stale database records by running: memory purge --orphans"),console.log("");return{exitCode:J.length>0||_.length>0||H.length>0&&!$.fix||!q?1:0}}function z9(...$){if($.some((Z)=>Z===void 0))return;return $.join("/")}E0();u();AZ();import{Command as XA,Option as YA}from"commander";import*as Y2 from"readline";import{existsSync as pK}from"fs";function Q2($){let Z=$.match(/^(\d+)([dmy])$/i);if(!Z)throw Error(`Invalid duration format: "${$}". Use format like "30d" (days), "6m" (months), or "1y" (years).`);let K=parseInt(Z[1],10),X=Z[2].toLowerCase();if(K<=0)throw Error("Duration value must be a positive number.");let Y=new Date,Q;switch(X){case"d":Q=new Date(Y.getTime()-K*24*60*60*1000);break;case"m":Q=new Date(Y.getFullYear(),Y.getMonth()-K,Y.getDate());break;case"y":Q=new Date(Y.getFullYear()-K,Y.getMonth(),Y.getDate());break;default:throw Error(`Unknown duration unit: "${X}"`)}return Q}function GZ($){return $.toISOString().split("T")[0]}async function lK($){let Z=Y2.createInterface({input:process.stdin,output:process.stdout});return new Promise((K)=>{Z.question($,(X)=>{Z.close(),K(X.toLowerCase()==="y"||X.toLowerCase()==="yes")})})}async function G2($,Z={}){let K=Z.askConfirmation??lK,X=Z.existsSync??pK,Y=Z.getDefaultDbPath??E,Q=Z.initializeDatabase??v,G=Z.closeDatabase??D,_=Z.createSessionRepository??((B)=>new g(B));if(!$.olderThan&&!$.orphans){if($.json)console.log(JSON.stringify({error:"Please specify either --older-than <duration> or --orphans."},null,2));else console.error("Error: Please specify either --older-than <duration> or --orphans.");return{exitCode:1}}let J;if($.olderThan)try{J=Q2($.olderThan)}catch(B){let z=A(B);if($.json)console.log(JSON.stringify({error:z},null,2));else console.error(`Error: ${z}`);return{exitCode:1}}let H=Z.dbPath??Y(),V;try{V=Q({path:H}).db}catch(B){let z=A(B);if($.json)console.log(JSON.stringify({error:`Database error: ${z}`},null,2));else console.error("Error: Database not found or could not be opened.");return{exitCode:1}}try{let B=_(V),z=new Map;if(J){let q=await B.findOlderThan(J);for(let I of q)z.set(I.id,I)}if($.orphans){let q=await B.findFiltered({limit:1e5});for(let I of q){let F=I.projectPath.decoded,L=P0.resolveExistingPath(F,X);if(!X(L))z.set(I.id,I)}}let W=z.size;if(W===0){if($.json)console.log(JSON.stringify({sessionsDeleted:0,cutoffDate:J?.toISOString()??null,dryRun:$.dryRun??!1,message:J&&!$.orphans?`No sessions older than ${GZ(J)}`:"No sessions matched the purge criteria."},null,2));else if(!$.quiet)if(J&&!$.orphans)console.log(`No sessions older than ${GZ(J)}.`);else console.log("No sessions matched the purge criteria.");return{exitCode:0}}if($.dryRun){let q=Array.from(z.values());if($.json)console.log(JSON.stringify({sessionsToDelete:W,cutoffDate:J?.toISOString()??null,dryRun:!0,sessions:q.map((I)=>({id:I.id,project:I.projectPath.projectName,startTime:I.startTime.toISOString(),messageCount:I.messageCount}))},null,2));else if($.quiet)console.log(W.toString());else{if(J&&!$.orphans)console.log(`Would delete ${W} session(s) older than ${GZ(J)}:
|
|
1145
|
+
`);else console.log(`Would delete ${W} session(s):
|
|
1146
|
+
`);let I=k();for(let F of q){let L=F.id.substring(0,16),O=F.projectPath.projectName,M=F.startTime.toISOString().split("T")[0],x=F.messageCount;if(I)console.log(` \x1B[33m${L}\x1B[0m ${O} ${M} (${x} messages)`);else console.log(` ${L} ${O} ${M} (${x} messages)`)}}return{exitCode:0}}if(!$.force){if(!await K(J&&!$.orphans?`Delete ${W} session(s) older than ${GZ(J)}? This cannot be undone. (y/n) `:`Delete ${W} session(s)? This cannot be undone. (y/n) `)){if($.json)console.log(JSON.stringify({cancelled:!0},null,2));else if(!$.quiet)console.log("Purge cancelled.");return{exitCode:0}}}if(V.transaction(()=>{for(let q of z.keys())B.delete(q)}).immediate(),$.json)console.log(JSON.stringify({sessionsDeleted:W,cutoffDate:J?.toISOString()??null,dryRun:!1},null,2));else if($.quiet)console.log(W.toString());else if(J&&!$.orphans)console.log(`Deleted ${W} session(s) older than ${GZ(J)}.`);else console.log(`Deleted ${W} session(s).`);return{exitCode:0}}catch(B){let z=A(B);if($.json)console.log(JSON.stringify({error:z},null,2));else console.error(`Error: ${z}`);return{exitCode:2}}finally{if(V)G(V)}}import{Command as zA}from"commander";u();p();z$();u();import{Command as RA,Option as FA}from"commander";XZ();import{existsSync as _2}from"fs";import{dirname as nK}from"path";async function J2($,Z={}){let K=nK($);if(K!=="."&&!_2(K))return console.error(`Error: Directory does not exist: ${K}`),{exitCode:1};let X=E();if(!_2(X))return console.error("Error: Database does not exist. Run 'memory sync' first."),{exitCode:1};let{db:Y}=v({path:X});try{let Q=await F9(Y,$,{includeSensitive:Z.includeSensitive,redactor:new o0});if(Z.json)console.log(JSON.stringify({success:!0,path:$,stats:Q},null,2));else if(Z.quiet)console.log($);else console.log(aK(Q,$));return{exitCode:0}}catch(Q){let G=A(Q);if(Z.json)console.log(JSON.stringify({success:!1,error:G},null,2));else console.error(`Error: ${G}`);return{exitCode:1}}finally{D(Y)}}function aK($,Z){let K=[];return K.push(`Exported ${$.sessions} sessions, ${$.messages} messages to ${Z}`),K.push(""),K.push("Details:"),K.push(` Sessions: ${$.sessions}`),K.push(` Messages: ${$.messages}`),K.push(` Tool uses: ${$.toolUses}`),K.push(` Entities: ${$.entities}`),K.push(` Links: ${$.links}`),K.push(` File size: ${iK($.bytes)}`),K.join(`
|
|
1147
|
+
`)}function iK($){if($===0)return"0 B";let Z=["B","KB","MB","GB"],K=1024,X=Math.floor(Math.log($)/Math.log(K));return`${($/Math.pow(K,X)).toFixed(X>0?1:0)} ${Z[X]}`}u();import{Command as vA,Option as CA}from"commander";import{existsSync as rK}from"fs";async function H2($,Z={}){if(!rK($))return _Z("File does not exist",$,Z),{exitCode:1};let K=await qZ($);if(!K.valid)return _Z(`Invalid backup file: ${K.error}`,$,Z),{exitCode:1};let X=E(),{db:Y}=v({path:X});try{if(j9(Y)&&!Z.clear&&!Z.force){if(!Z.json&&!Z.quiet)console.log("Warning: Database contains existing data."),console.log("Use --clear to replace all data, or --force to merge without prompt.");if(!process.stdout.isTTY)return _Z("Cannot merge with existing data in non-interactive mode. Use --clear or --force.",$,Z),{exitCode:1};return _Z("Use --clear to replace data or --force to merge",$,Z),{exitCode:1}}let G=await M9(Y,$,{clearExisting:Z.clear});if(Z.json){let _={success:!0,path:$,version:K.version,stats:G,cleared:Z.clear??!1};console.log(JSON.stringify(_,null,2))}else if(Z.quiet);else console.log(oK(G,$,Z.clear??!1));return{exitCode:0}}catch(Q){let G=A(Q);return _Z(G,$,Z),{exitCode:1}}finally{D(Y)}}function _Z($,Z,K){if(K.json)console.log(JSON.stringify({success:!1,path:Z,error:$},null,2));else console.error(`Error: ${$}`)}function oK($,Z,K){let X=[],Y=K?"Replaced":"Imported";return X.push(`${Y} ${$.sessions} sessions, ${$.messages} messages from ${Z}`),X.push(""),X.push("Details:"),X.push(` Sessions: ${$.sessions}`),X.push(` Messages: ${$.messages}`),X.push(` Tool uses: ${$.toolUses}`),X.push(` Entities: ${$.entities}`),X.push(` Links: ${$.links}`),X.join(`
|
|
1148
|
+
`)}import{Command as mA}from"commander";function tK($){return $==="bash"||$==="zsh"||$==="fish"}function sK(){return`# memory bash completion
|
|
1149
|
+
# Add to ~/.bashrc: eval "$(memory completion bash)"
|
|
1150
|
+
|
|
1151
|
+
_memory_completion() {
|
|
1152
|
+
local cur prev words cword
|
|
1153
|
+
_init_completion || return
|
|
1154
|
+
|
|
1155
|
+
local commands="sync search list stats context related show browse install uninstall status doctor purge export import completion"
|
|
1156
|
+
local search_opts="--limit --project --role --session --after --before --case-sensitive --json --verbose --quiet"
|
|
1157
|
+
local list_opts="--limit --project --after --before --sort --json --verbose --quiet"
|
|
1158
|
+
local stats_opts="--projects --json --verbose --quiet"
|
|
1159
|
+
local context_opts="--limit --json --verbose --quiet"
|
|
1160
|
+
local related_opts="--limit --depth --json --verbose --quiet"
|
|
1161
|
+
local show_opts="--json --verbose --quiet"
|
|
1162
|
+
local browse_opts="--project"
|
|
1163
|
+
local sync_opts="--force --dry-run --verbose --quiet"
|
|
1164
|
+
local install_opts="--force"
|
|
1165
|
+
local uninstall_opts="--restore"
|
|
1166
|
+
local doctor_opts="--json --fix"
|
|
1167
|
+
local purge_opts="--before --dry-run --force --json --verbose --quiet"
|
|
1168
|
+
local export_opts="--json --verbose --quiet --include-sensitive"
|
|
1169
|
+
local import_opts="--force --dry-run --json --verbose --quiet"
|
|
1170
|
+
local completion_opts=""
|
|
1171
|
+
|
|
1172
|
+
case "\${prev}" in
|
|
1173
|
+
memory)
|
|
1174
|
+
COMPREPLY=( $(compgen -W "\${commands}" -- "\${cur}") )
|
|
1175
|
+
return 0
|
|
1176
|
+
;;
|
|
1177
|
+
search)
|
|
1178
|
+
COMPREPLY=( $(compgen -W "\${search_opts}" -- "\${cur}") )
|
|
1179
|
+
return 0
|
|
1180
|
+
;;
|
|
1181
|
+
list)
|
|
1182
|
+
COMPREPLY=( $(compgen -W "\${list_opts}" -- "\${cur}") )
|
|
1183
|
+
return 0
|
|
1184
|
+
;;
|
|
1185
|
+
stats)
|
|
1186
|
+
COMPREPLY=( $(compgen -W "\${stats_opts}" -- "\${cur}") )
|
|
1187
|
+
return 0
|
|
1188
|
+
;;
|
|
1189
|
+
context)
|
|
1190
|
+
COMPREPLY=( $(compgen -W "\${context_opts}" -- "\${cur}") )
|
|
1191
|
+
return 0
|
|
1192
|
+
;;
|
|
1193
|
+
related)
|
|
1194
|
+
COMPREPLY=( $(compgen -W "\${related_opts}" -- "\${cur}") )
|
|
1195
|
+
return 0
|
|
1196
|
+
;;
|
|
1197
|
+
show)
|
|
1198
|
+
COMPREPLY=( $(compgen -W "\${show_opts}" -- "\${cur}") )
|
|
1199
|
+
return 0
|
|
1200
|
+
;;
|
|
1201
|
+
browse)
|
|
1202
|
+
COMPREPLY=( $(compgen -W "\${browse_opts}" -- "\${cur}") )
|
|
1203
|
+
return 0
|
|
1204
|
+
;;
|
|
1205
|
+
sync)
|
|
1206
|
+
COMPREPLY=( $(compgen -W "\${sync_opts}" -- "\${cur}") )
|
|
1207
|
+
return 0
|
|
1208
|
+
;;
|
|
1209
|
+
install)
|
|
1210
|
+
COMPREPLY=( $(compgen -W "\${install_opts}" -- "\${cur}") )
|
|
1211
|
+
return 0
|
|
1212
|
+
;;
|
|
1213
|
+
uninstall)
|
|
1214
|
+
COMPREPLY=( $(compgen -W "\${uninstall_opts}" -- "\${cur}") )
|
|
1215
|
+
return 0
|
|
1216
|
+
;;
|
|
1217
|
+
doctor)
|
|
1218
|
+
COMPREPLY=( $(compgen -W "\${doctor_opts}" -- "\${cur}") )
|
|
1219
|
+
return 0
|
|
1220
|
+
;;
|
|
1221
|
+
purge)
|
|
1222
|
+
COMPREPLY=( $(compgen -W "\${purge_opts}" -- "\${cur}") )
|
|
1223
|
+
return 0
|
|
1224
|
+
;;
|
|
1225
|
+
export)
|
|
1226
|
+
COMPREPLY=( $(compgen -W "\${export_opts}" -- "\${cur}") )
|
|
1227
|
+
return 0
|
|
1228
|
+
;;
|
|
1229
|
+
import)
|
|
1230
|
+
COMPREPLY=( $(compgen -W "\${import_opts}" -- "\${cur}") )
|
|
1231
|
+
return 0
|
|
1232
|
+
;;
|
|
1233
|
+
completion)
|
|
1234
|
+
COMPREPLY=( $(compgen -W "bash zsh fish" -- "\${cur}") )
|
|
1235
|
+
return 0
|
|
1236
|
+
;;
|
|
1237
|
+
--role)
|
|
1238
|
+
COMPREPLY=( $(compgen -W "user assistant" -- "\${cur}") )
|
|
1239
|
+
return 0
|
|
1240
|
+
;;
|
|
1241
|
+
--sort)
|
|
1242
|
+
COMPREPLY=( $(compgen -W "recent oldest largest" -- "\${cur}") )
|
|
1243
|
+
return 0
|
|
1244
|
+
;;
|
|
1245
|
+
esac
|
|
1246
|
+
|
|
1247
|
+
if [[ "\${cur}" == -* ]]; then
|
|
1248
|
+
case "\${words[1]}" in
|
|
1249
|
+
search) COMPREPLY=( $(compgen -W "\${search_opts}" -- "\${cur}") ) ;;
|
|
1250
|
+
list) COMPREPLY=( $(compgen -W "\${list_opts}" -- "\${cur}") ) ;;
|
|
1251
|
+
stats) COMPREPLY=( $(compgen -W "\${stats_opts}" -- "\${cur}") ) ;;
|
|
1252
|
+
context) COMPREPLY=( $(compgen -W "\${context_opts}" -- "\${cur}") ) ;;
|
|
1253
|
+
related) COMPREPLY=( $(compgen -W "\${related_opts}" -- "\${cur}") ) ;;
|
|
1254
|
+
show) COMPREPLY=( $(compgen -W "\${show_opts}" -- "\${cur}") ) ;;
|
|
1255
|
+
browse) COMPREPLY=( $(compgen -W "\${browse_opts}" -- "\${cur}") ) ;;
|
|
1256
|
+
sync) COMPREPLY=( $(compgen -W "\${sync_opts}" -- "\${cur}") ) ;;
|
|
1257
|
+
install) COMPREPLY=( $(compgen -W "\${install_opts}" -- "\${cur}") ) ;;
|
|
1258
|
+
uninstall) COMPREPLY=( $(compgen -W "\${uninstall_opts}" -- "\${cur}") ) ;;
|
|
1259
|
+
doctor) COMPREPLY=( $(compgen -W "\${doctor_opts}" -- "\${cur}") ) ;;
|
|
1260
|
+
purge) COMPREPLY=( $(compgen -W "\${purge_opts}" -- "\${cur}") ) ;;
|
|
1261
|
+
export) COMPREPLY=( $(compgen -W "\${export_opts}" -- "\${cur}") ) ;;
|
|
1262
|
+
import) COMPREPLY=( $(compgen -W "\${import_opts}" -- "\${cur}") ) ;;
|
|
1263
|
+
esac
|
|
1264
|
+
return 0
|
|
1265
|
+
fi
|
|
1266
|
+
|
|
1267
|
+
COMPREPLY=( $(compgen -W "\${commands}" -- "\${cur}") )
|
|
1268
|
+
}
|
|
1269
|
+
|
|
1270
|
+
complete -F _memory_completion memory
|
|
1271
|
+
`}function eK(){return`#compdef memory
|
|
1272
|
+
# memory zsh completion
|
|
1273
|
+
# Add to ~/.zshrc: eval "$(memory completion zsh)"
|
|
1274
|
+
|
|
1275
|
+
_memory() {
|
|
1276
|
+
local -a commands
|
|
1277
|
+
commands=(
|
|
1278
|
+
'sync:Sync Claude Code sessions to database'
|
|
1279
|
+
'search:Search messages across all sessions'
|
|
1280
|
+
'list:List sessions with filtering'
|
|
1281
|
+
'stats:Show database statistics'
|
|
1282
|
+
'context:Get context for a project'
|
|
1283
|
+
'related:Find sessions related to a given session'
|
|
1284
|
+
'show:Show session details and conversation'
|
|
1285
|
+
'browse:Browse and select sessions interactively'
|
|
1286
|
+
'install:Install automatic sync hook'
|
|
1287
|
+
'uninstall:Remove automatic sync hook'
|
|
1288
|
+
'status:Show hook installation status'
|
|
1289
|
+
'doctor:Check system health and diagnose issues'
|
|
1290
|
+
'purge:Remove old sessions from database'
|
|
1291
|
+
'export:Export database to JSON file'
|
|
1292
|
+
'import:Import database from JSON file'
|
|
1293
|
+
'completion:Generate shell completion script'
|
|
1294
|
+
)
|
|
1295
|
+
|
|
1296
|
+
local -a search_opts list_opts stats_opts context_opts related_opts show_opts browse_opts
|
|
1297
|
+
local -a sync_opts install_opts uninstall_opts doctor_opts purge_opts export_opts import_opts completion_shells
|
|
1298
|
+
|
|
1299
|
+
search_opts=(
|
|
1300
|
+
'--limit[Maximum number of results]:number'
|
|
1301
|
+
'--project[Filter by project name]:project'
|
|
1302
|
+
'--role[Filter by message role]:role:(user assistant)'
|
|
1303
|
+
'--session[Filter by session ID]:session'
|
|
1304
|
+
'--after[Filter by start date]:date'
|
|
1305
|
+
'--before[Filter by end date]:date'
|
|
1306
|
+
'--case-sensitive[Enable case-sensitive search]'
|
|
1307
|
+
'--json[Output as JSON]'
|
|
1308
|
+
'--verbose[Show detailed output]'
|
|
1309
|
+
'--quiet[Minimal output]'
|
|
1310
|
+
)
|
|
1311
|
+
|
|
1312
|
+
list_opts=(
|
|
1313
|
+
'--limit[Maximum number of results]:number'
|
|
1314
|
+
'--project[Filter by project name]:project'
|
|
1315
|
+
'--after[Filter by start date]:date'
|
|
1316
|
+
'--before[Filter by end date]:date'
|
|
1317
|
+
'--sort[Sort order]:order:(recent oldest largest)'
|
|
1318
|
+
'--json[Output as JSON]'
|
|
1319
|
+
'--verbose[Show detailed output]'
|
|
1320
|
+
'--quiet[Minimal output]'
|
|
1321
|
+
)
|
|
1322
|
+
|
|
1323
|
+
stats_opts=(
|
|
1324
|
+
'--projects[Number of top projects to show]:number'
|
|
1325
|
+
'--json[Output as JSON]'
|
|
1326
|
+
'--verbose[Show detailed output]'
|
|
1327
|
+
'--quiet[Minimal output]'
|
|
1328
|
+
)
|
|
1329
|
+
|
|
1330
|
+
context_opts=(
|
|
1331
|
+
'--limit[Maximum number of results]:number'
|
|
1332
|
+
'--json[Output as JSON]'
|
|
1333
|
+
'--verbose[Show detailed output]'
|
|
1334
|
+
'--quiet[Minimal output]'
|
|
1335
|
+
)
|
|
1336
|
+
|
|
1337
|
+
related_opts=(
|
|
1338
|
+
'--limit[Maximum number of results]:number'
|
|
1339
|
+
'--depth[Maximum hop depth]:number'
|
|
1340
|
+
'--json[Output as JSON]'
|
|
1341
|
+
'--verbose[Show detailed output]'
|
|
1342
|
+
'--quiet[Minimal output]'
|
|
1343
|
+
)
|
|
1344
|
+
|
|
1345
|
+
show_opts=(
|
|
1346
|
+
'--json[Output as JSON]'
|
|
1347
|
+
'--verbose[Show detailed output]'
|
|
1348
|
+
'--quiet[Minimal output]'
|
|
1349
|
+
)
|
|
1350
|
+
|
|
1351
|
+
browse_opts=(
|
|
1352
|
+
'--project[Filter by project name]:project'
|
|
1353
|
+
)
|
|
1354
|
+
|
|
1355
|
+
sync_opts=(
|
|
1356
|
+
'--force[Force re-sync all sessions]'
|
|
1357
|
+
'--dry-run[Preview changes without syncing]'
|
|
1358
|
+
'--verbose[Show detailed output]'
|
|
1359
|
+
'--quiet[Minimal output]'
|
|
1360
|
+
)
|
|
1361
|
+
|
|
1362
|
+
install_opts=(
|
|
1363
|
+
'--force[Overwrite existing hook]'
|
|
1364
|
+
)
|
|
1365
|
+
|
|
1366
|
+
uninstall_opts=(
|
|
1367
|
+
'--restore[Restore original settings backup]'
|
|
1368
|
+
)
|
|
1369
|
+
|
|
1370
|
+
doctor_opts=(
|
|
1371
|
+
'--json[Output as JSON]'
|
|
1372
|
+
'--fix[Attempt to fix common issues]'
|
|
1373
|
+
)
|
|
1374
|
+
|
|
1375
|
+
purge_opts=(
|
|
1376
|
+
'--before[Delete sessions before date]:date'
|
|
1377
|
+
'--dry-run[Preview deletions without removing]'
|
|
1378
|
+
'--force[Skip confirmation prompt]'
|
|
1379
|
+
'--json[Output as JSON]'
|
|
1380
|
+
'--verbose[Show detailed output]'
|
|
1381
|
+
'--quiet[Minimal output]'
|
|
1382
|
+
)
|
|
1383
|
+
|
|
1384
|
+
export_opts=(
|
|
1385
|
+
'--json[Output as JSON]'
|
|
1386
|
+
'--verbose[Show detailed output]'
|
|
1387
|
+
'--quiet[Minimal output]'
|
|
1388
|
+
'--include-sensitive[Export raw sensitive values without redaction]'
|
|
1389
|
+
)
|
|
1390
|
+
|
|
1391
|
+
import_opts=(
|
|
1392
|
+
'--force[Overwrite existing data]'
|
|
1393
|
+
'--dry-run[Preview import without changes]'
|
|
1394
|
+
'--json[Output as JSON]'
|
|
1395
|
+
'--verbose[Show detailed output]'
|
|
1396
|
+
'--quiet[Minimal output]'
|
|
1397
|
+
)
|
|
1398
|
+
|
|
1399
|
+
completion_shells=(bash zsh fish)
|
|
1400
|
+
|
|
1401
|
+
_arguments -C \\
|
|
1402
|
+
'1:command:->command' \\
|
|
1403
|
+
'*::arg:->args'
|
|
1404
|
+
|
|
1405
|
+
case "$state" in
|
|
1406
|
+
command)
|
|
1407
|
+
_describe 'command' commands
|
|
1408
|
+
;;
|
|
1409
|
+
args)
|
|
1410
|
+
case "$words[1]" in
|
|
1411
|
+
search) _arguments "$search_opts[@]" ':query:' ;;
|
|
1412
|
+
list) _arguments "$list_opts[@]" ;;
|
|
1413
|
+
stats) _arguments "$stats_opts[@]" ;;
|
|
1414
|
+
context) _arguments "$context_opts[@]" ':project:' ;;
|
|
1415
|
+
related) _arguments "$related_opts[@]" ':session:' ;;
|
|
1416
|
+
show) _arguments "$show_opts[@]" ':session:' ;;
|
|
1417
|
+
browse) _arguments "$browse_opts[@]" ;;
|
|
1418
|
+
sync) _arguments "$sync_opts[@]" ;;
|
|
1419
|
+
install) _arguments "$install_opts[@]" ;;
|
|
1420
|
+
uninstall) _arguments "$uninstall_opts[@]" ;;
|
|
1421
|
+
doctor) _arguments "$doctor_opts[@]" ;;
|
|
1422
|
+
purge) _arguments "$purge_opts[@]" ;;
|
|
1423
|
+
export) _arguments "$export_opts[@]" ':output-file:_files' ;;
|
|
1424
|
+
import) _arguments "$import_opts[@]" ':input-file:_files' ;;
|
|
1425
|
+
completion) _arguments '1:shell:(bash zsh fish)' ;;
|
|
1426
|
+
esac
|
|
1427
|
+
;;
|
|
1428
|
+
esac
|
|
1429
|
+
}
|
|
1430
|
+
|
|
1431
|
+
_memory "$@"
|
|
1432
|
+
`}function $X(){return`# memory fish completion
|
|
1433
|
+
# Save to ~/.config/fish/completions/memory.fish:
|
|
1434
|
+
# memory completion fish > ~/.config/fish/completions/memory.fish
|
|
1435
|
+
|
|
1436
|
+
# Disable file completion by default
|
|
1437
|
+
complete -c memory -f
|
|
1438
|
+
|
|
1439
|
+
# Commands
|
|
1440
|
+
complete -c memory -n "__fish_use_subcommand" -a sync -d "Sync Claude Code sessions to database"
|
|
1441
|
+
complete -c memory -n "__fish_use_subcommand" -a search -d "Search messages across all sessions"
|
|
1442
|
+
complete -c memory -n "__fish_use_subcommand" -a list -d "List sessions with filtering"
|
|
1443
|
+
complete -c memory -n "__fish_use_subcommand" -a stats -d "Show database statistics"
|
|
1444
|
+
complete -c memory -n "__fish_use_subcommand" -a context -d "Get context for a project"
|
|
1445
|
+
complete -c memory -n "__fish_use_subcommand" -a related -d "Find sessions related to a given session"
|
|
1446
|
+
complete -c memory -n "__fish_use_subcommand" -a show -d "Show session details and conversation"
|
|
1447
|
+
complete -c memory -n "__fish_use_subcommand" -a browse -d "Browse and select sessions interactively"
|
|
1448
|
+
complete -c memory -n "__fish_use_subcommand" -a install -d "Install automatic sync hook"
|
|
1449
|
+
complete -c memory -n "__fish_use_subcommand" -a uninstall -d "Remove automatic sync hook"
|
|
1450
|
+
complete -c memory -n "__fish_use_subcommand" -a status -d "Show hook installation status"
|
|
1451
|
+
complete -c memory -n "__fish_use_subcommand" -a doctor -d "Check system health and diagnose issues"
|
|
1452
|
+
complete -c memory -n "__fish_use_subcommand" -a purge -d "Remove old sessions from database"
|
|
1453
|
+
complete -c memory -n "__fish_use_subcommand" -a export -d "Export database to JSON file"
|
|
1454
|
+
complete -c memory -n "__fish_use_subcommand" -a import -d "Import database from JSON file"
|
|
1455
|
+
complete -c memory -n "__fish_use_subcommand" -a completion -d "Generate shell completion script"
|
|
1456
|
+
|
|
1457
|
+
# search options
|
|
1458
|
+
complete -c memory -n "__fish_seen_subcommand_from search" -l limit -d "Maximum number of results"
|
|
1459
|
+
complete -c memory -n "__fish_seen_subcommand_from search" -l project -d "Filter by project name"
|
|
1460
|
+
complete -c memory -n "__fish_seen_subcommand_from search" -l role -d "Filter by message role" -a "user assistant"
|
|
1461
|
+
complete -c memory -n "__fish_seen_subcommand_from search" -l session -d "Filter by session ID"
|
|
1462
|
+
complete -c memory -n "__fish_seen_subcommand_from search" -l after -d "Filter by start date"
|
|
1463
|
+
complete -c memory -n "__fish_seen_subcommand_from search" -l before -d "Filter by end date"
|
|
1464
|
+
complete -c memory -n "__fish_seen_subcommand_from search" -l case-sensitive -d "Enable case-sensitive search"
|
|
1465
|
+
complete -c memory -n "__fish_seen_subcommand_from search" -l json -d "Output as JSON"
|
|
1466
|
+
complete -c memory -n "__fish_seen_subcommand_from search" -l verbose -d "Show detailed output"
|
|
1467
|
+
complete -c memory -n "__fish_seen_subcommand_from search" -l quiet -d "Minimal output"
|
|
1468
|
+
|
|
1469
|
+
# list options
|
|
1470
|
+
complete -c memory -n "__fish_seen_subcommand_from list" -l limit -d "Maximum number of results"
|
|
1471
|
+
complete -c memory -n "__fish_seen_subcommand_from list" -l project -d "Filter by project name"
|
|
1472
|
+
complete -c memory -n "__fish_seen_subcommand_from list" -l after -d "Filter by start date"
|
|
1473
|
+
complete -c memory -n "__fish_seen_subcommand_from list" -l before -d "Filter by end date"
|
|
1474
|
+
complete -c memory -n "__fish_seen_subcommand_from list" -l sort -d "Sort order" -a "recent oldest largest"
|
|
1475
|
+
complete -c memory -n "__fish_seen_subcommand_from list" -l json -d "Output as JSON"
|
|
1476
|
+
complete -c memory -n "__fish_seen_subcommand_from list" -l verbose -d "Show detailed output"
|
|
1477
|
+
complete -c memory -n "__fish_seen_subcommand_from list" -l quiet -d "Minimal output"
|
|
1478
|
+
|
|
1479
|
+
# stats options
|
|
1480
|
+
complete -c memory -n "__fish_seen_subcommand_from stats" -l projects -d "Number of top projects to show"
|
|
1481
|
+
complete -c memory -n "__fish_seen_subcommand_from stats" -l json -d "Output as JSON"
|
|
1482
|
+
complete -c memory -n "__fish_seen_subcommand_from stats" -l verbose -d "Show detailed output"
|
|
1483
|
+
complete -c memory -n "__fish_seen_subcommand_from stats" -l quiet -d "Minimal output"
|
|
1484
|
+
|
|
1485
|
+
# context options
|
|
1486
|
+
complete -c memory -n "__fish_seen_subcommand_from context" -l limit -d "Maximum number of results"
|
|
1487
|
+
complete -c memory -n "__fish_seen_subcommand_from context" -l json -d "Output as JSON"
|
|
1488
|
+
complete -c memory -n "__fish_seen_subcommand_from context" -l verbose -d "Show detailed output"
|
|
1489
|
+
complete -c memory -n "__fish_seen_subcommand_from context" -l quiet -d "Minimal output"
|
|
1490
|
+
|
|
1491
|
+
# related options
|
|
1492
|
+
complete -c memory -n "__fish_seen_subcommand_from related" -l limit -d "Maximum number of results"
|
|
1493
|
+
complete -c memory -n "__fish_seen_subcommand_from related" -l depth -d "Maximum hop depth"
|
|
1494
|
+
complete -c memory -n "__fish_seen_subcommand_from related" -l json -d "Output as JSON"
|
|
1495
|
+
complete -c memory -n "__fish_seen_subcommand_from related" -l verbose -d "Show detailed output"
|
|
1496
|
+
complete -c memory -n "__fish_seen_subcommand_from related" -l quiet -d "Minimal output"
|
|
1497
|
+
|
|
1498
|
+
# show options
|
|
1499
|
+
complete -c memory -n "__fish_seen_subcommand_from show" -l json -d "Output as JSON"
|
|
1500
|
+
complete -c memory -n "__fish_seen_subcommand_from show" -l verbose -d "Show detailed output"
|
|
1501
|
+
complete -c memory -n "__fish_seen_subcommand_from show" -l quiet -d "Minimal output"
|
|
1502
|
+
|
|
1503
|
+
# browse options
|
|
1504
|
+
complete -c memory -n "__fish_seen_subcommand_from browse" -l project -d "Filter by project name"
|
|
1505
|
+
|
|
1506
|
+
# sync options
|
|
1507
|
+
complete -c memory -n "__fish_seen_subcommand_from sync" -l force -d "Force re-sync all sessions"
|
|
1508
|
+
complete -c memory -n "__fish_seen_subcommand_from sync" -l dry-run -d "Preview changes without syncing"
|
|
1509
|
+
complete -c memory -n "__fish_seen_subcommand_from sync" -l verbose -d "Show detailed output"
|
|
1510
|
+
complete -c memory -n "__fish_seen_subcommand_from sync" -l quiet -d "Minimal output"
|
|
1511
|
+
|
|
1512
|
+
# install options
|
|
1513
|
+
complete -c memory -n "__fish_seen_subcommand_from install" -l force -d "Overwrite existing hook"
|
|
1514
|
+
|
|
1515
|
+
# uninstall options
|
|
1516
|
+
complete -c memory -n "__fish_seen_subcommand_from uninstall" -l restore -d "Restore original settings backup"
|
|
1517
|
+
|
|
1518
|
+
# doctor options
|
|
1519
|
+
complete -c memory -n "__fish_seen_subcommand_from doctor" -l json -d "Output as JSON"
|
|
1520
|
+
complete -c memory -n "__fish_seen_subcommand_from doctor" -l fix -d "Attempt to fix common issues"
|
|
1521
|
+
|
|
1522
|
+
# purge options
|
|
1523
|
+
complete -c memory -n "__fish_seen_subcommand_from purge" -l before -d "Delete sessions before date"
|
|
1524
|
+
complete -c memory -n "__fish_seen_subcommand_from purge" -l dry-run -d "Preview deletions without removing"
|
|
1525
|
+
complete -c memory -n "__fish_seen_subcommand_from purge" -l force -d "Skip confirmation prompt"
|
|
1526
|
+
complete -c memory -n "__fish_seen_subcommand_from purge" -l json -d "Output as JSON"
|
|
1527
|
+
complete -c memory -n "__fish_seen_subcommand_from purge" -l verbose -d "Show detailed output"
|
|
1528
|
+
complete -c memory -n "__fish_seen_subcommand_from purge" -l quiet -d "Minimal output"
|
|
1529
|
+
|
|
1530
|
+
# export options
|
|
1531
|
+
complete -c memory -n "__fish_seen_subcommand_from export" -l json -d "Output as JSON"
|
|
1532
|
+
complete -c memory -n "__fish_seen_subcommand_from export" -l verbose -d "Show detailed output"
|
|
1533
|
+
complete -c memory -n "__fish_seen_subcommand_from export" -l quiet -d "Minimal output"
|
|
1534
|
+
complete -c memory -n "__fish_seen_subcommand_from export" -l include-sensitive -d "Export raw sensitive values without redaction"
|
|
1535
|
+
|
|
1536
|
+
# import options
|
|
1537
|
+
complete -c memory -n "__fish_seen_subcommand_from import" -l force -d "Overwrite existing data"
|
|
1538
|
+
complete -c memory -n "__fish_seen_subcommand_from import" -l dry-run -d "Preview import without changes"
|
|
1539
|
+
complete -c memory -n "__fish_seen_subcommand_from import" -l json -d "Output as JSON"
|
|
1540
|
+
complete -c memory -n "__fish_seen_subcommand_from import" -l verbose -d "Show detailed output"
|
|
1541
|
+
complete -c memory -n "__fish_seen_subcommand_from import" -l quiet -d "Minimal output"
|
|
1542
|
+
|
|
1543
|
+
# completion shells
|
|
1544
|
+
complete -c memory -n "__fish_seen_subcommand_from completion" -a "bash zsh fish"
|
|
1545
|
+
`}function ZX($){switch($){case"bash":return sK();case"zsh":return eK();case"fish":return $X();default:throw Error(`Unknown shell type: ${$}`)}}function V2($){if(!tK($))return console.error(`Error: Invalid shell type '${$}'`),console.error("Valid shells: bash, zsh, fish"),{exitCode:1};let Z=ZX($);return console.log(Z),{exitCode:0}}Q0();u();import{Command as XN,Option as YN}from"commander";import{join as _X}from"path";import{homedir as JX}from"os";M0();async function W2($,Z){if(!Z.description)return console.error("Error: description is required for log action"),{exitCode:1};let K=await $.log({description:Z.description,severity:Z.severity,category:Z.category,tool:Z.tool,context:Z.context,sourceProject:Z.source});if(Z.json)console.log(JSON.stringify({id:K.id,description:K.description,severity:K.severity,category:K.category,tool:K.tool,status:K.status,loggedAt:K.loggedAt.toISOString(),context:K.context??null,sourceProject:K.sourceProject??null}));else console.log(`Logged friction #${K.id} (${K.severity}/${K.category})`);return{exitCode:0}}async function B2($,Z){let K=Z.limit?parseInt(Z.limit,10):void 0,X=await $.list({all:Z.all,status:Z.status,category:Z.category,tool:Z.tool,limit:K});if(Z.json)console.log(JSON.stringify(X.map((Y)=>({id:Y.id,description:Y.description,severity:Y.severity,category:Y.category,tool:Y.tool,status:Y.status,loggedAt:Y.loggedAt.toISOString(),resolvedAt:Y.resolvedAt?.toISOString()??null,resolution:Y.resolution??null,context:Y.context??null,sourceProject:Y.sourceProject??null,lastReviewedAt:Y.lastReviewedAt?.toISOString()??null}))));else if(X.length===0)console.log(Z.all?"No friction entries found.":"No open friction entries.");else{console.log(`${"".padEnd(5)}${"ID".padEnd(6)}${"Severity".padEnd(10)}${"Category".padEnd(14)}${"Description".padEnd(62)}Age`),console.log("-".repeat(101));let Y=0,Q={};for(let H of X){let V=!H.lastReviewedAt||H.lastReviewedAt<H.loggedAt;if(V)Y++;Q[H.severity]=(Q[H.severity]??0)+1;let B=V?"[NEW]":" ",z=H.description.length>60?H.description.slice(0,57)+"...":H.description,W=Date.now()-H.loggedAt.getTime(),N=Math.floor(W/86400000),q=N===0?"today":`${N}d`;console.log(`${B}${String(H.id).padEnd(6)}${H.severity.padEnd(10)}${H.category.padEnd(14)}${z.padEnd(62)}${q}`)}let G=Object.entries(Q).map(([H,V])=>`${V} ${H}`).join(", "),_=Z.tool?` for ${Z.tool}`:"",J=Y>0?` -- ${Y} new since last review`:"";console.log(`
|
|
1546
|
+
${X.length} ${Z.all?"total":"open"} entries${_} (${G})${J}`)}if(Z.tool)await $.markReviewed(Z.tool);return{exitCode:0}}async function z2($,Z){if(!Z.id||!Z.resolution)return console.error("Error: id and --resolution are required for resolve action"),{exitCode:1};let K=parseInt(Z.id,10);if(isNaN(K))return console.error("Error: id must be a number"),{exitCode:1};if(await $.resolve(K,Z.resolution),Z.json)console.log(JSON.stringify({id:K,status:"resolved",resolution:Z.resolution}));else console.log(`Resolved friction #${K}`);return{exitCode:0}}async function A2($,Z){if(!Z.id||!Z.resolution)return console.error("Error: id and --resolution are required for wont-fix action"),{exitCode:1};let K=parseInt(Z.id,10);if(isNaN(K))return console.error("Error: id must be a number"),{exitCode:1};if(await $.wontFix(K,Z.resolution),Z.json)console.log(JSON.stringify({id:K,status:"wont-fix",resolution:Z.resolution}));else console.log(`Marked friction #${K} as won't fix`);return{exitCode:0}}import{exec as KX}from"child_process";import{mkdirSync as XX,writeFileSync as YX}from"fs";import{join as QX}from"path";import{platform as N2}from"os";F0();p();async function q2($,Z,K=GX){let X=await $.getStats(),Y=await $.getWeeklyTrends(12),Q=await $.list({tool:Z.tool}),G=await $.detectPatterns();if(Z.html){let _=l4(X,Y,Q,G),J=MZ();XX(J,{recursive:!0});let H=QX(J,"dashboard.html");if(YX(H,_,"utf-8"),!Z.json)console.log(`Dashboard written to ${H}`),K(H)}else if(Z.json)console.log(JSON.stringify({stats:X,trends:Y,patterns:G},null,2));else{let _=p4(X,Y,Q,k(),G);if(Z.format==="ai")_=a(_);console.log(_)}return{exitCode:0}}function GX($){let Z=N2()==="win32"?"start":N2()==="darwin"?"open":"xdg-open";KX(`${Z} "${$}"`)}async function O2($,Z){if(!Z.pattern)return console.error("Error: pattern is required for purge action"),{exitCode:1};if(Z.dryRun){let Y=(await $.list({all:!0})).filter((Q)=>{return new RegExp("^"+Z.pattern.replace(/%/g,".*").replace(/_/g,".")+"$").test(Q.description)});if(Y.length===0)if(Z.json)console.log(JSON.stringify({wouldDelete:0,pattern:Z.pattern}));else console.log(`No entries match pattern: "${Z.pattern}"`);else if(Z.json)console.log(JSON.stringify({wouldDelete:Y.length,pattern:Z.pattern}));else{console.log(`Would delete ${Y.length} entries matching "${Z.pattern}":`);for(let Q of Y.slice(0,10))console.log(` #${Q.id}: ${Q.description}`);if(Y.length>10)console.log(` ... and ${Y.length-10} more`)}return{exitCode:0}}if(!Z.force)return console.error(`Use --dry-run to preview or --force to delete entries matching "${Z.pattern}".`),{exitCode:1};let K=await $.purge(Z.pattern);if(K===0)if(Z.json)console.log(JSON.stringify({deleted:0,pattern:Z.pattern}));else console.log(`No entries match pattern: "${Z.pattern}"`);else if(Z.json)console.log(JSON.stringify({deleted:K,pattern:Z.pattern}));else console.log(`Purged ${K} friction entries matching "${Z.pattern}"`);return{exitCode:0}}async function U2($,Z={}){let K;try{let X=Z.dbPath??E();K=v({path:X}).db;let Y=new k0(K),Q=new UZ(Y),G=_X(JX(),".claude","friction.jsonl"),_=await Q.ingestFallbackFile(G);if(_>0)process.stderr.write(`Ingested ${_} friction entries from fallback file
|
|
1547
|
+
`);switch($.action){case"log":return await W2(Q,$);case"list":return await B2(Q,$);case"resolve":return await z2(Q,$);case"wont-fix":return await A2(Q,$);case"dashboard":return await q2(Q,$,Z.openInBrowser);case"purge":return await O2(Q,$);default:return console.error(`Unknown friction action: ${$.action}`),{exitCode:1}}}catch(X){let Y=X instanceof R?X:new R(T.UNKNOWN,A(X));if($.json)console.log(r0(Y));else console.error(c(Y));return{exitCode:1}}finally{if(K)D(K)}}import{Command as IN}from"commander";u();X$();E0();h$();Z0();import{Command as DN}from"commander";v$();Y5();S$();L0();XZ();wZ();class HX{current=0;total=0;isTty=process.stdout.isTTY;quiet=!1;constructor($,Z=!1){if(this.total=$,this.quiet=Z,this.quiet)return;if(this.isTty)process.stdout.write(`\rExtracting facts... [0/${$}] \u2591\u2591\u2591\u2591\u2591\u2591\u2591\u2591\u2591\u2591 0%`);else console.log(`Extracting facts from ${$} sessions...`)}update($){if(this.quiet)return;this.current++;let Z=Math.round(this.current/this.total*100),K=Math.min(10,Math.max(0,Math.floor(Z/10))),X="\u2588".repeat(K)+"\u2591".repeat(10-K);if(this.isTty){let Y=$.length>25?$.substring(0,22)+"...":$;process.stdout.write(`\rExtracting facts... [${this.current}/${this.total}] [${X}] ${Z}% - Session: ${Y}`)}else console.log(`[${this.current}/${this.total}] Processed session: ${$}`)}stop(){if(this.quiet)return;if(this.isTty)process.stdout.write(`
|
|
1548
|
+
`)}}u();X$();import{Command as lN}from"commander";export{qZ as validateExportFile,A as unknownErrorMessage,u0 as sanitizeFtsQuery,x9 as reciprocalRankFusion,M9 as importFromJson,j9 as hasExistingData,P5 as extractSessionId,F9 as exportToJson,K2 as executeUninstallCommand,L8 as executeSyncCommand,h0 as executeStatusCommand,H9 as executeStatsCommand,I$ as executeShowCommand,E$ as executeSearchCommand,x$ as executeRelatedCommand,B9 as executeQueryCommand,G2 as executePurgeCommand,J9 as executeListCommand,Z2 as executeInstallCommand,H2 as executeImportCommand,U2 as executeFrictionCommand,J2 as executeExportCommand,X2 as executeDoctorCommand,M$ as executeContextCommand,V2 as executeCompletionCommand,e8 as executeBrowseCommand,I9 as computeModelHash,n2 as applyTemporalDecayWithExemptions,p2 as applyTemporalDecay,P9 as allocateBudget,z0 as ToolUse,NZ as SyncService,f$ as SmartContextService,B0 as Session,Y0 as SearchResult,C$ as SearchQuery,x5 as RecoveryService,U9 as QueryParser,i as ProjectPath,E5 as PatternExtractor,P0 as PathDecoder,W0 as Message,OZ as MemoryFileSyncService,m0 as MemoryFile,R as MemoryError,q0 as LlmExtractor,$$ as Link,UZ as FrictionService,x0 as FrictionEntry,A0 as Fact,$0 as ExtractionState,T as ErrorCode,e as Entity,T9 as EmbeddingService,X0 as EmbeddingResult,zZ as EmbeddingConfig,N0 as ContentExtractor,l2 as CURATED_FILE_TYPES,c0 as BackfillState,S5 as BackfillService,E9 as AmbientContextService};
|