@vpxa/aikit 0.1.208 → 0.1.210

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (55) hide show
  1. package/package.json +1 -1
  2. package/packages/cli/dist/index.js +13 -13
  3. package/packages/cli/dist/{init-BoKsQg2-.js → init-CYp6FjZO.js} +1 -1
  4. package/packages/cli/dist/{templates-D-McT4sX.js → templates-CeowBw5E.js} +1 -1
  5. package/packages/core/dist/index.d.ts +2 -0
  6. package/packages/server/dist/auth-Bz5dmZgR.js +1 -0
  7. package/packages/server/dist/bin.js +12 -6
  8. package/packages/server/dist/config-C4mVyqAF.js +2 -0
  9. package/packages/server/dist/config-jGZ91cRx.js +1 -0
  10. package/packages/server/dist/curated-manager-D1u5qOwK.js +7 -0
  11. package/packages/server/dist/evolution-9hXRopDC.js +3 -0
  12. package/packages/server/dist/evolution-DJhTM6nu.js +2 -0
  13. package/packages/server/dist/index.d.ts +28 -1
  14. package/packages/server/dist/index.js +1 -1
  15. package/packages/server/dist/lessons-B05P_TOl.js +3 -0
  16. package/packages/server/dist/lessons-D7sdHa2e.js +2 -0
  17. package/packages/server/dist/promotion-Bd_YB7E1.js +3 -0
  18. package/packages/server/dist/promotion-OY53YCsT.js +2 -0
  19. package/packages/server/dist/proxy.js +1 -1
  20. package/packages/server/dist/replay-interceptor-CGLyom5f.js +7 -0
  21. package/packages/server/dist/retention-B4ITAs7F.js +1 -0
  22. package/packages/server/dist/retention-C3tsarCT.js +2 -0
  23. package/packages/server/dist/rolldown-runtime-DT7IzrpZ.js +1 -0
  24. package/packages/server/dist/{server-BaMsrcyc.js → server-BA1mIjBc.js} +163 -139
  25. package/packages/server/dist/{server-BhQwVWsr.js → server-CtFr8YsZ.js} +162 -140
  26. package/packages/server/dist/supersession-9edUDEQ8.js +1 -0
  27. package/packages/server/dist/{version-check-BgHzxxCW.js → version-check-D_uN0n0Y.js} +1 -1
  28. package/packages/store/dist/index.js +30 -30
  29. package/packages/tools/dist/index.d.ts +9 -1
  30. package/packages/tools/dist/index.js +78 -79
  31. package/packages/tools/package.json +5 -5
  32. package/scaffold/dist/adapters/claude-code.mjs +10 -10
  33. package/scaffold/dist/adapters/copilot.mjs +17 -17
  34. package/scaffold/dist/adapters/hooks.mjs +1 -0
  35. package/scaffold/dist/definitions/bodies.mjs +20 -114
  36. package/scaffold/dist/definitions/exec-hooks.mjs +1 -0
  37. package/scaffold/dist/definitions/flows.mjs +81 -345
  38. package/scaffold/dist/definitions/protocols.mjs +21 -4
  39. package/scaffold/dist/definitions/skills/aikit.mjs +35 -55
  40. package/scaffold/dist/definitions/skills/lesson-learned.mjs +46 -0
  41. package/scaffold/general/hooks/scripts/_runtime.mjs +161 -0
  42. package/scaffold/general/hooks/scripts/post-edit-check.mjs +36 -0
  43. package/scaffold/general/hooks/scripts/pre-compact-save.mjs +13 -0
  44. package/scaffold/general/hooks/scripts/privacy-guard.mjs +39 -0
  45. package/scaffold/general/hooks/scripts/scout-guard.mjs +45 -0
  46. package/scaffold/general/hooks/scripts/session-init.mjs +85 -0
  47. package/scaffold/general/hooks/scripts/session-learn.mjs +53 -0
  48. package/scaffold/general/hooks/scripts/session-observer.mjs +77 -0
  49. package/scaffold/general/hooks/scripts/subagent-context.mjs +59 -0
  50. package/packages/server/dist/auth-BfqgawfR.js +0 -1
  51. package/packages/server/dist/config-DAnAxrUW.js +0 -1
  52. package/packages/server/dist/config-PfoXsIC3.js +0 -2
  53. package/packages/server/dist/curated-manager-BnP6VqvL.js +0 -7
  54. package/packages/server/dist/supersession-BIV-v6JG.js +0 -3
  55. package/packages/server/dist/supersession-DJQGXMWm.js +0 -2
@@ -1,8 +1,14 @@
1
1
  #!/usr/bin/env node
