chore: bump version to 7.0.2

Auto-start worker functionality improvements

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
This commit is contained in:
Alex Newman
2025-12-09 01:02:55 -05:00
parent b003a43e73
commit 06ba1cd92c
13 changed files with 94 additions and 86 deletions
+6 -6
View File
@@ -1,11 +1,11 @@
#!/usr/bin/env node
import{stdin as d}from"process";import m from"path";import{existsSync as C}from"fs";import{homedir as w}from"os";import{spawnSync as v}from"child_process";import{join as r,dirname as R,basename as G}from"path";import{homedir as O}from"os";import{fileURLToPath as U}from"url";function h(){return typeof __dirname<"u"?__dirname:R(U(import.meta.url))}var y=h(),a=process.env.CLAUDE_MEM_DATA_DIR||r(O(),".claude-mem"),S=process.env.CLAUDE_CONFIG_DIR||r(O(),".claude"),q=r(a,"archives"),z=r(a,"logs"),Q=r(a,"trash"),Z=r(a,"backups"),tt=r(a,"settings.json"),et=r(a,"claude-mem.db"),ot=r(a,"vector-db"),rt=r(S,"settings.json"),nt=r(S,"commands"),st=r(S,"CLAUDE.md");function g(){return r(y,"..","..")}import{readFileSync as P,existsSync as k}from"fs";var I=["bugfix","feature","refactor","discovery","decision","change"],x=["how-it-works","why-it-exists","what-changed","problem-solution","gotcha","pattern","trade-off"];var f=I.join(","),A=x.join(",");var u=class{static DEFAULTS={CLAUDE_MEM_MODEL:"claude-haiku-4-5",CLAUDE_MEM_CONTEXT_OBSERVATIONS:"50",CLAUDE_MEM_WORKER_PORT:"37777",CLAUDE_MEM_CONTEXT_SHOW_READ_TOKENS:"true",CLAUDE_MEM_CONTEXT_SHOW_WORK_TOKENS:"true",CLAUDE_MEM_CONTEXT_SHOW_SAVINGS_AMOUNT:"true",CLAUDE_MEM_CONTEXT_SHOW_SAVINGS_PERCENT:"true",CLAUDE_MEM_CONTEXT_OBSERVATION_TYPES:f,CLAUDE_MEM_CONTEXT_OBSERVATION_CONCEPTS:A,CLAUDE_MEM_CONTEXT_FULL_COUNT:"5",CLAUDE_MEM_CONTEXT_FULL_FIELD:"narrative",CLAUDE_MEM_CONTEXT_SESSION_COUNT:"10",CLAUDE_MEM_CONTEXT_SHOW_LAST_SUMMARY:"true",CLAUDE_MEM_CONTEXT_SHOW_LAST_MESSAGE:"false"};static getAllDefaults(){return{...this.DEFAULTS}}static get(t){return process.env[t]||this.DEFAULTS[t]}static getInt(t){let o=this.get(t);return parseInt(o,10)}static getBool(t){return this.get(t)==="true"}static loadFromFile(t){if(!k(t))return this.getAllDefaults();let o=P(t,"utf-8"),n=JSON.parse(o).env||{},s={...this.DEFAULTS};for(let c of Object.keys(this.DEFAULTS))n[c]!==void 0&&(s[c]=n[c]);return s}};var b=100,W=500,F=10;function T(){let e=m.join(w(),".claude-mem","settings.json"),t=u.loadFromFile(e);return parseInt(t.CLAUDE_MEM_WORKER_PORT,10)}async function D(){try{let e=T();return(await fetch(`http://127.0.0.1:${e}/health`,{signal:AbortSignal.timeout(b)})).ok}catch{return!1}}async function H(){try{let e=g(),t=m.join(e,"ecosystem.config.cjs");if(!C(t))throw new Error(`Ecosystem config not found at ${t}`);let o=m.join(e,"node_modules",".bin","pm2"),i=process.platform==="win32"?o+".cmd":o,n=C(i)?i:"pm2",s=v(n,["start",t],{cwd:e,stdio:"pipe",encoding:"utf-8",windowsHide:!0});if(s.status!==0)throw new Error(s.stderr||"PM2 start failed");for(let c=0;c<F;c++)if(await new Promise(_=>setTimeout(_,W)),await D())return!0;return!1}catch{return!1}}async function M(){if(await D())return;if(!await H()){let t=T(),o=g();throw new Error(`Worker service failed to start on port ${t}.
import{stdin as u}from"process";import T from"path";import{existsSync as f}from"fs";import{homedir as d}from"os";import{spawnSync as U}from"child_process";import{readFileSync as D,existsSync as h}from"fs";var N=["bugfix","feature","refactor","discovery","decision","change"],L=["how-it-works","why-it-exists","what-changed","problem-solution","gotcha","pattern","trade-off"];var p=N.join(","),g=L.join(",");var _=class{static DEFAULTS={CLAUDE_MEM_MODEL:"claude-haiku-4-5",CLAUDE_MEM_CONTEXT_OBSERVATIONS:"50",CLAUDE_MEM_WORKER_PORT:"37777",CLAUDE_MEM_CONTEXT_SHOW_READ_TOKENS:"true",CLAUDE_MEM_CONTEXT_SHOW_WORK_TOKENS:"true",CLAUDE_MEM_CONTEXT_SHOW_SAVINGS_AMOUNT:"true",CLAUDE_MEM_CONTEXT_SHOW_SAVINGS_PERCENT:"true",CLAUDE_MEM_CONTEXT_OBSERVATION_TYPES:p,CLAUDE_MEM_CONTEXT_OBSERVATION_CONCEPTS:g,CLAUDE_MEM_CONTEXT_FULL_COUNT:"5",CLAUDE_MEM_CONTEXT_FULL_FIELD:"narrative",CLAUDE_MEM_CONTEXT_SESSION_COUNT:"10",CLAUDE_MEM_CONTEXT_SHOW_LAST_SUMMARY:"true",CLAUDE_MEM_CONTEXT_SHOW_LAST_MESSAGE:"false"};static getAllDefaults(){return{...this.DEFAULTS}}static get(t){return process.env[t]||this.DEFAULTS[t]}static getInt(t){let n=this.get(t);return parseInt(n,10)}static getBool(t){return this.get(t)==="true"}static loadFromFile(t){if(!h(t))return this.getAllDefaults();let n=D(t,"utf-8"),o=JSON.parse(n).env||{},s={...this.DEFAULTS};for(let i of Object.keys(this.DEFAULTS))o[i]!==void 0&&(s[i]=o[i]);return s}};var E=T.join(d(),".claude","plugins","marketplaces","thedotmack"),y=100,R=500,I=10;function l(){let e=T.join(d(),".claude-mem","settings.json"),t=_.loadFromFile(e);return parseInt(t.CLAUDE_MEM_WORKER_PORT,10)}async function A(){try{let e=l();return(await fetch(`http://127.0.0.1:${e}/health`,{signal:AbortSignal.timeout(y)})).ok}catch{return!1}}async function P(){try{let e=T.join(E,"ecosystem.config.cjs");if(!f(e))throw new Error(`Ecosystem config not found at ${e}`);let t=T.join(E,"node_modules",".bin","pm2"),n=process.platform==="win32"?t+".cmd":t,r=f(n)?n:"pm2",o=U(r,["start",e],{cwd:E,stdio:"pipe",encoding:"utf-8",windowsHide:!0});if(o.status!==0)throw new Error(o.stderr||"PM2 start failed");for(let s=0;s<I;s++)if(await new Promise(i=>setTimeout(i,R)),await A())return!0;return!1}catch{return!1}}async function C(){if(await A())return;if(!await P()){let t=l();throw new Error(`Worker service failed to start on port ${t}.
To start manually, run:
cd ${o}
cd ${E}
npx pm2 start ecosystem.config.cjs
If already running, try: npx pm2 restart claude-mem-worker`)}}import{appendFileSync as X}from"fs";import{homedir as B}from"os";import{join as V}from"path";var $=V(B(),".claude-mem","silent.log");function E(e,t,o=""){let i=new Date().toISOString(),_=((new Error().stack||"").split(`
`)[2]||"").match(/at\s+(?:.*\s+)?\(?([^:]+):(\d+):(\d+)\)?/),L=_?`${_[1].split("/").pop()}:${_[2]}`:"unknown",p=`[${i}] [${L}] ${e}`;if(t!==void 0)try{p+=` ${JSON.stringify(t)}`}catch(l){p+=` [stringify error: ${l}]`}p+=`
`;try{X($,p)}catch(l){console.error("[silent-debug] Failed to write to log:",l)}return o}async function N(e){await M(),E("[cleanup-hook] Hook fired",{session_id:e?.session_id,cwd:e?.cwd,reason:e?.reason}),e||(console.log("No input provided - this script is designed to run as a Claude Code SessionEnd hook"),console.log(`
Expected input format:`),console.log(JSON.stringify({session_id:"string",cwd:"string",transcript_path:"string",hook_event_name:"SessionEnd",reason:"exit"},null,2)),process.exit(0));let{session_id:t,reason:o}=e,i=T();try{let n=await fetch(`http://127.0.0.1:${i}/api/sessions/complete`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({claudeSessionId:t,reason:o}),signal:AbortSignal.timeout(2e3)});if(n.ok){let s=await n.json();E("[cleanup-hook] Session cleanup completed",s)}else E("[cleanup-hook] Session not found or already cleaned up")}catch(n){E("[cleanup-hook] Worker not reachable (non-critical)",{error:n.message})}console.log('{"continue": true, "suppressOutput": true}'),process.exit(0)}if(d.isTTY)N(void 0);else{let e="";d.on("data",t=>e+=t),d.on("end",async()=>{let t=e?JSON.parse(e):void 0;await N(t)})}
If already running, try: npx pm2 restart claude-mem-worker`)}}import{appendFileSync as k}from"fs";import{homedir as w}from"os";import{join as x}from"path";var W=x(w(),".claude-mem","silent.log");function a(e,t,n=""){let r=new Date().toISOString(),S=((new Error().stack||"").split(`
`)[2]||"").match(/at\s+(?:.*\s+)?\(?([^:]+):(\d+):(\d+)\)?/),M=S?`${S[1].split("/").pop()}:${S[2]}`:"unknown",c=`[${r}] [${M}] ${e}`;if(t!==void 0)try{c+=` ${JSON.stringify(t)}`}catch(O){c+=` [stringify error: ${O}]`}c+=`
`;try{k(W,c)}catch(O){console.error("[silent-debug] Failed to write to log:",O)}return n}async function m(e){await C(),a("[cleanup-hook] Hook fired",{session_id:e?.session_id,cwd:e?.cwd,reason:e?.reason}),e||(console.log("No input provided - this script is designed to run as a Claude Code SessionEnd hook"),console.log(`
Expected input format:`),console.log(JSON.stringify({session_id:"string",cwd:"string",transcript_path:"string",hook_event_name:"SessionEnd",reason:"exit"},null,2)),process.exit(0));let{session_id:t,reason:n}=e,r=l();try{let o=await fetch(`http://127.0.0.1:${r}/api/sessions/complete`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({claudeSessionId:t,reason:n}),signal:AbortSignal.timeout(2e3)});if(o.ok){let s=await o.json();a("[cleanup-hook] Session cleanup completed",s)}else a("[cleanup-hook] Session not found or already cleaned up")}catch(o){a("[cleanup-hook] Worker not reachable (non-critical)",{error:o.message})}console.log('{"continue": true, "suppressOutput": true}'),process.exit(0)}if(u.isTTY)m(void 0);else{let e="";u.on("data",t=>e+=t),u.on("end",async()=>{let t=e?JSON.parse(e):void 0;await m(t)})}