ai-projects 1.3.0 → 1.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.ts +35 -10
- package/dist/index.js +98 -182
- package/package.json +9 -6
package/dist/index.d.ts
CHANGED
|
@@ -122,6 +122,34 @@ declare const commands: {
|
|
|
122
122
|
type: "pre-create" | "post-create" | "pre-complete" | "post-complete" | "pre-start" | "post-start" | "pre-update" | "post-update";
|
|
123
123
|
}>>;
|
|
124
124
|
};
|
|
125
|
+
readonly log: {
|
|
126
|
+
readonly append: CommandDef<zod.ZodObject<{
|
|
127
|
+
project: zod.ZodOptional<zod.ZodString>;
|
|
128
|
+
task: zod.ZodOptional<zod.ZodString>;
|
|
129
|
+
}, "strip", zod.ZodTypeAny, {
|
|
130
|
+
project?: string | undefined;
|
|
131
|
+
task?: string | undefined;
|
|
132
|
+
}, {
|
|
133
|
+
project?: string | undefined;
|
|
134
|
+
task?: string | undefined;
|
|
135
|
+
}>, zod.ZodObject<{
|
|
136
|
+
text: zod.ZodString;
|
|
137
|
+
}, "strip", zod.ZodTypeAny, {
|
|
138
|
+
text: string;
|
|
139
|
+
}, {
|
|
140
|
+
text: string;
|
|
141
|
+
}>>;
|
|
142
|
+
readonly read: CommandDef<zod.ZodObject<{
|
|
143
|
+
project: zod.ZodOptional<zod.ZodString>;
|
|
144
|
+
task: zod.ZodOptional<zod.ZodString>;
|
|
145
|
+
}, "strip", zod.ZodTypeAny, {
|
|
146
|
+
project?: string | undefined;
|
|
147
|
+
task?: string | undefined;
|
|
148
|
+
}, {
|
|
149
|
+
project?: string | undefined;
|
|
150
|
+
task?: string | undefined;
|
|
151
|
+
}>, zod.ZodObject<{}, "strip", zod.ZodTypeAny, {}, {}>>;
|
|
152
|
+
};
|
|
125
153
|
readonly project: {
|
|
126
154
|
readonly create: CommandDef<zod.ZodObject<{
|
|
127
155
|
description: zod.ZodString;
|
|
@@ -170,19 +198,16 @@ declare const commands: {
|
|
|
170
198
|
description: zod.ZodOptional<zod.ZodString>;
|
|
171
199
|
status: zod.ZodOptional<zod.ZodString>;
|
|
172
200
|
assignee: zod.ZodOptional<zod.ZodString>;
|
|
173
|
-
summary: zod.ZodOptional<zod.ZodString>;
|
|
174
201
|
}, "strip", zod.ZodTypeAny, {
|
|
175
202
|
status?: string | undefined;
|
|
176
203
|
description?: string | undefined;
|
|
177
204
|
name?: string | undefined;
|
|
178
205
|
assignee?: string | undefined;
|
|
179
|
-
summary?: string | undefined;
|
|
180
206
|
}, {
|
|
181
207
|
status?: string | undefined;
|
|
182
208
|
description?: string | undefined;
|
|
183
209
|
name?: string | undefined;
|
|
184
210
|
assignee?: string | undefined;
|
|
185
|
-
summary?: string | undefined;
|
|
186
211
|
}>, zod.ZodObject<{
|
|
187
212
|
project: zod.ZodOptional<zod.ZodString>;
|
|
188
213
|
}, "strip", zod.ZodTypeAny, {
|
|
@@ -217,11 +242,11 @@ declare const commands: {
|
|
|
217
242
|
project: zod.ZodString;
|
|
218
243
|
name: zod.ZodString;
|
|
219
244
|
}, "strip", zod.ZodTypeAny, {
|
|
220
|
-
name: string;
|
|
221
245
|
project: string;
|
|
222
|
-
}, {
|
|
223
246
|
name: string;
|
|
247
|
+
}, {
|
|
224
248
|
project: string;
|
|
249
|
+
name: string;
|
|
225
250
|
}>>;
|
|
226
251
|
readonly current: CommandDef<zod.ZodObject<{}, "strip", zod.ZodTypeAny, {}, {}>, zod.ZodObject<any, zod.UnknownKeysParam, zod.ZodTypeAny, {
|
|
227
252
|
[x: string]: any;
|
|
@@ -246,16 +271,19 @@ declare const commands: {
|
|
|
246
271
|
statuses: zod.ZodDefault<zod.ZodArray<zod.ZodString, "many">>;
|
|
247
272
|
assignee: zod.ZodOptional<zod.ZodString>;
|
|
248
273
|
all: zod.ZodDefault<zod.ZodBoolean>;
|
|
274
|
+
search: zod.ZodOptional<zod.ZodString>;
|
|
249
275
|
}, "strip", zod.ZodTypeAny, {
|
|
250
276
|
statuses: string[];
|
|
251
277
|
all: boolean;
|
|
252
278
|
project?: string | undefined;
|
|
253
279
|
assignee?: string | undefined;
|
|
280
|
+
search?: string | undefined;
|
|
254
281
|
}, {
|
|
255
282
|
project?: string | undefined;
|
|
256
283
|
assignee?: string | undefined;
|
|
257
284
|
statuses?: string[] | undefined;
|
|
258
285
|
all?: boolean | undefined;
|
|
286
|
+
search?: string | undefined;
|
|
259
287
|
}>, zod.ZodObject<any, zod.UnknownKeysParam, zod.ZodTypeAny, {
|
|
260
288
|
[x: string]: any;
|
|
261
289
|
}, {
|
|
@@ -296,21 +324,18 @@ declare const commands: {
|
|
|
296
324
|
status: zod.ZodOptional<zod.ZodString>;
|
|
297
325
|
assignee: zod.ZodOptional<zod.ZodString>;
|
|
298
326
|
project: zod.ZodOptional<zod.ZodString>;
|
|
299
|
-
summary: zod.ZodOptional<zod.ZodString>;
|
|
300
327
|
}, "strip", zod.ZodTypeAny, {
|
|
328
|
+
project?: string | undefined;
|
|
301
329
|
status?: string | undefined;
|
|
302
330
|
description?: string | undefined;
|
|
303
331
|
name?: string | undefined;
|
|
304
|
-
project?: string | undefined;
|
|
305
332
|
assignee?: string | undefined;
|
|
306
|
-
summary?: string | undefined;
|
|
307
333
|
}, {
|
|
334
|
+
project?: string | undefined;
|
|
308
335
|
status?: string | undefined;
|
|
309
336
|
description?: string | undefined;
|
|
310
337
|
name?: string | undefined;
|
|
311
|
-
project?: string | undefined;
|
|
312
338
|
assignee?: string | undefined;
|
|
313
|
-
summary?: string | undefined;
|
|
314
339
|
}>, zod.ZodObject<{
|
|
315
340
|
task: zod.ZodOptional<zod.ZodString>;
|
|
316
341
|
}, "strip", zod.ZodTypeAny, {
|
package/dist/index.js
CHANGED
|
@@ -1,26 +1,26 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
import {z as z$1}from'zod';import {parser}from'zod-opts';import
|
|
2
|
+
import {z as z$1}from'zod';import {parser}from'zod-opts';import Je from'dotenv';import Be from'fs';import F from'path';import {fileURLToPath}from'url';import {spawn,exec}from'child_process';import K from'fs/promises';import y from'lodash';import W from'moment';import {inspect}from'util';import Pt from'yaml';var He=Object.defineProperty;var f=(t,e)=>()=>(t&&(e=t(t=0)),e);var Ke=(t,e)=>{for(var o in e)He(t,o,{get:e[o],enumerable:true});};var b,B=f(()=>{b={name:"ai-projects",version:"1.5.0",type:"module",description:"Useful CLI for AI agents to create and manage projects, tasks, skills and agents",main:"dist/index.js",types:"dist/index.d.ts",bin:{aip:"dist/index.js"},files:["dist/**/*","README.md","LICENSE"],scripts:{build:"npm run build:map && npm run build:code","build:map":"tsx bin/map-commands.ts","build:code":"tsup --no-dts","build:all":"npm run build:map && tsup","build:check":"tsc --noEmit","build:watch":"npm run build:code -- --watch","build:clean":"rimraf dist/*","build:incr":"tsup --no-dts",start:"dist/index.js",dev:'npm run build:watch -- --onSuccess "dist/index.js"',cli:"npm run build && npm start --",ts:"tsx",vitest:"VITE_CJS_IGNORE_WARNING=true vitest",test:"npm run test:types && npm run test:unit","test:unit":"npm run vitest -- run","test:types:test":"tsc -p tsconfig.test.json --incremental --tsBuildInfoFile dist/test.tsbuildinfo","test:types:bin":"tsc -p bin/tsconfig.json --incremental --tsBuildInfoFile dist/bin.tsbuildinfo","test:types":"npm run test:types:test && npm run test:types:bin","test:full":"npm run lint:full && npm run test",eslint:"eslint --cache",lint:"npm run eslint -- '{src,bin}/**/*.ts'","lint:fix":"npm run lint -- --fix","lint:full":"npm run build:incr && npm run test:types:bin && npm run lint:fix","lint:full:silent":"npm run -s lint:full && echo LINT OK",map:"npm run build:map",link:"npm link",unlink:"npm unlink",prepare:'[ "$CI" != "true" ] && [ -d node_modules/husky ] && husky || true',prepack:"npm run test:full && npm run build:all","publish:dry":"npm pack --dry-run","version:patch":"npm version patch","version:minor":"npm version minor","version:major":"npm version major","agent:stop":"npm run -s lint:full:silent"},keywords:["ai","aip","project","task","kanban","cli","agent","automation"],author:"Ariel Flesler <aflesler@gmail.com>",license:"MIT",repository:{type:"git",url:"git+https://github.com/flesler/ai-projects.git"},homepage:"https://github.com/flesler/ai-projects#readme",bugs:{url:"https://github.com/flesler/ai-projects/issues"},engines:{node:">=20.0.0"},dependencies:{dotenv:"^17.3.1",lodash:"^4.17.21",moment:"^2.30.1",tslib:"^2.8.1",yaml:"^2.8.0",zod:"^3.25.76","zod-opts":"^1.0.0"},devDependencies:{"@eslint/js":"^10.0.1","@stylistic/eslint-plugin":"^5.7.0","@types/dotenv":"^8.2.3","@types/eslint":"^9.6.1","@types/lodash":"^4.17.23","@types/moment":"^2.13.0","@types/node":"^25.0.9","@types/source-map-support":"^0.5.10","@typescript-eslint/eslint-plugin":"^8.53.0","@typescript-eslint/parser":"^8.53.0",eslint:"^10.0.3","eslint-plugin-import-x":"^4.16.2","eslint-plugin-unused-imports":"^4.4.1","fast-glob":"^3.3.3",husky:"^9.1.7",rimraf:"^6.0.1","source-map-support":"^0.5.21",tsup:"^8.5.1",tsx:"^4.20.3","types-package-json":"^2.0.39",typescript:"^5.8.3",vitest:"^4.0.17"}};});function p(t){let{description:e,options:o=z$1.object({}),args:r,handler:s}=t,i=o.shape,a={};for(let[m,d]of Object.entries(i))a[m]={type:d};let l=parser().options(a);if(r){let m=r.shape,d=Object.entries(m).map(([k,P])=>({name:k,type:P}));d.length>0&&(l=l.args(d));}return e&&(l=l.description(e)),{description:e,options:o,args:r,parser:l,handler:s,cli:m=>s(l.parse(m))}}var g=f(()=>{});var c,$=f(()=>{c={dirs:{PROJECTS:"projects",SKILLS:"skills",AGENTS:"agents",TASKS:"tasks",INPUTS:"inputs",OUTPUTS:"outputs",HOOKS:"hooks",SCRIPTS:"scripts"},files:{MAIN:"main.md",STATUS:"status.tsv",LOG:"audit.log",SKILL:"SKILL.md"},hookTypes:["pre-create","post-create","pre-complete","post-complete","pre-start","post-start","pre-update","post-update"],languages:["ts","js","sh","py"],targets:["project","task"]};});var Ve,bt,N,Ze,E,H=f(()=>{$();Ve=()=>{let t=fileURLToPath(import.meta.url),e=F.dirname(t),o=10;for(let r=0;r<o;r++)try{if(Be.existsSync(F.join(e,"package.json")))return e;let s=F.dirname(e);if(s===e)break;e=s;}catch{break}return process.cwd()},bt=Ve(),N=process.env.AIP_HOME;N||(Je.config({path:F.join(bt,".env"),quiet:true}),N=process.env.AIP_HOME);if(!N){N=process.cwd();let t=N.split(F.sep);for(let e of [c.dirs.PROJECTS,c.dirs.SKILLS,c.dirs.AGENTS]){let o=t.indexOf(e);if(o!==-1){N=t.slice(0,o).join(F.sep);break}}}Ze={ROOT:bt,AIP_HOME:N},E=Ze;});var h,n,T=f(()=>{H();h={REPO:fileURLToPath(import.meta.url.replace(/\/(dist|src)\/.*/,"/")),join:(...t)=>F.join(...t),onRepo:(...t)=>h.join(h.REPO,...t),joinHome:(...t)=>h.join(E.AIP_HOME,...t),async ensureDir(t){await K.mkdir(t,{recursive:true});},async write(t,e){await h.ensureDir(F.dirname(t)),await K.writeFile(t,e,"utf8");},async append(t,e){await h.ensureDir(F.dirname(t)),await K.appendFile(t,e,"utf8");},async read(t){return K.readFile(t,"utf8")},async readRepo(...t){return h.read(h.onRepo(...t))},async readMany(...t){return (await Promise.all(t.map(async o=>{if(await h.fileExists(o)){let r=await h.read(o);return `# ${o}
|
|
3
3
|
|
|
4
|
-
${r}`}return ""}))).filter(Boolean)},async logFiles(...t){let e=await
|
|
4
|
+
${r}`}return ""}))).filter(Boolean)},async logFiles(...t){let e=await h.readMany(...t);console.log(e.join(`
|
|
5
5
|
|
|
6
6
|
---
|
|
7
7
|
|
|
8
|
-
`));},dumpCommandMapLines(t,e){let o=e?
|
|
8
|
+
`));},dumpCommandMapLines(t,e){let o=e?y.pick(t,e):t,r=[];for(let[s,i]of h.entriesOf(o))r.push(`${s} {${Object.keys(i).join("|")}}`);return r},async fileExists(t){try{return await K.access(t),!0}catch{return false}},async listDir(t){try{return await K.readdir(t)}catch{return []}},spawn:spawn,cd(t){process.chdir(t);},async exec(t,e){return new Promise(o=>{exec(t,{encoding:"utf8",...e},(r,s,i)=>{let a=r?.code;o({stdout:s??"",stderr:i??"",code:r?typeof a=="number"?a:1:0});});})},noop:()=>{},omitByDeep:(t,e)=>y.isArray(t)?t.map(o=>h.omitByDeep(o,e)):y.isPlainObject(t)?y.mapValues(y.omitBy(t,e),o=>h.omitByDeep(o,e)):t,omitNilsDeep:t=>h.omitByDeep(t,y.isNil),omitUndefinedsDeep:t=>h.omitByDeep(t,y.isUndefined),cloneDeep:t=>y.cloneDeep(t),int:t=>Number.parseInt(t,10),keysOf:t=>Object.keys(t),entriesOf:t=>Object.entries(t),isKeyOf:(t,e)=>!y.isNil(t)&&t in e,typeOf:t=>typeof t,never:{},undef:t=>t??void 0,toNull:t=>t??null,same:t=>t,notNil:t=>{if(y.isNil(t))throw new Error(`Received unexpected ${t} value`);return t},randomInt:(t,e)=>Math.floor(Math.random()*(e-t+1))+t,promise:()=>{let t,e=new Promise((o,r)=>{t={resolve:o,reject:r};});return y.extend(e,t)},isPromise:t=>y.isObject(t)&&"catch"in t,delay:t=>{let e=y.isObject(t)?h.toMS(t):t;return new Promise(o=>setTimeout(o,e))},promiseMap:(t,e)=>Promise.all(t.map(e)),promiseEach:(t,e)=>Promise.all(t.map(e)).then(()=>{}),memoize:t=>y.memoize(t,h.memoizeKey),toMS:t=>W.duration(t).asMilliseconds(),toSecs:t=>W.duration(t).asSeconds(),inspect:(t,e)=>inspect(t,{colors:false,showHidden:false,depth:null,compact:true,breakLength:1/0,...e}),stringify(t,e,o){let r=new WeakSet;return JSON.stringify(t,(s,i)=>{if(y.isObject(i)){if(r.has(i))return "[Circular]";r.add(i);}return y.isFunction(e)?e(s,i):i},o)},dump:t=>h.oneLine(h.stringify(t)),compactWhitespace:t=>t.replace(/\\n/g,`
|
|
9
9
|
`).replace(/\r/g,"").replace(/[ \t]*\n[ \t]*/g,`
|
|
10
10
|
`).replace(/\n{3,}/g,`
|
|
11
11
|
|
|
12
|
-
`).replace(/ {2,}/g," ").trim(),oneLine:t=>t.replace(/\n/g,"\\n").replace(/\t/g,"\\t").replace(/ +/g," ").trim(),fuzzySearch:(t,e)=>
|
|
13
|
-
${
|
|
12
|
+
`).replace(/ {2,}/g," ").trim(),oneLine:t=>t.replace(/\n/g,"\\n").replace(/\t/g,"\\t").replace(/ +/g," ").trim(),fuzzySearch:(t,e)=>y.includes(y.toLower(t||""),y.toLower(e||"")),elapsed:(t,e=Date.now())=>W.duration(W(e).diff(t||0)),iso:t=>W.utc(t).toISOString(),isoDate:t=>h.iso(t).slice(0,10),memoizeKey:(...t)=>t.join(""),exit:(t=0)=>{process.exit(t);},set:(t,e,o)=>(t[e]=o,t),run:async t=>{try{await t(),process.exit(0);}catch(e){console.error(e),process.exit(1);}},isMain:()=>{let t=process.argv[1]||"";return t.includes("/index.")||t.endsWith("/bin/aip")},errorMessage:t=>t instanceof Error?t.message:String(t),slugify:t=>t.toLowerCase().replace(/[^a-z0-9]+/g,"-").replace(/^-+|-+$/g,"")},n=h;});var xt,V,ut,Z,$t=f(()=>{T();xt=t=>{let e=t.trim();if(!e.startsWith("---"))return null;let o=e.match(/^---\n([\s\S]*?)\n---\n?([\s\S]*)$/);return o?{frontmatter:Pt.parse(o[1]),content:o[2].trim()}:null},V=async(t,e,o="")=>{let s=`---
|
|
13
|
+
${Pt.stringify(e).trim()}
|
|
14
14
|
---
|
|
15
15
|
|
|
16
|
-
${o}`.trim();await
|
|
17
|
-
`);},
|
|
18
|
-
Expected at: ${o}`);console.log(e);}});});var
|
|
19
|
-
Expected at: ${o}`);let i=[r,o];await
|
|
20
|
-
`,r.length>0||
|
|
16
|
+
${o}`.trim();await n.write(t,s+`
|
|
17
|
+
`);},ut=async(t,e)=>{let o=await n.read(t),r=xt(o);if(!r)throw new Error(`No frontmatter found in ${t}`);let s={...r.frontmatter,...e};return await V(t,s,r.content),s},Z=async t=>{let e=await n.read(t),o=xt(e);if(!o)throw new Error(`No frontmatter found in ${t}`);return o.frontmatter};});var M,et,vt,Et,to,eo,u,x=f(()=>{$();H();$t();T();M=(a=>(a.BACKLOG="backlog",a.IN_PROGRESS="in-progress",a.ONGOING="ongoing",a.DONE="done",a.BLOCKED="blocked",a.TO_DO="to-do",a))(M||{}),et=Object.values(M),vt=["backlog","in-progress","ongoing"],Et=[c.dirs.HOOKS,c.dirs.INPUTS,c.dirs.OUTPUTS,c.dirs.SCRIPTS],to=[c.dirs.TASKS,...Et],eo={getProjectDir(t){return n.joinHome(c.dirs.PROJECTS,t)},getTaskDir(t,e){return n.join(this.getProjectDir(t),c.dirs.TASKS,e)},async findTask(t,e){if(e)return {project:e,task:t};let o=await this.listProjects(),r=[];if(await n.promiseEach(o,async s=>{(await this.listTasks(s)).includes(t)&&r.push(s);}),r.length===0)throw new Error(`Task '${t}' not found. Use --project to specify the project.`);if(r.length>1)throw new Error(`Task '${t}' found in multiple projects: ${r.join(", ")}. Use --project to specify which one.`);return {project:r[0],task:t}},getAgentDir(t){return n.join(E.AIP_HOME,c.dirs.AGENTS,t)},async listProjects(){let t=n.join(E.AIP_HOME,c.dirs.PROJECTS),e=await n.listDir(t);return (await n.promiseMap(e,async r=>{let s=this.getProjectDir(r);return await n.fileExists(s)&&r!==c.dirs.AGENTS?r:null})).filter(r=>r!==null).sort()},async listTasks(t){let e=n.join(this.getProjectDir(t),c.dirs.TASKS);return await n.fileExists(e)?await n.listDir(e):[]},async listAgents(){let t=n.join(E.AIP_HOME,c.dirs.AGENTS);return await n.fileExists(t)?await n.listDir(t):[]},async createProject(t,e){let o=this.getProjectDir(t);return await n.ensureDir(o),await Promise.all(to.map(r=>n.ensureDir(n.join(o,r)))),await V(n.join(o,c.files.MAIN),e),await n.write(n.join(o,c.files.STATUS),""),o},async createTask(t,e,o){let r=this.getTaskDir(t,e);return await n.ensureDir(r),await Promise.all(Et.map(s=>n.ensureDir(n.join(r,s)))),await V(n.join(r,c.files.MAIN),o),await n.write(n.join(r,c.files.STATUS),""),r},async createAgent(t,e){let o=this.getAgentDir(t);return await n.ensureDir(o),await V(n.join(o,c.files.MAIN),e),o},async getProject(t){let e=n.join(this.getProjectDir(t),c.files.MAIN);return await n.fileExists(e)?await Z(e):null},async getTask(t,e){let o=n.join(this.getTaskDir(t,e),c.files.MAIN);return await n.fileExists(o)?await Z(o):null},async getAgent(t){let e=n.join(this.getAgentDir(t),c.files.MAIN);return await n.fileExists(e)?await Z(e):null},async updateProject(t,e){let o=n.join(this.getProjectDir(t),c.files.MAIN);return await ut(o,e)},async updateTask(t,e,o){let r=n.join(this.getTaskDir(t,e),c.files.MAIN);if((await Z(r))?.status==="ongoing")throw new Error("Cannot update ongoing task. Should be done by user or update manually");return await ut(r,o)},async ingestTask(t,e){let o=this.getTaskDir(t,e),r=this.getProjectDir(t),s=[n.join(r,c.files.MAIN),n.join(o,c.files.MAIN),n.join(o,c.files.STATUS)];await n.logFiles(...s);},async ingestProject(t){let e=this.getProjectDir(t),o=await this.listTasks(t),r=[n.join(e,c.files.MAIN),n.join(e,c.files.STATUS),...o.map(s=>n.join(this.getTaskDir(t,s),c.files.MAIN))];await n.logFiles(...r);},async ingestFiles(t){await n.logFiles(...t);}},u=eo;});var At,Dt=f(()=>{g();T();x();At=p({options:z$1.object({description:z$1.string().describe("Agent description"),status:z$1.string().default("active").describe("Initial status")}),args:z$1.object({name:z$1.string().describe("Agent name")}),handler:async({name:t,description:e,status:o})=>{let r=n.slugify(t);await u.createAgent(r,{name:t,description:e,status:o,created:new Date().toISOString()}),console.log(`Agent created: ${r}`),console.log(` Path: ${u.getAgentDir(r)}`);}});});var Ot,Ct=f(()=>{g();Ot=p({options:z$1.object({}),handler:async()=>{let t=process.env.CURRENT_AGENT;t||(console.error("CURRENT_AGENT not set"),process.exit(1)),console.log(t);}});});var Rt,Nt=f(()=>{g();x();Rt=p({options:z$1.object({}),handler:async()=>{let t=await u.listAgents(),e=[];for(let o of t){let r=await u.getAgent(o);r&&e.push({slug:o,name:r.name||o,status:r.status,description:r.description});}if(e.length===0){console.log("No agents found");return}console.log("Agents:"),console.log("---");for(let o of e)console.log(`${o.slug.padEnd(20)} ${o.name?.padEnd(30)||""} ${o.status||""} ${o.description||""}`);}});});var It,Ut=f(()=>{$();g();H();T();It=p({description:"Output agent directory path (for cd)",options:z$1.object({}),args:z$1.object({name:z$1.string().describe("Agent name (directory name)")}),handler:async({name:t})=>{let e=n.join(E.AIP_HOME,c.dirs.AGENTS,t),o=n.join(e,c.files.MAIN);if(!await n.fileExists(o))throw new Error(`Agent not found: ${t}
|
|
18
|
+
Expected at: ${o}`);console.log(e);}});});var _t,Lt=f(()=>{$();g();H();T();_t=p({description:"Start an agent: read SOUL.md and AGENTS.md content",options:z$1.object({}),args:z$1.object({name:z$1.string().describe("Agent name (directory name)")}),handler:async({name:t})=>{let e=n.join(E.AIP_HOME,c.dirs.AGENTS,t),o=n.join(e,c.files.MAIN),r=n.join(e,"SOUL.md");if(!await n.fileExists(o))throw new Error(`Agent not found: ${t}
|
|
19
|
+
Expected at: ${o}`);let i=[r,o];await n.logFiles(...i);}});});var Ft,Ht,no,Kt,Mt=f(()=>{g();Ft=t=>{let e=t.shape,o=[];for(let[r,s]of Object.entries(e)){let i=s._def,a="unknown",l,m;i.typeName==="ZodString"?a="string":i.typeName==="ZodNumber"?a="number":i.typeName==="ZodBoolean"?a="boolean":i.typeName==="ZodEnum"?a=`enum: ${i.values.join(" | ")}`:i.typeName==="ZodOptional"?a=Ht(i.innerType):i.typeName==="ZodDefault"&&(a=Ht(i.innerType),m=i.defaultValue()),i.description&&(l=i.description);let d=i.typeName!=="ZodOptional"&&i.typeName!=="ZodDefault";o.push({name:r,type:a,required:d,description:l,defaultValue:m});}return o},Ht=t=>{let e=t._def;return e.typeName==="ZodString"?"string":e.typeName==="ZodNumber"?"number":e.typeName==="ZodBoolean"?"boolean":e.typeName==="ZodEnum"?`enum: ${e.values.join(" | ")}`:"unknown"},no=(t,e,o)=>{let r=Ft(o.options),s=o.args?Ft(o.args):[],i=o.description,a=`\`${t} ${e}\``;if(i&&(a+=`: ${i}`),a+=`
|
|
20
|
+
`,r.length>0||s.length>0){let m=[];for(let d of s){let k=d.required?`<${d.name}>`:`[${d.name}]`,P=d.description||"";d.defaultValue!==void 0&&(P+=P?` (default: ${d.defaultValue})`:`(default: ${d.defaultValue})`),m.push(`\xB7 ${k}${P?": "+P:""}`);}for(let d of r){let k=d.description||"";d.defaultValue!==void 0&&(k+=k?` (default: ${d.defaultValue})`:`(default: ${d.defaultValue})`),m.push(`\xB7 --${d.name}${k?": "+k:""}`);}a+=m.join(`
|
|
21
21
|
`)+`
|
|
22
|
-
`;}return
|
|
23
|
-
`,
|
|
22
|
+
`;}return a+=`
|
|
23
|
+
`,a},Kt=p({description:"Print generated CLI reference from command schemas",options:z$1.object({}),handler:async()=>{let{default:t}=await Promise.resolve().then(()=>(ot(),kt)),e="Prepend `aip` to each command\n\n",o=Object.keys(t).sort();for(let r of o){let s=t[r],i=Object.keys(s).sort();for(let a of i){let l=s[a];e+=no(r,a,l);}}console.log(e);}});});var ao,Gt,zt=f(()=>{g();ao=`# AIP Hooks
|
|
24
24
|
|
|
25
25
|
Automated scripts that run before/after project/task actions.
|
|
26
26
|
|
|
@@ -62,7 +62,7 @@ Projects can include validation scripts and hooks to enforce folder semantics:
|
|
|
62
62
|
|
|
63
63
|
- **\`hooks/pre-complete.sh\`** \u2013 Runs before task completion
|
|
64
64
|
- Validates required files exist
|
|
65
|
-
- Checks status.
|
|
65
|
+
- Checks status.tsv has completion entry
|
|
66
66
|
- Runs structure validation (warning only)
|
|
67
67
|
- Exit 1 blocks completion
|
|
68
68
|
|
|
@@ -113,9 +113,9 @@ if (!content.includes('description:')) {
|
|
|
113
113
|
}
|
|
114
114
|
|
|
115
115
|
// Require status update
|
|
116
|
-
const statusPath = join(taskDir, 'status.
|
|
116
|
+
const statusPath = join(taskDir, 'status.tsv')
|
|
117
117
|
if (!existsSync(statusPath) || readFileSync(statusPath, 'utf-8').length === 0) {
|
|
118
|
-
console.error('\u274C status.
|
|
118
|
+
console.error('\u274C status.tsv is empty')
|
|
119
119
|
process.exit(1)
|
|
120
120
|
}
|
|
121
121
|
\`\`\`
|
|
@@ -183,7 +183,7 @@ DEBUG=1 aip task update --status done
|
|
|
183
183
|
- Require tests before completion
|
|
184
184
|
- Check outputs exist
|
|
185
185
|
- Validate frontmatter fields
|
|
186
|
-
- Ensure status.
|
|
186
|
+
- Ensure status.tsv updated
|
|
187
187
|
|
|
188
188
|
### Automation
|
|
189
189
|
- Backup before changes
|
|
@@ -200,26 +200,26 @@ DEBUG=1 aip task update --status done
|
|
|
200
200
|
---
|
|
201
201
|
|
|
202
202
|
*Hooks automate workflow enforcement. Pre-hooks guard quality, post-hooks handle cleanup.*
|
|
203
|
-
`,
|
|
203
|
+
`,Gt=p({description:"Hook types, env vars, and patterns",options:z$1.object({}),handler:async()=>{console.log(ao);}});});var O,po,Jt,Bt=f(()=>{B();g();O=Object.keys(b.bin)[0],po=`# Quick Start
|
|
204
204
|
|
|
205
205
|
## New Task/Project
|
|
206
206
|
|
|
207
207
|
\`\`\`bash
|
|
208
208
|
# 1. Create project (if needed)
|
|
209
|
-
${
|
|
209
|
+
${O} project create "my-project" --description "What I'm building"
|
|
210
210
|
|
|
211
211
|
# 2. Create task
|
|
212
|
-
${
|
|
212
|
+
${O} task create my-project "first-task" --description "Start here"
|
|
213
213
|
|
|
214
214
|
# 3. Navigate to task
|
|
215
|
-
cd $(${
|
|
215
|
+
cd $(${O} task path first-task)
|
|
216
216
|
|
|
217
217
|
# 4. Start working (implicit from PWD)
|
|
218
|
-
${
|
|
219
|
-
# \u2192 sets status to in-progress
|
|
218
|
+
${O} task start
|
|
219
|
+
# \u2192 sets status to in-progress, reads all context to stdout
|
|
220
220
|
|
|
221
221
|
# 5. Work session
|
|
222
|
-
# Log:
|
|
222
|
+
# Log progress: ${O} log append "API integration complete"
|
|
223
223
|
# Save: outputs/ to deliver, inputs/ for data
|
|
224
224
|
\`\`\`
|
|
225
225
|
|
|
@@ -227,20 +227,27 @@ ${C} task start
|
|
|
227
227
|
|
|
228
228
|
\`\`\`bash
|
|
229
229
|
# Find your tasks (searches all projects)
|
|
230
|
-
${
|
|
230
|
+
${O} task list
|
|
231
231
|
|
|
232
232
|
# Navigate to task
|
|
233
|
-
cd $(${
|
|
233
|
+
cd $(${O} task path task-slug)
|
|
234
234
|
|
|
235
235
|
# All commands work implicitly from PWD:
|
|
236
|
-
${
|
|
236
|
+
${O} task start # Start working (sets status to in-progress, reads all context to stdout)
|
|
237
237
|
\`\`\`
|
|
238
238
|
|
|
239
239
|
## Completing
|
|
240
240
|
|
|
241
241
|
\`\`\`bash
|
|
242
242
|
# Mark done (implicit from PWD)
|
|
243
|
-
${
|
|
243
|
+
${O} task update --status done
|
|
244
|
+
${O} log append "if you want to log something extra"
|
|
245
|
+
\`\`\`
|
|
246
|
+
|
|
247
|
+
## Check current task
|
|
248
|
+
|
|
249
|
+
\`\`\`bash
|
|
250
|
+
${O} task current
|
|
244
251
|
\`\`\`
|
|
245
252
|
|
|
246
253
|
**Note:** All task commands accept an optional task slug, but use PWD if not provided. Navigate with \`cd\` first for smoother workflow.
|
|
@@ -250,15 +257,15 @@ ${C} task update --status done --summary "What I built"
|
|
|
250
257
|
\`\`\`
|
|
251
258
|
$AIP_HOME/projects/slug/
|
|
252
259
|
\u251C\u2500\u2500 main.md # Goals (read first)
|
|
253
|
-
\u251C\u2500\u2500 status.
|
|
260
|
+
\u251C\u2500\u2500 status.tsv # Log (append every session)
|
|
254
261
|
\u2514\u2500\u2500 tasks/task/
|
|
255
262
|
\u251C\u2500\u2500 main.md # Task definition
|
|
256
|
-
\u2514\u2500\u2500 status.
|
|
263
|
+
\u2514\u2500\u2500 status.tsv # Updates
|
|
257
264
|
\`\`\`
|
|
258
265
|
|
|
259
|
-
**Status format:**
|
|
260
|
-
**Example:** \`
|
|
261
|
-
`,
|
|
266
|
+
**Status format:** TSV with columns: date, time, entityType, slug, action, text
|
|
267
|
+
**Example:** \`2026-03-30<TAB>14:30:00<TAB>task<TAB>api-integration<TAB>log<TAB>API integration complete\`
|
|
268
|
+
`,Jt=p({description:"Quick start guide for new users",options:z$1.object({}),handler:async()=>{console.log(po);}});});var lo,mo,uo,fo,go,ko,jo,Vt,Zt,G,jt,qt,Yt=f(()=>{B();$();g();x();lo=Object.values(M).join("|"),{PROJECTS:mo,TASKS:uo,HOOKS:fo,INPUTS:go,OUTPUTS:ko,SCRIPTS:jo}=c.dirs,{MAIN:Vt,STATUS:Zt}=c.files,G=Object.keys(b.bin)[0],jt=`# AIP - Project Management Skill
|
|
262
269
|
|
|
263
270
|
Automated project and task creation with proper structure, front-matter, and file organization.
|
|
264
271
|
|
|
@@ -266,166 +273,75 @@ Automated project and task creation with proper structure, front-matter, and fil
|
|
|
266
273
|
|
|
267
274
|
Streamline creation of new projects and tasks with the correct directory structure, file templates, and front-matter. Ensures consistency across all autonomous work.
|
|
268
275
|
|
|
269
|
-
##
|
|
276
|
+
## Quick Start
|
|
277
|
+
|
|
278
|
+
- New user? Run: \`${G} help quickstart\`
|
|
279
|
+
- All commands? Run: \`${G} help usage\`
|
|
280
|
+
- Just for one noun? Run: \`${G} help usage <noun>\` (e.g., \`${G} help usage task\`)
|
|
281
|
+
- Need EVERYTHING (big)? Run: \`${G} help api\` - Shows all commands with full option details
|
|
270
282
|
|
|
271
|
-
|
|
283
|
+
## File Structure Overview
|
|
272
284
|
|
|
273
285
|
\`\`\`
|
|
274
|
-
$AIP_HOME/${
|
|
275
|
-
\u251C\u2500\u2500 ${
|
|
276
|
-
\u251C\u2500\u2500 ${
|
|
277
|
-
\u251C\u2500\u2500 ${
|
|
278
|
-
\u251C\u2500\u2500 ${
|
|
279
|
-
\u251C\u2500\u2500 ${
|
|
280
|
-
\u251C\u2500\u2500 ${
|
|
281
|
-
\u2514\u2500\u2500 ${
|
|
286
|
+
$AIP_HOME/${mo}/{project-slug}/
|
|
287
|
+
\u251C\u2500\u2500 ${Vt} # Primary context: goals, scope, data
|
|
288
|
+
\u251C\u2500\u2500 ${Zt} # Chronological log (TSV: date, time, entityType, slug, action, text)
|
|
289
|
+
\u251C\u2500\u2500 ${fo}/ # pre|post-{create,start,update,complete}.*
|
|
290
|
+
\u251C\u2500\u2500 ${ko}/ # Deliverables
|
|
291
|
+
\u251C\u2500\u2500 ${go}/ # External data
|
|
292
|
+
\u251C\u2500\u2500 ${jo}/ # Automation
|
|
293
|
+
\u2514\u2500\u2500 ${uo}/
|
|
282
294
|
\u2514\u2500\u2500 {task-slug}/
|
|
283
|
-
\u251C\u2500\u2500 ${
|
|
284
|
-
\u251C\u2500\u2500 ${
|
|
285
|
-
\
|
|
286
|
-
\u251C\u2500\u2500 ${Jt}/ # Task-specific deliverables
|
|
287
|
-
\u251C\u2500\u2500 ${Wt}/ # Task-specific data files
|
|
288
|
-
\u2514\u2500\u2500 ${Bt}/ # Task-specific automation
|
|
295
|
+
\u251C\u2500\u2500 ${Vt} # Task definition
|
|
296
|
+
\u251C\u2500\u2500 ${Zt} # Activity log
|
|
297
|
+
\u2514\u2500\u2500 ... (same structure)
|
|
289
298
|
\`\`\`
|
|
290
299
|
|
|
291
|
-
##
|
|
292
|
-
|
|
293
|
-
### \`main.md\` - Primary Context (Read First)
|
|
294
|
-
**What goes here:**
|
|
295
|
-
- Project/task objectives and goals
|
|
296
|
-
- Scope and success criteria
|
|
297
|
-
- Background information and context
|
|
298
|
-
- Requirements and constraints
|
|
299
|
-
- Reference information
|
|
300
|
+
## Front-matter Format
|
|
300
301
|
|
|
301
|
-
**Front-matter:**
|
|
302
302
|
\`\`\`yaml
|
|
303
303
|
---
|
|
304
304
|
name: Clear Title
|
|
305
|
-
description: One-line summary
|
|
305
|
+
description: One-line summary
|
|
306
306
|
assignee: agent-name
|
|
307
|
-
status: ${
|
|
307
|
+
status: ${lo}
|
|
308
308
|
created: YYYY-MM-DD
|
|
309
309
|
---
|
|
310
310
|
\`\`\`
|
|
311
311
|
|
|
312
|
-
**When to read:** Always first, before starting work
|
|
313
|
-
|
|
314
|
-
**When to update:** Only when scope/goals change (rare)
|
|
315
|
-
|
|
316
|
-
### \`status.md\` - Activity Log (Append Only)
|
|
317
|
-
**What goes here:** Single-line timestamped entries
|
|
318
|
-
|
|
319
|
-
**Task examples:**
|
|
320
|
-
\`\`\`markdown
|
|
321
|
-
[2026-03-17 14:30] Task created: optimize-config
|
|
322
|
-
[2026-03-17 15:45] Updated: status=in-progress
|
|
323
|
-
[2026-03-17 16:20] API integration complete
|
|
324
|
-
\`\`\`
|
|
325
|
-
|
|
326
|
-
**Project example:**
|
|
327
|
-
\`\`\`markdown
|
|
328
|
-
[2026-03-17 16:00] Task completed: gather-requirements (details: tasks/gather-requirements/)
|
|
329
|
-
\`\`\`
|
|
330
|
-
|
|
331
|
-
**When to update:** Every work session (tasks) or task completion (projects)
|
|
332
|
-
|
|
333
|
-
### \`outputs/\` - Deliverables
|
|
334
|
-
**What:** Final deliverables (reports, code, data)
|
|
335
|
-
**Examples:** \`outputs/report.md\`, \`outputs/code.zip\`
|
|
336
|
-
|
|
337
|
-
### \`inputs/\` - External Data
|
|
338
|
-
**What:** External data (API responses, downloads)
|
|
339
|
-
**Examples:** \`inputs/api.json\`, \`inputs/data.csv\`
|
|
340
|
-
|
|
341
|
-
### \`scripts/\` - Automation
|
|
342
|
-
**What:** Automation scripts (bash, python, js)
|
|
343
|
-
**Examples:** \`scripts/deploy.sh\`, \`scripts/process.py\`
|
|
344
|
-
|
|
345
|
-
## Usage
|
|
346
|
-
|
|
347
|
-
### Create New Project
|
|
348
|
-
|
|
349
|
-
\`\`\`bash
|
|
350
|
-
# Via AIP CLI
|
|
351
|
-
aip project create "optimize-hermes-config" \\
|
|
352
|
-
--description "Analyze and optimize Hermes Agent configuration" \\
|
|
353
|
-
--assignee basic
|
|
354
|
-
\`\`\`
|
|
355
|
-
|
|
356
|
-
### Create New Task in Existing Project
|
|
357
|
-
|
|
358
|
-
\`\`\`bash
|
|
359
|
-
aip task create "optimize-hermes-config" "apply-config-changes" \\
|
|
360
|
-
--description "Implement safe optimizations" \\
|
|
361
|
-
--assignee basic
|
|
362
|
-
\`\`\`
|
|
363
|
-
|
|
364
|
-
### Navigate to Project/Task
|
|
365
|
-
|
|
366
|
-
\`\`\`bash
|
|
367
|
-
cd $(aip project path optimize-hermes-config)
|
|
368
|
-
cd $(aip task path apply-config-changes)
|
|
369
|
-
\`\`\`
|
|
370
|
-
|
|
371
|
-
### Update Task Status (implicit from PWD)
|
|
372
|
-
|
|
373
|
-
\`\`\`bash
|
|
374
|
-
aip task update --status done
|
|
375
|
-
aip task update --summary "Completed implementation"
|
|
376
|
-
\`\`\`
|
|
377
|
-
|
|
378
|
-
**Note:** All task commands accept optional task slug, but use PWD if not provided. Navigate with \`cd\` first for smoother workflow.
|
|
379
|
-
|
|
380
|
-
## Work Session
|
|
381
|
-
|
|
382
|
-
1. **Read:** \`main.md\` + \`status.md\`
|
|
383
|
-
2. **Work:** Save data to \`inputs/\`, deliverables to \`outputs/\`
|
|
384
|
-
3. **Log:** Append to \`status.md\`: \`[timestamp] message\`
|
|
385
|
-
4. **Complete:** Set status=\`done\`, summarize to project \`status.md\`
|
|
386
|
-
|
|
387
312
|
## Best Practices
|
|
388
313
|
|
|
389
|
-
**DO:** Concise status entries, update every session
|
|
390
|
-
**DON'T:** Long paragraphs, mix inputs/outputs
|
|
314
|
+
**DO:** Concise status entries, update every session, save deliverables to outputs/
|
|
315
|
+
**DON'T:** Long paragraphs in status, mix inputs/outputs
|
|
391
316
|
|
|
392
|
-
|
|
317
|
+
## For Agents
|
|
393
318
|
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
\u2514\u2500\u2500 task-1/
|
|
402
|
-
\u251C\u2500\u2500 ${X} # Task definition
|
|
403
|
-
\u2514\u2500\u2500 ${tt} # Updates
|
|
404
|
-
\`\`\`
|
|
405
|
-
|
|
406
|
-
**Status log:**
|
|
407
|
-
\`\`\`markdown
|
|
408
|
-
[2026-03-17 09:00] Task created: implement-api
|
|
409
|
-
[2026-03-17 10:30] Updated: status=in-progress
|
|
410
|
-
[2026-03-17 12:00] Tests passing
|
|
411
|
-
\`\`\`
|
|
412
|
-
`,Zt=p({description:"Project management skill for creating and managing projects/tasks",options:z$1.object({mode:z$1.enum(["md","claude","hermes"]).default("md").describe("Output format: md (no header), claude (name+description), hermes (full frontmatter)")}),handler:async t=>{let e=Object.keys(x.bin)[0];if(t.mode==="md"){console.log(dt);return}if(t.mode==="claude"){console.log(`---
|
|
319
|
+
When working on a task:
|
|
320
|
+
1. Read \`main.md\` first (goals/context)
|
|
321
|
+
2. Review \`status.tsv\` (activity history)
|
|
322
|
+
3. Work and save outputs to \`outputs/\`
|
|
323
|
+
4. Log progress: \`${G} log append "message"\`
|
|
324
|
+
5. On completion: set status=\`done\`, log summary
|
|
325
|
+
`,qt=p({description:"Project management skill for creating and managing projects/tasks",options:z$1.object({mode:z$1.enum(["md","claude","hermes"]).default("md").describe("Output format: md (no header), claude (name+description), hermes (full frontmatter)")}),handler:async t=>{let e=Object.keys(b.bin)[0];if(t.mode==="md"){console.log(jt);return}if(t.mode==="claude"){console.log(`---
|
|
413
326
|
name: ${e}
|
|
414
|
-
description: ${
|
|
415
|
-
---`),console.log(),console.log(
|
|
327
|
+
description: ${b.description}
|
|
328
|
+
---`),console.log(),console.log(jt);return}if(t.mode==="hermes"){console.log(`---
|
|
416
329
|
name: ${e}
|
|
417
|
-
description: ${
|
|
418
|
-
version: ${
|
|
419
|
-
author: ${
|
|
420
|
-
license: ${
|
|
421
|
-
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
|
|
330
|
+
description: ${b.description}
|
|
331
|
+
version: ${b.version}
|
|
332
|
+
author: ${b.author}
|
|
333
|
+
license: ${b.license}
|
|
334
|
+
metadata:
|
|
335
|
+
hermes:
|
|
336
|
+
tags: [${b.keywords.join(", ")}]
|
|
337
|
+
---`),console.log(),console.log(jt);return}}});});var Qt,Xt=f(()=>{B();g();T();Qt=p({description:"Print compact CLI usage (all nouns, or one noun if name is given)",options:z$1.object({}),args:z$1.object({name:z$1.string().optional().describe("Noun (e.g. task) to list verbs for")}),handler:async({name:t})=>{let{default:e}=await Promise.resolve().then(()=>(ot(),kt)),o=`${b.name} ${b.version} -`,r=n.dumpCommandMapLines(e,t);if(!t)console.log(o,"Usage: aip <noun> <verb> [options]"),console.log(r.map(s=>`-> ${s}`).join(`
|
|
338
|
+
`)),console.log(),console.log("Run `aip help quickstart` for a quick start guide"),console.log("Run `aip help skill` for a broader overview");else {let s=r[0]??`${t} {?}`;console.log(o,`Usage: aip ${s} [options]`);}}});});var yt,ho,j,A=f(()=>{$();T();yt=n.joinHome(c.dirs.PROJECTS),ho={getProjectFromPwd(t=process.cwd()){let e=F.relative(yt,t);if(!e||e.startsWith(".."))return null;let o=e.split(F.sep).filter(Boolean);return o.length===0?null:o[0]},getTaskFromPwd(t=process.cwd()){let e=F.relative(yt,t);if(!e||e.startsWith(".."))return null;let o=e.split(F.sep).filter(Boolean);return o.length<3||o[1]!==c.dirs.TASKS?null:o[2]},getCurrentContext(t=process.cwd()){return {project:this.getProjectFromPwd(t),task:this.getTaskFromPwd(t)}},requireProject(t=process.cwd()){let e=this.getProjectFromPwd(t);if(!e)throw new Error(`Not in a project directory. PWD: ${t}, projects: ${yt}`);return e},requireTask(t=process.cwd()){let e=this.getCurrentContext(t);if(!e.project||!e.task)throw new Error(`Not in a task directory. PWD: ${t}`);return {project:e.project,task:e.task}},exportContext(t=process.cwd()){let e=this.getCurrentContext(t),o=[];return e.project&&o.push(`export CURRENT_PROJECT="${e.project}"`),e.task&&o.push(`export CURRENT_TASK="${e.task}"`),process.env.CURRENT_AGENT&&o.push(`export CURRENT_AGENT="${process.env.CURRENT_AGENT}"`),o.join(`
|
|
339
|
+
`)},getTargetDir(t,e=process.cwd()){let o=this.getCurrentContext(e);if(t==="project"){let r=this.getProjectFromPwd(e);if(!r)throw new Error("Not in a project directory. Use --project flag or cd into a project.");let s=n.joinHome(c.dirs.PROJECTS,r);return {targetDir:s,projectDir:s,entityType:"project"}}if(t==="task"){if(!o.project||!o.task)throw new Error("Not in a task directory. Use --project and --task flags or cd into a task.");let r=n.joinHome(c.dirs.PROJECTS,o.project);return {targetDir:n.join(r,c.dirs.TASKS,o.task),projectDir:r,entityType:"task"}}if(o.task&&o.project){let r=n.joinHome(c.dirs.PROJECTS,o.project);return {targetDir:n.join(r,c.dirs.TASKS,o.task),projectDir:r,entityType:"task"}}if(o.project){let r=n.joinHome(c.dirs.PROJECTS,o.project);return {targetDir:r,projectDir:r,entityType:"project"}}throw new Error("Not in a project or task directory. Specify --target flag.")}},j=ho;});var te,ee=f(()=>{g();T();A();$();te=p({options:z$1.object({lang:z$1.enum(c.languages).default("ts").describe("Language"),target:z$1.enum(c.targets).default("project").describe("Target level")}),args:z$1.object({type:z$1.enum(c.hookTypes).describe("Hook type (e.g., pre-create, post-complete)")}),handler:async({type:t,lang:e,target:o})=>{let r=e,s=`.${r}`,{targetDir:i,entityType:a}=j.getTargetDir(o),l=n.join(i,c.dirs.HOOKS);await n.ensureDir(l);let m=n.join(l,`${t}${s}`);if(await n.fileExists(m))throw new Error(`Hook already exists: ${m}`);let k;if(r==="ts")k=`#!/usr/bin/env tsx
|
|
340
|
+
/** ${t} hook for ${a} */
|
|
425
341
|
|
|
426
342
|
import { env } from 'node:process'
|
|
427
343
|
|
|
428
|
-
console.log('Running ${t} hook for ${
|
|
344
|
+
console.log('Running ${t} hook for ${a}')
|
|
429
345
|
console.log('PROJECT_SLUG:', env.PROJECT_SLUG)
|
|
430
346
|
if (env.TASK_SLUG) {
|
|
431
347
|
console.log('TASK_SLUG:', env.TASK_SLUG)
|
|
@@ -434,9 +350,9 @@ if (env.TASK_SLUG) {
|
|
|
434
350
|
// Exit with non-zero to prevent action (for pre-hooks)
|
|
435
351
|
// process.exit(1)
|
|
436
352
|
`;else if(r==="js")k=`#!/usr/bin/env node
|
|
437
|
-
/** ${t} hook for ${
|
|
353
|
+
/** ${t} hook for ${a} */
|
|
438
354
|
|
|
439
|
-
console.log('Running ${t} hook for ${
|
|
355
|
+
console.log('Running ${t} hook for ${a}')
|
|
440
356
|
console.log('PROJECT_SLUG:', process.env.PROJECT_SLUG)
|
|
441
357
|
if (process.env.TASK_SLUG) {
|
|
442
358
|
console.log('TASK_SLUG:', process.env.TASK_SLUG)
|
|
@@ -445,9 +361,9 @@ if (process.env.TASK_SLUG) {
|
|
|
445
361
|
// Exit with non-zero to prevent action (for pre-hooks)
|
|
446
362
|
// process.exit(1)
|
|
447
363
|
`;else if(r==="sh")k=`#!/bin/bash
|
|
448
|
-
# ${t} hook for ${
|
|
364
|
+
# ${t} hook for ${a}
|
|
449
365
|
|
|
450
|
-
echo "Running ${t} hook for ${
|
|
366
|
+
echo "Running ${t} hook for ${a}"
|
|
451
367
|
echo "PROJECT_SLUG: $PROJECT_SLUG"
|
|
452
368
|
if [ -n "$TASK_SLUG" ]; then
|
|
453
369
|
echo "TASK_SLUG: $TASK_SLUG"
|
|
@@ -456,24 +372,24 @@ fi
|
|
|
456
372
|
# Exit with non-zero to prevent action (for pre-hooks)
|
|
457
373
|
# exit 1
|
|
458
374
|
`;else if(r==="py")k=`#!/usr/bin/env python3
|
|
459
|
-
"""${t} hook for ${
|
|
375
|
+
"""${t} hook for ${a}"""
|
|
460
376
|
|
|
461
377
|
import os
|
|
462
378
|
|
|
463
|
-
print(f"Running ${t} hook for ${
|
|
379
|
+
print(f"Running ${t} hook for ${a}")
|
|
464
380
|
print(f"PROJECT_SLUG: {os.environ.get('PROJECT_SLUG')}")
|
|
465
381
|
if os.environ.get('TASK_SLUG'):
|
|
466
382
|
print(f"TASK_SLUG: {os.environ.get('TASK_SLUG')}")
|
|
467
383
|
|
|
468
384
|
# Exit with non-zero to prevent action (for pre-hooks)
|
|
469
385
|
# sys.exit(1)
|
|
470
|
-
`;else throw new Error(`Unsupported language: ${r}`);await
|
|
471
|
-
`},async appendStatus(t,e,o){let
|
|
472
|
-
Expected at: ${o}`);await
|
|
473
|
-
${d}:`),console.log("---");for(let
|
|
474
|
-
`).filter(
|
|
475
|
-
=== Post-Mortem Analysis ===`),console.log(`Project: ${t}`),console.log(`Task: ${e}`),console.log(`Name: ${
|
|
476
|
-
Suggestions:`),
|
|
386
|
+
`;else throw new Error(`Unsupported language: ${r}`);await n.write(m,k);let{chmod:P}=await import('fs/promises');await P(m,493),console.log(`Hook created: ${m}`);}});});var To,v,z=f(()=>{$();T();To={async findHooks(t,e){let o=n.join(t,c.dirs.HOOKS);if(!await n.fileExists(o))return [];let s=await n.listDir(o),i=`${e}.`;return s.filter(a=>a.startsWith(i)).map(a=>n.join(o,a))},async executeHook(t,e,o){if(!await n.fileExists(t))return true;let s=e.project?n.joinHome(c.dirs.PROJECTS,e.project):o,i=e.task?n.join(s,c.dirs.TASKS,e.task):"",a={...process.env,HOOK_TYPE:e.action,ENTITY_TYPE:e.entityType,TARGET_DIR:o,PROJECT_DIR:s,...e.project?{PROJECT_SLUG:e.project}:{},...e.task?{TASK_SLUG:e.task,TASK_DIR:i}:{}};return new Promise(l=>{let m=spawn(t,[],{stdio:"inherit",env:a,cwd:F.dirname(t),shell:false});m.on("close",(d,k)=>{d===0?l(true):(console.error(`Hook ${F.basename(t)} failed (code=${d??k})`),l(false));}),m.on("error",d=>{console.error(`Failed to execute hook ${t}: ${d.message}`),l(false);});})},async runHooks(t,e,o){let r=await this.findHooks(t,e),s=e.startsWith("pre-");for(let i of r)if(!await this.executeHook(i,o,t)&&s)return false;return true},async runHooksForContext(t,e,o,r){return !(!await this.runHooks(t,o,r)||e&&!await this.runHooks(e,o,r))}},v=To;});var re,se=f(()=>{g();z();A();$();re=p({options:z$1.object({target:z$1.enum(c.targets).optional().describe("Target level")}),args:z$1.object({type:z$1.enum(c.hookTypes).describe("Hook type to run")}),handler:async({type:t,target:e})=>{let{targetDir:o,entityType:r}=j.getTargetDir(e),s={action:t,entityType:r,project:j.getProjectFromPwd()||void 0,task:j.getTaskFromPwd()||void 0};await v.runHooks(o,t,s)||(console.error(`Hook ${t} failed`),process.exit(1)),console.log(`Hook ${t} completed successfully`);}});});var wo,w,C=f(()=>{$();A();T();wo={formatEntry(t,e,o,r){let s=new Date,i=s.toISOString().split("T")[0],a=s.toLocaleTimeString("en-US",{hour12:false,hour:"2-digit",minute:"2-digit",second:"2-digit"});return `${i} ${a} ${t} ${e} ${o} ${r}
|
|
387
|
+
`},async appendStatus(t,e,o,r,s){let i=n.join(t,c.files.STATUS),a=this.formatEntry(e,o,r,s);await n.append(i,a);},async appendStatusIfExists(t,e,o,r,s){let i=n.join(t,c.files.STATUS);if(!await n.fileExists(i))return false;let l=this.formatEntry(e,o,r,s);return await n.append(i,l),true},async readStatus(t){let e=n.join(t,c.files.STATUS);return await n.fileExists(e)?await n.read(e):""},getCurrentAgent(){return process.env.CURRENT_AGENT},async logTask(t,e,o){let r=j.getCurrentContext();if(!r.project||!r.task)throw new Error("Not in a task directory");let s=n.joinHome(c.dirs.PROJECTS,r.project,c.dirs.TASKS,r.task);await this.appendStatus(s,"task",t,"log",o?`${o}: ${e}`:e);},async logProject(t,e,o){let r=j.getProjectFromPwd();if(!r)throw new Error("Not in a project directory");let s=n.joinHome(c.dirs.PROJECTS,r);await this.appendStatus(s,"project",t,"log",o?`${o}: ${e}`:e);},async logStatusChange(t,e,o,r,s,i){let a=r;if(s&&Object.keys(s).length>0){let l=Object.entries(s).map(([m,d])=>`${m}=${d}`).join(", ");a=`${r}: ${l}`;}await this.appendStatus(t,e,o,"updated",i?`${i} | ${a}`:a);}},w=wo;});var ne,ie=f(()=>{g();A();T();C();$();ne=p({description:"Append a custom entry to status.tsv",options:z$1.object({project:z$1.string().optional().describe("Project slug (uses current project from $PWD if not provided)"),task:z$1.string().optional().describe("Task slug (uses current task from $PWD if not provided)")}),args:z$1.object({text:z$1.string().describe("Text to append")}),handler:async({project:t,task:e,text:o})=>{let r=j.getCurrentContext(),s=t||r.project;if(!s)throw new Error("No project specified. Use --project or run from a project/task directory");let i=n.joinHome(c.dirs.PROJECTS,s);if(e||r.task){let a=e||r.task;if(!a)throw new Error("No task specified");let l=n.join(i,c.dirs.TASKS,a);await w.appendStatus(l,"task",a,"log",o),console.log(`Appended to task ${a} status.tsv`);}else await w.appendStatus(i,"project",s,"log",o),console.log(`Appended to project ${s} status.tsv`);}});});var ae,ce=f(()=>{g();A();T();C();$();ae=p({description:"Read status.tsv history",options:z$1.object({project:z$1.string().optional().describe("Project slug (uses current project from $PWD if not provided)"),task:z$1.string().optional().describe("Task slug (uses current task from $PWD if not provided)")}),args:z$1.object({}),handler:async({project:t,task:e})=>{let o=j.getCurrentContext(),r=t||o.project;if(!r)throw new Error("No project specified. Use --project or run from a project/task directory");let s=n.joinHome(c.dirs.PROJECTS,r);if(e||o.task){let i=e||o.task;if(!i)throw new Error("No task specified");let a=n.join(s,c.dirs.TASKS,i),l=await w.readStatus(a);console.log(l||`No status.tsv found for task ${i}`);}else {let i=await w.readStatus(s);console.log(i||`No status.tsv found for project ${r}`);}}});});var pe,le=f(()=>{g();z();T();x();C();pe=p({description:"Create a new project with name, description, optional status and assignee",options:z$1.object({description:z$1.string().describe("Project description"),status:z$1.string().default("active").describe("Initial status"),assignee:z$1.string().optional().describe("Assignee agent slug")}),args:z$1.object({name:z$1.string().describe("Project name")}),handler:async({name:t,description:e,status:o,assignee:r})=>{let s=n.slugify(t),i=u.getProjectDir(s);if(!await v.runHooks(i,"pre-create",{action:"pre-create",entityType:"project"}))throw new Error("Pre-create hook failed, aborting project creation");await u.createProject(s,{name:t,description:e,status:o,assignee:r,created:new Date().toISOString()}),await w.appendStatus(i,"project",s,"created",`status is ${o}`),await v.runHooks(i,"post-create",{action:"post-create",entityType:"project"}),console.log(`Project created: ${s}`),console.log(` Path: ${i}`);}});});var me,de=f(()=>{g();A();me=p({options:z$1.object({}),handler:async()=>{let t=j.getProjectFromPwd();t||(console.error("Not in a project directory"),process.exit(1)),console.log(t);}});});var fe,ge=f(()=>{g();x();fe=p({description:"List all projects, optionally filtered by status",options:z$1.object({status:z$1.string().optional().describe("Filter by status")}),handler:async({status:t})=>{let e=await u.listProjects(),o=[];for(let r of e){let s=await u.getProject(r);s&&(t&&s.status!==t||o.push({slug:r,name:s.name||r,status:s.status,assignee:s.assignee}));}if(o.length===0){console.log("No projects found");return}console.log("Projects:"),console.log("---");for(let r of o)console.log(`${r.slug.padEnd(20)} ${r.name?.padEnd(30)||""} ${r.status||""} ${r.assignee||""}`);}});});var ke,je=f(()=>{g();x();ke=p({description:"Output project directory path (for cd)",options:z$1.object({}),args:z$1.object({name:z$1.string().describe("Project name (slug)")}),handler:async({name:t})=>{let e=u.getProjectDir(t);console.log(e);}});});var he,ye=f(()=>{g();x();z();C();A();he=p({description:"Update project properties: name, description, status, assignee",options:z$1.object({name:z$1.string().optional().describe("New name"),description:z$1.string().optional().describe("New description"),status:z$1.string().optional().describe("New status"),assignee:z$1.string().optional().describe("New assignee")}),args:z$1.object({project:z$1.string().optional().describe("Project slug (defaults to current project from $PWD)")}),handler:async({project:t,name:e,description:o,status:r,assignee:s})=>{let i=t||j.getProjectFromPwd();if(!i)throw new Error("No project specified and not in a project directory");let a=u.getProjectDir(i);if(!await v.runHooks(a,"pre-update",{action:"pre-update",entityType:"project"}))throw new Error("Pre-update hook failed, aborting update");let m={};if(e&&(m.name=e),o&&(m.description=o),r&&(m.status=r),s&&(m.assignee=s),Object.keys(m).length===0){console.log("No updates provided");return}await u.updateProject(i,m);let d=Object.entries(m).map(([k,P])=>`${k}=${P}`).join(", ");await w.appendStatus(a,"project",i,"updated",d),await v.runHooks(a,"post-update",{action:"post-update",entityType:"project"}),console.log(`Project ${i} updated`);}});});var Te,we=f(()=>{$();g();H();T();Te=p({description:"Read a skill's SKILL.md file into the console for agent context",options:z$1.object({}),args:z$1.object({name:z$1.string().describe("Skill name (directory name)")}),handler:async({name:t})=>{let e=n.join(E.AIP_HOME,c.dirs.SKILLS,t),o=n.join(e,c.files.SKILL);if(!await n.fileExists(o))throw new Error(`Skill not found: ${t}
|
|
388
|
+
Expected at: ${o}`);await n.logFiles(o);}});});var Se,be=f(()=>{g();z();T();x();C();Se=p({description:"Create a new task with assignee and initial status",options:z$1.object({description:z$1.string().optional().describe("Task description"),assignee:z$1.string().optional().describe("Assignee agent slug"),status:z$1.string().default("backlog").describe("Initial status")}),args:z$1.object({project:z$1.string().describe("Project slug"),name:z$1.string().describe("Task name")}),handler:async({project:t,name:e,description:o,assignee:r,status:s})=>{let i=n.slugify(e),a=u.getProjectDir(t),l=u.getTaskDir(t,i);if(!await v.runHooksForContext(a,l,"pre-create",{action:"pre-create",entityType:"task",project:t}))throw new Error("Pre-create hook failed, aborting task creation");await u.createTask(t,i,{name:e,description:o,assignee:r,status:s,created:new Date().toISOString()}),await w.appendStatus(l,"task",i,"created",e),await w.appendStatus(a,"task",i,"created",`status is ${s}`),await v.runHooksForContext(a,l,"post-create",{action:"post-create",entityType:"task",project:t}),console.log(`Task created: ${i}`),console.log(` Project: ${t}`),console.log(` Path: ${l}`);}});});var Pe,xe=f(()=>{g();A();Pe=p({description:"Get the current task slug from PWD",options:z$1.object({}),handler:async()=>{let t=j.getTaskFromPwd();t||(console.error("Not in a task directory"),process.exit(1)),console.log(t);}});});var $e,ve=f(()=>{A();g();x();$e=p({description:"Output full task context (main.md, status.tsv) for ingestion by agents",options:z$1.object({project:z$1.string().optional().describe("Project slug (searches all projects if not provided)")}),args:z$1.object({task:z$1.string().optional().describe("Task slug (default: from $PWD)")}),handler:async({project:t,task:e})=>{let o=j.getCurrentContext(),r=e??o.task;if(!r)throw new Error("Need task slug (or cd into task dir)");let{project:s}=await u.findTask(r,t);await u.ingestTask(s,r);}});});var Ee,Ae=f(()=>{g();x();Ee=p({description:"List tasks, optionally filtered by project, status, assignee, or search query",options:z$1.object({project:z$1.string().optional().describe("Project slug (searches all projects if not provided)"),statuses:z$1.array(z$1.string()).default([]).describe("Filter by statuses (multiple allowed)"),assignee:z$1.string().optional().describe("Filter by assignee"),all:z$1.boolean().default(false).describe("Include all tasks (including done/blocked)"),search:z$1.string().optional().describe("Search query (matches task slug or name, case-insensitive)")}),handler:async({project:t,statuses:e,assignee:o,all:r,search:s})=>{if(e&&e.length>0){for(let d of e)if(!et.includes(d))throw new Error(`Invalid status: ${d}. Valid values: ${et.join(", ")}`)}let i;e&&e.length>0?i=e:r?i=et:i=vt;let a=t?[t]:await u.listProjects(),l={};for(let d of a){let k=await u.listTasks(d),P=[];for(let S of k){let D=await u.getTask(d,S);if(D&&!(i.length>0&&!i.includes(D.status||""))&&!(o&&D.assignee!==o)){if(s){let tt=s.toLowerCase(),mt=S.toLowerCase().includes(tt),Fe=(D.name||"").toLowerCase().includes(tt);if(!mt&&!Fe)continue}P.push({slug:S,name:D.name||S,status:D.status,assignee:D.assignee});}}P.length>0&&(l[d]=P.sort((S,D)=>S.slug.localeCompare(D.slug)));}let m=Object.keys(l).sort();if(m.length===0){console.log("No tasks found");return}for(let d of m){console.log(`
|
|
389
|
+
${d}:`),console.log("---");for(let k of l[d])console.log(`${k.slug.padEnd(20)} ${k.name?.padEnd(30)||""} ${k.status||""} ${k.assignee||""}`);}}});});var De,Oe=f(()=>{g();x();De=p({description:"Output task directory path (for cd)",options:z$1.object({project:z$1.string().optional().describe("Project slug (searches all projects if not provided)")}),args:z$1.object({task:z$1.string().describe("Task slug")}),handler:async({project:t,task:e})=>{let{project:o,task:r}=await u.findTask(e,t),s=u.getTaskDir(o,r);console.log(s);}});});var ct,St=f(()=>{A();g();z();x();C();ct=p({description:"Update task properties: name, description, status, assignee",options:z$1.object({name:z$1.string().optional().describe("New name"),description:z$1.string().optional().describe("New description"),status:z$1.string().optional().describe("New status"),assignee:z$1.string().optional().describe("New assignee"),project:z$1.string().optional().describe("Project slug (searches all projects if not provided)")}),args:z$1.object({task:z$1.string().optional().describe("Task slug (default: from $PWD)")}),handler:async({project:t,task:e,name:o,description:r,status:s,assignee:i})=>{let a=j.getCurrentContext(),l=e??a.task;if(!l)throw new Error("No task specified (use --task or cd into task dir)");let{project:m}=await u.findTask(l,t),d=u.getTaskDir(m,l),k=u.getProjectDir(m);if(!await v.runHooksForContext(k,d,"pre-update",{action:"pre-update",entityType:"task",project:m,task:l}))throw new Error("Pre-update hook failed, aborting update");let S={};if(o&&(S.name=o),r&&(S.description=r),s&&(S.status=s),i&&(S.assignee=i),Object.keys(S).length===0){console.log("No updates provided");return}if(Object.keys(S).length>0){await u.updateTask(m,l,S);let D=Object.entries(S).map(([tt,mt])=>`${tt}=${mt}`).join(", ");await w.appendStatus(d,"task",l,"updated",D);}S.status&&await w.appendStatus(k,"task",l,"updated",`status to ${S.status}`),await v.runHooksForContext(u.getProjectDir(m),d,"post-update",{action:"post-update",entityType:"task",project:m,task:l}),console.log(`Task ${l} updated`);}});});var Ce,Re=f(()=>{A();g();x();St();Ce=p({description:"Start a task: set status to in-progress, optionally print context",options:z$1.object({project:z$1.string().optional().describe("Project slug (searches all projects if not provided)"),ingest:z$1.boolean().default(false).describe("Also output context for this task")}),args:z$1.object({task:z$1.string().optional().describe("Task slug (default: from $PWD)")}),handler:async({project:t,task:e,ingest:o})=>{let r=j.getCurrentContext(),s=e??r.task;if(!s)throw new Error("No task specified (use --task or cd into task dir)");let{project:i}=await u.findTask(s,t);(await u.getTask(i,s))?.status!=="in-progress"&&await ct.handler({project:i,task:s,status:"in-progress"}),o&&await u.ingestTask(i,s);}});});var Ne,Ie=f(()=>{g();x();C();Ne=p({description:"Post-mortem analysis for a completed task",options:z$1.object({}),args:z$1.object({project:z$1.string().describe("Project slug"),task:z$1.string().describe("Task slug")}),handler:async({project:t,task:e})=>{let o=u.getTaskDir(t,e),r=await u.getTask(t,e),i=(await w.readStatus(o)).split(`
|
|
390
|
+
`).filter(m=>m.startsWith("[")).length,a=[],l=r?.name||e;i>5&&a.push("High status update count - consider breaking into smaller tasks"),l.toLowerCase().includes("implement")&&a.push("Implementation task - check if similar patterns exist to reuse"),l.toLowerCase().includes("create")&&l.toLowerCase().includes("command")&&a.push("Command creation - check existing command patterns in src/commands/"),console.log(`
|
|
391
|
+
=== Post-Mortem Analysis ===`),console.log(`Project: ${t}`),console.log(`Task: ${e}`),console.log(`Name: ${l}`),console.log(`Status: ${r?.status||"unknown"}`),console.log(`Status updates: ${i}`),a.length>0?(console.log(`
|
|
392
|
+
Suggestions:`),a.forEach(m=>console.log(` - ${m}`))):console.log(`
|
|
477
393
|
No specific suggestions - task looks well-scoped`),console.log(`
|
|
478
394
|
=== End Post-Mortem ===
|
|
479
|
-
`);}});});var
|
|
395
|
+
`);}});});var Ue,_e=f(()=>{g();T();Ue=p({description:"Read one or more files into the console",options:z$1.object({}),args:z$1.object({paths:z$1.array(z$1.string()).describe("File paths to read")}),handler:async({paths:t})=>{await n.logFiles(...t);}});});var kt={};Ke(kt,{default:()=>L});var Po,L,ot=f(()=>{Dt();Ct();Nt();Ut();Lt();Mt();zt();Bt();Yt();Xt();ee();se();ie();ce();le();de();ge();je();ye();we();be();xe();ve();Ae();Oe();Re();St();Ie();_e();Po={agent:{create:At,current:Ot,list:Rt,path:It,start:_t},help:{api:Kt,hooks:Gt,quickstart:Jt,skill:qt,usage:Qt},hook:{create:te,run:re},log:{append:ne,read:ae},project:{create:pe,current:me,list:fe,path:ke,update:he},skill:{read:Te},task:{create:Se,current:Pe,ingest:$e,list:Ee,path:De,start:Ce,update:ct},util:{postmortem:Ne,read:Ue}},L=Po;});B();ot();T();process.on("unhandledRejection",t=>{console.error("Unhandled Rejection:",t),process.exit(1);});process.on("uncaughtException",t=>{console.error("Unhandled Exception:",t),process.exit(1);});async function Le(t){let[e,o,...r]=t;(e==="--version"||e==="-v")&&(console.log(b.version),process.exit(0));try{(!e||!n.isKeyOf(e,L))&&(await L.help.usage.handler({}),process.exit(1));let s=L[e];(!o||!n.isKeyOf(o,s))&&(await L.help.usage.handler({name:e}),process.exit(1));let i=s[o];i||(console.error(`Error: unknown command '${e} ${o}'`),console.log("Run with --help for more information"),process.exit(1)),await i.handler(i.parser.name(`${e} ${o}`).parse(r));}catch(s){console.error("Error:",n.errorMessage(s)),process.exit(1);}}var Ri=Le,Ni=L;n.isMain()&&Le(process.argv.slice(2));export{Ni as commands,Ri as default};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "ai-projects",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.5.0",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Useful CLI for AI agents to create and manage projects, tasks, skills and agents",
|
|
6
6
|
"main": "dist/index.js",
|
|
@@ -46,15 +46,18 @@
|
|
|
46
46
|
"publish:dry": "npm pack --dry-run",
|
|
47
47
|
"version:patch": "npm version patch",
|
|
48
48
|
"version:minor": "npm version minor",
|
|
49
|
-
"version:major": "npm version major"
|
|
49
|
+
"version:major": "npm version major",
|
|
50
|
+
"agent:stop": "npm run -s lint:full:silent"
|
|
50
51
|
},
|
|
51
52
|
"keywords": [
|
|
52
53
|
"ai",
|
|
53
|
-
"
|
|
54
|
-
"
|
|
54
|
+
"aip",
|
|
55
|
+
"project",
|
|
56
|
+
"task",
|
|
57
|
+
"kanban",
|
|
55
58
|
"cli",
|
|
56
|
-
"
|
|
57
|
-
"
|
|
59
|
+
"agent",
|
|
60
|
+
"automation"
|
|
58
61
|
],
|
|
59
62
|
"author": "Ariel Flesler <aflesler@gmail.com>",
|
|
60
63
|
"license": "MIT",
|