2
- import{createHash as e,randomUUID as t}from"node:crypto";import{readFileSync as n}from"node:fs";import{dirname as r,isAbsolute as i,join as a,resolve as o}from"node:path";import{fileURLToPath as s,pathToFileURL as c}from"node:url";import{parseArgs as l}from"node:util";import{createLogger as u,serializeError as d}from"../../core/dist/index.js";import{GIT_REF_SLUG_PATTERN as f,gitAvailable as p,gitCommitToRef as m,gitExec as h,slugForRef as g}from"../../tools/dist/index.js";import{mkdir as _,readFile as v,readdir as y,stat as b,unlink as x,writeFile as S}from"node:fs/promises";const C=`__pending__:`;function w(e){return e.startsWith(C)}function T(e){let t=e.headers[`mcp-session-id`];return Array.isArray(t)?t[0]:t}function E(e,t,n,r){e.status(t).json({jsonrpc:`2.0`,error:{code:n,message:r},id:null})}var D=class{options;runtimes=new Map;maxSessions;sessionTimeoutMs;now;constructor(e){this.options=e,this.maxSessions=e.maxSessions??8,this.sessionTimeoutMs=(e.sessionTimeoutMinutes??30)*60*1e3,this.now=e.now??(()=>Date.now())}hasSession(e){return this.runtimes.has(e)}getSessionCount(){return this.runtimes.size}async handleRequest(e,t,n=e.body){let r=T(e),i=r?this.runtimes.get(r):void 0;if(r&&!i){E(t,404,-32001,`Session not found`);return}if(!i){if(e.method!==`POST`){E(t,400,-32e3,`Session required`);return}if(i=await this.createRuntime(t),!i)return}await this.withRuntimeLock(i,async()=>{await i.transport.handleRequest(e,t,n),i.lastAccessAt=this.now();let r=i.transport.sessionId??i.id;e.method!==`DELETE`&&!w(r)&&this.options.onSessionActivity?.(r),e.method===`DELETE`&&!w(r)&&await this.closeSession(r,{closeTransport:!1})})}async closeExpiredSessions(){let e=[...this.runtimes.values()].filter(e=>this.now()-e.lastAccessAt>=this.sessionTimeoutMs).map(e=>e.id);for(let t of e)await this.closeSession(t);return e.length}async closeSession(e,t={}){let n=this.runtimes.get(e);return n?(this.runtimes.delete(e),t.notifySessionEnd!==!1&&!w(e)&&this.options.onSessionEnd?.(e),t.closeTransport!==!1&&await n.transport.close().catch(()=>void 0),await n.server.close().catch(()=>void 0),!0):!1}async closeAll(){let e=[...this.runtimes.keys()];for(let t of e)await this.closeSession(t)}async createRuntime(e){if(await this.closeExpiredSessions(),this.runtimes.size>=this.maxSessions){E(e,503,-32003,`Session capacity reached`);return}let n=this.now(),r=await this.options.createServer(),i={id:`${C}${t()}`,transport:void 0,createdAt:n,lastAccessAt:n,server:r,requestChain:Promise.resolve()},a=this.options.createTransport({sessionIdGenerator:()=>t(),onsessioninitialized:async e=>{this.runtimes.delete(i.id),i.id=e,this.runtimes.set(e,i),this.options.onSessionStart?.(e)},onsessionclosed:async e=>{e&&await this.closeSession(e,{closeTransport:!1})}});return i.transport=a,a.onclose=()=>{let e=i.transport.sessionId??i.id;this.closeSession(e,{closeTransport:!1})},this.runtimes.set(i.id,i),await r.connect(a),i}async withRuntimeLock(e,t){let n=e.requestChain,r;e.requestChain=new Promise(e=>{r=e}),await n;try{await t()}finally{r()}}};function O(e){let t=e.includes(`T`)?e:`${e.replace(` `,`T`)}Z`;return Date.parse(t)}var k=class{stateStore;options;gcTimer=null;constructor(e,t={}){this.stateStore=e,this.options=t}onSessionStart(e,t){this.stateStore.sessionCreate(e,t)}onSessionActivity(e){this.stateStore.sessionTouch(e)}onSessionEnd(e){this.stateStore.sessionDelete(e)}startGC(){if(this.gcTimer)return;let e=(this.options.gcIntervalMinutes??5)*60*1e3;this.gcTimer=setInterval(()=>{this.runGC()},e),this.gcTimer.unref()}runGC(){let e=this.getStaleSessionIds();for(let t of e)this.options.onBeforeSessionDelete?.(t),this.stateStore.sessionDelete(t);return e.length}stop(){this.gcTimer&&=(clearInterval(this.gcTimer),null)}getActiveSessions(){return this.stateStore.sessionList().length}listSessions(){return this.stateStore.sessionList()}getStaleSessionIds(e=Date.now()){let t=(this.options.staleTimeoutMinutes??30)*60*1e3;return this.stateStore.sessionList().filter(n=>{let r=O(n.lastActivity);return Number.isFinite(r)&&e-r>=t}).map(e=>e.sessionId)}},A=class{baseDir;constructor(e){this.baseDir=e}async initialize(){await _(this.baseDir,{recursive:!0})}async read(e){let t=a(this.baseDir,e);try{return await v(t,`utf-8`)}catch(e){if(e.code===`ENOENT`)return null;throw e}}async write(e,t,n){let i=a(this.baseDir,e);await _(r(i),{recursive:!0}),await S(i,t,{encoding:`utf-8`,flag:n?.exclusive?`wx`:`w`})}async delete(e){let t=a(this.baseDir,e);try{return await x(t),!0}catch(e){if(e.code===`ENOENT`)return!1;throw e}}async list(e){let t=[],n=e?[e]:await this.listDirectories();for(let e of n){let n=a(this.baseDir,e),r;try{r=await y(n)}catch{continue}for(let n of r){if(!n.endsWith(`.md`))continue;let r=`${e}/${n}`,i=a(this.baseDir,r);try{let e=await b(i);t.push({path:r,size:e.size})}catch{}}}return t}async exists(e){let t=a(this.baseDir,e);try{return await b(t),!0}catch{return!1}}async listDirectories(){try{return(await y(this.baseDir,{withFileTypes:!0})).filter(e=>e.isDirectory()&&/^[a-z][a-z0-9-]*$/.test(e.name)).map(e=>e.name)}catch{return[]}}async close(){}};const j=50*1024,M=`refs/aikit/knowledge`,N=u(`server`);var P=class{curatedDir;store;embedder;adapter;constructor(e,t,n,r=new A(e)){this.curatedDir=e,this.store=t,this.embedder=n,this.adapter=r}async remember(e,t,n,r=[]){this.validateCategoryName(n),this.validateContentSize(t);let i=this.slugify(e),a=await this.uniqueRelativePath(n,i),o=new Date().toISOString(),s={title:e,category:n,tags:r,created:o,updated:o,version:1,origin:`curated`,changelog:[{version:1,date:o,reason:`Initial creation`}]},c=this.serializeFile(t,s);try{await this.adapter.write(a,c,{exclusive:!0})}catch(e){throw e.code===`EEXIST`?Error(`Concurrent write collision for "${a}" — retry the operation`):e}try{await this.indexCuratedFile(a,t,s)}catch(e){throw await this.adapter.delete(a).catch(()=>{}),Error(`Remember failed: wrote file but indexing failed — rolled back. ${e.message}`)}return this.gitCommitKnowledge(a,c,`remember: ${e}\n\nCategory: ${n}\nTags: ${r.join(`, `)}`),{path:a}}async update(e,t,n){e=this.guardPath(e),this.validateContentSize(t);let r=await this.adapter.read(e);if(r==null)throw Error(`Curated entry not found: ${e}`);let{frontmatter:i}=this.parseFile(r),a=(i.version??1)+1,o=new Date().toISOString();i.version=a,i.updated=o,i.changelog=[...i.changelog??[],{version:a,date:o,reason:n}];let s=this.serializeFile(t,i);return await this.adapter.write(e,s),await this.indexCuratedFile(e,t,i),this.gitCommitKnowledge(e,s,`update(v${a}): ${i.title}\n\nReason: ${n}\nVersion: ${a}`),{path:e,version:a}}async forget(e,t){if(e=this.guardPath(e),!await this.adapter.delete(e))throw Error(`Curated entry not found: ${e}`);let n=`.ai/curated/${e}`;return await this.store.deleteBySourcePath(n).catch(e=>{N.warn(`File deleted but vector cleanup failed`,{sourcePath:n,...d(e)})}),this.gitDeleteKnowledgeRef(e),{path:e}}async history(e,t=20){if(e=this.guardPath(e),!p(this.curatedDir))return[];let n=this.knowledgeRefForPath(e);if(!n)return[];let r=h([`log`,`--format=%H|%aI|%s`,n,`-n`,String(t)],this.curatedDir);return r?r.split(`
3
- `).filter(Boolean).map(e=>{let[t,n,...r]=e.split(`|`);return{sha:t,date:n,message:r.join(`|`)}}):[]}async diff(e,t,n){if(e=this.guardPath(e),!p(this.curatedDir))return``;if(!n){let r=await this.history(e,2);if(r.length===0)return``;n=r[0].sha,r.length>1&&!t&&(t=r[1].sha)}return t&&n?h([`diff`,`${t}:entry.md`,`${n}:entry.md`],this.curatedDir)??``:n?h([`show`,`${n}:entry.md`],this.curatedDir)??``:``}async recover(e){if(e=this.guardPath(e),await this.adapter.exists(e))throw Error(`Entry already exists on filesystem: ${e}. Use update() instead.`);if(!p(this.curatedDir))return null;let t=this.knowledgeRefForPath(e);if(!t)return null;let n=h([`show`,`${t}:entry.md`],this.curatedDir);if(!n)return null;await this.adapter.write(e,n);let{frontmatter:r,content:i}=this.parseFile(n);return await this.indexCuratedFile(e,i,r),{path:e,version:r.version??1}}async listOrphaned(){if(!p(this.curatedDir))return[];let e=h([`for-each-ref`,`--format=%(refname)|%(subject)`,`${M}/`],this.curatedDir);if(!e)return[];let t=[];for(let n of e.split(`
4
- `).filter(Boolean)){let[e,...r]=n.split(`|`),i=r.join(`|`),a=`${e.replace(`${M}/`,``)}.md`;await this.adapter.exists(a)||t.push({ref:e,path:a,lastMessage:i})}return t}async read(e){e=this.guardPath(e);let t=await this.adapter.read(e);if(t==null)throw Error(`Curated entry not found: ${e}`);let{frontmatter:n,content:r}=this.parseFile(t),i=e.split(`/`)[0];return{path:e,title:n.title??e,category:i,tags:n.tags??[],version:n.version??1,created:n.created??``,updated:n.updated??``,contentPreview:r.slice(0,200),content:r}}async list(e){let t=[],n=e?.category?[e.category]:await this.discoverCategories();for(let r of n){let n=await this.adapter.list(r);for(let i of n){let n=await this.adapter.read(i.path);if(n==null)continue;let{frontmatter:a,content:o}=this.parseFile(n);e?.tag&&!(a.tags??[]).includes(e.tag)||t.push({path:i.path,title:a.title??i.path,category:r,tags:a.tags??[],version:a.version??1,created:a.created??``,updated:a.updated??``,contentPreview:o.slice(0,200)})}}return t}async reindexAll(){let e=await this.discoverCategories(),t=[],n=[];for(let r of e){let e=await this.adapter.list(r);for(let r of e){let e=r.path;try{let r=await this.adapter.read(e);if(r==null){t.push(`${e}: read failed`);continue}let{frontmatter:i,content:a}=this.parseFile(r);n.push({relativePath:e,content:a,frontmatter:i})}catch(n){N.error(`Failed to read curated file`,{relativePath:e,...d(n)}),t.push(`${e}: read failed`)}}}if(n.length===0)return{indexed:0,errors:t};let r=await this.embedder.embedBatch(n.map(e=>e.content)),i=new Date().toISOString(),a=n.map(e=>{let t=`.ai/curated/${e.relativePath}`;return{id:this.hashId(t,0),content:e.content,sourcePath:t,contentType:`curated-knowledge`,headingPath:e.frontmatter.title,chunkIndex:0,totalChunks:1,startLine:1,endLine:e.content.split(`
5
- `).length,fileHash:this.hash(e.content),indexedAt:i,origin:`curated`,tags:e.frontmatter.tags,category:e.frontmatter.category,version:e.frontmatter.version}});return await this.store.upsert(a,r),{indexed:n.length,errors:t}}gitCommitKnowledge(e,t,n){try{if(!p(this.curatedDir))return;let r=this.knowledgeRefForPath(e);if(!r)return;m(r,`entry.md`,t,n,this.curatedDir)}catch{}}gitDeleteKnowledgeRef(e){try{if(!p(this.curatedDir))return;let t=this.knowledgeRefForPath(e);if(!t)return;h([`update-ref`,`-d`,t],this.curatedDir)}catch{}}knowledgeRefForPath(e){let t=e.replace(/\.md$/,``).split(`/`).map(e=>g(e)).join(`/`);return t.split(`/`).every(e=>f.test(e))?`${M}/${t}`:null}async indexCuratedFile(e,t,n){let r=await this.embedder.embed(t),i=`.ai/curated/${e}`,a=new Date().toISOString(),o={id:this.hashId(i,0),content:t,sourcePath:i,contentType:`curated-knowledge`,headingPath:n.title,chunkIndex:0,totalChunks:1,startLine:1,endLine:t.split(`
6
- `).length,fileHash:this.hash(t),indexedAt:a,origin:`curated`,tags:n.tags,category:n.category,version:n.version};await this.store.upsert([o],[r])}async discoverCategories(){return this.adapter.listDirectories()}guardPath(e){let t=e.replace(/^\.ai\/curated\//,``);if(t.endsWith(`.md`)||(t+=`.md`),t.includes(`..`)||i(t))throw Error(`Invalid path: ${t}. Must be relative within .ai/curated/ directory.`);let n=t.split(`/`)[0];return this.validateCategoryName(n),t}validateCategoryName(e){if(!/^[a-z][a-z0-9-]*$/.test(e))throw Error(`Invalid category name: "${e}". Must be lowercase kebab-case (e.g., "decisions", "api-contracts").`)}validateContentSize(e){if(Buffer.byteLength(e,`utf-8`)>j)throw Error(`Content exceeds maximum size of ${j/1024}KB`)}slugify(e){return e.toLowerCase().replace(/[^a-z0-9]+/g,`-`).replace(/^-|-$/g,``).slice(0,80)}async uniqueRelativePath(e,t){let n=`${e}/${t}.md`;if(!await this.adapter.exists(n))return n;for(let n=2;n<=100;n++){let r=`${e}/${t}-${n}.md`;if(!await this.adapter.exists(r))return r}throw Error(`Too many entries with slug "${t}" in category "${e}"`)}hash(t){return e(`sha256`).update(t).digest(`hex`).slice(0,16)}hashId(e,t){return this.hash(`${e}::${t}`)}serializeFile(e,t){return`${[`---`,`title: "${t.title.replace(/"/g,`\\"`)}"`,`category: ${t.category}`,`tags: [${t.tags.map(e=>`"${e}"`).join(`, `)}]`,`created: ${t.created}`,`updated: ${t.updated}`,`version: ${t.version}`,`origin: ${t.origin}`,`changelog:`,...t.changelog.map(e=>` - version: ${e.version}\n date: ${e.date}\n reason: "${e.reason.replace(/"/g,`\\"`)}"`),`---`].join(`
2
+ import"node:module";import{createHash as e,randomUUID as t}from"node:crypto";import{readFileSync as n}from"node:fs";import{dirname as r,isAbsolute as i,join as a,resolve as o}from"node:path";import{fileURLToPath as s,pathToFileURL as c}from"node:url";import{parseArgs as l}from"node:util";import{createLogger as u,serializeError as d}from"../../core/dist/index.js";import{mkdir as f,readFile as p,readdir as m,stat as h,unlink as g,writeFile as _}from"node:fs/promises";import{tmpdir as v}from"node:os";import{GIT_REF_SLUG_PATTERN as y,gitAvailable as b,gitCommitToRef as x,gitExec as S,replayAppend as C,slugForRef as w}from"../../tools/dist/index.js";var T=Object.defineProperty,E=(e,t)=>{let n={};for(var r in e)T(n,r,{get:e[r],enumerable:!0});return t||T(n,Symbol.toStringTag,{value:`Module`}),n};const D=`__pending__:`;function O(e){return e.startsWith(D)}function k(e){let t=e.headers[`mcp-session-id`];return Array.isArray(t)?t[0]:t}function A(e,t,n,r){e.status(t).json({jsonrpc:`2.0`,error:{code:n,message:r},id:null})}var ee=class{options;runtimes=new Map;maxSessions;sessionTimeoutMs;now;constructor(e){this.options=e,this.maxSessions=e.maxSessions??8,this.sessionTimeoutMs=(e.sessionTimeoutMinutes??30)*60*1e3,this.now=e.now??(()=>Date.now())}hasSession(e){return this.runtimes.has(e)}getSessionCount(){return this.runtimes.size}async handleRequest(e,t,n=e.body){let r=k(e),i=r?this.runtimes.get(r):void 0;if(r&&!i){A(t,404,-32001,`Session not found`);return}if(!i){if(e.method!==`POST`){A(t,400,-32e3,`Session required`);return}if(i=await this.createRuntime(t),!i)return}await this.withRuntimeLock(i,async()=>{await i.transport.handleRequest(e,t,n),i.lastAccessAt=this.now();let r=i.transport.sessionId??i.id;e.method!==`DELETE`&&!O(r)&&this.options.onSessionActivity?.(r),e.method===`DELETE`&&!O(r)&&await this.closeSession(r,{closeTransport:!1})})}async closeExpiredSessions(){let e=[...this.runtimes.values()].filter(e=>this.now()-e.lastAccessAt>=this.sessionTimeoutMs).map(e=>e.id);for(let t of e)await this.closeSession(t);return e.length}async closeSession(e,t={}){let n=this.runtimes.get(e);return n?(this.runtimes.delete(e),t.notifySessionEnd!==!1&&!O(e)&&this.options.onSessionEnd?.(e),t.closeTransport!==!1&&await n.transport.close().catch(()=>void 0),await n.server.close().catch(()=>void 0),!0):!1}async closeAll(){let e=[...this.runtimes.keys()];for(let t of e)await this.closeSession(t)}async createRuntime(e){if(await this.closeExpiredSessions(),this.runtimes.size>=this.maxSessions){A(e,503,-32003,`Session capacity reached`);return}let n=this.now(),r=await this.options.createServer(),i={id:`${D}${t()}`,transport:void 0,createdAt:n,lastAccessAt:n,server:r,requestChain:Promise.resolve()},a=this.options.createTransport({sessionIdGenerator:()=>t(),onsessioninitialized:async e=>{this.runtimes.delete(i.id),i.id=e,this.runtimes.set(e,i),this.options.onSessionStart?.(e)},onsessionclosed:async e=>{e&&await this.closeSession(e,{closeTransport:!1})}});return i.transport=a,a.onclose=()=>{let e=i.transport.sessionId??i.id;this.closeSession(e,{closeTransport:!1})},this.runtimes.set(i.id,i),await r.connect(a),i}async withRuntimeLock(e,t){let n=e.requestChain,r;e.requestChain=new Promise(e=>{r=e}),await n;try{await t()}finally{r()}}};const j=u(`auto-gc`);let M=`warming`,N=null,P=0;function F(){let e=[...Oe()];if(e.length<10)return 0;e.sort((e,t)=>e-t);let t=Math.floor(e.length*.95);return e[Math.min(t,e.length-1)]}function te(e){let t=F();if(t===0){M=`warming`;return}if(t>500){M=`degraded`;let n=Date.now();if(N&&n-N<36e5){j.debug(`GC cooldown active — skipping`,{lastGcAgoMs:n-N});return}N=n,P++,j.warn(`p95 latency exceeds threshold, triggering GC`,{p95:t,cycle:P}),e&&e().catch(e=>j.error(`GC callback failed`,{err:String(e)}))}else t<200&&(M=`healthy`)}function I(){return{state:M,p95:F(),lastGcAt:N,gcCount:P,bufferSize:Oe().length}}var ne=E({DEFAULT_SUPERSESSION_CONFIG:()=>L,findSupersessionCandidates:()=>re,jaccardSimilarity:()=>B,performSupersession:()=>ie,resolveSupersessionConfig:()=>R,tokenize:()=>z});const L={threshold:.7,maxCompare:50,autoThreshold:.95};function R(e){let t=Math.min(1,Math.max(0,e?.threshold??L.threshold)),n=Math.min(1,Math.max(t,e?.autoThreshold??L.autoThreshold));return{threshold:t,maxCompare:Math.max(1,Math.trunc(e?.maxCompare??L.maxCompare)),autoThreshold:n}}function z(e){let t=e.toLowerCase().match(/[a-z0-9]{2,}/g)??[];return new Set(t)}function B(e,t){let n=z(e),r=z(t);if(n.size===0&&r.size===0)return 1;if(n.size===0||r.size===0)return 0;let i=new Set([...n].filter(e=>r.has(e))),a=new Set([...n,...r]);return i.size/a.size}function re(e,t,n=L){let r=R(n);return t.slice(0,r.maxCompare).map(t=>({entryId:t.id,title:t.title,similarity:B(e,t.content),path:t.path})).filter(e=>e.similarity>=r.threshold).sort((e,t)=>t.similarity-e.similarity)}function ie(e,t,n){e.memoryMetaCreate(t),e.memoryMetaSetSuperseded(t,n)}const V={enabled:!0,batchThreshold:20,cooldownMs:3e5,maxCandidatesPerSession:5,initialConfidence:40,excludeTools:[`knowledge`,`replay`,`stash`,`checkpoint`,`session_digest`,`reindex`,`status`,`flow`,`evidence_map`,`present`]},ae=new Set([`search`,`find`,`symbol`,`grep_search`,`semantic_search`]),oe=new Set([`replace_string_in_file`,`editfiles`,`create_file`,`apply_patch`]),se=new Set([`check`,`test_run`]),ce=new Set(`action.and.args.auto.buffer.category.content.create.cwd.false.file.files.find.grep.json.knowledge.list.path.query.read.replace.search.semantic.subaction.symbol.test.tool.true.update`.split(`.`));function H(e){return e.replace(/^mcp_[^_]+_/,``).toLowerCase()}function le(e){return[...new Set(e.filter(e=>e.length>0))]}function U(e,t){return{...t,confidence:V.initialConfidence,tags:[`auto-observed`,`detector:${e}`],detector:e}}function ue(e,t){let n=new Map;for(let t of e)for(let e of z(t))ce.has(e)||n.set(e,(n.get(e)??0)+1);let r=[...n.entries()].filter(([,e])=>e>=t).sort((e,t)=>t[1]-e[1]||e[0].localeCompare(t[0])).map(([e])=>e);return r.length>0?r.slice(0,4):[...n.entries()].sort((e,t)=>t[1]-e[1]||e[0].localeCompare(t[0])).slice(0,4).map(([e])=>e)}function de(e){return e.length>0?e.join(`, `):`similar tasks`}function fe(e){if(typeof e!=`object`||!e)return!1;let t=e;return typeof t.ts==`number`&&Number.isFinite(t.ts)&&typeof t.tool==`string`&&typeof t.input==`string`&&Array.isArray(t.files)&&t.files.every(e=>typeof e==`string`)}function pe(e){let t=[];for(let n of e)t.some(e=>B(e.title,n.title)>.8)||t.push(n);return t}function me(e){let t=new Map;for(let n of e){let e=H(n.tool),r=t.get(e)??[];r.push(n),t.set(e,r)}return[...t.entries()].filter(([,e])=>e.length>=5).map(([e,t])=>{let n=de(ue(t.map(e=>e.input),Math.max(2,Math.ceil(t.length/2))));return U(`tool-preference`,{title:`Preferred tool: ${e} for ${n}`,context:`Observed ${t.length} ${e} calls with recurring inputs around ${n}.`,insight:`Use ${e} when working with ${n}.`,evidence:t.slice(0,5).map(e=>`${e.tool}: ${e.input}`).join(`
3
+ `)})})}function he(e){let t=new Map;for(let n=0;n<e.length;n+=1){let r=e[n];if(ae.has(H(r.tool)))for(let i=n+1;i<e.length&&i<=n+5;i+=1){let n=e[i];if(!(!oe.has(H(n.tool))||n.files.length===0))for(let e of le(n.files)){let i=t.get(e)??{count:0,queries:[],evidence:[]};i.count+=1,i.queries.push(r.input),i.evidence.push(`${r.tool}: ${r.input} -> ${n.tool}: ${e}`),t.set(e,i)}}}return[...t.entries()].filter(([,e])=>e.count>=3).map(([e,t])=>{let n=de(ue(t.queries,Math.max(2,Math.ceil(t.count/2))));return U(`search-action`,{title:`Check ${e} when searching for ${n}`,context:`Searches related to ${n} were followed by edits to ${e} ${t.count} times within five tool calls.`,insight:`When working on ${n}, check ${e} early because searches repeatedly led there.`,evidence:t.evidence.slice(0,5).join(`
4
+ `)})})}function ge(e){let t=new Map;for(let n=0;n<e.length-2;n+=1){let r=e[n];if(!se.has(H(r.tool)))continue;let i=new Set,a=!1;for(let o=n+1;o<e.length;o+=1){let n=e[o],s=H(n.tool);if(oe.has(s)){a=!0;for(let e of n.files)i.add(e);continue}if(se.has(s)){if(!a||i.size===0)break;let e=[...i].sort(),o=e.join(`|`),s=t.get(o)??{count:0,evidence:[]};s.count+=1,s.evidence.push(`${r.tool} -> edit(${e.join(`, `)}) -> ${n.tool}`),t.set(o,s);break}if(!a)break}}return[...t.entries()].filter(([,e])=>e.count>=2).map(([e,t])=>{let n=e.split(`|`);return U(`error-fix-cycle`,{title:`Repeated validation-edit loop in ${n.length===1?n[0]:`${n[0]} and related files`}`,context:`Observed ${t.count} validation cycles touching ${n.join(`, `)}.`,insight:`Common fix pattern in ${n.join(`, `)}: check -> edit -> recheck.`,evidence:t.evidence.slice(0,5).join(`
5
+ `)})})}function _e(e,t=V){if(!t.enabled||e.length===0)return[];let n=new Set(t.excludeTools.map(e=>e.toLowerCase())),r=e.filter(e=>!n.has(H(e.tool)));return pe([...me(r),...he(r),...ge(r)].map(e=>({...e,confidence:t.initialConfidence,tags:le([`auto-observed`,`detector:${e.detector}`,...e.tags])}))).slice(0,t.maxCandidatesPerSession)}function ve(e){return e.split(`
6
+ `).filter(Boolean).map(e=>{try{return JSON.parse(e)}catch{return null}}).filter(fe)}const ye=u(`replay-interceptor`),be=/key|token|secret|auth|password|bearer/i,xe=new Set([`eval`,`env`]);function W(e){if(typeof e==`string`)return/^(Bearer |sk-|ghp_|glpat-|ghu_|ghs_|github_pat_)/i.test(e)?`[REDACTED]`:e;if(Array.isArray(e))return e.map(W);if(e&&typeof e==`object`){let t={};for(let[n,r]of Object.entries(e))/(?:token|secret|password|passphrase|key|auth|credential|api.?key)/i.test(n)?t[n]=`[REDACTED]`:t[n]=W(r);return t}return e}function G(e,t){if(xe.has(e))return JSON.stringify({_redacted:!0,tool:e});let n=W(t);if(e===`http`&&n.headers&&typeof n.headers==`object`){let e={};for(let[t,r]of Object.entries(n.headers))e[t]=be.test(t)?`[REDACTED]`:r;return n.headers=e,JSON.stringify(n).slice(0,2e3)}return JSON.stringify(n).slice(0,2e3)}const K=new Map,q=[],J=[];let Se=0,Y;function Ce(e,t){return G(e,t).slice(0,500)}function we(e){let t=new Set,n=[e];for(;n.length>0&&t.size<20;){let e=n.pop();if(e!=null){if(Array.isArray(e)){for(let t of e)n.push(t);continue}if(typeof e==`object`)for(let[r,i]of Object.entries(e)){if(Array.isArray(i)){if(/^(?:files|paths)$/i.test(r))for(let e of i)typeof e==`string`&&e.length>0&&t.add(e);else n.push(i);continue}if(typeof i==`string`&&/^(?:file|filepath|path)$/i.test(r)&&i.length>0){t.add(i);continue}i&&typeof i==`object`&&n.push(i)}}}return[...t]}function Te(e,t,n){if(Se+=1,J.push(JSON.stringify({tool:e,input:Ce(e,t),output:n.slice(0,500),files:we(t),ts:Date.now()})),J.length>100&&J.shift(),Se%50!=0)return;let r=J.join(`
7
+ `);J.length=0,!(!Y||r.trim().split(`
8
+ `).filter(Boolean).length<20)&&Promise.resolve().then(async()=>{let e=_e(ve(r),V);if(e.length!==0){try{let t=a(v(),`aikit-auto-observe-${process.pid}-${Date.now()}.json`);await _(t,JSON.stringify(e,null,2),`utf8`),ye.info(`Auto-observe candidates detected`,{count:e.length,filePath:t})}catch(e){ye.warn(`Failed to persist auto-observe candidates`,{error:String(e)})}Y?.(e)}}).catch(()=>{})}function Ee(e,t,n,r,i){let a=K.get(e);a||(a={callCount:0,totalDurationMs:0,totalInputChars:0,totalOutputChars:0,errorCount:0},K.set(e,a)),a.callCount++,a.totalDurationMs+=t,a.totalInputChars+=n,a.totalOutputChars+=r,i&&a.errorCount++,q.push(t),q.length>100&&q.shift(),q.length>=10&&q.length%20==0&&te()}function De(){return Array.from(K.entries()).map(([e,t])=>({tool:e,...t}))}function Oe(){return q}function ke(e){Y=e}function Ae(){return async(e,t)=>{let n=Date.now(),r=JSON.stringify(e.args??{}).length;try{let i=await t(),a=Date.now()-n,o=JSON.stringify(i);return C({ts:new Date().toISOString(),source:`mcp`,tool:e.toolName,input:G(e.toolName,e.args),durationMs:a,status:`ok`,output:o,traceId:e.requestId,outputChars:o.length}),Te(e.toolName,e.args,o),Ee(e.toolName,a,r,o.length,!1),i}catch(t){let i=Date.now()-n,a=t instanceof Error?t.message:String(t);throw C({ts:new Date().toISOString(),source:`mcp`,tool:e.toolName,input:G(e.toolName,e.args),durationMs:i,status:`error`,output:a,traceId:e.requestId,outputChars:0}),Te(e.toolName,e.args,a),Ee(e.toolName,i,r,0,!0),t}}}function je(e){let t=e.includes(`T`)?e:`${e.replace(` `,`T`)}Z`;return Date.parse(t)}var Me=class{stateStore;options;gcTimer=null;constructor(e,t={}){this.stateStore=e,this.options=t}onSessionStart(e,t){this.stateStore.sessionCreate(e,t)}onSessionActivity(e){this.stateStore.sessionTouch(e)}onSessionEnd(e){this.stateStore.sessionDelete(e),Promise.resolve(this.options.onSessionEndMaintenance?.(e)).catch(()=>{})}startGC(){if(this.gcTimer)return;let e=(this.options.gcIntervalMinutes??5)*60*1e3;this.gcTimer=setInterval(()=>{this.runGC()},e),this.gcTimer.unref()}runGC(){let e=this.getStaleSessionIds();for(let t of e)this.options.onBeforeSessionDelete?.(t),Promise.resolve(this.options.onSessionEndMaintenance?.(t)).catch(()=>{}),this.stateStore.sessionDelete(t);return e.length}stop(){this.gcTimer&&=(clearInterval(this.gcTimer),null)}getActiveSessions(){return this.stateStore.sessionList().length}listSessions(){return this.stateStore.sessionList()}getStaleSessionIds(e=Date.now()){let t=(this.options.staleTimeoutMinutes??30)*60*1e3;return this.stateStore.sessionList().filter(n=>{let r=je(n.lastActivity);return Number.isFinite(r)&&e-r>=t}).map(e=>e.sessionId)}},Ne=class{baseDir;constructor(e){this.baseDir=e}async initialize(){await f(this.baseDir,{recursive:!0})}async read(e){let t=a(this.baseDir,e);try{return await p(t,`utf-8`)}catch(e){if(e.code===`ENOENT`)return null;throw e}}async write(e,t,n){let i=a(this.baseDir,e);await f(r(i),{recursive:!0}),await _(i,t,{encoding:`utf-8`,flag:n?.exclusive?`wx`:`w`})}async delete(e){let t=a(this.baseDir,e);try{return await g(t),!0}catch(e){if(e.code===`ENOENT`)return!1;throw e}}async list(e){let t=[],n=e?[e]:await this.listDirectories();for(let e of n){let n=a(this.baseDir,e),r;try{r=await m(n)}catch{continue}for(let n of r){if(!n.endsWith(`.md`))continue;let r=`${e}/${n}`,i=a(this.baseDir,r);try{let e=await h(i);t.push({path:r,size:e.size})}catch{}}}return t}async exists(e){let t=a(this.baseDir,e);try{return await h(t),!0}catch{return!1}}async listDirectories(){try{return(await m(this.baseDir,{withFileTypes:!0})).filter(e=>e.isDirectory()&&/^[a-z][a-z0-9-]*$/.test(e.name)).map(e=>e.name)}catch{return[]}}async close(){}},Pe=E({CuratedKnowledgeManager:()=>Le});const Fe=50*1024,X=`refs/aikit/knowledge`,Ie=u(`server`);var Le=class{curatedDir;store;embedder;adapter;constructor(e,t,n,r=new Ne(e)){this.curatedDir=e,this.store=t,this.embedder=n,this.adapter=r}async remember(e,t,n,r=[]){this.validateCategoryName(n),this.validateContentSize(t);let i=this.slugify(e),a=await this.uniqueRelativePath(n,i),o=new Date().toISOString(),s={title:e,category:n,tags:r,created:o,updated:o,version:1,origin:`curated`,changelog:[{version:1,date:o,reason:`Initial creation`}]},c=this.serializeFile(t,s);try{await this.adapter.write(a,c,{exclusive:!0})}catch(e){throw e.code===`EEXIST`?Error(`Concurrent write collision for "${a}" — retry the operation`):e}try{await this.indexCuratedFile(a,t,s)}catch(e){throw await this.adapter.delete(a).catch(()=>{}),Error(`Remember failed: wrote file but indexing failed — rolled back. ${e.message}`)}return this.gitCommitKnowledge(a,c,`remember: ${e}\n\nCategory: ${n}\nTags: ${r.join(`, `)}`),{path:a}}async update(e,t,n){e=this.guardPath(e),this.validateContentSize(t);let r=await this.adapter.read(e);if(r==null)throw Error(`Curated entry not found: ${e}`);let{frontmatter:i}=this.parseFile(r),a=(i.version??1)+1,o=new Date().toISOString();i.version=a,i.updated=o,i.changelog=[...i.changelog??[],{version:a,date:o,reason:n}];let s=this.serializeFile(t,i);return await this.adapter.write(e,s),await this.indexCuratedFile(e,t,i),this.gitCommitKnowledge(e,s,`update(v${a}): ${i.title}\n\nReason: ${n}\nVersion: ${a}`),{path:e,version:a}}async forget(e,t){if(e=this.guardPath(e),!await this.adapter.delete(e))throw Error(`Curated entry not found: ${e}`);let n=`.ai/curated/${e}`;return await this.store.deleteBySourcePath(n).catch(e=>{Ie.warn(`File deleted but vector cleanup failed`,{sourcePath:n,...d(e)})}),this.gitDeleteKnowledgeRef(e),{path:e}}async history(e,t=20){if(e=this.guardPath(e),!b(this.curatedDir))return[];let n=this.knowledgeRefForPath(e);if(!n)return[];let r=S([`log`,`--format=%H|%aI|%s`,n,`-n`,String(t)],this.curatedDir);return r?r.split(`
9
+ `).filter(Boolean).map(e=>{let[t,n,...r]=e.split(`|`);return{sha:t,date:n,message:r.join(`|`)}}):[]}async diff(e,t,n){if(e=this.guardPath(e),!b(this.curatedDir))return``;if(!n){let r=await this.history(e,2);if(r.length===0)return``;n=r[0].sha,r.length>1&&!t&&(t=r[1].sha)}return t&&n?S([`diff`,`${t}:entry.md`,`${n}:entry.md`],this.curatedDir)??``:n?S([`show`,`${n}:entry.md`],this.curatedDir)??``:``}async recover(e){if(e=this.guardPath(e),await this.adapter.exists(e))throw Error(`Entry already exists on filesystem: ${e}. Use update() instead.`);if(!b(this.curatedDir))return null;let t=this.knowledgeRefForPath(e);if(!t)return null;let n=S([`show`,`${t}:entry.md`],this.curatedDir);if(!n)return null;await this.adapter.write(e,n);let{frontmatter:r,content:i}=this.parseFile(n);return await this.indexCuratedFile(e,i,r),{path:e,version:r.version??1}}async listOrphaned(){if(!b(this.curatedDir))return[];let e=S([`for-each-ref`,`--format=%(refname)|%(subject)`,`${X}/`],this.curatedDir);if(!e)return[];let t=[];for(let n of e.split(`
10
+ `).filter(Boolean)){let[e,...r]=n.split(`|`),i=r.join(`|`),a=`${e.replace(`${X}/`,``)}.md`;await this.adapter.exists(a)||t.push({ref:e,path:a,lastMessage:i})}return t}async read(e){e=this.guardPath(e);let t=await this.adapter.read(e);if(t==null)throw Error(`Curated entry not found: ${e}`);let{frontmatter:n,content:r}=this.parseFile(t),i=e.split(`/`)[0];return{path:e,title:n.title??e,category:i,tags:n.tags??[],version:n.version??1,created:n.created??``,updated:n.updated??``,contentPreview:r.slice(0,200),content:r}}async list(e){let t=[],n=e?.category?[e.category]:await this.discoverCategories();for(let r of n){let n=await this.adapter.list(r);for(let i of n){let n=await this.adapter.read(i.path);if(n==null)continue;let{frontmatter:a,content:o}=this.parseFile(n);e?.tag&&!(a.tags??[]).includes(e.tag)||t.push({path:i.path,title:a.title??i.path,category:r,tags:a.tags??[],version:a.version??1,created:a.created??``,updated:a.updated??``,contentPreview:o.slice(0,200)})}}return t}async reindexAll(){let e=await this.discoverCategories(),t=[],n=[];for(let r of e){let e=await this.adapter.list(r);for(let r of e){let e=r.path;try{let r=await this.adapter.read(e);if(r==null){t.push(`${e}: read failed`);continue}let{frontmatter:i,content:a}=this.parseFile(r);n.push({relativePath:e,content:a,frontmatter:i})}catch(n){Ie.error(`Failed to read curated file`,{relativePath:e,...d(n)}),t.push(`${e}: read failed`)}}}if(n.length===0)return{indexed:0,errors:t};let r=await this.embedder.embedBatch(n.map(e=>e.content)),i=new Date().toISOString(),a=n.map(e=>{let t=`.ai/curated/${e.relativePath}`;return{id:this.hashId(t,0),content:e.content,sourcePath:t,contentType:`curated-knowledge`,headingPath:e.frontmatter.title,chunkIndex:0,totalChunks:1,startLine:1,endLine:e.content.split(`
11
+ `).length,fileHash:this.hash(e.content),indexedAt:i,origin:`curated`,tags:e.frontmatter.tags,category:e.frontmatter.category,version:e.frontmatter.version}});return await this.store.upsert(a,r),{indexed:n.length,errors:t}}gitCommitKnowledge(e,t,n){try{if(!b(this.curatedDir))return;let r=this.knowledgeRefForPath(e);if(!r)return;x(r,`entry.md`,t,n,this.curatedDir)}catch{}}gitDeleteKnowledgeRef(e){try{if(!b(this.curatedDir))return;let t=this.knowledgeRefForPath(e);if(!t)return;S([`update-ref`,`-d`,t],this.curatedDir)}catch{}}knowledgeRefForPath(e){let t=e.replace(/\.md$/,``).split(`/`).map(e=>w(e)).join(`/`);return t.split(`/`).every(e=>y.test(e))?`${X}/${t}`:null}async indexCuratedFile(e,t,n){let r=await this.embedder.embed(t),i=`.ai/curated/${e}`,a=new Date().toISOString(),o={id:this.hashId(i,0),content:t,sourcePath:i,contentType:`curated-knowledge`,headingPath:n.title,chunkIndex:0,totalChunks:1,startLine:1,endLine:t.split(`
12
+ `).length,fileHash:this.hash(t),indexedAt:a,origin:`curated`,tags:n.tags,category:n.category,version:n.version};await this.store.upsert([o],[r])}async discoverCategories(){return this.adapter.listDirectories()}guardPath(e){let t=e.replace(/^\.ai\/curated\//,``);if(t.endsWith(`.md`)||(t+=`.md`),t.includes(`..`)||i(t))throw Error(`Invalid path: ${t}. Must be relative within .ai/curated/ directory.`);let n=t.split(`/`)[0];return this.validateCategoryName(n),t}validateCategoryName(e){if(!/^[a-z][a-z0-9-]*$/.test(e))throw Error(`Invalid category name: "${e}". Must be lowercase kebab-case (e.g., "decisions", "api-contracts").`)}validateContentSize(e){if(Buffer.byteLength(e,`utf-8`)>Fe)throw Error(`Content exceeds maximum size of ${Fe/1024}KB`)}slugify(e){return e.toLowerCase().replace(/[^a-z0-9]+/g,`-`).replace(/^-|-$/g,``).slice(0,80)}async uniqueRelativePath(e,t){let n=`${e}/${t}.md`;if(!await this.adapter.exists(n))return n;for(let n=2;n<=100;n++){let r=`${e}/${t}-${n}.md`;if(!await this.adapter.exists(r))return r}throw Error(`Too many entries with slug "${t}" in category "${e}"`)}hash(t){return e(`sha256`).update(t).digest(`hex`).slice(0,16)}hashId(e,t){return this.hash(`${e}::${t}`)}serializeFile(e,t){return`${[`---`,`title: "${t.title.replace(/"/g,`\\"`)}"`,`category: ${t.category}`,`tags: [${t.tags.map(e=>`"${e}"`).join(`, `)}]`,`created: ${t.created}`,`updated: ${t.updated}`,`version: ${t.version}`,`origin: ${t.origin}`,`changelog:`,...t.changelog.map(e=>` - version: ${e.version}\n date: ${e.date}\n reason: "${e.reason.replace(/"/g,`\\"`)}"`),`---`].join(`
7
13
  `)}\n\n${e}\n`}parseFile(e){let t=e.match(/^---\n([\s\S]*?)\n---\n\n?([\s\S]*)$/);if(!t)return{frontmatter:{title:`Untitled`,category:`notes`,tags:[],created:``,updated:``,version:1,origin:`curated`,changelog:[]},content:e};let n=t[1],r=t[2].trim(),i={},a=[],o=n.split(`
8
- `),s=!1,c={};for(let e of o){if(/^changelog:\s*$/.test(e)){s=!0;continue}if(s){let t=e.match(/^\s+-\s+version:\s*(\d+)$/);if(t){c.version!=null&&a.push(c),c={version:parseInt(t[1],10)};continue}let n=e.match(/^\s+date:\s*(.+)$/);if(n){c.date=n[1].trim();continue}let r=e.match(/^\s+reason:\s*"?(.*?)"?\s*$/);if(r){c.reason=r[1];continue}/^\w/.test(e)&&(s=!1,c.version!=null&&a.push(c),c={});continue}let t=e.match(/^(\w+):\s*(.*)$/);if(t){let e=t[1],n=t[2];typeof n==`string`&&n.startsWith(`[`)&&n.endsWith(`]`)?n=n.slice(1,-1).split(`,`).map(e=>e.trim().replace(/^"|"$/g,``)).filter(e=>e.length>0):typeof n==`string`&&/^\d+$/.test(n)?n=parseInt(n,10):typeof n==`string`&&n.startsWith(`"`)&&n.endsWith(`"`)&&(n=n.slice(1,-1)),i[e]=n}}return c.version!=null&&a.push(c),{frontmatter:{title:i.title??`Untitled`,category:i.category??`notes`,tags:i.tags??[],created:i.created??``,updated:i.updated??``,version:i.version??1,origin:`curated`,changelog:a},content:r}}};function F(){try{let e=o(r(s(import.meta.url)),`..`,`..`,`..`,`package.json`);return JSON.parse(n(e,`utf-8`)).version??`0.0.0`}catch{return`0.0.0`}}const I=u(`server`);function L(){return process.env.AIKIT_TRANSPORT?process.env.AIKIT_TRANSPORT:process.stdin.isTTY?`http`:`stdio`}function R(){let e=process.argv[1];if(!e)return!1;try{return import.meta.url===c(e).href}catch{return!1}}function z(e){let t=e.headers[`mcp-session-id`];return Array.isArray(t)?t[0]:t}function B(e,t){let n=process.env[e];if(!n)return t;let r=Number.parseInt(n,10);return Number.isFinite(r)&&r>0?r:t}function V(){return R()?l({allowPositionals:!0,options:{transport:{type:`string`,default:L()},port:{type:`string`,default:process.env.AIKIT_PORT??`3210`}}}).values:{transport:L(),port:process.env.AIKIT_PORT??`3210`}}async function H(){let e=F(),n=V();process.on(`unhandledRejection`,e=>{I.error(`Unhandled rejection`,d(e))}),process.on(`uncaughtException`,e=>{I.error(`Uncaught exception — exiting`,d(e)),process.exit(1)});let r=e=>{e.then(async()=>{try{let{shouldRunStartupPrune:e,prune:t,markPruneRun:n}=await import(`../../tools/dist/index.js`);if(!e())return;let r=await t({});n(),r.totalBytesFreed>0&&I.info(`Storage maintenance complete`,{forgeOrphans:r.forgeGroundOrphans.count,legacyLance:r.legacyLance.count,bytesFreed:r.totalBytesFreed})}catch(e){I.warn(`Startup maintenance failed (non-critical)`,d(e))}}).catch(()=>{})};if(I.info(`Starting MCP AI Kit server`,{version:e}),n.transport===`http`){let[{default:e},{loadConfig:i,resolveIndexMode:a},{registerDashboardRoutes:o,resolveDashboardDir:s},{registerSettingsRoutes:c,resolveSettingsDir:l},{createSettingsRouter:u},{authMiddleware:f,getOrCreateToken:p}]=await Promise.all([import(`express`),import(`./config-PfoXsIC3.js`),import(`./dashboard-static-CRfR1yKU.js`),import(`./settings-static-B3lnYvcb.js`),import(`./routes-Afg7J7xK.js`),import(`./auth-lzZKfxlV.js`)]),m=i();I.info(`Config loaded`,{sourceCount:m.sources.length,storePath:m.store.path});let h=e();h.use(e.json());let g=Number(n.port),_=B(`AIKIT_HTTP_MAX_SESSIONS`,8),v=B(`AIKIT_HTTP_SESSION_TIMEOUT_MINUTES`,30),y=B(`AIKIT_HTTP_SESSION_GC_INTERVAL_MINUTES`,5);h.use((e,t,n)=>{if(t.setHeader(`Access-Control-Allow-Origin`,process.env.AIKIT_CORS_ORIGIN??`http://localhost:${g}`),t.setHeader(`Access-Control-Allow-Methods`,`GET, POST, PUT, PATCH, DELETE, OPTIONS`),t.setHeader(`Access-Control-Allow-Headers`,`Content-Type, Authorization, Mcp-Session-Id, Mcp-Protocol-Version, Last-Event-ID`),t.setHeader(`Access-Control-Expose-Headers`,`Mcp-Session-Id`),e.method===`OPTIONS`){t.status(204).end();return}n()});let b=p();console.error(`[aikit] Auth token: ~/.aikit/token`),h.use(f(b)),o(h,s(),I);let x=new Date().toISOString();h.use(`/settings/api`,u({log:I,mcpInfo:()=>({transport:`http`,port:g,pid:process.pid,startedAt:x})})),c(h,l(),I),h.get(`/health`,(e,t)=>{t.json({status:`ok`})});let S=!1,C=null,w=null,T=null,E=null,O=null,A=null,j=null,M=Promise.resolve(),N=async(e,n)=>{if(!S||!T||!E){n.status(503).json({jsonrpc:`2.0`,error:{code:-32603,message:`Server initializing — please retry in a few seconds`},id:null});return}let r=M,i;M=new Promise(e=>{i=e}),await r;try{let r=z(e);if(!A){if(r){n.status(404).json({jsonrpc:`2.0`,error:{code:-32001,message:`Session not found`},id:null});return}let e=new E({sessionIdGenerator:()=>t(),onsessioninitialized:async e=>{j=e,w?.onSessionStart(e,{transport:`http`})},onsessionclosed:async e=>{e&&w?.onSessionEnd(e),j=null}});e.onclose=()=>{A===e&&(A=null),j===e.sessionId&&(j=null)},A=e,await T.connect(e)}let i=A;await i.handleRequest(e,n,e.body),e.method!==`DELETE`&&(!r&&i.sessionId?(j=i.sessionId,w?.onSessionStart(i.sessionId,{transport:`http`}),w?.onSessionActivity(i.sessionId)):r&&w?.onSessionActivity(r))}catch(e){if(I.error(`MCP handler error`,d(e)),!n.headersSent){let t=e instanceof Error?e.message:String(e),r=t.includes(`Not Acceptable`);n.status(r?406:500).json({jsonrpc:`2.0`,error:{code:r?-32e3:-32603,message:r?t:`Internal server error`},id:null})}}finally{i()}},P=async(e,t)=>{let n=z(e);if(O&&(!A||n!==j)){await O.handleRequest(e,t,e.body);return}await N(e,t)};h.post(`/mcp`,P),h.get(`/mcp`,P),h.delete(`/mcp`,P);let F=h.listen(g,`127.0.0.1`,()=>{I.info(`MCP server listening`,{url:`http://127.0.0.1:${g}/mcp`,port:g}),setTimeout(async()=>{try{let[{createLazyServer:e,createMcpServer:t,ALL_TOOL_NAMES:n},{StreamableHTTPServerTransport:i},{checkForUpdates:o,autoUpgradeScaffold:s}]=await Promise.all([import(`./server-BhQwVWsr.js`),import(`@modelcontextprotocol/sdk/server/streamableHttp.js`),import(`./version-check-gazMo-D4.js`)]);o(),s();let c=a(m),l=e(m,c);T=l.server,E=i,S=!0,I.info(`MCP server configured (lazy — AI Kit initializing in background)`,{toolCount:n.length,resourceCount:2}),l.startInit(),l.ready.then(()=>{if(!l.aikit)throw Error(`AI Kit components are not available after initialization`);w=new k(l.aikit.stateStore,{staleTimeoutMinutes:v,gcIntervalMinutes:y,onBeforeSessionDelete:e=>{if(j===e&&A){let e=A;A=null,j=null,e.close().catch(()=>void 0)}O?.closeSession(e,{notifySessionEnd:!1})}}),O=new D({createServer:()=>{if(!l.aikit)throw Error(`AI Kit components are not available after initialization`);return t(l.aikit,m)},createTransport:e=>new i(e),maxSessions:_,sessionTimeoutMinutes:v,onSessionStart:e=>w?.onSessionStart(e,{transport:`http`}),onSessionActivity:e=>w?.onSessionActivity(e),onSessionEnd:e=>w?.onSessionEnd(e)}),w.startGC(),j&&(w.onSessionStart(j,{transport:`http`}),w.onSessionActivity(j)),I.info(`HTTP session runtime ready`,{maxSessions:_,sessionTimeoutMinutes:v,gcIntervalMinutes:y})}).catch(e=>I.error(`Failed to start session manager`,d(e))),c===`auto`?l.ready.then(async()=>{try{let e=m.sources.map(e=>e.path).join(`, `);I.info(`Running initial index`,{sourcePaths:e}),await l.runInitialIndex(),I.info(`Initial index complete`)}catch(e){I.error(`Initial index failed; will retry on aikit_reindex`,d(e))}}).catch(e=>I.error(`AI Kit init or indexing failed`,d(e))):c===`smart`?l.ready.then(async()=>{try{if(!l.aikit)throw Error(`AI Kit components are not available after initialization`);let{SmartIndexScheduler:e}=await import(`../../indexer/dist/index.js`),t=new e(l.aikit.indexer,m,l.aikit.store),n=l.aikit.store;C=t,t.start(),n.onBeforeClose&&n.onBeforeClose(()=>t.stop()),l.setSmartScheduler(t),I.info(`Smart index scheduler started (HTTP mode)`)}catch(e){I.error(`Failed to start smart index scheduler`,d(e))}}).catch(e=>I.error(`AI Kit initialization failed`,d(e))):(l.ready.catch(e=>I.error(`AI Kit initialization failed`,d(e))),I.info(`Initial full indexing skipped in HTTP mode`,{indexMode:c})),r(l.ready)}catch(e){I.error(`Failed to load server modules`,d(e))}},100)}),L=async e=>{I.info(`Shutdown signal received`,{signal:e}),C?.stop(),w?.stop(),await O?.closeAll().catch(()=>void 0),j&&w?.onSessionEnd(j),A&&(await A.close().catch(()=>void 0),A=null,j=null),F.close(),T&&await T.close(),process.exit(0)};process.on(`SIGINT`,()=>L(`SIGINT`)),process.on(`SIGTERM`,()=>L(`SIGTERM`))}else{let[{loadConfig:e,reconfigureForWorkspace:t,resolveIndexMode:n},{createLazyServer:i},{checkForUpdates:a,autoUpgradeScaffold:o},{RootsListChangedNotificationSchema:c}]=await Promise.all([import(`./config-PfoXsIC3.js`),import(`./server-BhQwVWsr.js`),import(`./version-check-gazMo-D4.js`),import(`@modelcontextprotocol/sdk/types.js`)]),l=e();I.info(`Config loaded`,{sourceCount:l.sources.length,storePath:l.store.path}),a(),o();let u=n(l),f=i(l,u),{server:p,startInit:m,ready:h,runInitialIndex:g}=f,{StdioServerTransport:_}=await import(`@modelcontextprotocol/sdk/server/stdio.js`),v=new _;await p.connect(v),I.info(`MCP server started`,{transport:`stdio`});let y=e=>{if(e.length===0)return!1;let n=e[0].uri,r=n.startsWith(`file://`)?s(n):n;return I.info(`MCP roots resolved`,{rootUri:n,rootPath:r,rootCount:e.length}),t(l,r),l.allRoots=e.map(e=>{let t=e.uri;return t.startsWith(`file://`)?s(t):t}),!0},b=!1;try{b=y((await p.server.listRoots()).roots),b||I.info(`No MCP roots yet; waiting for roots/list_changed notification`)}catch(e){I.warn(`MCP roots/list not supported by client; using cwd fallback`,{cwd:process.cwd(),...d(e)}),b=!0}b||=await new Promise(e=>{let t=setTimeout(()=>{I.warn(`Timed out waiting for MCP roots/list_changed; using cwd fallback`,{cwd:process.cwd()}),e(!1)},5e3);p.server.setNotificationHandler(c,async()=>{clearTimeout(t);try{e(y((await p.server.listRoots()).roots))}catch(t){I.warn(`roots/list retry failed after notification`,d(t)),e(!1)}})}),m();let x=null,S=()=>{x&&clearTimeout(x),x=setTimeout(async()=>{I.info(`Auto-shutdown: no activity for 30 minutes — shutting down gracefully`);try{let e=f.aikit;e&&await Promise.all([e.embedder.shutdown?.().catch(()=>{})??Promise.resolve(),e.graphStore.close().catch(()=>{}),e.store.close().catch(()=>{})])}catch{}process.exit(0)},18e5),x.unref&&x.unref()};S(),process.stdin.on(`data`,()=>S()),h.catch(e=>{I.error(`Initialization failed — server will continue with limited tools`,d(e))}),u===`auto`?g().catch(e=>I.error(`Initial index failed`,d(e))):u===`smart`?h.then(async()=>{try{if(!f.aikit)throw Error(`AI Kit components are not available after initialization`);let{SmartIndexScheduler:e}=await import(`../../indexer/dist/index.js`),t=new e(f.aikit.indexer,l,f.aikit.store),n=f.aikit.store;t.start(),n.onBeforeClose&&n.onBeforeClose(()=>t.stop()),f.setSmartScheduler(t),I.info(`Smart index scheduler started (stdio mode)`)}catch(e){I.error(`Failed to start smart index scheduler`,d(e))}}).catch(e=>I.error(`AI Kit init failed for smart scheduler`,d(e))):I.warn(`Initial full indexing skipped; use aikit_reindex to index manually`,{indexMode:u}),r(h)}}H();export{A as n,P as t};
14
+ `),s=!1,c={};for(let e of o){if(/^changelog:\s*$/.test(e)){s=!0;continue}if(s){let t=e.match(/^\s+-\s+version:\s*(\d+)$/);if(t){c.version!=null&&a.push(c),c={version:parseInt(t[1],10)};continue}let n=e.match(/^\s+date:\s*(.+)$/);if(n){c.date=n[1].trim();continue}let r=e.match(/^\s+reason:\s*"?(.*?)"?\s*$/);if(r){c.reason=r[1];continue}/^\w/.test(e)&&(s=!1,c.version!=null&&a.push(c),c={});continue}let t=e.match(/^(\w+):\s*(.*)$/);if(t){let e=t[1],n=t[2];typeof n==`string`&&n.startsWith(`[`)&&n.endsWith(`]`)?n=n.slice(1,-1).split(`,`).map(e=>e.trim().replace(/^"|"$/g,``)).filter(e=>e.length>0):typeof n==`string`&&/^\d+$/.test(n)?n=parseInt(n,10):typeof n==`string`&&n.startsWith(`"`)&&n.endsWith(`"`)&&(n=n.slice(1,-1)),i[e]=n}}return c.version!=null&&a.push(c),{frontmatter:{title:i.title??`Untitled`,category:i.category??`notes`,tags:i.tags??[],created:i.created??``,updated:i.updated??``,version:i.version??1,origin:`curated`,changelog:a},content:r}}};function Re(){try{let e=o(r(s(import.meta.url)),`..`,`..`,`..`,`package.json`);return JSON.parse(n(e,`utf-8`)).version??`0.0.0`}catch{return`0.0.0`}}const Z=u(`server`),ze=/^https?:\/\/(localhost|127\.0\.0\.1)(:\d+)?$/i;function Be({requestOrigin:e,configuredOrigin:t,allowAnyOrigin:n,fallbackOrigin:r}){let i=t??r;return i===`*`?n?{allowOrigin:`*`,warn:!1}:e?ze.test(e)?{allowOrigin:e,warn:!1}:{allowOrigin:null,warn:!0}:{allowOrigin:r,warn:!1}:{allowOrigin:i,warn:!1}}function Ve({limit:e,windowMs:t}){let n=new Map,r=(e,r)=>{let i=r-t,a=n.get(e)?.filter(e=>e>i)??[];return a.length===0?(n.delete(e),[]):(n.set(e,a),a)};return{allow(t,i=Date.now()){let a=r(t,i);return a.length>=e?!1:(a.push(i),n.set(t,a),!0)},getRetryAfterMs(n,i=Date.now()){let a=r(n,i);return a.length<e?0:Math.max(0,a[0]+t-i)}}}function He(){return process.env.AIKIT_TRANSPORT?process.env.AIKIT_TRANSPORT:process.stdin.isTTY?`http`:`stdio`}function Ue(){let e=process.argv[1];if(!e)return!1;try{return import.meta.url===c(e).href}catch{return!1}}function Q(e){let t=e.headers[`mcp-session-id`];return Array.isArray(t)?t[0]:t}function $(e,t){let n=process.env[e];if(!n)return t;let r=Number.parseInt(n,10);return Number.isFinite(r)&&r>0?r:t}function We(){return Ue()?l({allowPositionals:!0,options:{transport:{type:`string`,default:He()},port:{type:`string`,default:process.env.AIKIT_PORT??`3210`}}}).values:{transport:He(),port:process.env.AIKIT_PORT??`3210`}}function Ge(e){return`## Context\n${e.context}\n\n## Insight\n${e.insight}\n\n## Evidence\n${e.evidence}`}function Ke(e){ke(t=>{(async()=>{let n=e();if(!n)return;let{jaccardSimilarity:r}=await Promise.resolve().then(()=>ne),i=await n.curated.list({category:`lessons`});for(let e of t)i.some(t=>r(e.title,t.title)>.6)||(await n.curated.remember(e.title,Ge(e),`lessons`,[`lesson`,`auto-observed`,`detector:${e.detector}`]),i.push({path:`lessons/${e.title}`,title:e.title,category:`lessons`,tags:[`lesson`,`auto-observed`,`detector:${e.detector}`],version:1,created:new Date().toISOString(),updated:new Date().toISOString(),contentPreview:e.insight.slice(0,200)}))})().catch(()=>{})})}async function qe(){let e=Re(),n=We();process.on(`unhandledRejection`,e=>{Z.error(`Unhandled rejection`,d(e))}),process.on(`uncaughtException`,e=>{Z.error(`Uncaught exception — exiting`,d(e)),process.exit(1)});let r=(e,t)=>{e.then(async()=>{try{let{markPromoteRun:e,markPruneRun:n,prune:r,shouldRunStartupPrune:i,shouldRunWeeklyPromote:a}=await import(`../../tools/dist/index.js`),o=t();if(!o)return;if(i()){let e=await r({});n(),e.totalBytesFreed>0&&Z.info(`Storage maintenance complete`,{forgeOrphans:e.forgeGroundOrphans.count,legacyLance:e.legacyLance.count,bytesFreed:e.totalBytesFreed});let{groupLessons:t,pruneLessons:i}=await import(`./evolution-9hXRopDC.js`).then(e=>e.t),a=await i(o.curated,o.stateStore,{dryRun:!1});a.pruned.length>0&&Z.info(`Startup lesson prune complete`,{pruned:a.pruned.length});let s=await t(o.curated,o.stateStore,{dryRun:!1});(s.groupsCreated>0||s.lessonsGrouped>0)&&Z.info(`Startup lesson grouping complete`,{groupsCreated:s.groupsCreated,lessonsGrouped:s.lessonsGrouped})}if(a()){let{DEFAULT_PROMOTE_CONFIG:t,collectWorkspaceLessons:n,getGlobalCuratedDir:r,promoteLessons:i,scanForDuplicates:a}=await import(`./promotion-Bd_YB7E1.js`).then(e=>e.o),{CuratedKnowledgeManager:s}=await Promise.resolve().then(()=>Pe),c=o.curated,l=new s(r(),c.store,c.embedder),u=await n(),d={...t,dryRun:!1},f=await i(a(u,d),l,d);e(),f.promoted.length>0&&Z.info(`Weekly lesson promotion complete`,{promoted:f.promoted.length,candidates:f.candidates.length})}}catch(e){Z.warn(`Startup maintenance failed (non-critical)`,d(e))}}).catch(()=>{})};if(Z.info(`Starting MCP AI Kit server`,{version:e}),n.transport===`http`){let[{default:e},{loadConfig:i,resolveIndexMode:a},{registerDashboardRoutes:o,resolveDashboardDir:s},{registerSettingsRoutes:c,resolveSettingsDir:l},{createSettingsRouter:u},{authMiddleware:f,getOrCreateToken:p}]=await Promise.all([import(`express`),import(`./config-C4mVyqAF.js`),import(`./dashboard-static-CRfR1yKU.js`),import(`./settings-static-B3lnYvcb.js`),import(`./routes-Afg7J7xK.js`),import(`./auth-lzZKfxlV.js`)]),m=i();Z.info(`Config loaded`,{sourceCount:m.sources.length,storePath:m.store.path});let h=e();h.use(e.json({limit:`1mb`}));let g=Number(n.port),_=`http://localhost:${g}`,v=process.env.AIKIT_CORS_ORIGIN??_,y=process.env.AIKIT_ALLOW_ANY_ORIGIN===`true`,b=$(`AIKIT_HTTP_MAX_SESSIONS`,8),x=$(`AIKIT_HTTP_SESSION_TIMEOUT_MINUTES`,30),S=$(`AIKIT_HTTP_SESSION_GC_INTERVAL_MINUTES`,5),C=Ve({limit:100,windowMs:6e4}),w=!1;h.use((e,t,n)=>{let r=Array.isArray(e.headers.origin)?e.headers.origin[0]:e.headers.origin,i=Be({requestOrigin:r,configuredOrigin:v,allowAnyOrigin:y,fallbackOrigin:_});if(i.warn&&!w&&(w=!0,Z.warn(`Rejected non-local CORS origin while AIKIT_CORS_ORIGIN=*`,{origin:r,allowAnyOriginEnv:`AIKIT_ALLOW_ANY_ORIGIN=true`})),r&&!i.allowOrigin){t.status(403).json({error:`Origin not allowed`});return}if(i.allowOrigin&&t.setHeader(`Access-Control-Allow-Origin`,i.allowOrigin),t.setHeader(`Access-Control-Allow-Methods`,`GET, POST, PUT, PATCH, DELETE, OPTIONS`),t.setHeader(`Access-Control-Allow-Headers`,`Content-Type, Authorization, Mcp-Session-Id, Mcp-Protocol-Version, Last-Event-ID`),t.setHeader(`Access-Control-Expose-Headers`,`Mcp-Session-Id`),e.method===`OPTIONS`){t.status(204).end();return}n()});let T=p();console.error(`[aikit] Auth token: ~/.aikit/token`),h.use(f(T)),h.use(`/mcp`,(e,t,n)=>{let r=Q(e)??e.ip??e.socket.remoteAddress??`anonymous`;if(C.allow(r)){n();return}let i=Math.max(1,Math.ceil(C.getRetryAfterMs(r)/1e3));t.setHeader(`Retry-After`,String(i)),t.status(429).json({jsonrpc:`2.0`,error:{code:-32003,message:`Rate limit exceeded`},id:null})}),o(h,s(),Z);let E=new Date().toISOString();h.use(`/settings/api`,u({log:Z,mcpInfo:()=>({transport:`http`,port:g,pid:process.pid,startedAt:E})})),c(h,l(),Z),h.get(`/health`,(e,t)=>{t.json({status:`ok`})});let D=!1,O=null,k=null,A=null,j=null,M=null,N=null,P=null,F=Promise.resolve(),te=async(e,n)=>{if(!D||!A||!j){n.status(503).json({jsonrpc:`2.0`,error:{code:-32603,message:`Server initializing — please retry in a few seconds`},id:null});return}let r=F,i;F=new Promise(e=>{i=e}),await r;try{let r=Q(e);if(!N){if(r){n.status(404).json({jsonrpc:`2.0`,error:{code:-32001,message:`Session not found`},id:null});return}let e=new j({sessionIdGenerator:()=>t(),onsessioninitialized:async e=>{P=e,k?.onSessionStart(e,{transport:`http`})},onsessionclosed:async e=>{e&&k?.onSessionEnd(e),P=null}});e.onclose=()=>{N===e&&(N=null),P===e.sessionId&&(P=null)},N=e,await A.connect(e)}let i=N;await i.handleRequest(e,n,e.body),e.method!==`DELETE`&&(!r&&i.sessionId?(P=i.sessionId,k?.onSessionStart(i.sessionId,{transport:`http`}),k?.onSessionActivity(i.sessionId)):r&&k?.onSessionActivity(r))}catch(e){if(Z.error(`MCP handler error`,d(e)),!n.headersSent){let t=e instanceof Error?e.message:String(e),r=t.includes(`Not Acceptable`);n.status(r?406:500).json({jsonrpc:`2.0`,error:{code:r?-32e3:-32603,message:r?t:`Internal server error`},id:null})}}finally{i()}},I=async(e,t)=>{let n=Q(e);if(M&&(!N||n!==P)){await M.handleRequest(e,t,e.body);return}await te(e,t)};h.post(`/mcp`,I),h.get(`/mcp`,I),h.delete(`/mcp`,I);let ne=h.listen(g,`127.0.0.1`,()=>{Z.info(`MCP server listening`,{url:`http://127.0.0.1:${g}/mcp`,port:g}),setTimeout(async()=>{try{let[{createLazyServer:e,createMcpServer:t,ALL_TOOL_NAMES:n},{StreamableHTTPServerTransport:i},{checkForUpdates:o,autoUpgradeScaffold:s}]=await Promise.all([import(`./server-BA1mIjBc.js`),import(`@modelcontextprotocol/sdk/server/streamableHttp.js`),import(`./version-check-gazMo-D4.js`)]);o(),s();let c=a(m),l=e(m,c);A=l.server,j=i,D=!0,Z.info(`MCP server configured (lazy — AI Kit initializing in background)`,{toolCount:n.length,resourceCount:2}),l.startInit(),l.ready.then(()=>{if(!l.aikit)throw Error(`AI Kit components are not available after initialization`);k=new Me(l.aikit.stateStore,{staleTimeoutMinutes:x,gcIntervalMinutes:S,onBeforeSessionDelete:e=>{if(P===e&&N){let e=N;N=null,P=null,e.close().catch(()=>void 0)}M?.closeSession(e,{notifySessionEnd:!1})},onSessionEndMaintenance:async()=>{if(!l.aikit?.curated||!l.aikit?.stateStore)return;let{pruneLessons:e}=await import(`./evolution-9hXRopDC.js`).then(e=>e.t),t=await e(l.aikit.curated,l.aikit.stateStore,{dryRun:!1});t.pruned.length>0&&Z.info(`Session-end lesson prune`,{pruned:t.pruned.length})}}),M=new ee({createServer:()=>{if(!l.aikit)throw Error(`AI Kit components are not available after initialization`);return t(l.aikit,m)},createTransport:e=>new i(e),maxSessions:b,sessionTimeoutMinutes:x,onSessionStart:e=>k?.onSessionStart(e,{transport:`http`}),onSessionActivity:e=>k?.onSessionActivity(e),onSessionEnd:e=>k?.onSessionEnd(e)}),k.startGC(),P&&(k.onSessionStart(P,{transport:`http`}),k.onSessionActivity(P)),Ke(()=>l.aikit?{curated:l.aikit.curated,stateStore:l.aikit.stateStore}:null),Z.info(`HTTP session runtime ready`,{maxSessions:b,sessionTimeoutMinutes:x,gcIntervalMinutes:S})}).catch(e=>Z.error(`Failed to start session manager`,d(e))),c===`auto`?l.ready.then(async()=>{try{let e=m.sources.map(e=>e.path).join(`, `);Z.info(`Running initial index`,{sourcePaths:e}),await l.runInitialIndex(),Z.info(`Initial index complete`)}catch(e){Z.error(`Initial index failed; will retry on aikit_reindex`,d(e))}}).catch(e=>Z.error(`AI Kit init or indexing failed`,d(e))):c===`smart`?l.ready.then(async()=>{try{if(!l.aikit)throw Error(`AI Kit components are not available after initialization`);let{SmartIndexScheduler:e}=await import(`../../indexer/dist/index.js`),t=new e(l.aikit.indexer,m,l.aikit.store),n=l.aikit.store;O=t,t.start(),n.onBeforeClose&&n.onBeforeClose(()=>t.stop()),l.setSmartScheduler(t),Z.info(`Smart index scheduler started (HTTP mode)`)}catch(e){Z.error(`Failed to start smart index scheduler`,d(e))}}).catch(e=>Z.error(`AI Kit initialization failed`,d(e))):(l.ready.catch(e=>Z.error(`AI Kit initialization failed`,d(e))),Z.info(`Initial full indexing skipped in HTTP mode`,{indexMode:c})),r(l.ready,()=>l.aikit?{curated:l.aikit.curated,stateStore:l.aikit.stateStore}:null)}catch(e){Z.error(`Failed to load server modules`,d(e))}},100)}),L=async e=>{Z.info(`Shutdown signal received`,{signal:e}),O?.stop(),k?.stop(),await M?.closeAll().catch(()=>void 0),P&&k?.onSessionEnd(P),N&&(await N.close().catch(()=>void 0),N=null,P=null),ne.close(),A&&await A.close(),process.exit(0)};process.on(`SIGINT`,()=>L(`SIGINT`)),process.on(`SIGTERM`,()=>L(`SIGTERM`))}else{let[{loadConfig:e,reconfigureForWorkspace:t,resolveIndexMode:n},{createLazyServer:i},{checkForUpdates:a,autoUpgradeScaffold:o},{RootsListChangedNotificationSchema:c}]=await Promise.all([import(`./config-C4mVyqAF.js`),import(`./server-BA1mIjBc.js`),import(`./version-check-gazMo-D4.js`),import(`@modelcontextprotocol/sdk/types.js`)]),l=e();Z.info(`Config loaded`,{sourceCount:l.sources.length,storePath:l.store.path}),a(),o();let u=n(l),f=i(l,u),{server:p,startInit:m,ready:h,runInitialIndex:g}=f,{StdioServerTransport:_}=await import(`@modelcontextprotocol/sdk/server/stdio.js`),v=new _;await p.connect(v),Z.info(`MCP server started`,{transport:`stdio`});let y=e=>{if(e.length===0)return!1;let n=e[0].uri,r=n.startsWith(`file://`)?s(n):n;return Z.info(`MCP roots resolved`,{rootUri:n,rootPath:r,rootCount:e.length}),t(l,r),l.allRoots=e.map(e=>{let t=e.uri;return t.startsWith(`file://`)?s(t):t}),!0},b=!1;try{b=y((await p.server.listRoots()).roots),b||Z.info(`No MCP roots yet; waiting for roots/list_changed notification`)}catch(e){Z.warn(`MCP roots/list not supported by client; using cwd fallback`,{cwd:process.cwd(),...d(e)}),b=!0}b||=await new Promise(e=>{let t=setTimeout(()=>{Z.warn(`Timed out waiting for MCP roots/list_changed; using cwd fallback`,{cwd:process.cwd()}),e(!1)},5e3);p.server.setNotificationHandler(c,async()=>{clearTimeout(t);try{e(y((await p.server.listRoots()).roots))}catch(t){Z.warn(`roots/list retry failed after notification`,d(t)),e(!1)}})}),m();let x=null,S=()=>{x&&clearTimeout(x),x=setTimeout(async()=>{Z.info(`Auto-shutdown: no activity for 30 minutes — shutting down gracefully`);try{let e=f.aikit;e&&await Promise.all([e.embedder.shutdown?.().catch(()=>{})??Promise.resolve(),e.graphStore.close().catch(()=>{}),e.store.close().catch(()=>{})])}catch{}process.exit(0)},18e5),x.unref&&x.unref()};S(),process.stdin.on(`data`,()=>S()),h.catch(e=>{Z.error(`Initialization failed — server will continue with limited tools`,d(e))}),h.then(()=>{Ke(()=>f.aikit?{curated:f.aikit.curated,stateStore:f.aikit.stateStore}:null)}).catch(()=>{}),u===`auto`?g().catch(e=>Z.error(`Initial index failed`,d(e))):u===`smart`?h.then(async()=>{try{if(!f.aikit)throw Error(`AI Kit components are not available after initialization`);let{SmartIndexScheduler:e}=await import(`../../indexer/dist/index.js`),t=new e(f.aikit.indexer,l,f.aikit.store),n=f.aikit.store;t.start(),n.onBeforeClose&&n.onBeforeClose(()=>t.stop()),f.setSmartScheduler(t),Z.info(`Smart index scheduler started (stdio mode)`)}catch(e){Z.error(`Failed to start smart index scheduler`,d(e))}}).catch(e=>Z.error(`AI Kit init failed for smart scheduler`,d(e))):Z.warn(`Initial full indexing skipped; use aikit_reindex to index manually`,{indexMode:u}),r(h,()=>f.aikit?{curated:f.aikit.curated,stateStore:f.aikit.stateStore}:null)}}qe();export{V as a,L as c,ie as d,R as f,De as i,re as l,E as m,Ne as n,ve as o,I as p,Ae as r,_e as s,Le as t,B as u};
@@ -0,0 +1,2 @@
1
+ #!/usr/bin/env node
2
+ import{c as e}from"./bin.js";import{a as t,t as n}from"./retention-C3tsarCT.js";import{t as r}from"./lessons-B05P_TOl.js";import{existsSync as i,readFileSync as a,writeFileSync as o}from"node:fs";import{dirname as s,resolve as c}from"node:path";import{fileURLToPath as l}from"node:url";import{AIKIT_PATHS as u,EMBEDDING_DEFAULTS as d,createLogger as f,getPartitionDir as p,isUserInstalled as m,registerWorkspace as h,serializeError as g}from"../../core/dist/index.js";const _=s(l(import.meta.url)),v=f(`server`),y=[`auto`,`manual`,`smart`],b={model:d.model,dimensions:d.dimensions,childProcess:!0,idleTimeoutMs:6e4};function x(e){return typeof e==`string`&&y.includes(e)}function S(e,t,n){let r=c(e),i=c(t);if(!r.startsWith(i))throw Error(`Config ${n} path escapes workspace root: ${e} is not under ${t}`);return r}function C(e){let t=process.env.AIKIT_INDEX_MODE;if(x(t))return t;if(e.indexMode)return e.indexMode;let n=process.env.AIKIT_AUTO_INDEX;return n===void 0?e.autoIndex===void 0?`smart`:e.autoIndex?`auto`:`manual`:n===`true`?`auto`:`manual`}function w(){let o=process.env.AIKIT_CONFIG_PATH??(i(c(process.cwd(),`aikit.config.json`))?c(process.cwd(),`aikit.config.json`):c(_,`..`,`..`,`..`,`aikit.config.json`));try{if(!i(o))return v.info(`No config file found, using defaults`,{configPath:o}),E();let l=a(o,`utf-8`),d=JSON.parse(l);if(d.embedding={...b,...d.embedding},d.memory={retention:{...n,...d.memory?.retention},lessons:{...r,...d.memory?.lessons},consolidation:{...t,...d.memory?.consolidation},supersession:{...e,...d.memory?.supersession}},!d.sources||!Array.isArray(d.sources)||d.sources.length===0)throw Error(`Config must have at least one source`);if(!d.store?.path)throw Error(`Config must specify store.path`);if(d.autoIndex!==void 0&&typeof d.autoIndex!=`boolean`)throw Error(`Config autoIndex must be a boolean`);if(d.indexMode!==void 0&&!x(d.indexMode))throw Error(`Config indexMode must be one of: ${y.join(`, `)}`);let f=s(o);return d.sources=d.sources.map(e=>({...e,path:S(c(f,e.path),f,`source`)})),d.store.path=S(c(f,d.store.path),f,`store`),d.curated=d.curated??{path:u.aiCurated},d.curated.path=S(c(f,d.curated.path),f,`curated`),O(d,f),D(d,o),d.indexMode=C(d),d}catch(e){return v.error(`Failed to load config`,{configPath:o,...g(e)}),v.warn(`Falling back to default configuration`,{configPath:o}),E()}}const T=[`.git/**`,`node_modules/**`,`*.lock`,`pnpm-lock.yaml`,`package-lock.json`,`dist/**`,`build/**`,`out/**`,`.output/**`,`cdk.out/**`,`.next/**`,`.nuxt/**`,`.vercel/**`,`.serverless/**`,`.turbo/**`,`.cache/**`,`.parcel-cache/**`,`coverage/**`,`.terraform/**`,`__pycache__/**`,`.venv/**`,`.docusaurus/**`,`.temp/**`,`tmp/**`];function E(){let i=process.env.AIKIT_WORKSPACE_ROOT??process.cwd(),a={sources:[{path:i,excludePatterns:[...T]}],serverName:`aikit`,indexing:{chunkSize:1500,chunkOverlap:200,minChunkSize:100},embedding:{...b},store:{backend:`sqlite-vec`,path:c(i,u.data)},curated:{path:c(i,u.aiCurated)},memory:{retention:{...n},lessons:{...r},consolidation:{...t},supersession:{...e}},onboardDir:c(i,u.aiContext),stateDir:c(i,u.state)};return O(a,i),a.indexMode=C(a),a}function D(e,t){let n=e.configVersion??0;if(n>=1)return e;if(n<1)for(let t of e.sources){t.excludePatterns=t.excludePatterns??[];let e=new Set(t.excludePatterns);for(let n of T)e.has(n)||t.excludePatterns.push(n)}e.configVersion=1;try{o(t,`${JSON.stringify(e,null,2)}\n`,`utf-8`),v.info(`Config auto-upgraded`,{from:n,to:1,configPath:t})}catch(e){v.warn(`Failed to write upgraded config`,{configPath:t,...g(e)})}return e}function O(e,t){if(!m())return;let n=h(t);e.store.path=c(p(n.partition)),e.onboardDir=c(p(n.partition),`onboard`),e.stateDir=c(p(n.partition),`state`),e.curated={path:c(p(n.partition),`curated`)}}function k(e,t){if(!i(t))throw Error(`Workspace root does not exist: ${t}`);v.info(`Reconfiguring for workspace root`,{workspaceRoot:t});try{process.chdir(t),v.info(`Changed process cwd to workspace root`,{cwd:process.cwd()})}catch(e){v.warn(`Failed to chdir to workspace root`,{workspaceRoot:t,...g(e)})}e.sources=[{path:t,excludePatterns:e.sources[0]?.excludePatterns??[`node_modules/**`,`dist/**`,`.git/**`,`coverage/**`,`*.lock`,`pnpm-lock.yaml`]}],e.store.path=c(t,u.data),e.curated={path:c(t,u.aiCurated)},e.onboardDir=c(t,u.aiContext),e.stateDir=c(t,u.state),O(e,t)}export{T as DEFAULT_EXCLUDE_PATTERNS,w as loadConfig,k as reconfigureForWorkspace,C as resolveIndexMode};
@@ -0,0 +1 @@
1
+ import{t as e}from"./supersession-9edUDEQ8.js";import{a as t,t as n}from"./retention-B4ITAs7F.js";import{t as r}from"./lessons-D7sdHa2e.js";import{existsSync as i,readFileSync as a,writeFileSync as o}from"node:fs";import{dirname as s,resolve as c}from"node:path";import{fileURLToPath as l}from"node:url";import{AIKIT_PATHS as u,EMBEDDING_DEFAULTS as d,createLogger as f,getPartitionDir as p,isUserInstalled as m,registerWorkspace as h,serializeError as g}from"../../core/dist/index.js";const _=s(l(import.meta.url)),v=f(`server`),y=[`auto`,`manual`,`smart`],b={model:d.model,dimensions:d.dimensions,childProcess:!0,idleTimeoutMs:6e4};function x(e){return typeof e==`string`&&y.includes(e)}function S(e,t,n){let r=c(e),i=c(t);if(!r.startsWith(i))throw Error(`Config ${n} path escapes workspace root: ${e} is not under ${t}`);return r}function C(e){let t=process.env.AIKIT_INDEX_MODE;if(x(t))return t;if(e.indexMode)return e.indexMode;let n=process.env.AIKIT_AUTO_INDEX;return n===void 0?e.autoIndex===void 0?`smart`:e.autoIndex?`auto`:`manual`:n===`true`?`auto`:`manual`}function w(){let o=process.env.AIKIT_CONFIG_PATH??(i(c(process.cwd(),`aikit.config.json`))?c(process.cwd(),`aikit.config.json`):c(_,`..`,`..`,`..`,`aikit.config.json`));try{if(!i(o))return v.info(`No config file found, using defaults`,{configPath:o}),E();let l=a(o,`utf-8`),d=JSON.parse(l);if(d.embedding={...b,...d.embedding},d.memory={retention:{...n,...d.memory?.retention},lessons:{...r,...d.memory?.lessons},consolidation:{...t,...d.memory?.consolidation},supersession:{...e,...d.memory?.supersession}},!d.sources||!Array.isArray(d.sources)||d.sources.length===0)throw Error(`Config must have at least one source`);if(!d.store?.path)throw Error(`Config must specify store.path`);if(d.autoIndex!==void 0&&typeof d.autoIndex!=`boolean`)throw Error(`Config autoIndex must be a boolean`);if(d.indexMode!==void 0&&!x(d.indexMode))throw Error(`Config indexMode must be one of: ${y.join(`, `)}`);let f=s(o);return d.sources=d.sources.map(e=>({...e,path:S(c(f,e.path),f,`source`)})),d.store.path=S(c(f,d.store.path),f,`store`),d.curated=d.curated??{path:u.aiCurated},d.curated.path=S(c(f,d.curated.path),f,`curated`),O(d,f),D(d,o),d.indexMode=C(d),d}catch(e){return v.error(`Failed to load config`,{configPath:o,...g(e)}),v.warn(`Falling back to default configuration`,{configPath:o}),E()}}const T=[`.git/**`,`node_modules/**`,`*.lock`,`pnpm-lock.yaml`,`package-lock.json`,`dist/**`,`build/**`,`out/**`,`.output/**`,`cdk.out/**`,`.next/**`,`.nuxt/**`,`.vercel/**`,`.serverless/**`,`.turbo/**`,`.cache/**`,`.parcel-cache/**`,`coverage/**`,`.terraform/**`,`__pycache__/**`,`.venv/**`,`.docusaurus/**`,`.temp/**`,`tmp/**`];function E(){let i=process.env.AIKIT_WORKSPACE_ROOT??process.cwd(),a={sources:[{path:i,excludePatterns:[...T]}],serverName:`aikit`,indexing:{chunkSize:1500,chunkOverlap:200,minChunkSize:100},embedding:{...b},store:{backend:`sqlite-vec`,path:c(i,u.data)},curated:{path:c(i,u.aiCurated)},memory:{retention:{...n},lessons:{...r},consolidation:{...t},supersession:{...e}},onboardDir:c(i,u.aiContext),stateDir:c(i,u.state)};return O(a,i),a.indexMode=C(a),a}function D(e,t){let n=e.configVersion??0;if(n>=1)return e;if(n<1)for(let t of e.sources){t.excludePatterns=t.excludePatterns??[];let e=new Set(t.excludePatterns);for(let n of T)e.has(n)||t.excludePatterns.push(n)}e.configVersion=1;try{o(t,`${JSON.stringify(e,null,2)}\n`,`utf-8`),v.info(`Config auto-upgraded`,{from:n,to:1,configPath:t})}catch(e){v.warn(`Failed to write upgraded config`,{configPath:t,...g(e)})}return e}function O(e,t){if(!m())return;let n=h(t);e.store.path=c(p(n.partition)),e.onboardDir=c(p(n.partition),`onboard`),e.stateDir=c(p(n.partition),`state`),e.curated={path:c(p(n.partition),`curated`)}}function k(e,t){if(!i(t))throw Error(`Workspace root does not exist: ${t}`);v.info(`Reconfiguring for workspace root`,{workspaceRoot:t});try{process.chdir(t),v.info(`Changed process cwd to workspace root`,{cwd:process.cwd()})}catch(e){v.warn(`Failed to chdir to workspace root`,{workspaceRoot:t,...g(e)})}e.sources=[{path:t,excludePatterns:e.sources[0]?.excludePatterns??[`node_modules/**`,`dist/**`,`.git/**`,`coverage/**`,`*.lock`,`pnpm-lock.yaml`]}],e.store.path=c(t,u.data),e.curated={path:c(t,u.aiCurated)},e.onboardDir=c(t,u.aiContext),e.stateDir=c(t,u.state),O(e,t)}export{T as DEFAULT_EXCLUDE_PATTERNS,w as loadConfig,k as reconfigureForWorkspace,C as resolveIndexMode};
@@ -0,0 +1,7 @@
1
+ import{t as e}from"./rolldown-runtime-DT7IzrpZ.js";import{createHash as t}from"node:crypto";import{dirname as n,isAbsolute as r,join as i}from"node:path";import{createLogger as a,serializeError as o}from"../../core/dist/index.js";import{mkdir as s,readFile as c,readdir as l,stat as u,unlink as d,writeFile as f}from"node:fs/promises";import{GIT_REF_SLUG_PATTERN as p,gitAvailable as m,gitCommitToRef as h,gitExec as g,slugForRef as _}from"../../tools/dist/index.js";var v=class{baseDir;constructor(e){this.baseDir=e}async initialize(){await s(this.baseDir,{recursive:!0})}async read(e){let t=i(this.baseDir,e);try{return await c(t,`utf-8`)}catch(e){if(e.code===`ENOENT`)return null;throw e}}async write(e,t,r){let a=i(this.baseDir,e);await s(n(a),{recursive:!0}),await f(a,t,{encoding:`utf-8`,flag:r?.exclusive?`wx`:`w`})}async delete(e){let t=i(this.baseDir,e);try{return await d(t),!0}catch(e){if(e.code===`ENOENT`)return!1;throw e}}async list(e){let t=[],n=e?[e]:await this.listDirectories();for(let e of n){let n=i(this.baseDir,e),r;try{r=await l(n)}catch{continue}for(let n of r){if(!n.endsWith(`.md`))continue;let r=`${e}/${n}`,a=i(this.baseDir,r);try{let e=await u(a);t.push({path:r,size:e.size})}catch{}}}return t}async exists(e){let t=i(this.baseDir,e);try{return await u(t),!0}catch{return!1}}async listDirectories(){try{return(await l(this.baseDir,{withFileTypes:!0})).filter(e=>e.isDirectory()&&/^[a-z][a-z0-9-]*$/.test(e.name)).map(e=>e.name)}catch{return[]}}async close(){}},y=e({CuratedKnowledgeManager:()=>C});const b=50*1024,x=`refs/aikit/knowledge`,S=a(`server`);var C=class{curatedDir;store;embedder;adapter;constructor(e,t,n,r=new v(e)){this.curatedDir=e,this.store=t,this.embedder=n,this.adapter=r}async remember(e,t,n,r=[]){this.validateCategoryName(n),this.validateContentSize(t);let i=this.slugify(e),a=await this.uniqueRelativePath(n,i),o=new Date().toISOString(),s={title:e,category:n,tags:r,created:o,updated:o,version:1,origin:`curated`,changelog:[{version:1,date:o,reason:`Initial creation`}]},c=this.serializeFile(t,s);try{await this.adapter.write(a,c,{exclusive:!0})}catch(e){throw e.code===`EEXIST`?Error(`Concurrent write collision for "${a}" — retry the operation`):e}try{await this.indexCuratedFile(a,t,s)}catch(e){throw await this.adapter.delete(a).catch(()=>{}),Error(`Remember failed: wrote file but indexing failed — rolled back. ${e.message}`)}return this.gitCommitKnowledge(a,c,`remember: ${e}\n\nCategory: ${n}\nTags: ${r.join(`, `)}`),{path:a}}async update(e,t,n){e=this.guardPath(e),this.validateContentSize(t);let r=await this.adapter.read(e);if(r==null)throw Error(`Curated entry not found: ${e}`);let{frontmatter:i}=this.parseFile(r),a=(i.version??1)+1,o=new Date().toISOString();i.version=a,i.updated=o,i.changelog=[...i.changelog??[],{version:a,date:o,reason:n}];let s=this.serializeFile(t,i);return await this.adapter.write(e,s),await this.indexCuratedFile(e,t,i),this.gitCommitKnowledge(e,s,`update(v${a}): ${i.title}\n\nReason: ${n}\nVersion: ${a}`),{path:e,version:a}}async forget(e,t){if(e=this.guardPath(e),!await this.adapter.delete(e))throw Error(`Curated entry not found: ${e}`);let n=`.ai/curated/${e}`;return await this.store.deleteBySourcePath(n).catch(e=>{S.warn(`File deleted but vector cleanup failed`,{sourcePath:n,...o(e)})}),this.gitDeleteKnowledgeRef(e),{path:e}}async history(e,t=20){if(e=this.guardPath(e),!m(this.curatedDir))return[];let n=this.knowledgeRefForPath(e);if(!n)return[];let r=g([`log`,`--format=%H|%aI|%s`,n,`-n`,String(t)],this.curatedDir);return r?r.split(`
2
+ `).filter(Boolean).map(e=>{let[t,n,...r]=e.split(`|`);return{sha:t,date:n,message:r.join(`|`)}}):[]}async diff(e,t,n){if(e=this.guardPath(e),!m(this.curatedDir))return``;if(!n){let r=await this.history(e,2);if(r.length===0)return``;n=r[0].sha,r.length>1&&!t&&(t=r[1].sha)}return t&&n?g([`diff`,`${t}:entry.md`,`${n}:entry.md`],this.curatedDir)??``:n?g([`show`,`${n}:entry.md`],this.curatedDir)??``:``}async recover(e){if(e=this.guardPath(e),await this.adapter.exists(e))throw Error(`Entry already exists on filesystem: ${e}. Use update() instead.`);if(!m(this.curatedDir))return null;let t=this.knowledgeRefForPath(e);if(!t)return null;let n=g([`show`,`${t}:entry.md`],this.curatedDir);if(!n)return null;await this.adapter.write(e,n);let{frontmatter:r,content:i}=this.parseFile(n);return await this.indexCuratedFile(e,i,r),{path:e,version:r.version??1}}async listOrphaned(){if(!m(this.curatedDir))return[];let e=g([`for-each-ref`,`--format=%(refname)|%(subject)`,`${x}/`],this.curatedDir);if(!e)return[];let t=[];for(let n of e.split(`
3
+ `).filter(Boolean)){let[e,...r]=n.split(`|`),i=r.join(`|`),a=`${e.replace(`${x}/`,``)}.md`;await this.adapter.exists(a)||t.push({ref:e,path:a,lastMessage:i})}return t}async read(e){e=this.guardPath(e);let t=await this.adapter.read(e);if(t==null)throw Error(`Curated entry not found: ${e}`);let{frontmatter:n,content:r}=this.parseFile(t),i=e.split(`/`)[0];return{path:e,title:n.title??e,category:i,tags:n.tags??[],version:n.version??1,created:n.created??``,updated:n.updated??``,contentPreview:r.slice(0,200),content:r}}async list(e){let t=[],n=e?.category?[e.category]:await this.discoverCategories();for(let r of n){let n=await this.adapter.list(r);for(let i of n){let n=await this.adapter.read(i.path);if(n==null)continue;let{frontmatter:a,content:o}=this.parseFile(n);e?.tag&&!(a.tags??[]).includes(e.tag)||t.push({path:i.path,title:a.title??i.path,category:r,tags:a.tags??[],version:a.version??1,created:a.created??``,updated:a.updated??``,contentPreview:o.slice(0,200)})}}return t}async reindexAll(){let e=await this.discoverCategories(),t=[],n=[];for(let r of e){let e=await this.adapter.list(r);for(let r of e){let e=r.path;try{let r=await this.adapter.read(e);if(r==null){t.push(`${e}: read failed`);continue}let{frontmatter:i,content:a}=this.parseFile(r);n.push({relativePath:e,content:a,frontmatter:i})}catch(n){S.error(`Failed to read curated file`,{relativePath:e,...o(n)}),t.push(`${e}: read failed`)}}}if(n.length===0)return{indexed:0,errors:t};let r=await this.embedder.embedBatch(n.map(e=>e.content)),i=new Date().toISOString(),a=n.map(e=>{let t=`.ai/curated/${e.relativePath}`;return{id:this.hashId(t,0),content:e.content,sourcePath:t,contentType:`curated-knowledge`,headingPath:e.frontmatter.title,chunkIndex:0,totalChunks:1,startLine:1,endLine:e.content.split(`
4
+ `).length,fileHash:this.hash(e.content),indexedAt:i,origin:`curated`,tags:e.frontmatter.tags,category:e.frontmatter.category,version:e.frontmatter.version}});return await this.store.upsert(a,r),{indexed:n.length,errors:t}}gitCommitKnowledge(e,t,n){try{if(!m(this.curatedDir))return;let r=this.knowledgeRefForPath(e);if(!r)return;h(r,`entry.md`,t,n,this.curatedDir)}catch{}}gitDeleteKnowledgeRef(e){try{if(!m(this.curatedDir))return;let t=this.knowledgeRefForPath(e);if(!t)return;g([`update-ref`,`-d`,t],this.curatedDir)}catch{}}knowledgeRefForPath(e){let t=e.replace(/\.md$/,``).split(`/`).map(e=>_(e)).join(`/`);return t.split(`/`).every(e=>p.test(e))?`${x}/${t}`:null}async indexCuratedFile(e,t,n){let r=await this.embedder.embed(t),i=`.ai/curated/${e}`,a=new Date().toISOString(),o={id:this.hashId(i,0),content:t,sourcePath:i,contentType:`curated-knowledge`,headingPath:n.title,chunkIndex:0,totalChunks:1,startLine:1,endLine:t.split(`
5
+ `).length,fileHash:this.hash(t),indexedAt:a,origin:`curated`,tags:n.tags,category:n.category,version:n.version};await this.store.upsert([o],[r])}async discoverCategories(){return this.adapter.listDirectories()}guardPath(e){let t=e.replace(/^\.ai\/curated\//,``);if(t.endsWith(`.md`)||(t+=`.md`),t.includes(`..`)||r(t))throw Error(`Invalid path: ${t}. Must be relative within .ai/curated/ directory.`);let n=t.split(`/`)[0];return this.validateCategoryName(n),t}validateCategoryName(e){if(!/^[a-z][a-z0-9-]*$/.test(e))throw Error(`Invalid category name: "${e}". Must be lowercase kebab-case (e.g., "decisions", "api-contracts").`)}validateContentSize(e){if(Buffer.byteLength(e,`utf-8`)>b)throw Error(`Content exceeds maximum size of ${b/1024}KB`)}slugify(e){return e.toLowerCase().replace(/[^a-z0-9]+/g,`-`).replace(/^-|-$/g,``).slice(0,80)}async uniqueRelativePath(e,t){let n=`${e}/${t}.md`;if(!await this.adapter.exists(n))return n;for(let n=2;n<=100;n++){let r=`${e}/${t}-${n}.md`;if(!await this.adapter.exists(r))return r}throw Error(`Too many entries with slug "${t}" in category "${e}"`)}hash(e){return t(`sha256`).update(e).digest(`hex`).slice(0,16)}hashId(e,t){return this.hash(`${e}::${t}`)}serializeFile(e,t){return`${[`---`,`title: "${t.title.replace(/"/g,`\\"`)}"`,`category: ${t.category}`,`tags: [${t.tags.map(e=>`"${e}"`).join(`, `)}]`,`created: ${t.created}`,`updated: ${t.updated}`,`version: ${t.version}`,`origin: ${t.origin}`,`changelog:`,...t.changelog.map(e=>` - version: ${e.version}\n date: ${e.date}\n reason: "${e.reason.replace(/"/g,`\\"`)}"`),`---`].join(`
6
+ `)}\n\n${e}\n`}parseFile(e){let t=e.match(/^---\n([\s\S]*?)\n---\n\n?([\s\S]*)$/);if(!t)return{frontmatter:{title:`Untitled`,category:`notes`,tags:[],created:``,updated:``,version:1,origin:`curated`,changelog:[]},content:e};let n=t[1],r=t[2].trim(),i={},a=[],o=n.split(`
7
+ `),s=!1,c={};for(let e of o){if(/^changelog:\s*$/.test(e)){s=!0;continue}if(s){let t=e.match(/^\s+-\s+version:\s*(\d+)$/);if(t){c.version!=null&&a.push(c),c={version:parseInt(t[1],10)};continue}let n=e.match(/^\s+date:\s*(.+)$/);if(n){c.date=n[1].trim();continue}let r=e.match(/^\s+reason:\s*"?(.*?)"?\s*$/);if(r){c.reason=r[1];continue}/^\w/.test(e)&&(s=!1,c.version!=null&&a.push(c),c={});continue}let t=e.match(/^(\w+):\s*(.*)$/);if(t){let e=t[1],n=t[2];typeof n==`string`&&n.startsWith(`[`)&&n.endsWith(`]`)?n=n.slice(1,-1).split(`,`).map(e=>e.trim().replace(/^"|"$/g,``)).filter(e=>e.length>0):typeof n==`string`&&/^\d+$/.test(n)?n=parseInt(n,10):typeof n==`string`&&n.startsWith(`"`)&&n.endsWith(`"`)&&(n=n.slice(1,-1)),i[e]=n}}return c.version!=null&&a.push(c),{frontmatter:{title:i.title??`Untitled`,category:i.category??`notes`,tags:i.tags??[],created:i.created??``,updated:i.updated??``,version:i.version??1,origin:`curated`,changelog:a},content:r}}};export{y as n,v as r,C as t};
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ import{m as e,u as t}from"./bin.js";import{c as n,i as r,t as i}from"./lessons-B05P_TOl.js";import{join as a}from"node:path";import{readFile as o,writeFile as s}from"node:fs/promises";var c=e({DEFAULT_GROUP_CONFIG:()=>u,DEFAULT_PRUNE_CONFIG:()=>l,groupLessons:()=>w,pruneLessons:()=>C});const l={maxConfidence:15,minIdleDays:30,safetyDays:7,maxPrune:20,dryRun:!0},u={similarityThreshold:.7,minGroupSize:2,maxGroups:10,dryRun:!0},d=new Set([`the`,`a`,`to`,`for`,`in`,`of`,`and`,`is`,`use`]);function f(e){return{maxConfidence:Math.min(100,Math.max(0,Math.trunc(e?.maxConfidence??l.maxConfidence))),minIdleDays:Math.max(1,Math.trunc(e?.minIdleDays??l.minIdleDays)),safetyDays:Math.max(0,Math.trunc(e?.safetyDays??l.safetyDays)),maxPrune:Math.max(1,Math.trunc(e?.maxPrune??l.maxPrune)),dryRun:e?.dryRun??l.dryRun}}function p(e){return{similarityThreshold:Math.min(1,Math.max(0,e?.similarityThreshold??u.similarityThreshold)),minGroupSize:Math.max(2,Math.trunc(e?.minGroupSize??u.minGroupSize)),maxGroups:Math.max(1,Math.trunc(e?.maxGroups??u.maxGroups)),dryRun:e?.dryRun??u.dryRun}}function m(e){if(!e)return 0;let t=Date.parse(e);return Number.isNaN(t)?0:t}function h(e,t){let n=Math.max(m(e),m(t));return n===0?1/0:Math.max(0,Date.now()-n)/864e5}function g(e){return e.toLowerCase().match(/[a-z0-9]{2,}/g)??[]}function _(e){return e.toLowerCase().replace(/[^a-z0-9]+/g,`-`).replace(/^-+|-+$/g,``).slice(0,60)}function v(e,t){return`${[`---`,`title: "${e.title.replace(/"/g,`\\"`)}"`,`category: ${e.category}`,`tags: [${e.tags.map(e=>`"${e}"`).join(`, `)}]`,`created: ${e.created}`,`updated: ${e.updated}`,`version: ${e.version}`,`origin: ${e.origin}`,`changelog:`,...e.changelog.map(e=>` - version: ${e.version}\n date: ${e.date}\n reason: "${e.reason.replace(/"/g,`\\"`)}"`),`---`].join(`
3
+ `)}\n\n${t}\n`}function y(e,n){let r=e.map(()=>[]);for(let i=0;i<e.length;i+=1)for(let a=i+1;a<e.length;a+=1)t(e[i],e[a])>=n&&(r[i].push(a),r[a].push(i));return r}function b(e){let t=new Set,n=[];for(let r=0;r<e.length;r+=1){if(t.has(r))continue;let i=[r],a=[];for(t.add(r);i.length>0;){let n=i.pop();if(n!==void 0){a.push(n);for(let r of e[n])t.has(r)||(t.add(r),i.push(r))}}n.push(a)}return n}function x(e){let t=new Map,n=new Map,r=0;for(let i of e)for(let e of g(i))d.has(e)||(t.set(e,(t.get(e)??0)+1),n.has(e)||(n.set(e,r),r+=1));let i=[...t.entries()].sort((e,t)=>t[1]-e[1]||(n.get(e[0])??0)-(n.get(t[0])??0))[0];return i&&i[1]>1?_(i[0]):_(e.flatMap(e=>g(e)).find(e=>!d.has(e))??`lesson-group`)}async function S(e,t,n){let r=a(e.curatedDir,t),i=await o(r,`utf8`),{frontmatter:c,content:l}=e.parseFile(i),u=`group:${n}`;if(c.tags.includes(u))return;let d=new Date().toISOString(),f=(c.version??1)+1;await s(r,v({...c,tags:[...new Set([...c.tags,u])],updated:d,version:f,changelog:[...c.changelog??[],{version:f,date:d,reason:`Grouped lesson under ${n}`}]},l),`utf8`)}async function C(e,t,a,o){let s=f(a),c=n(o??i),l=(await e.list({category:`lessons`})).filter(e=>e.tags.includes(`lesson`)),u=l.map(e=>{let n=t.memoryMetaGet(e.path);if(!n||n.supersededBy!=null)return null;let i=h(n.lastAccessedAt,n.createdAt??e.created);if(i<s.safetyDays)return null;let a=r(n.confidence,n.lastAccessedAt,n.createdAt,c);return a>=s.maxConfidence||i<s.minIdleDays?null:{path:e.path,effectiveConfidence:a}}).filter(e=>e!==null).sort((e,t)=>e.effectiveConfidence-t.effectiveConfidence||e.path.localeCompare(t.path)).slice(0,s.maxPrune);if(!s.dryRun)for(let e of u)t.memoryMetaSetSuperseded(e.path,`lesson:auto-prune`);return{pruned:u.map(e=>e.path),skipped:l.length-u.length,dryRun:s.dryRun}}async function w(e,t,n){let r=p(n),i=(await e.list({category:`lessons`})).filter(e=>{if(!e.tags.includes(`lesson`)||e.tags.some(e=>e.startsWith(`group:`)))return!1;let n=t.memoryMetaGet(e.path);return n?.supersededBy==null||n===void 0});if(i.length<r.minGroupSize)return{groupsCreated:0,lessonsGrouped:0,groups:[],dryRun:r.dryRun};let a=b(y(i.map(e=>e.title),r.similarityThreshold)).filter(e=>e.length>=r.minGroupSize).map(e=>{let t=e.map(e=>i[e]).sort((e,t)=>e.path.localeCompare(t.path));return{label:x(t.map(e=>e.title)),members:t.map(e=>e.path)}}).sort((e,t)=>t.members.length-e.members.length||e.members[0].localeCompare(t.members[0])).slice(0,r.maxGroups);if(!r.dryRun&&a.length>0){for(let t of a)for(let n of t.members)await S(e,n,t.label);await e.reindexAll()}return{groupsCreated:a.length,lessonsGrouped:a.reduce((e,t)=>e+t.members.length,0),groups:a,dryRun:r.dryRun}}export{w as n,C as r,c as t};
@@ -0,0 +1,2 @@
1
+ import{t as e}from"./rolldown-runtime-DT7IzrpZ.js";import{r as t}from"./supersession-9edUDEQ8.js";import{c as n,i as r,t as i}from"./lessons-D7sdHa2e.js";import{join as a}from"node:path";import{readFile as o,writeFile as s}from"node:fs/promises";var c=e({DEFAULT_GROUP_CONFIG:()=>u,DEFAULT_PRUNE_CONFIG:()=>l,groupLessons:()=>w,pruneLessons:()=>C});const l={maxConfidence:15,minIdleDays:30,safetyDays:7,maxPrune:20,dryRun:!0},u={similarityThreshold:.7,minGroupSize:2,maxGroups:10,dryRun:!0},d=new Set([`the`,`a`,`to`,`for`,`in`,`of`,`and`,`is`,`use`]);function f(e){return{maxConfidence:Math.min(100,Math.max(0,Math.trunc(e?.maxConfidence??l.maxConfidence))),minIdleDays:Math.max(1,Math.trunc(e?.minIdleDays??l.minIdleDays)),safetyDays:Math.max(0,Math.trunc(e?.safetyDays??l.safetyDays)),maxPrune:Math.max(1,Math.trunc(e?.maxPrune??l.maxPrune)),dryRun:e?.dryRun??l.dryRun}}function p(e){return{similarityThreshold:Math.min(1,Math.max(0,e?.similarityThreshold??u.similarityThreshold)),minGroupSize:Math.max(2,Math.trunc(e?.minGroupSize??u.minGroupSize)),maxGroups:Math.max(1,Math.trunc(e?.maxGroups??u.maxGroups)),dryRun:e?.dryRun??u.dryRun}}function m(e){if(!e)return 0;let t=Date.parse(e);return Number.isNaN(t)?0:t}function h(e,t){let n=Math.max(m(e),m(t));return n===0?1/0:Math.max(0,Date.now()-n)/864e5}function g(e){return e.toLowerCase().match(/[a-z0-9]{2,}/g)??[]}function _(e){return e.toLowerCase().replace(/[^a-z0-9]+/g,`-`).replace(/^-+|-+$/g,``).slice(0,60)}function v(e,t){return`${[`---`,`title: "${e.title.replace(/"/g,`\\"`)}"`,`category: ${e.category}`,`tags: [${e.tags.map(e=>`"${e}"`).join(`, `)}]`,`created: ${e.created}`,`updated: ${e.updated}`,`version: ${e.version}`,`origin: ${e.origin}`,`changelog:`,...e.changelog.map(e=>` - version: ${e.version}\n date: ${e.date}\n reason: "${e.reason.replace(/"/g,`\\"`)}"`),`---`].join(`
2
+ `)}\n\n${t}\n`}function y(e,n){let r=e.map(()=>[]);for(let i=0;i<e.length;i+=1)for(let a=i+1;a<e.length;a+=1)t(e[i],e[a])>=n&&(r[i].push(a),r[a].push(i));return r}function b(e){let t=new Set,n=[];for(let r=0;r<e.length;r+=1){if(t.has(r))continue;let i=[r],a=[];for(t.add(r);i.length>0;){let n=i.pop();if(n!==void 0){a.push(n);for(let r of e[n])t.has(r)||(t.add(r),i.push(r))}}n.push(a)}return n}function x(e){let t=new Map,n=new Map,r=0;for(let i of e)for(let e of g(i))d.has(e)||(t.set(e,(t.get(e)??0)+1),n.has(e)||(n.set(e,r),r+=1));let i=[...t.entries()].sort((e,t)=>t[1]-e[1]||(n.get(e[0])??0)-(n.get(t[0])??0))[0];return i&&i[1]>1?_(i[0]):_(e.flatMap(e=>g(e)).find(e=>!d.has(e))??`lesson-group`)}async function S(e,t,n){let r=a(e.curatedDir,t),i=await o(r,`utf8`),{frontmatter:c,content:l}=e.parseFile(i),u=`group:${n}`;if(c.tags.includes(u))return;let d=new Date().toISOString(),f=(c.version??1)+1;await s(r,v({...c,tags:[...new Set([...c.tags,u])],updated:d,version:f,changelog:[...c.changelog??[],{version:f,date:d,reason:`Grouped lesson under ${n}`}]},l),`utf8`)}async function C(e,t,a,o){let s=f(a),c=n(o??i),l=(await e.list({category:`lessons`})).filter(e=>e.tags.includes(`lesson`)),u=l.map(e=>{let n=t.memoryMetaGet(e.path);if(!n||n.supersededBy!=null)return null;let i=h(n.lastAccessedAt,n.createdAt??e.created);if(i<s.safetyDays)return null;let a=r(n.confidence,n.lastAccessedAt,n.createdAt,c);return a>=s.maxConfidence||i<s.minIdleDays?null:{path:e.path,effectiveConfidence:a}}).filter(e=>e!==null).sort((e,t)=>e.effectiveConfidence-t.effectiveConfidence||e.path.localeCompare(t.path)).slice(0,s.maxPrune);if(!s.dryRun)for(let e of u)t.memoryMetaSetSuperseded(e.path,`lesson:auto-prune`);return{pruned:u.map(e=>e.path),skipped:l.length-u.length,dryRun:s.dryRun}}async function w(e,t,n){let r=p(n),i=(await e.list({category:`lessons`})).filter(e=>{if(!e.tags.includes(`lesson`)||e.tags.some(e=>e.startsWith(`group:`)))return!1;let n=t.memoryMetaGet(e.path);return n?.supersededBy==null||n===void 0});if(i.length<r.minGroupSize)return{groupsCreated:0,lessonsGrouped:0,groups:[],dryRun:r.dryRun};let a=b(y(i.map(e=>e.title),r.similarityThreshold)).filter(e=>e.length>=r.minGroupSize).map(e=>{let t=e.map(e=>i[e]).sort((e,t)=>e.path.localeCompare(t.path));return{label:x(t.map(e=>e.title)),members:t.map(e=>e.path)}}).sort((e,t)=>t.members.length-e.members.length||e.members[0].localeCompare(t.members[0])).slice(0,r.maxGroups);if(!r.dryRun&&a.length>0){for(let t of a)for(let n of t.members)await S(e,n,t.label);await e.reindexAll()}return{groupsCreated:a.length,lessonsGrouped:a.reduce((e,t)=>e+t.members.length,0),groups:a,dryRun:r.dryRun}}export{w as n,C as r,c as t};
@@ -182,6 +182,33 @@ declare class CuratedKnowledgeManager {
182
182
  }
183
183
  //#endregion
184
184
  //#region packages/server/src/index.d.ts
185
+ interface CorsOriginResolution {
186
+ allowOrigin: string | null;
187
+ warn: boolean;
188
+ }
189
+ interface ResolveCorsOriginOptions {
190
+ requestOrigin: string | undefined;
191
+ configuredOrigin: string | undefined;
192
+ allowAnyOrigin: boolean;
193
+ fallbackOrigin: string;
194
+ }
195
+ interface SlidingWindowRateLimiter {
196
+ allow: (key: string, now?: number) => boolean;
197
+ getRetryAfterMs: (key: string, now?: number) => number;
198
+ }
199
+ declare function resolveCorsOrigin({
200
+ requestOrigin,
201
+ configuredOrigin,
202
+ allowAnyOrigin,
203
+ fallbackOrigin
204
+ }: ResolveCorsOriginOptions): CorsOriginResolution;
205
+ declare function createSlidingWindowRateLimiter({
206
+ limit,
207
+ windowMs
208
+ }: {
209
+ limit: number;
210
+ windowMs: number;
211
+ }): SlidingWindowRateLimiter;
185
212
  declare function main(): Promise<void>;
186
213
  //#endregion
187
- export { CuratedKnowledgeManager, main };
214
+ export { CuratedKnowledgeManager, createSlidingWindowRateLimiter, main, resolveCorsOrigin };
@@ -1 +1 @@
1
- import{t as e}from"./curated-manager-BnP6VqvL.js";import{randomUUID as t}from"node:crypto";import{readFileSync as n}from"node:fs";import{dirname as r,resolve as i}from"node:path";import{fileURLToPath as a,pathToFileURL as o}from"node:url";import{parseArgs as s}from"node:util";import{createLogger as c,serializeError as l}from"../../core/dist/index.js";const u=`__pending__:`;function d(e){return e.startsWith(u)}function f(e){let t=e.headers[`mcp-session-id`];return Array.isArray(t)?t[0]:t}function p(e,t,n,r){e.status(t).json({jsonrpc:`2.0`,error:{code:n,message:r},id:null})}var m=class{options;runtimes=new Map;maxSessions;sessionTimeoutMs;now;constructor(e){this.options=e,this.maxSessions=e.maxSessions??8,this.sessionTimeoutMs=(e.sessionTimeoutMinutes??30)*60*1e3,this.now=e.now??(()=>Date.now())}hasSession(e){return this.runtimes.has(e)}getSessionCount(){return this.runtimes.size}async handleRequest(e,t,n=e.body){let r=f(e),i=r?this.runtimes.get(r):void 0;if(r&&!i){p(t,404,-32001,`Session not found`);return}if(!i){if(e.method!==`POST`){p(t,400,-32e3,`Session required`);return}if(i=await this.createRuntime(t),!i)return}await this.withRuntimeLock(i,async()=>{await i.transport.handleRequest(e,t,n),i.lastAccessAt=this.now();let r=i.transport.sessionId??i.id;e.method!==`DELETE`&&!d(r)&&this.options.onSessionActivity?.(r),e.method===`DELETE`&&!d(r)&&await this.closeSession(r,{closeTransport:!1})})}async closeExpiredSessions(){let e=[...this.runtimes.values()].filter(e=>this.now()-e.lastAccessAt>=this.sessionTimeoutMs).map(e=>e.id);for(let t of e)await this.closeSession(t);return e.length}async closeSession(e,t={}){let n=this.runtimes.get(e);return n?(this.runtimes.delete(e),t.notifySessionEnd!==!1&&!d(e)&&this.options.onSessionEnd?.(e),t.closeTransport!==!1&&await n.transport.close().catch(()=>void 0),await n.server.close().catch(()=>void 0),!0):!1}async closeAll(){let e=[...this.runtimes.keys()];for(let t of e)await this.closeSession(t)}async createRuntime(e){if(await this.closeExpiredSessions(),this.runtimes.size>=this.maxSessions){p(e,503,-32003,`Session capacity reached`);return}let n=this.now(),r=await this.options.createServer(),i={id:`${u}${t()}`,transport:void 0,createdAt:n,lastAccessAt:n,server:r,requestChain:Promise.resolve()},a=this.options.createTransport({sessionIdGenerator:()=>t(),onsessioninitialized:async e=>{this.runtimes.delete(i.id),i.id=e,this.runtimes.set(e,i),this.options.onSessionStart?.(e)},onsessionclosed:async e=>{e&&await this.closeSession(e,{closeTransport:!1})}});return i.transport=a,a.onclose=()=>{let e=i.transport.sessionId??i.id;this.closeSession(e,{closeTransport:!1})},this.runtimes.set(i.id,i),await r.connect(a),i}async withRuntimeLock(e,t){let n=e.requestChain,r;e.requestChain=new Promise(e=>{r=e}),await n;try{await t()}finally{r()}}};function h(e){let t=e.includes(`T`)?e:`${e.replace(` `,`T`)}Z`;return Date.parse(t)}var g=class{stateStore;options;gcTimer=null;constructor(e,t={}){this.stateStore=e,this.options=t}onSessionStart(e,t){this.stateStore.sessionCreate(e,t)}onSessionActivity(e){this.stateStore.sessionTouch(e)}onSessionEnd(e){this.stateStore.sessionDelete(e)}startGC(){if(this.gcTimer)return;let e=(this.options.gcIntervalMinutes??5)*60*1e3;this.gcTimer=setInterval(()=>{this.runGC()},e),this.gcTimer.unref()}runGC(){let e=this.getStaleSessionIds();for(let t of e)this.options.onBeforeSessionDelete?.(t),this.stateStore.sessionDelete(t);return e.length}stop(){this.gcTimer&&=(clearInterval(this.gcTimer),null)}getActiveSessions(){return this.stateStore.sessionList().length}listSessions(){return this.stateStore.sessionList()}getStaleSessionIds(e=Date.now()){let t=(this.options.staleTimeoutMinutes??30)*60*1e3;return this.stateStore.sessionList().filter(n=>{let r=h(n.lastActivity);return Number.isFinite(r)&&e-r>=t}).map(e=>e.sessionId)}};function _(){try{let e=i(r(a(import.meta.url)),`..`,`..`,`..`,`package.json`);return JSON.parse(n(e,`utf-8`)).version??`0.0.0`}catch{return`0.0.0`}}const v=c(`server`);function y(){return process.env.AIKIT_TRANSPORT?process.env.AIKIT_TRANSPORT:process.stdin.isTTY?`http`:`stdio`}function b(){let e=process.argv[1];if(!e)return!1;try{return import.meta.url===o(e).href}catch{return!1}}function x(e){let t=e.headers[`mcp-session-id`];return Array.isArray(t)?t[0]:t}function S(e,t){let n=process.env[e];if(!n)return t;let r=Number.parseInt(n,10);return Number.isFinite(r)&&r>0?r:t}function C(){return b()?s({allowPositionals:!0,options:{transport:{type:`string`,default:y()},port:{type:`string`,default:process.env.AIKIT_PORT??`3210`}}}).values:{transport:y(),port:process.env.AIKIT_PORT??`3210`}}async function w(){let e=_(),n=C();process.on(`unhandledRejection`,e=>{v.error(`Unhandled rejection`,l(e))}),process.on(`uncaughtException`,e=>{v.error(`Uncaught exception — exiting`,l(e)),process.exit(1)});let r=e=>{e.then(async()=>{try{let{shouldRunStartupPrune:e,prune:t,markPruneRun:n}=await import(`../../tools/dist/index.js`);if(!e())return;let r=await t({});n(),r.totalBytesFreed>0&&v.info(`Storage maintenance complete`,{forgeOrphans:r.forgeGroundOrphans.count,legacyLance:r.legacyLance.count,bytesFreed:r.totalBytesFreed})}catch(e){v.warn(`Startup maintenance failed (non-critical)`,l(e))}}).catch(()=>{})};if(v.info(`Starting MCP AI Kit server`,{version:e}),n.transport===`http`){let[{default:e},{loadConfig:i,resolveIndexMode:a},{registerDashboardRoutes:o,resolveDashboardDir:s},{registerSettingsRoutes:c,resolveSettingsDir:u},{createSettingsRouter:d},{authMiddleware:f,getOrCreateToken:p}]=await Promise.all([import(`express`),import(`./config-DAnAxrUW.js`),import(`./dashboard-static-FmfoS46e.js`),import(`./settings-static-BtvyIrza.js`),import(`./routes-CR3fI-HJ.js`),import(`./auth-BfqgawfR.js`).then(e=>e.t)]),h=i();v.info(`Config loaded`,{sourceCount:h.sources.length,storePath:h.store.path});let _=e();_.use(e.json());let y=Number(n.port),b=S(`AIKIT_HTTP_MAX_SESSIONS`,8),C=S(`AIKIT_HTTP_SESSION_TIMEOUT_MINUTES`,30),w=S(`AIKIT_HTTP_SESSION_GC_INTERVAL_MINUTES`,5);_.use((e,t,n)=>{if(t.setHeader(`Access-Control-Allow-Origin`,process.env.AIKIT_CORS_ORIGIN??`http://localhost:${y}`),t.setHeader(`Access-Control-Allow-Methods`,`GET, POST, PUT, PATCH, DELETE, OPTIONS`),t.setHeader(`Access-Control-Allow-Headers`,`Content-Type, Authorization, Mcp-Session-Id, Mcp-Protocol-Version, Last-Event-ID`),t.setHeader(`Access-Control-Expose-Headers`,`Mcp-Session-Id`),e.method===`OPTIONS`){t.status(204).end();return}n()});let T=p();console.error(`[aikit] Auth token: ~/.aikit/token`),_.use(f(T)),o(_,s(),v);let E=new Date().toISOString();_.use(`/settings/api`,d({log:v,mcpInfo:()=>({transport:`http`,port:y,pid:process.pid,startedAt:E})})),c(_,u(),v),_.get(`/health`,(e,t)=>{t.json({status:`ok`})});let D=!1,O=null,k=null,A=null,j=null,M=null,N=null,P=null,F=Promise.resolve(),I=async(e,n)=>{if(!D||!A||!j){n.status(503).json({jsonrpc:`2.0`,error:{code:-32603,message:`Server initializing — please retry in a few seconds`},id:null});return}let r=F,i;F=new Promise(e=>{i=e}),await r;try{let r=x(e);if(!N){if(r){n.status(404).json({jsonrpc:`2.0`,error:{code:-32001,message:`Session not found`},id:null});return}let e=new j({sessionIdGenerator:()=>t(),onsessioninitialized:async e=>{P=e,k?.onSessionStart(e,{transport:`http`})},onsessionclosed:async e=>{e&&k?.onSessionEnd(e),P=null}});e.onclose=()=>{N===e&&(N=null),P===e.sessionId&&(P=null)},N=e,await A.connect(e)}let i=N;await i.handleRequest(e,n,e.body),e.method!==`DELETE`&&(!r&&i.sessionId?(P=i.sessionId,k?.onSessionStart(i.sessionId,{transport:`http`}),k?.onSessionActivity(i.sessionId)):r&&k?.onSessionActivity(r))}catch(e){if(v.error(`MCP handler error`,l(e)),!n.headersSent){let t=e instanceof Error?e.message:String(e),r=t.includes(`Not Acceptable`);n.status(r?406:500).json({jsonrpc:`2.0`,error:{code:r?-32e3:-32603,message:r?t:`Internal server error`},id:null})}}finally{i()}},L=async(e,t)=>{let n=x(e);if(M&&(!N||n!==P)){await M.handleRequest(e,t,e.body);return}await I(e,t)};_.post(`/mcp`,L),_.get(`/mcp`,L),_.delete(`/mcp`,L);let R=_.listen(y,`127.0.0.1`,()=>{v.info(`MCP server listening`,{url:`http://127.0.0.1:${y}/mcp`,port:y}),setTimeout(async()=>{try{let[{createLazyServer:e,createMcpServer:t,ALL_TOOL_NAMES:n},{StreamableHTTPServerTransport:i},{checkForUpdates:o,autoUpgradeScaffold:s}]=await Promise.all([import(`./server-BaMsrcyc.js`),import(`@modelcontextprotocol/sdk/server/streamableHttp.js`),import(`./version-check-BgHzxxCW.js`)]);o(),s();let c=a(h),u=e(h,c);A=u.server,j=i,D=!0,v.info(`MCP server configured (lazy — AI Kit initializing in background)`,{toolCount:n.length,resourceCount:2}),u.startInit(),u.ready.then(()=>{if(!u.aikit)throw Error(`AI Kit components are not available after initialization`);k=new g(u.aikit.stateStore,{staleTimeoutMinutes:C,gcIntervalMinutes:w,onBeforeSessionDelete:e=>{if(P===e&&N){let e=N;N=null,P=null,e.close().catch(()=>void 0)}M?.closeSession(e,{notifySessionEnd:!1})}}),M=new m({createServer:()=>{if(!u.aikit)throw Error(`AI Kit components are not available after initialization`);return t(u.aikit,h)},createTransport:e=>new i(e),maxSessions:b,sessionTimeoutMinutes:C,onSessionStart:e=>k?.onSessionStart(e,{transport:`http`}),onSessionActivity:e=>k?.onSessionActivity(e),onSessionEnd:e=>k?.onSessionEnd(e)}),k.startGC(),P&&(k.onSessionStart(P,{transport:`http`}),k.onSessionActivity(P)),v.info(`HTTP session runtime ready`,{maxSessions:b,sessionTimeoutMinutes:C,gcIntervalMinutes:w})}).catch(e=>v.error(`Failed to start session manager`,l(e))),c===`auto`?u.ready.then(async()=>{try{let e=h.sources.map(e=>e.path).join(`, `);v.info(`Running initial index`,{sourcePaths:e}),await u.runInitialIndex(),v.info(`Initial index complete`)}catch(e){v.error(`Initial index failed; will retry on aikit_reindex`,l(e))}}).catch(e=>v.error(`AI Kit init or indexing failed`,l(e))):c===`smart`?u.ready.then(async()=>{try{if(!u.aikit)throw Error(`AI Kit components are not available after initialization`);let{SmartIndexScheduler:e}=await import(`../../indexer/dist/index.js`),t=new e(u.aikit.indexer,h,u.aikit.store),n=u.aikit.store;O=t,t.start(),n.onBeforeClose&&n.onBeforeClose(()=>t.stop()),u.setSmartScheduler(t),v.info(`Smart index scheduler started (HTTP mode)`)}catch(e){v.error(`Failed to start smart index scheduler`,l(e))}}).catch(e=>v.error(`AI Kit initialization failed`,l(e))):(u.ready.catch(e=>v.error(`AI Kit initialization failed`,l(e))),v.info(`Initial full indexing skipped in HTTP mode`,{indexMode:c})),r(u.ready)}catch(e){v.error(`Failed to load server modules`,l(e))}},100)}),z=async e=>{v.info(`Shutdown signal received`,{signal:e}),O?.stop(),k?.stop(),await M?.closeAll().catch(()=>void 0),P&&k?.onSessionEnd(P),N&&(await N.close().catch(()=>void 0),N=null,P=null),R.close(),A&&await A.close(),process.exit(0)};process.on(`SIGINT`,()=>z(`SIGINT`)),process.on(`SIGTERM`,()=>z(`SIGTERM`))}else{let[{loadConfig:e,reconfigureForWorkspace:t,resolveIndexMode:n},{createLazyServer:i},{checkForUpdates:o,autoUpgradeScaffold:s},{RootsListChangedNotificationSchema:c}]=await Promise.all([import(`./config-DAnAxrUW.js`),import(`./server-BaMsrcyc.js`),import(`./version-check-BgHzxxCW.js`),import(`@modelcontextprotocol/sdk/types.js`)]),u=e();v.info(`Config loaded`,{sourceCount:u.sources.length,storePath:u.store.path}),o(),s();let d=n(u),f=i(u,d),{server:p,startInit:m,ready:h,runInitialIndex:g}=f,{StdioServerTransport:_}=await import(`@modelcontextprotocol/sdk/server/stdio.js`),y=new _;await p.connect(y),v.info(`MCP server started`,{transport:`stdio`});let b=e=>{if(e.length===0)return!1;let n=e[0].uri,r=n.startsWith(`file://`)?a(n):n;return v.info(`MCP roots resolved`,{rootUri:n,rootPath:r,rootCount:e.length}),t(u,r),u.allRoots=e.map(e=>{let t=e.uri;return t.startsWith(`file://`)?a(t):t}),!0},x=!1;try{x=b((await p.server.listRoots()).roots),x||v.info(`No MCP roots yet; waiting for roots/list_changed notification`)}catch(e){v.warn(`MCP roots/list not supported by client; using cwd fallback`,{cwd:process.cwd(),...l(e)}),x=!0}x||=await new Promise(e=>{let t=setTimeout(()=>{v.warn(`Timed out waiting for MCP roots/list_changed; using cwd fallback`,{cwd:process.cwd()}),e(!1)},5e3);p.server.setNotificationHandler(c,async()=>{clearTimeout(t);try{e(b((await p.server.listRoots()).roots))}catch(t){v.warn(`roots/list retry failed after notification`,l(t)),e(!1)}})}),m();let S=null,C=()=>{S&&clearTimeout(S),S=setTimeout(async()=>{v.info(`Auto-shutdown: no activity for 30 minutes — shutting down gracefully`);try{let e=f.aikit;e&&await Promise.all([e.embedder.shutdown?.().catch(()=>{})??Promise.resolve(),e.graphStore.close().catch(()=>{}),e.store.close().catch(()=>{})])}catch{}process.exit(0)},18e5),S.unref&&S.unref()};C(),process.stdin.on(`data`,()=>C()),h.catch(e=>{v.error(`Initialization failed — server will continue with limited tools`,l(e))}),d===`auto`?g().catch(e=>v.error(`Initial index failed`,l(e))):d===`smart`?h.then(async()=>{try{if(!f.aikit)throw Error(`AI Kit components are not available after initialization`);let{SmartIndexScheduler:e}=await import(`../../indexer/dist/index.js`),t=new e(f.aikit.indexer,u,f.aikit.store),n=f.aikit.store;t.start(),n.onBeforeClose&&n.onBeforeClose(()=>t.stop()),f.setSmartScheduler(t),v.info(`Smart index scheduler started (stdio mode)`)}catch(e){v.error(`Failed to start smart index scheduler`,l(e))}}).catch(e=>v.error(`AI Kit init failed for smart scheduler`,l(e))):v.warn(`Initial full indexing skipped; use aikit_reindex to index manually`,{indexMode:d}),r(h)}}export{e as CuratedKnowledgeManager,w as main};
1
+ import{r as e}from"./replay-interceptor-CGLyom5f.js";import{t}from"./curated-manager-D1u5qOwK.js";import{randomUUID as n}from"node:crypto";import{readFileSync as r}from"node:fs";import{dirname as i,resolve as a}from"node:path";import{fileURLToPath as o,pathToFileURL as s}from"node:url";import{parseArgs as c}from"node:util";import{createLogger as l,serializeError as u}from"../../core/dist/index.js";const d=`__pending__:`;function f(e){return e.startsWith(d)}function p(e){let t=e.headers[`mcp-session-id`];return Array.isArray(t)?t[0]:t}function m(e,t,n,r){e.status(t).json({jsonrpc:`2.0`,error:{code:n,message:r},id:null})}var h=class{options;runtimes=new Map;maxSessions;sessionTimeoutMs;now;constructor(e){this.options=e,this.maxSessions=e.maxSessions??8,this.sessionTimeoutMs=(e.sessionTimeoutMinutes??30)*60*1e3,this.now=e.now??(()=>Date.now())}hasSession(e){return this.runtimes.has(e)}getSessionCount(){return this.runtimes.size}async handleRequest(e,t,n=e.body){let r=p(e),i=r?this.runtimes.get(r):void 0;if(r&&!i){m(t,404,-32001,`Session not found`);return}if(!i){if(e.method!==`POST`){m(t,400,-32e3,`Session required`);return}if(i=await this.createRuntime(t),!i)return}await this.withRuntimeLock(i,async()=>{await i.transport.handleRequest(e,t,n),i.lastAccessAt=this.now();let r=i.transport.sessionId??i.id;e.method!==`DELETE`&&!f(r)&&this.options.onSessionActivity?.(r),e.method===`DELETE`&&!f(r)&&await this.closeSession(r,{closeTransport:!1})})}async closeExpiredSessions(){let e=[...this.runtimes.values()].filter(e=>this.now()-e.lastAccessAt>=this.sessionTimeoutMs).map(e=>e.id);for(let t of e)await this.closeSession(t);return e.length}async closeSession(e,t={}){let n=this.runtimes.get(e);return n?(this.runtimes.delete(e),t.notifySessionEnd!==!1&&!f(e)&&this.options.onSessionEnd?.(e),t.closeTransport!==!1&&await n.transport.close().catch(()=>void 0),await n.server.close().catch(()=>void 0),!0):!1}async closeAll(){let e=[...this.runtimes.keys()];for(let t of e)await this.closeSession(t)}async createRuntime(e){if(await this.closeExpiredSessions(),this.runtimes.size>=this.maxSessions){m(e,503,-32003,`Session capacity reached`);return}let t=this.now(),r=await this.options.createServer(),i={id:`${d}${n()}`,transport:void 0,createdAt:t,lastAccessAt:t,server:r,requestChain:Promise.resolve()},a=this.options.createTransport({sessionIdGenerator:()=>n(),onsessioninitialized:async e=>{this.runtimes.delete(i.id),i.id=e,this.runtimes.set(e,i),this.options.onSessionStart?.(e)},onsessionclosed:async e=>{e&&await this.closeSession(e,{closeTransport:!1})}});return i.transport=a,a.onclose=()=>{let e=i.transport.sessionId??i.id;this.closeSession(e,{closeTransport:!1})},this.runtimes.set(i.id,i),await r.connect(a),i}async withRuntimeLock(e,t){let n=e.requestChain,r;e.requestChain=new Promise(e=>{r=e}),await n;try{await t()}finally{r()}}};function g(e){let t=e.includes(`T`)?e:`${e.replace(` `,`T`)}Z`;return Date.parse(t)}var _=class{stateStore;options;gcTimer=null;constructor(e,t={}){this.stateStore=e,this.options=t}onSessionStart(e,t){this.stateStore.sessionCreate(e,t)}onSessionActivity(e){this.stateStore.sessionTouch(e)}onSessionEnd(e){this.stateStore.sessionDelete(e),Promise.resolve(this.options.onSessionEndMaintenance?.(e)).catch(()=>{})}startGC(){if(this.gcTimer)return;let e=(this.options.gcIntervalMinutes??5)*60*1e3;this.gcTimer=setInterval(()=>{this.runGC()},e),this.gcTimer.unref()}runGC(){let e=this.getStaleSessionIds();for(let t of e)this.options.onBeforeSessionDelete?.(t),Promise.resolve(this.options.onSessionEndMaintenance?.(t)).catch(()=>{}),this.stateStore.sessionDelete(t);return e.length}stop(){this.gcTimer&&=(clearInterval(this.gcTimer),null)}getActiveSessions(){return this.stateStore.sessionList().length}listSessions(){return this.stateStore.sessionList()}getStaleSessionIds(e=Date.now()){let t=(this.options.staleTimeoutMinutes??30)*60*1e3;return this.stateStore.sessionList().filter(n=>{let r=g(n.lastActivity);return Number.isFinite(r)&&e-r>=t}).map(e=>e.sessionId)}};function v(){try{let e=a(i(o(import.meta.url)),`..`,`..`,`..`,`package.json`);return JSON.parse(r(e,`utf-8`)).version??`0.0.0`}catch{return`0.0.0`}}const y=l(`server`),b=/^https?:\/\/(localhost|127\.0\.0\.1)(:\d+)?$/i;function x({requestOrigin:e,configuredOrigin:t,allowAnyOrigin:n,fallbackOrigin:r}){let i=t??r;return i===`*`?n?{allowOrigin:`*`,warn:!1}:e?b.test(e)?{allowOrigin:e,warn:!1}:{allowOrigin:null,warn:!0}:{allowOrigin:r,warn:!1}:{allowOrigin:i,warn:!1}}function S({limit:e,windowMs:t}){let n=new Map,r=(e,r)=>{let i=r-t,a=n.get(e)?.filter(e=>e>i)??[];return a.length===0?(n.delete(e),[]):(n.set(e,a),a)};return{allow(t,i=Date.now()){let a=r(t,i);return a.length>=e?!1:(a.push(i),n.set(t,a),!0)},getRetryAfterMs(n,i=Date.now()){let a=r(n,i);return a.length<e?0:Math.max(0,a[0]+t-i)}}}function C(){return process.env.AIKIT_TRANSPORT?process.env.AIKIT_TRANSPORT:process.stdin.isTTY?`http`:`stdio`}function w(){let e=process.argv[1];if(!e)return!1;try{return import.meta.url===s(e).href}catch{return!1}}function T(e){let t=e.headers[`mcp-session-id`];return Array.isArray(t)?t[0]:t}function E(e,t){let n=process.env[e];if(!n)return t;let r=Number.parseInt(n,10);return Number.isFinite(r)&&r>0?r:t}function D(){return w()?c({allowPositionals:!0,options:{transport:{type:`string`,default:C()},port:{type:`string`,default:process.env.AIKIT_PORT??`3210`}}}).values:{transport:C(),port:process.env.AIKIT_PORT??`3210`}}function O(e){return`## Context\n${e.context}\n\n## Insight\n${e.insight}\n\n## Evidence\n${e.evidence}`}function k(t){e(e=>{(async()=>{let n=t();if(!n)return;let{jaccardSimilarity:r}=await import(`./supersession-9edUDEQ8.js`).then(e=>e.o),i=await n.curated.list({category:`lessons`});for(let t of e)i.some(e=>r(t.title,e.title)>.6)||(await n.curated.remember(t.title,O(t),`lessons`,[`lesson`,`auto-observed`,`detector:${t.detector}`]),i.push({path:`lessons/${t.title}`,title:t.title,category:`lessons`,tags:[`lesson`,`auto-observed`,`detector:${t.detector}`],version:1,created:new Date().toISOString(),updated:new Date().toISOString(),contentPreview:t.insight.slice(0,200)}))})().catch(()=>{})})}async function A(){let e=v(),t=D();process.on(`unhandledRejection`,e=>{y.error(`Unhandled rejection`,u(e))}),process.on(`uncaughtException`,e=>{y.error(`Uncaught exception — exiting`,u(e)),process.exit(1)});let r=(e,t)=>{e.then(async()=>{try{let{markPromoteRun:e,markPruneRun:n,prune:r,shouldRunStartupPrune:i,shouldRunWeeklyPromote:a}=await import(`../../tools/dist/index.js`),o=t();if(!o)return;if(i()){let e=await r({});n(),e.totalBytesFreed>0&&y.info(`Storage maintenance complete`,{forgeOrphans:e.forgeGroundOrphans.count,legacyLance:e.legacyLance.count,bytesFreed:e.totalBytesFreed});let{groupLessons:t,pruneLessons:i}=await import(`./evolution-DJhTM6nu.js`).then(e=>e.t),a=await i(o.curated,o.stateStore,{dryRun:!1});a.pruned.length>0&&y.info(`Startup lesson prune complete`,{pruned:a.pruned.length});let s=await t(o.curated,o.stateStore,{dryRun:!1});(s.groupsCreated>0||s.lessonsGrouped>0)&&y.info(`Startup lesson grouping complete`,{groupsCreated:s.groupsCreated,lessonsGrouped:s.lessonsGrouped})}if(a()){let{DEFAULT_PROMOTE_CONFIG:t,collectWorkspaceLessons:n,getGlobalCuratedDir:r,promoteLessons:i,scanForDuplicates:a}=await import(`./promotion-OY53YCsT.js`).then(e=>e.o),{CuratedKnowledgeManager:s}=await import(`./curated-manager-D1u5qOwK.js`).then(e=>e.n),c=o.curated,l=new s(r(),c.store,c.embedder),u=await n(),d={...t,dryRun:!1},f=await i(a(u,d),l,d);e(),f.promoted.length>0&&y.info(`Weekly lesson promotion complete`,{promoted:f.promoted.length,candidates:f.candidates.length})}}catch(e){y.warn(`Startup maintenance failed (non-critical)`,u(e))}}).catch(()=>{})};if(y.info(`Starting MCP AI Kit server`,{version:e}),t.transport===`http`){let[{default:e},{loadConfig:i,resolveIndexMode:a},{registerDashboardRoutes:o,resolveDashboardDir:s},{registerSettingsRoutes:c,resolveSettingsDir:l},{createSettingsRouter:d},{authMiddleware:f,getOrCreateToken:p}]=await Promise.all([import(`express`),import(`./config-jGZ91cRx.js`),import(`./dashboard-static-FmfoS46e.js`),import(`./settings-static-BtvyIrza.js`),import(`./routes-CR3fI-HJ.js`),import(`./auth-Bz5dmZgR.js`).then(e=>e.t)]),m=i();y.info(`Config loaded`,{sourceCount:m.sources.length,storePath:m.store.path});let g=e();g.use(e.json({limit:`1mb`}));let v=Number(t.port),b=`http://localhost:${v}`,C=process.env.AIKIT_CORS_ORIGIN??b,w=process.env.AIKIT_ALLOW_ANY_ORIGIN===`true`,D=E(`AIKIT_HTTP_MAX_SESSIONS`,8),O=E(`AIKIT_HTTP_SESSION_TIMEOUT_MINUTES`,30),A=E(`AIKIT_HTTP_SESSION_GC_INTERVAL_MINUTES`,5),j=S({limit:100,windowMs:6e4}),M=!1;g.use((e,t,n)=>{let r=Array.isArray(e.headers.origin)?e.headers.origin[0]:e.headers.origin,i=x({requestOrigin:r,configuredOrigin:C,allowAnyOrigin:w,fallbackOrigin:b});if(i.warn&&!M&&(M=!0,y.warn(`Rejected non-local CORS origin while AIKIT_CORS_ORIGIN=*`,{origin:r,allowAnyOriginEnv:`AIKIT_ALLOW_ANY_ORIGIN=true`})),r&&!i.allowOrigin){t.status(403).json({error:`Origin not allowed`});return}if(i.allowOrigin&&t.setHeader(`Access-Control-Allow-Origin`,i.allowOrigin),t.setHeader(`Access-Control-Allow-Methods`,`GET, POST, PUT, PATCH, DELETE, OPTIONS`),t.setHeader(`Access-Control-Allow-Headers`,`Content-Type, Authorization, Mcp-Session-Id, Mcp-Protocol-Version, Last-Event-ID`),t.setHeader(`Access-Control-Expose-Headers`,`Mcp-Session-Id`),e.method===`OPTIONS`){t.status(204).end();return}n()});let N=p();console.error(`[aikit] Auth token: ~/.aikit/token`),g.use(f(N)),g.use(`/mcp`,(e,t,n)=>{let r=T(e)??e.ip??e.socket.remoteAddress??`anonymous`;if(j.allow(r)){n();return}let i=Math.max(1,Math.ceil(j.getRetryAfterMs(r)/1e3));t.setHeader(`Retry-After`,String(i)),t.status(429).json({jsonrpc:`2.0`,error:{code:-32003,message:`Rate limit exceeded`},id:null})}),o(g,s(),y);let P=new Date().toISOString();g.use(`/settings/api`,d({log:y,mcpInfo:()=>({transport:`http`,port:v,pid:process.pid,startedAt:P})})),c(g,l(),y),g.get(`/health`,(e,t)=>{t.json({status:`ok`})});let F=!1,I=null,L=null,R=null,z=null,B=null,V=null,H=null,U=Promise.resolve(),W=async(e,t)=>{if(!F||!R||!z){t.status(503).json({jsonrpc:`2.0`,error:{code:-32603,message:`Server initializing — please retry in a few seconds`},id:null});return}let r=U,i;U=new Promise(e=>{i=e}),await r;try{let r=T(e);if(!V){if(r){t.status(404).json({jsonrpc:`2.0`,error:{code:-32001,message:`Session not found`},id:null});return}let e=new z({sessionIdGenerator:()=>n(),onsessioninitialized:async e=>{H=e,L?.onSessionStart(e,{transport:`http`})},onsessionclosed:async e=>{e&&L?.onSessionEnd(e),H=null}});e.onclose=()=>{V===e&&(V=null),H===e.sessionId&&(H=null)},V=e,await R.connect(e)}let i=V;await i.handleRequest(e,t,e.body),e.method!==`DELETE`&&(!r&&i.sessionId?(H=i.sessionId,L?.onSessionStart(i.sessionId,{transport:`http`}),L?.onSessionActivity(i.sessionId)):r&&L?.onSessionActivity(r))}catch(e){if(y.error(`MCP handler error`,u(e)),!t.headersSent){let n=e instanceof Error?e.message:String(e),r=n.includes(`Not Acceptable`);t.status(r?406:500).json({jsonrpc:`2.0`,error:{code:r?-32e3:-32603,message:r?n:`Internal server error`},id:null})}}finally{i()}},G=async(e,t)=>{let n=T(e);if(B&&(!V||n!==H)){await B.handleRequest(e,t,e.body);return}await W(e,t)};g.post(`/mcp`,G),g.get(`/mcp`,G),g.delete(`/mcp`,G);let K=g.listen(v,`127.0.0.1`,()=>{y.info(`MCP server listening`,{url:`http://127.0.0.1:${v}/mcp`,port:v}),setTimeout(async()=>{try{let[{createLazyServer:e,createMcpServer:t,ALL_TOOL_NAMES:n},{StreamableHTTPServerTransport:i},{checkForUpdates:o,autoUpgradeScaffold:s}]=await Promise.all([import(`./server-CtFr8YsZ.js`),import(`@modelcontextprotocol/sdk/server/streamableHttp.js`),import(`./version-check-D_uN0n0Y.js`)]);o(),s();let c=a(m),l=e(m,c);R=l.server,z=i,F=!0,y.info(`MCP server configured (lazy — AI Kit initializing in background)`,{toolCount:n.length,resourceCount:2}),l.startInit(),l.ready.then(()=>{if(!l.aikit)throw Error(`AI Kit components are not available after initialization`);L=new _(l.aikit.stateStore,{staleTimeoutMinutes:O,gcIntervalMinutes:A,onBeforeSessionDelete:e=>{if(H===e&&V){let e=V;V=null,H=null,e.close().catch(()=>void 0)}B?.closeSession(e,{notifySessionEnd:!1})},onSessionEndMaintenance:async()=>{if(!l.aikit?.curated||!l.aikit?.stateStore)return;let{pruneLessons:e}=await import(`./evolution-DJhTM6nu.js`).then(e=>e.t),t=await e(l.aikit.curated,l.aikit.stateStore,{dryRun:!1});t.pruned.length>0&&y.info(`Session-end lesson prune`,{pruned:t.pruned.length})}}),B=new h({createServer:()=>{if(!l.aikit)throw Error(`AI Kit components are not available after initialization`);return t(l.aikit,m)},createTransport:e=>new i(e),maxSessions:D,sessionTimeoutMinutes:O,onSessionStart:e=>L?.onSessionStart(e,{transport:`http`}),onSessionActivity:e=>L?.onSessionActivity(e),onSessionEnd:e=>L?.onSessionEnd(e)}),L.startGC(),H&&(L.onSessionStart(H,{transport:`http`}),L.onSessionActivity(H)),k(()=>l.aikit?{curated:l.aikit.curated,stateStore:l.aikit.stateStore}:null),y.info(`HTTP session runtime ready`,{maxSessions:D,sessionTimeoutMinutes:O,gcIntervalMinutes:A})}).catch(e=>y.error(`Failed to start session manager`,u(e))),c===`auto`?l.ready.then(async()=>{try{let e=m.sources.map(e=>e.path).join(`, `);y.info(`Running initial index`,{sourcePaths:e}),await l.runInitialIndex(),y.info(`Initial index complete`)}catch(e){y.error(`Initial index failed; will retry on aikit_reindex`,u(e))}}).catch(e=>y.error(`AI Kit init or indexing failed`,u(e))):c===`smart`?l.ready.then(async()=>{try{if(!l.aikit)throw Error(`AI Kit components are not available after initialization`);let{SmartIndexScheduler:e}=await import(`../../indexer/dist/index.js`),t=new e(l.aikit.indexer,m,l.aikit.store),n=l.aikit.store;I=t,t.start(),n.onBeforeClose&&n.onBeforeClose(()=>t.stop()),l.setSmartScheduler(t),y.info(`Smart index scheduler started (HTTP mode)`)}catch(e){y.error(`Failed to start smart index scheduler`,u(e))}}).catch(e=>y.error(`AI Kit initialization failed`,u(e))):(l.ready.catch(e=>y.error(`AI Kit initialization failed`,u(e))),y.info(`Initial full indexing skipped in HTTP mode`,{indexMode:c})),r(l.ready,()=>l.aikit?{curated:l.aikit.curated,stateStore:l.aikit.stateStore}:null)}catch(e){y.error(`Failed to load server modules`,u(e))}},100)}),q=async e=>{y.info(`Shutdown signal received`,{signal:e}),I?.stop(),L?.stop(),await B?.closeAll().catch(()=>void 0),H&&L?.onSessionEnd(H),V&&(await V.close().catch(()=>void 0),V=null,H=null),K.close(),R&&await R.close(),process.exit(0)};process.on(`SIGINT`,()=>q(`SIGINT`)),process.on(`SIGTERM`,()=>q(`SIGTERM`))}else{let[{loadConfig:e,reconfigureForWorkspace:t,resolveIndexMode:n},{createLazyServer:i},{checkForUpdates:a,autoUpgradeScaffold:s},{RootsListChangedNotificationSchema:c}]=await Promise.all([import(`./config-jGZ91cRx.js`),import(`./server-CtFr8YsZ.js`),import(`./version-check-D_uN0n0Y.js`),import(`@modelcontextprotocol/sdk/types.js`)]),l=e();y.info(`Config loaded`,{sourceCount:l.sources.length,storePath:l.store.path}),a(),s();let d=n(l),f=i(l,d),{server:p,startInit:m,ready:h,runInitialIndex:g}=f,{StdioServerTransport:_}=await import(`@modelcontextprotocol/sdk/server/stdio.js`),v=new _;await p.connect(v),y.info(`MCP server started`,{transport:`stdio`});let b=e=>{if(e.length===0)return!1;let n=e[0].uri,r=n.startsWith(`file://`)?o(n):n;return y.info(`MCP roots resolved`,{rootUri:n,rootPath:r,rootCount:e.length}),t(l,r),l.allRoots=e.map(e=>{let t=e.uri;return t.startsWith(`file://`)?o(t):t}),!0},x=!1;try{x=b((await p.server.listRoots()).roots),x||y.info(`No MCP roots yet; waiting for roots/list_changed notification`)}catch(e){y.warn(`MCP roots/list not supported by client; using cwd fallback`,{cwd:process.cwd(),...u(e)}),x=!0}x||=await new Promise(e=>{let t=setTimeout(()=>{y.warn(`Timed out waiting for MCP roots/list_changed; using cwd fallback`,{cwd:process.cwd()}),e(!1)},5e3);p.server.setNotificationHandler(c,async()=>{clearTimeout(t);try{e(b((await p.server.listRoots()).roots))}catch(t){y.warn(`roots/list retry failed after notification`,u(t)),e(!1)}})}),m();let S=null,C=()=>{S&&clearTimeout(S),S=setTimeout(async()=>{y.info(`Auto-shutdown: no activity for 30 minutes — shutting down gracefully`);try{let e=f.aikit;e&&await Promise.all([e.embedder.shutdown?.().catch(()=>{})??Promise.resolve(),e.graphStore.close().catch(()=>{}),e.store.close().catch(()=>{})])}catch{}process.exit(0)},18e5),S.unref&&S.unref()};C(),process.stdin.on(`data`,()=>C()),h.catch(e=>{y.error(`Initialization failed — server will continue with limited tools`,u(e))}),h.then(()=>{k(()=>f.aikit?{curated:f.aikit.curated,stateStore:f.aikit.stateStore}:null)}).catch(()=>{}),d===`auto`?g().catch(e=>y.error(`Initial index failed`,u(e))):d===`smart`?h.then(async()=>{try{if(!f.aikit)throw Error(`AI Kit components are not available after initialization`);let{SmartIndexScheduler:e}=await import(`../../indexer/dist/index.js`),t=new e(f.aikit.indexer,l,f.aikit.store),n=f.aikit.store;t.start(),n.onBeforeClose&&n.onBeforeClose(()=>t.stop()),f.setSmartScheduler(t),y.info(`Smart index scheduler started (stdio mode)`)}catch(e){y.error(`Failed to start smart index scheduler`,u(e))}}).catch(e=>y.error(`AI Kit init failed for smart scheduler`,u(e))):y.warn(`Initial full indexing skipped; use aikit_reindex to index manually`,{indexMode:d}),r(h,()=>f.aikit?{curated:f.aikit.curated,stateStore:f.aikit.stateStore}:null)}}export{t as CuratedKnowledgeManager,S as createSlidingWindowRateLimiter,A as main,x as resolveCorsOrigin};
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ const e={confirmIncrement:10,contradictDecrement:20,weeklyDecay:2,implicitUseIncrement:3,staleThreshold:30,staleDays:21,decayFloor:10,autoArchiveDays:30,archiveThreshold:20},t=`lesson:auto-archive`;function n(t){return{confirmIncrement:Math.max(0,Math.trunc(t?.confirmIncrement??e.confirmIncrement)),contradictDecrement:Math.max(0,Math.trunc(t?.contradictDecrement??e.contradictDecrement)),weeklyDecay:Math.max(0,Math.trunc(t?.weeklyDecay??e.weeklyDecay)),implicitUseIncrement:Math.max(0,Math.trunc(t?.implicitUseIncrement??e.implicitUseIncrement)),staleThreshold:Math.min(100,Math.max(0,Math.trunc(t?.staleThreshold??e.staleThreshold))),staleDays:Math.max(1,Math.trunc(t?.staleDays??e.staleDays)),decayFloor:Math.min(100,Math.max(0,Math.trunc(t?.decayFloor??e.decayFloor))),autoArchiveDays:Math.max(1,Math.trunc(t?.autoArchiveDays??e.autoArchiveDays)),archiveThreshold:Math.min(100,Math.max(0,Math.trunc(t?.archiveThreshold??e.archiveThreshold)))}}function r(e){return[`## Lesson: ${e.title}`,``,`**Confidence:** ${e.confidence}/100`,``,`### Context`,e.context,``,`### Insight`,e.insight,``,`### Evidence`,e.evidence].join(`
3
+ `)}function i(e){let t=e.match(/^## Lesson:\s+(.+)$/m),n=e.match(/\*\*Confidence:\*\*\s+(\d+)\/100/),r=e.match(/### Context\r?\n([\s\S]*?)(?=\r?\n### |$)/),i=e.match(/### Insight\r?\n([\s\S]*?)(?=\r?\n### |$)/),a=e.match(/### Evidence\r?\n([\s\S]*?)(?=\r?\n### |$)/);return{title:t?.[1]?.trim(),confidence:n?Number(n[1]):void 0,context:r?.[1]?.trim(),insight:i?.[1]?.trim(),evidence:a?.[1]?.trim()}}function a(e,t){let n=Math.min(100,Math.max(0,Math.trunc(t)));return/\*\*Confidence:\*\*/.test(e)?e.replace(/\*\*Confidence:\*\*\s+\d+\/100/,`**Confidence:** ${n}/100`):e.match(/^(## Lesson:[^\r\n]*)(\r?\n)/)?e.replace(/^(## Lesson:[^\r\n]*)(\r?\n)/,`$1$2$2**Confidence:** ${n}/100$2$2`):`**Confidence:** ${n}/100\n\n${e}`}function o(t,r,i=e){let a=n(i);return r===`confirm`?Math.min(100,t+a.confirmIncrement):Math.max(0,t-a.contradictDecrement)}function s(t,r,i,a=e,o=Date.now()){let s=n(a),c=!!r,l=r?new Date(r):new Date(i),u=Math.max(0,o-l.getTime());c||(u=Math.min(u,336*60*60*1e3));let d=u/(10080*60*1e3),f=Math.floor(d)*s.weeklyDecay;return Math.max(s.decayFloor,t-f)}function c(t,r=e,i=Date.now()){let a=n(r);if(s(t.confidence,t.lastAccessedAt,t.createdAt,r,i)>=a.staleThreshold)return!1;let o=t.lastAccessedAt?new Date(t.lastAccessedAt):new Date(t.createdAt);return Math.max(0,i-o.getTime())/(1e3*60*60*24)>=a.staleDays}function l(t,r=e,i=Date.now()){let a=n(r);if(s(t.confidence,t.lastAccessedAt,t.createdAt,r,i)>=a.archiveThreshold)return!1;let o=t.lastAccessedAt?new Date(t.lastAccessedAt):new Date(t.createdAt);return Math.max(0,i-o.getTime())/(1e3*60*60*24)>=a.autoArchiveDays}export{r as a,n as c,s as i,a as l,t as n,c as o,o as r,i as s,e as t,l as u};
@@ -0,0 +1,2 @@
1
+ const e={confirmIncrement:10,contradictDecrement:20,weeklyDecay:2,implicitUseIncrement:3,staleThreshold:30,staleDays:21,decayFloor:10,autoArchiveDays:30,archiveThreshold:20},t=`lesson:auto-archive`;function n(t){return{confirmIncrement:Math.max(0,Math.trunc(t?.confirmIncrement??e.confirmIncrement)),contradictDecrement:Math.max(0,Math.trunc(t?.contradictDecrement??e.contradictDecrement)),weeklyDecay:Math.max(0,Math.trunc(t?.weeklyDecay??e.weeklyDecay)),implicitUseIncrement:Math.max(0,Math.trunc(t?.implicitUseIncrement??e.implicitUseIncrement)),staleThreshold:Math.min(100,Math.max(0,Math.trunc(t?.staleThreshold??e.staleThreshold))),staleDays:Math.max(1,Math.trunc(t?.staleDays??e.staleDays)),decayFloor:Math.min(100,Math.max(0,Math.trunc(t?.decayFloor??e.decayFloor))),autoArchiveDays:Math.max(1,Math.trunc(t?.autoArchiveDays??e.autoArchiveDays)),archiveThreshold:Math.min(100,Math.max(0,Math.trunc(t?.archiveThreshold??e.archiveThreshold)))}}function r(e){return[`## Lesson: ${e.title}`,``,`**Confidence:** ${e.confidence}/100`,``,`### Context`,e.context,``,`### Insight`,e.insight,``,`### Evidence`,e.evidence].join(`
2
+ `)}function i(e){let t=e.match(/^## Lesson:\s+(.+)$/m),n=e.match(/\*\*Confidence:\*\*\s+(\d+)\/100/),r=e.match(/### Context\r?\n([\s\S]*?)(?=\r?\n### |$)/),i=e.match(/### Insight\r?\n([\s\S]*?)(?=\r?\n### |$)/),a=e.match(/### Evidence\r?\n([\s\S]*?)(?=\r?\n### |$)/);return{title:t?.[1]?.trim(),confidence:n?Number(n[1]):void 0,context:r?.[1]?.trim(),insight:i?.[1]?.trim(),evidence:a?.[1]?.trim()}}function a(e,t){let n=Math.min(100,Math.max(0,Math.trunc(t)));return/\*\*Confidence:\*\*/.test(e)?e.replace(/\*\*Confidence:\*\*\s+\d+\/100/,`**Confidence:** ${n}/100`):e.match(/^(## Lesson:[^\r\n]*)(\r?\n)/)?e.replace(/^(## Lesson:[^\r\n]*)(\r?\n)/,`$1$2$2**Confidence:** ${n}/100$2$2`):`**Confidence:** ${n}/100\n\n${e}`}function o(t,r,i=e){let a=n(i);return r===`confirm`?Math.min(100,t+a.confirmIncrement):Math.max(0,t-a.contradictDecrement)}function s(t,r,i,a=e,o=Date.now()){let s=n(a),c=!!r,l=r?new Date(r):new Date(i),u=Math.max(0,o-l.getTime());c||(u=Math.min(u,336*60*60*1e3));let d=u/(10080*60*1e3),f=Math.floor(d)*s.weeklyDecay;return Math.max(s.decayFloor,t-f)}function c(t,r=e,i=Date.now()){let a=n(r);if(s(t.confidence,t.lastAccessedAt,t.createdAt,r,i)>=a.staleThreshold)return!1;let o=t.lastAccessedAt?new Date(t.lastAccessedAt):new Date(t.createdAt);return Math.max(0,i-o.getTime())/(1e3*60*60*24)>=a.staleDays}function l(t,r=e,i=Date.now()){let a=n(r);if(s(t.confidence,t.lastAccessedAt,t.createdAt,r,i)>=a.archiveThreshold)return!1;let o=t.lastAccessedAt?new Date(t.lastAccessedAt):new Date(t.createdAt);return Math.max(0,i-o.getTime())/(1e3*60*60*24)>=a.autoArchiveDays}export{r as a,n as c,s as i,a as l,t as n,c as o,o as r,i as s,e as t,l as u};
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ import{m as e,t,u as n}from"./bin.js";import{a as r,s as i}from"./lessons-B05P_TOl.js";import{existsSync as a,mkdirSync as o}from"node:fs";import{join as s}from"node:path";import{getGlobalDataDir as c,isUserInstalled as l,listWorkspaces as u}from"../../core/dist/index.js";var d=e({DEFAULT_PROMOTE_CONFIG:()=>f,collectWorkspaceLessons:()=>w,demoteLesson:()=>D,getGlobalCuratedDir:()=>C,promoteLessons:()=>E,scanForDuplicates:()=>T});const f={minWorkspaces:2,minAvgConfidence:80,similarityThreshold:.7,dryRun:!0};function p(e){return{minWorkspaces:Math.max(2,Math.trunc(e?.minWorkspaces??f.minWorkspaces)),minAvgConfidence:Math.min(100,Math.max(0,Math.trunc(e?.minAvgConfidence??f.minAvgConfidence))),similarityThreshold:Math.min(1,Math.max(0,e?.similarityThreshold??f.similarityThreshold)),dryRun:e?.dryRun??f.dryRun}}function m(e,t){let r=e.map(()=>[]);for(let i=0;i<e.length;i+=1)for(let a=i+1;a<e.length;a+=1)n(e[i].insight,e[a].insight)>=t&&(r[i].push(a),r[a].push(i));return r}function h(e){let t=new Set,n=[];for(let r=0;r<e.length;r+=1){if(t.has(r))continue;let i=[r],a=[];for(t.add(r);i.length>0;){let n=i.pop();if(n!==void 0){a.push(n);for(let r of e[n])t.has(r)||(t.add(r),i.push(r))}}n.push(a)}return n}function g(e){return new t(e,null,null)}function _(e){return(e??``).replace(/\s+/g,` `).trim()}function v(e){let t=_(e);return t.length<=80?t:`${t.slice(0,77).replace(/\s+\S*$/,``)}...`}function y(e){return r({title:v(e.insight),context:`Observed across ${e.foundIn.length} workspaces: ${e.foundIn.join(`, `)}`,insight:e.insight,evidence:[`Promoted from workspaces: ${e.foundIn.join(`, `)}`,`Average confidence: ${e.avgConfidence}/100`,`Reason: ${e.reason}`].join(`
3
+ `),confidence:e.avgConfidence,tags:[`lesson`,`promoted`,`global`]})}async function b(e,t){let n=await e.list({category:`lessons`});return(await Promise.all(n.map(async n=>{let r=await e.read(n.path),a=i(r.content),o=_(a.insight);return o?{workspace:t,path:n.path,title:a.title??r.title??n.title,insight:o,confidence:a.confidence??0}:null}))).filter(e=>e!==null)}async function x(e){return(await b(e,`global`)).map(e=>e.insight)}function S(e,t,r){return t.some(t=>n(t,e)>=r)}function C(){let e=s(c(),`global-knowledge`,`.ai`,`curated`);return a(e)||o(e,{recursive:!0}),e}async function w(e){let t=new Map;if(!l())return t;for(let e of u()){let n=s(e.workspacePath,`.ai`,`curated`);if(!a(n))continue;let r=await b(g(n),e.partition);r.length>0&&t.set(e.partition,r)}return t}function T(e,t=f){let n=p(t),r=[...e.values()].flat();if(r.length===0)return[];let i=h(m(r,n.similarityThreshold)),a=[];for(let e of i){let t=e.map(e=>r[e]),i=[...new Set(t.map(e=>e.workspace))].sort();if(i.length<n.minWorkspaces)continue;let o=Math.round(t.reduce((e,t)=>e+t.confidence,0)/t.length),s=[...t].sort((e,t)=>t.confidence-e.confidence||e.title.localeCompare(t.title)||e.path.localeCompare(t.path))[0];a.push({insight:s.insight,foundIn:i,avgConfidence:o,action:o>=n.minAvgConfidence?`promote`:`skip`,reason:o>=n.minAvgConfidence?`Shared across ${i.length} workspaces`:`Below confidence threshold`})}return a.sort((e,t)=>Number(t.action===`promote`)-Number(e.action===`promote`)||t.foundIn.length-e.foundIn.length||t.avgConfidence-e.avgConfidence||e.insight.localeCompare(t.insight))}async function E(e,t,n=f){let r=p(n),i=[],a=await x(t);for(let n of e){if(n.action!==`promote`||S(n.insight,a,r.similarityThreshold)||r.dryRun)continue;let e=await t.remember(v(n.insight),y(n),`lessons`,[`lesson`,`promoted`,`global`]);i.push(e.path),a.push(n.insight)}return{candidates:e,promoted:i}}async function D(e,t){try{return await e.forget(t,`Demoted from global knowledge partition`),{removed:!0,path:t}}catch(e){if(e instanceof Error&&/not found/i.test(e.message))return{removed:!1,path:t};throw e}}export{E as a,C as i,w as n,d as o,D as r,T as s,f as t};
@@ -0,0 +1,2 @@
1
+ import{t as e}from"./rolldown-runtime-DT7IzrpZ.js";import{r as t}from"./supersession-9edUDEQ8.js";import{t as n}from"./curated-manager-D1u5qOwK.js";import{a as r,s as i}from"./lessons-D7sdHa2e.js";import{existsSync as a,mkdirSync as o}from"node:fs";import{join as s}from"node:path";import{getGlobalDataDir as c,isUserInstalled as l,listWorkspaces as u}from"../../core/dist/index.js";var d=e({DEFAULT_PROMOTE_CONFIG:()=>f,collectWorkspaceLessons:()=>w,demoteLesson:()=>D,getGlobalCuratedDir:()=>C,promoteLessons:()=>E,scanForDuplicates:()=>T});const f={minWorkspaces:2,minAvgConfidence:80,similarityThreshold:.7,dryRun:!0};function p(e){return{minWorkspaces:Math.max(2,Math.trunc(e?.minWorkspaces??f.minWorkspaces)),minAvgConfidence:Math.min(100,Math.max(0,Math.trunc(e?.minAvgConfidence??f.minAvgConfidence))),similarityThreshold:Math.min(1,Math.max(0,e?.similarityThreshold??f.similarityThreshold)),dryRun:e?.dryRun??f.dryRun}}function m(e,n){let r=e.map(()=>[]);for(let i=0;i<e.length;i+=1)for(let a=i+1;a<e.length;a+=1)t(e[i].insight,e[a].insight)>=n&&(r[i].push(a),r[a].push(i));return r}function h(e){let t=new Set,n=[];for(let r=0;r<e.length;r+=1){if(t.has(r))continue;let i=[r],a=[];for(t.add(r);i.length>0;){let n=i.pop();if(n!==void 0){a.push(n);for(let r of e[n])t.has(r)||(t.add(r),i.push(r))}}n.push(a)}return n}function g(e){return new n(e,null,null)}function _(e){return(e??``).replace(/\s+/g,` `).trim()}function v(e){let t=_(e);return t.length<=80?t:`${t.slice(0,77).replace(/\s+\S*$/,``)}...`}function y(e){return r({title:v(e.insight),context:`Observed across ${e.foundIn.length} workspaces: ${e.foundIn.join(`, `)}`,insight:e.insight,evidence:[`Promoted from workspaces: ${e.foundIn.join(`, `)}`,`Average confidence: ${e.avgConfidence}/100`,`Reason: ${e.reason}`].join(`
2
+ `),confidence:e.avgConfidence,tags:[`lesson`,`promoted`,`global`]})}async function b(e,t){let n=await e.list({category:`lessons`});return(await Promise.all(n.map(async n=>{let r=await e.read(n.path),a=i(r.content),o=_(a.insight);return o?{workspace:t,path:n.path,title:a.title??r.title??n.title,insight:o,confidence:a.confidence??0}:null}))).filter(e=>e!==null)}async function x(e){return(await b(e,`global`)).map(e=>e.insight)}function S(e,n,r){return n.some(n=>t(n,e)>=r)}function C(){let e=s(c(),`global-knowledge`,`.ai`,`curated`);return a(e)||o(e,{recursive:!0}),e}async function w(e){let t=new Map;if(!l())return t;for(let e of u()){let n=s(e.workspacePath,`.ai`,`curated`);if(!a(n))continue;let r=await b(g(n),e.partition);r.length>0&&t.set(e.partition,r)}return t}function T(e,t=f){let n=p(t),r=[...e.values()].flat();if(r.length===0)return[];let i=h(m(r,n.similarityThreshold)),a=[];for(let e of i){let t=e.map(e=>r[e]),i=[...new Set(t.map(e=>e.workspace))].sort();if(i.length<n.minWorkspaces)continue;let o=Math.round(t.reduce((e,t)=>e+t.confidence,0)/t.length),s=[...t].sort((e,t)=>t.confidence-e.confidence||e.title.localeCompare(t.title)||e.path.localeCompare(t.path))[0];a.push({insight:s.insight,foundIn:i,avgConfidence:o,action:o>=n.minAvgConfidence?`promote`:`skip`,reason:o>=n.minAvgConfidence?`Shared across ${i.length} workspaces`:`Below confidence threshold`})}return a.sort((e,t)=>Number(t.action===`promote`)-Number(e.action===`promote`)||t.foundIn.length-e.foundIn.length||t.avgConfidence-e.avgConfidence||e.insight.localeCompare(t.insight))}async function E(e,t,n=f){let r=p(n),i=[],a=await x(t);for(let n of e){if(n.action!==`promote`||S(n.insight,a,r.similarityThreshold)||r.dryRun)continue;let e=await t.remember(v(n.insight),y(n),`lessons`,[`lesson`,`promoted`,`global`]);i.push(e.path),a.push(n.insight)}return{candidates:e,promoted:i}}async function D(e,t){try{return await e.forget(t,`Demoted from global knowledge partition`),{removed:!0,path:t}}catch(e){if(e instanceof Error&&/not found/i.test(e.message))return{removed:!1,path:t};throw e}}export{E as a,C as i,w as n,d as o,D as r,T as s,f as t};
@@ -1,4 +1,4 @@
1
- import{n as e}from"./auth-BfqgawfR.js";import{fileURLToPath as t}from"node:url";import{spawn as n}from"node:child_process";import{createInterface as r}from"node:readline";const i={input:process.stdin,output:process.stdout,error:process.stderr,fetchImpl:globalThis.fetch,spawnImpl:n,readTokenImpl:e,sleep:e=>new Promise(t=>setTimeout(t,e))};async function a(e={},t={}){let n={...i,...t},a=s(e.port),c=`http://127.0.0.1:${a}`,h=await o(c,n.fetchImpl);if(!h&&e.autoStart!==!1)try{l(a,n),await u(c,1e4,n),h=!0}catch(e){n.error.write(`[aikit-proxy] ${m(e)}\n`)}else h||n.error.write(`[aikit-proxy] Daemon not running and autoStart=false
1
+ import{n as e}from"./auth-Bz5dmZgR.js";import{fileURLToPath as t}from"node:url";import{spawn as n}from"node:child_process";import{createInterface as r}from"node:readline";const i={input:process.stdin,output:process.stdout,error:process.stderr,fetchImpl:globalThis.fetch,spawnImpl:n,readTokenImpl:e,sleep:e=>new Promise(t=>setTimeout(t,e))};async function a(e={},t={}){let n={...i,...t},a=s(e.port),c=`http://127.0.0.1:${a}`,h=await o(c,n.fetchImpl);if(!h&&e.autoStart!==!1)try{l(a,n),await u(c,1e4,n),h=!0}catch(e){n.error.write(`[aikit-proxy] ${m(e)}\n`)}else h||n.error.write(`[aikit-proxy] Daemon not running and autoStart=false
2
2
  `);let g=n.readTokenImpl();if(!g){n.error.write(`[aikit-proxy] No token found at ~/.aikit/token
3
3
  `);return}let _=r({input:n.input,crlfDelay:1/0}),v;for await(let e of _)if(e.trim())try{let t=await n.fetchImpl(`${c}/mcp`,{method:`POST`,headers:d(g,v),body:e}),r=t.headers.get(`mcp-session-id`);r&&(v=r);let i=await t.text();i&&f(n.output,i)}catch(t){f(n.output,p(e,t))}}async function o(e,t=globalThis.fetch){try{return(await t(`${e}/health`,{method:`GET`,signal:AbortSignal.timeout(2e3)})).ok}catch{return!1}}function s(e){if(typeof e==`number`&&Number.isFinite(e)&&e>0)return e;let t=Number.parseInt(process.env.AIKIT_PORT??``,10);return Number.isFinite(t)&&t>0?t:3210}function c(){return t(new URL(`./index.js`,import.meta.url))}function l(e,t){t.spawnImpl(process.execPath,[c(),`--transport`,`http`,`--port`,String(e)],{env:{...process.env,AIKIT_TRANSPORT:`http`,AIKIT_PORT:String(e)},detached:!0,stdio:`ignore`}).unref(),t.error.write(`[aikit-proxy] Started daemon on port ${e}\n`)}async function u(e,t,n){let r=Date.now();for(;Date.now()-r<t;){if(await o(e,n.fetchImpl))return;await n.sleep(200)}throw Error(`Daemon did not start within ${t}ms`)}function d(e,t){return{"Content-Type":`application/json`,Authorization:`Bearer ${e}`,...t?{"Mcp-Session-Id":t}:{}}}function f(e,t){e.write(t.endsWith(`
4
4
  `)?t:`${t}\n`)}function p(e,t){let n=null;try{n=JSON.parse(e).id??null}catch{n=null}return JSON.stringify({jsonrpc:`2.0`,id:n,error:{code:-32603,message:`Proxy error: ${m(t)}`}})}function m(e){return e instanceof Error?e.message:`Unknown error`}export{o as isDaemonAlive,a as runProxy};
@@ -0,0 +1,7 @@
1
+ import{r as e,s as t}from"./supersession-9edUDEQ8.js";import{join as n}from"node:path";import{createLogger as r}from"../../core/dist/index.js";import{writeFile as i}from"node:fs/promises";import{tmpdir as a}from"node:os";import{replayAppend as o}from"../../tools/dist/index.js";const s=r(`auto-gc`);let c=`warming`,l=null,u=0;function d(){let e=[...K()];if(e.length<10)return 0;e.sort((e,t)=>e-t);let t=Math.floor(e.length*.95);return e[Math.min(t,e.length-1)]}function f(e){let t=d();if(t===0){c=`warming`;return}if(t>500){c=`degraded`;let n=Date.now();if(l&&n-l<36e5){s.debug(`GC cooldown active — skipping`,{lastGcAgoMs:n-l});return}l=n,u++,s.warn(`p95 latency exceeds threshold, triggering GC`,{p95:t,cycle:u}),e&&e().catch(e=>s.error(`GC callback failed`,{err:String(e)}))}else t<200&&(c=`healthy`)}function p(){return{state:c,p95:d(),lastGcAt:l,gcCount:u,bufferSize:K().length}}const m={enabled:!0,batchThreshold:20,cooldownMs:3e5,maxCandidatesPerSession:5,initialConfidence:40,excludeTools:[`knowledge`,`replay`,`stash`,`checkpoint`,`session_digest`,`reindex`,`status`,`flow`,`evidence_map`,`present`]},h=new Set([`search`,`find`,`symbol`,`grep_search`,`semantic_search`]),g=new Set([`replace_string_in_file`,`editfiles`,`create_file`,`apply_patch`]),_=new Set([`check`,`test_run`]),v=new Set(`action.and.args.auto.buffer.category.content.create.cwd.false.file.files.find.grep.json.knowledge.list.path.query.read.replace.search.semantic.subaction.symbol.test.tool.true.update`.split(`.`));function y(e){return e.replace(/^mcp_[^_]+_/,``).toLowerCase()}function b(e){return[...new Set(e.filter(e=>e.length>0))]}function x(e,t){return{...t,confidence:m.initialConfidence,tags:[`auto-observed`,`detector:${e}`],detector:e}}function S(e,n){let r=new Map;for(let n of e)for(let e of t(n))v.has(e)||r.set(e,(r.get(e)??0)+1);let i=[...r.entries()].filter(([,e])=>e>=n).sort((e,t)=>t[1]-e[1]||e[0].localeCompare(t[0])).map(([e])=>e);return i.length>0?i.slice(0,4):[...r.entries()].sort((e,t)=>t[1]-e[1]||e[0].localeCompare(t[0])).slice(0,4).map(([e])=>e)}function C(e){return e.length>0?e.join(`, `):`similar tasks`}function w(e){if(typeof e!=`object`||!e)return!1;let t=e;return typeof t.ts==`number`&&Number.isFinite(t.ts)&&typeof t.tool==`string`&&typeof t.input==`string`&&Array.isArray(t.files)&&t.files.every(e=>typeof e==`string`)}function T(t){let n=[];for(let r of t)n.some(t=>e(t.title,r.title)>.8)||n.push(r);return n}function E(e){let t=new Map;for(let n of e){let e=y(n.tool),r=t.get(e)??[];r.push(n),t.set(e,r)}return[...t.entries()].filter(([,e])=>e.length>=5).map(([e,t])=>{let n=C(S(t.map(e=>e.input),Math.max(2,Math.ceil(t.length/2))));return x(`tool-preference`,{title:`Preferred tool: ${e} for ${n}`,context:`Observed ${t.length} ${e} calls with recurring inputs around ${n}.`,insight:`Use ${e} when working with ${n}.`,evidence:t.slice(0,5).map(e=>`${e.tool}: ${e.input}`).join(`
2
+ `)})})}function D(e){let t=new Map;for(let n=0;n<e.length;n+=1){let r=e[n];if(h.has(y(r.tool)))for(let i=n+1;i<e.length&&i<=n+5;i+=1){let n=e[i];if(!(!g.has(y(n.tool))||n.files.length===0))for(let e of b(n.files)){let i=t.get(e)??{count:0,queries:[],evidence:[]};i.count+=1,i.queries.push(r.input),i.evidence.push(`${r.tool}: ${r.input} -> ${n.tool}: ${e}`),t.set(e,i)}}}return[...t.entries()].filter(([,e])=>e.count>=3).map(([e,t])=>{let n=C(S(t.queries,Math.max(2,Math.ceil(t.count/2))));return x(`search-action`,{title:`Check ${e} when searching for ${n}`,context:`Searches related to ${n} were followed by edits to ${e} ${t.count} times within five tool calls.`,insight:`When working on ${n}, check ${e} early because searches repeatedly led there.`,evidence:t.evidence.slice(0,5).join(`
3
+ `)})})}function O(e){let t=new Map;for(let n=0;n<e.length-2;n+=1){let r=e[n];if(!_.has(y(r.tool)))continue;let i=new Set,a=!1;for(let o=n+1;o<e.length;o+=1){let n=e[o],s=y(n.tool);if(g.has(s)){a=!0;for(let e of n.files)i.add(e);continue}if(_.has(s)){if(!a||i.size===0)break;let e=[...i].sort(),o=e.join(`|`),s=t.get(o)??{count:0,evidence:[]};s.count+=1,s.evidence.push(`${r.tool} -> edit(${e.join(`, `)}) -> ${n.tool}`),t.set(o,s);break}if(!a)break}}return[...t.entries()].filter(([,e])=>e.count>=2).map(([e,t])=>{let n=e.split(`|`);return x(`error-fix-cycle`,{title:`Repeated validation-edit loop in ${n.length===1?n[0]:`${n[0]} and related files`}`,context:`Observed ${t.count} validation cycles touching ${n.join(`, `)}.`,insight:`Common fix pattern in ${n.join(`, `)}: check -> edit -> recheck.`,evidence:t.evidence.slice(0,5).join(`
4
+ `)})})}function k(e,t=m){if(!t.enabled||e.length===0)return[];let n=new Set(t.excludeTools.map(e=>e.toLowerCase())),r=e.filter(e=>!n.has(y(e.tool)));return T([...E(r),...D(r),...O(r)].map(e=>({...e,confidence:t.initialConfidence,tags:b([`auto-observed`,`detector:${e.detector}`,...e.tags])}))).slice(0,t.maxCandidatesPerSession)}function A(e){return e.split(`
5
+ `).filter(Boolean).map(e=>{try{return JSON.parse(e)}catch{return null}}).filter(w)}const j=r(`replay-interceptor`),M=/key|token|secret|auth|password|bearer/i,N=new Set([`eval`,`env`]);function P(e){if(typeof e==`string`)return/^(Bearer |sk-|ghp_|glpat-|ghu_|ghs_|github_pat_)/i.test(e)?`[REDACTED]`:e;if(Array.isArray(e))return e.map(P);if(e&&typeof e==`object`){let t={};for(let[n,r]of Object.entries(e))/(?:token|secret|password|passphrase|key|auth|credential|api.?key)/i.test(n)?t[n]=`[REDACTED]`:t[n]=P(r);return t}return e}function F(e,t){if(N.has(e))return JSON.stringify({_redacted:!0,tool:e});let n=P(t);if(e===`http`&&n.headers&&typeof n.headers==`object`){let e={};for(let[t,r]of Object.entries(n.headers))e[t]=M.test(t)?`[REDACTED]`:r;return n.headers=e,JSON.stringify(n).slice(0,2e3)}return JSON.stringify(n).slice(0,2e3)}const I=new Map,L=[],R=[];let z=0,B;function V(e,t){return F(e,t).slice(0,500)}function H(e){let t=new Set,n=[e];for(;n.length>0&&t.size<20;){let e=n.pop();if(e!=null){if(Array.isArray(e)){for(let t of e)n.push(t);continue}if(typeof e==`object`)for(let[r,i]of Object.entries(e)){if(Array.isArray(i)){if(/^(?:files|paths)$/i.test(r))for(let e of i)typeof e==`string`&&e.length>0&&t.add(e);else n.push(i);continue}if(typeof i==`string`&&/^(?:file|filepath|path)$/i.test(r)&&i.length>0){t.add(i);continue}i&&typeof i==`object`&&n.push(i)}}}return[...t]}function U(e,t,r){if(z+=1,R.push(JSON.stringify({tool:e,input:V(e,t),output:r.slice(0,500),files:H(t),ts:Date.now()})),R.length>100&&R.shift(),z%50!=0)return;let o=R.join(`
6
+ `);R.length=0,!(!B||o.trim().split(`
7
+ `).filter(Boolean).length<20)&&Promise.resolve().then(async()=>{let e=k(A(o),m);if(e.length!==0){try{let t=n(a(),`aikit-auto-observe-${process.pid}-${Date.now()}.json`);await i(t,JSON.stringify(e,null,2),`utf8`),j.info(`Auto-observe candidates detected`,{count:e.length,filePath:t})}catch(e){j.warn(`Failed to persist auto-observe candidates`,{error:String(e)})}B?.(e)}}).catch(()=>{})}function W(e,t,n,r,i){let a=I.get(e);a||(a={callCount:0,totalDurationMs:0,totalInputChars:0,totalOutputChars:0,errorCount:0},I.set(e,a)),a.callCount++,a.totalDurationMs+=t,a.totalInputChars+=n,a.totalOutputChars+=r,i&&a.errorCount++,L.push(t),L.length>100&&L.shift(),L.length>=10&&L.length%20==0&&f()}function G(){return Array.from(I.entries()).map(([e,t])=>({tool:e,...t}))}function K(){return L}function q(e){B=e}function J(){return async(e,t)=>{let n=Date.now(),r=JSON.stringify(e.args??{}).length;try{let i=await t(),a=Date.now()-n,s=JSON.stringify(i);return o({ts:new Date().toISOString(),source:`mcp`,tool:e.toolName,input:F(e.toolName,e.args),durationMs:a,status:`ok`,output:s,traceId:e.requestId,outputChars:s.length}),U(e.toolName,e.args,s),W(e.toolName,a,r,s.length,!1),i}catch(t){let i=Date.now()-n,a=t instanceof Error?t.message:String(t);throw o({ts:new Date().toISOString(),source:`mcp`,tool:e.toolName,input:F(e.toolName,e.args),durationMs:i,status:`error`,output:a,traceId:e.requestId,outputChars:0}),U(e.toolName,e.args,a),W(e.toolName,i,r,0,!0),t}}}export{A as a,m as i,G as n,k as o,q as r,p as s,J as t};
@@ -0,0 +1 @@
1
+ const e={workingToEpisodicAccesses:2,episodicToSemanticReferences:3,semanticToProceduralVerifications:5},t={working:1,episodic:2,semantic:4,procedural:12};function n(t,n=e){switch(t.tier){case`working`:if(t.accessCount>=n.workingToEpisodicAccesses)return`episodic`;break;case`episodic`:if(t.accessCount>=n.workingToEpisodicAccesses+n.episodicToSemanticReferences)return`semantic`;break;case`semantic`:if(t.accessCount>=n.workingToEpisodicAccesses+n.episodicToSemanticReferences+n.semanticToProceduralVerifications)return`procedural`;break;case`procedural`:break;default:break}}function r(e,t,n){e.memoryMetaUpdateTier(t,n)}const i={stabilityHours:168,accessMultiplier:1.5,flagThreshold:.1,maxStabilityHours:8760};function a(e){return{...i,...e}}function o(e,t){if(!e)return t;let n=Date.parse(e);return Number.isNaN(n)?t:n}function s(e){return e&&e in t?e:`working`}function c(e,n,r,c=i,l){let u=typeof c==`string`?s(c):`working`,d=a(typeof c==`string`?l:c),f=o(e,o(r,Date.now())),p=Math.max(0,Date.now()-f)/(1e3*60*60),m=Math.min(d.stabilityHours*t[u]*d.accessMultiplier**Math.max(0,n),d.maxStabilityHours);return Math.exp(-p/m)}function l(e,t,n){let r=e.memoryMetaGet(t);if(!r)return;let i=c(r.lastAccessedAt,r.accessCount,r.createdAt,r.tier,n);return r.retentionScore!==i&&e.memoryMetaUpdateScore(t,i),e.memoryMetaGet(t)??{...r,retentionScore:i}}function u(e,t,n){e.memoryMetaGet(t)||e.memoryMetaCreate(t),e.memoryMetaTouch(t);let r=e.memoryMetaGet(t);if(!r)return 1;let i=c(r.lastAccessedAt,r.accessCount,r.createdAt,r.tier,n);return e.memoryMetaUpdateScore(t,i),i}function d(e,t){let n=a(t);return e.memoryMetaList().map(t=>l(e,t.entryId,n)??t).filter(e=>e.retentionScore<n.flagThreshold).sort((e,t)=>e.retentionScore-t.retentionScore)}export{e as a,u as i,d as n,n as o,l as r,r as s,i as t};
@@ -0,0 +1,2 @@
1
+ #!/usr/bin/env node
2
+ const e={workingToEpisodicAccesses:2,episodicToSemanticReferences:3,semanticToProceduralVerifications:5},t={working:1,episodic:2,semantic:4,procedural:12};function n(t,n=e){switch(t.tier){case`working`:if(t.accessCount>=n.workingToEpisodicAccesses)return`episodic`;break;case`episodic`:if(t.accessCount>=n.workingToEpisodicAccesses+n.episodicToSemanticReferences)return`semantic`;break;case`semantic`:if(t.accessCount>=n.workingToEpisodicAccesses+n.episodicToSemanticReferences+n.semanticToProceduralVerifications)return`procedural`;break;case`procedural`:break;default:break}}function r(e,t,n){e.memoryMetaUpdateTier(t,n)}const i={stabilityHours:168,accessMultiplier:1.5,flagThreshold:.1,maxStabilityHours:8760};function a(e){return{...i,...e}}function o(e,t){if(!e)return t;let n=Date.parse(e);return Number.isNaN(n)?t:n}function s(e){return e&&e in t?e:`working`}function c(e,n,r,c=i,l){let u=typeof c==`string`?s(c):`working`,d=a(typeof c==`string`?l:c),f=o(e,o(r,Date.now())),p=Math.max(0,Date.now()-f)/(1e3*60*60),m=Math.min(d.stabilityHours*t[u]*d.accessMultiplier**Math.max(0,n),d.maxStabilityHours);return Math.exp(-p/m)}function l(e,t,n){let r=e.memoryMetaGet(t);if(!r)return;let i=c(r.lastAccessedAt,r.accessCount,r.createdAt,r.tier,n);return r.retentionScore!==i&&e.memoryMetaUpdateScore(t,i),e.memoryMetaGet(t)??{...r,retentionScore:i}}function u(e,t,n){e.memoryMetaGet(t)||e.memoryMetaCreate(t),e.memoryMetaTouch(t);let r=e.memoryMetaGet(t);if(!r)return 1;let i=c(r.lastAccessedAt,r.accessCount,r.createdAt,r.tier,n);return e.memoryMetaUpdateScore(t,i),i}function d(e,t){let n=a(t);return e.memoryMetaList().map(t=>l(e,t.entryId,n)??t).filter(e=>e.retentionScore<n.flagThreshold).sort((e,t)=>e.retentionScore-t.retentionScore)}export{e as a,u as i,d as n,n as o,l as r,r as s,i as t};
@@ -0,0 +1 @@
1
+ import"node:module";var e=Object.defineProperty,t=(t,n)=>{let r={};for(var i in t)e(r,i,{get:t[i],enumerable:!0});return n||e(r,Symbol.toStringTag,{value:`Module`}),r};export{t};