@fxri/toolkit 1.12.3 → 1.12.5
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/CHANGELOG.md +68 -0
- package/README.md +2 -2
- package/SPEC.md +3 -2
- package/dist/cli.cjs +64 -64
- package/dist/cli.js +64 -64
- package/dist/index.cjs +1 -1
- package/dist/index.js +1 -1
- package/package.json +21 -22
- package/skills/README.md +10 -10
- package/skills/fxri-plan-to-task/SKILL.md +33 -19
- package/skills/fxri-plan-to-task/references/conventions-migration.md +59 -0
- package/skills/fxri-plan-to-task/references/conventions-spec.md +10 -142
- package/skills/fxri-plan-to-task/references/conventions-templates.md +83 -0
- package/skills/fxri-plan-to-task/references/task-spec.md +8 -3
- package/skills/fxri-release-changelog/SKILL.md +5 -5
- package/skills/fxri-release-changelog/references/changelog-format.md +2 -2
- package/skills/fxri-session-recap/SKILL.md +24 -32
- package/skills/fxri-session-recap/references/mode-2-recovery.md +13 -0
- package/skills/fxri-session-recap/references/mode-3-time-fix.md +12 -0
package/dist/index.cjs
CHANGED
|
@@ -62,7 +62,7 @@ ${Tt(Xe)}
|
|
|
62
62
|
${Vo}
|
|
63
63
|
|
|
64
64
|
${Tt(Je)}
|
|
65
|
-
`;var Ie=require("fs"),It=require("path");var Ze=require("fs"),Lt=require("path");var Ko=/^\s*(`{3,}|~{3,})/;function Go(e){let t=Ko.exec(e)?.[1];return t?{char:t.charAt(0),len:t.length}:null}function Xo(e){return/^\s*/.exec(e)?.[0]??""}function Jo(e){return e.replace(/^(:?)-+(:?)$/,"$1---$2")}function Zo(e){if(!ue(e))return e;let t=ee(e),n=Ce(e)?t.map(Jo):t;return`${Xo(e)}| ${n.join(" | ")} |`}function qe(e){let t=e.map(()=>!0),n=null;for(let r=0;r<e.length;r++){let o=Go(e[r]??"");if(n===null){o&&(n=o,t[r]=!1);continue}t[r]=!1,o&&o.char===n.char&&o.len>=n.len&&(n=null)}return t}function Vn(e){let t=e.split(/\r?\n/),n=qe(t),r=[];for(let o=0;o<t.length;o++){if(!n[o])continue;let s=t[o]??"";ue(s)&&Zo(s)!==s&&r.push(o+1)}return r}function Kn(e){if(!(0,Ze.existsSync)(e))return[];let t=[],n=r=>{for(let o of(0,Ze.readdirSync)(r,{withFileTypes:!0})){let s=(0,Lt.join)(r,o.name);o.isDirectory()?n(s):o.isFile()&&o.name.endsWith(".md")&&t.push(s)}};return n(e),t.sort()}var qo=/^[-*]\s+(?:\*\*)?确立来源/,Qo=/本次起入表|新立条目:|条文全文落/;function Gn(e,t){return e.length===t.length&&t.every((n,r)=>e[r]===n)}function Qe(e){return e.map(t=>`\u300C${t}\u300D`).join("")}function es(e){return Gn(e.header,Ge)?[]:[{file:e.indexFile,message:`${te} \u7D22\u5F15\u8868\u5217\u96C6\u5408\u504F\u79BB v3 \u89C4\u8303\uFF1A\u5E94\u6070\u4E3A ${Qe(Ge)}\uFF0C\u5B9E\u4E3A ${Qe(e.header)}\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \u5F52\u4E00`}]}function ts(e){let t=[],n=[[z,e.historyFile,Xe,Se],[Ae,e.retiredFile,Je,wt]];for(let[r,o,s,i]of n){if(!(0,Ie.existsSync)(o))continue;let l=xe(R(o).split(/\r?\n/),i);!l||Gn(l.header,s)||t.push({file:o,line:l.headerLine+1,message:`${r} \u8868\u5934\u504F\u79BB v3 \u89C4\u8303\uFF1A\u5E94\u6070\u4E3A ${Qe(s)}\uFF0C\u5B9E\u4E3A ${Qe(l.header)}\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \u5F52\u4E00`})}return t}function ns(e){let t=[],n=[...At(e),e.historyFile,e.retiredFile];for(let r of n){if(!(0,Ie.existsSync)(r))continue;let o=R(r).split(/\r?\n/),s=qe(o),i=o.map((p,m)=>s[m]?p:""),l=Pn(i),c=l[0];if(c===void 0)continue;let f=l.length>1?`\uFF08\u53E6\u6709 ${l.length-1} \u5904\uFF09`:"";t.push({file:r,line:c.line,message:`${(0,It.basename)(r)} \u7B2C ${c.line} \u884C\u8868\u5934\u4E0E\u5206\u9694\u884C\u5217\u6570\u4E0D\u4E00\u81F4\uFF08\u8868\u5934 ${c.headerCols} \u5217 / \u5206\u9694\u884C ${c.sepCols} \u5217\uFF09${f}\uFF1A\u8BF7\u6309 conventions-spec \u5F52\u4E00`})}return t}function rs(e){let t=[],n=At(e).filter(r=>r!==e.indexFile);for(let r of n){if(!(0,Ie.existsSync)(r))continue;let o=R(r).split(/\r?\n/),s=qe(o),i=[];o.forEach((f,p)=>{s[p]&&qo.test(f)&&i.push(p+1)});let l=i[0];if(l===void 0)continue;let c=i.length>1?`\uFF08\u53E6\u6709 ${i.length-1} \u5904\uFF09`:"";t.push({file:r,line:l,message:`${(0,It.basename)(r)} \u7B2C ${l} \u884C\u6B8B\u7559\u300C\u786E\u7ACB\u6765\u6E90\u300D\u5B50\u9879${c}\uFF1A\u6765\u6E90\u7531\u7D22\u5F15\u884C\u4E0E history.md / retired.md \u627F\u8F7D\uFF0C\u5206\u518C\u5185\u4E0D\u91CD\u590D\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \u5F52\u4E00`})}return t}function os(e){if(!(0,Ie.existsSync)(e.historyFile))return[];let t=xe(R(e.historyFile).split(/\r?\n/),Se);if(!t)return[];let n=zn(t.header,$t);if(n<0)return[];let r=[];t.rows.forEach((i,l)=>{let c=t.rowLines[l];c!==void 0&&Qo.test(i[n]??"")&&r.push(c+1)});let o=r[0];if(o===void 0)return[];let s=r.length>1?`\uFF08\u53E6\u6709 ${r.length-1} \u5904\uFF09`:"";return[{file:e.historyFile,line:o,message:`${z} \u7B2C ${o} \u884C\u300C\u4FEE\u8BA2\u5185\u5BB9\u300D\u5217\u542B\u7981\u7528\u8BED\u6599${s}\uFF1A\u4E0D\u5F97\u5199\u81EA\u6307\u5957\u8BDD\uFF08\u5982\u300C\uFF08\u672C\u6B21\u8D77\u5165\u8868\uFF09\u300D\u300C\u65B0\u7ACB\u6761\u76EE\uFF1A\u300D\uFF09\u6216\u91CD\u590D\u7D22\u5F15\u5217\u7684\u6761\u6587\u53BB\u5411\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \xA73.2 \u5F52\u4E00`}]}function Xn(e){if(!e.hasIndex)return[];let t=[];return e.form==="v3"&&t.push(...es(e),...ts(e),...rs(e),...os(e)),t.push(...ns(e)),t}var Jn=require("fs"),_t=require("path");var ss="toolkit-conventions",is="SKILL.md",cs=[".agents/skills",".trae/skills",".
|
|
65
|
+
`;var Ie=require("fs"),It=require("path");var Ze=require("fs"),Lt=require("path");var Ko=/^\s*(`{3,}|~{3,})/;function Go(e){let t=Ko.exec(e)?.[1];return t?{char:t.charAt(0),len:t.length}:null}function Xo(e){return/^\s*/.exec(e)?.[0]??""}function Jo(e){return e.replace(/^(:?)-+(:?)$/,"$1---$2")}function Zo(e){if(!ue(e))return e;let t=ee(e),n=Ce(e)?t.map(Jo):t;return`${Xo(e)}| ${n.join(" | ")} |`}function qe(e){let t=e.map(()=>!0),n=null;for(let r=0;r<e.length;r++){let o=Go(e[r]??"");if(n===null){o&&(n=o,t[r]=!1);continue}t[r]=!1,o&&o.char===n.char&&o.len>=n.len&&(n=null)}return t}function Vn(e){let t=e.split(/\r?\n/),n=qe(t),r=[];for(let o=0;o<t.length;o++){if(!n[o])continue;let s=t[o]??"";ue(s)&&Zo(s)!==s&&r.push(o+1)}return r}function Kn(e){if(!(0,Ze.existsSync)(e))return[];let t=[],n=r=>{for(let o of(0,Ze.readdirSync)(r,{withFileTypes:!0})){let s=(0,Lt.join)(r,o.name);o.isDirectory()?n(s):o.isFile()&&o.name.endsWith(".md")&&t.push(s)}};return n(e),t.sort()}var qo=/^[-*]\s+(?:\*\*)?确立来源/,Qo=/本次起入表|新立条目:|条文全文落/;function Gn(e,t){return e.length===t.length&&t.every((n,r)=>e[r]===n)}function Qe(e){return e.map(t=>`\u300C${t}\u300D`).join("")}function es(e){return Gn(e.header,Ge)?[]:[{file:e.indexFile,message:`${te} \u7D22\u5F15\u8868\u5217\u96C6\u5408\u504F\u79BB v3 \u89C4\u8303\uFF1A\u5E94\u6070\u4E3A ${Qe(Ge)}\uFF0C\u5B9E\u4E3A ${Qe(e.header)}\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \u5F52\u4E00`}]}function ts(e){let t=[],n=[[z,e.historyFile,Xe,Se],[Ae,e.retiredFile,Je,wt]];for(let[r,o,s,i]of n){if(!(0,Ie.existsSync)(o))continue;let l=xe(R(o).split(/\r?\n/),i);!l||Gn(l.header,s)||t.push({file:o,line:l.headerLine+1,message:`${r} \u8868\u5934\u504F\u79BB v3 \u89C4\u8303\uFF1A\u5E94\u6070\u4E3A ${Qe(s)}\uFF0C\u5B9E\u4E3A ${Qe(l.header)}\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \u5F52\u4E00`})}return t}function ns(e){let t=[],n=[...At(e),e.historyFile,e.retiredFile];for(let r of n){if(!(0,Ie.existsSync)(r))continue;let o=R(r).split(/\r?\n/),s=qe(o),i=o.map((p,m)=>s[m]?p:""),l=Pn(i),c=l[0];if(c===void 0)continue;let f=l.length>1?`\uFF08\u53E6\u6709 ${l.length-1} \u5904\uFF09`:"";t.push({file:r,line:c.line,message:`${(0,It.basename)(r)} \u7B2C ${c.line} \u884C\u8868\u5934\u4E0E\u5206\u9694\u884C\u5217\u6570\u4E0D\u4E00\u81F4\uFF08\u8868\u5934 ${c.headerCols} \u5217 / \u5206\u9694\u884C ${c.sepCols} \u5217\uFF09${f}\uFF1A\u8BF7\u6309 conventions-spec \u5F52\u4E00`})}return t}function rs(e){let t=[],n=At(e).filter(r=>r!==e.indexFile);for(let r of n){if(!(0,Ie.existsSync)(r))continue;let o=R(r).split(/\r?\n/),s=qe(o),i=[];o.forEach((f,p)=>{s[p]&&qo.test(f)&&i.push(p+1)});let l=i[0];if(l===void 0)continue;let c=i.length>1?`\uFF08\u53E6\u6709 ${i.length-1} \u5904\uFF09`:"";t.push({file:r,line:l,message:`${(0,It.basename)(r)} \u7B2C ${l} \u884C\u6B8B\u7559\u300C\u786E\u7ACB\u6765\u6E90\u300D\u5B50\u9879${c}\uFF1A\u6765\u6E90\u7531\u7D22\u5F15\u884C\u4E0E history.md / retired.md \u627F\u8F7D\uFF0C\u5206\u518C\u5185\u4E0D\u91CD\u590D\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \u5F52\u4E00`})}return t}function os(e){if(!(0,Ie.existsSync)(e.historyFile))return[];let t=xe(R(e.historyFile).split(/\r?\n/),Se);if(!t)return[];let n=zn(t.header,$t);if(n<0)return[];let r=[];t.rows.forEach((i,l)=>{let c=t.rowLines[l];c!==void 0&&Qo.test(i[n]??"")&&r.push(c+1)});let o=r[0];if(o===void 0)return[];let s=r.length>1?`\uFF08\u53E6\u6709 ${r.length-1} \u5904\uFF09`:"";return[{file:e.historyFile,line:o,message:`${z} \u7B2C ${o} \u884C\u300C\u4FEE\u8BA2\u5185\u5BB9\u300D\u5217\u542B\u7981\u7528\u8BED\u6599${s}\uFF1A\u4E0D\u5F97\u5199\u81EA\u6307\u5957\u8BDD\uFF08\u5982\u300C\uFF08\u672C\u6B21\u8D77\u5165\u8868\uFF09\u300D\u300C\u65B0\u7ACB\u6761\u76EE\uFF1A\u300D\uFF09\u6216\u91CD\u590D\u7D22\u5F15\u5217\u7684\u6761\u6587\u53BB\u5411\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \xA73.2 \u5F52\u4E00`}]}function Xn(e){if(!e.hasIndex)return[];let t=[];return e.form==="v3"&&t.push(...es(e),...ts(e),...rs(e),...os(e)),t.push(...ns(e)),t}var Jn=require("fs"),_t=require("path");var ss="toolkit-conventions",is="SKILL.md",cs=[".agents/skills",".trae/skills",".claude/skills","agent/skills",".augment/skills",".codebuddy/skills",".continue/skills",".crush/skills",".devin/skills",".goose/skills",".grok/skills",".hermes/skills",".iflow/skills",".junie/skills",".kiro/skills",".openhands/skills",".qwen/skills",".roo/skills",".windsurf/skills"];function Zn(e){let t=[];for(let n of cs){let r=`${n}/${ss}`,o=`${r}/${is}`;(0,Jn.existsSync)((0,_t.join)(e,o))&&t.push({dir:r,file:o,version:Wn(R((0,_t.join)(e,o)))})}return t}function qn(e){let[t]=e;if(!t)return null;let n=o=>o.version===null?"\u65E0":`v${o.version}`;if(e.length===1)return{file:t.file,message:`\u5165\u53E3\u58F3\u6807\u8BB0 ${n(t)}\uFF0C\u4E0E\u5F53\u524D toolkit \u7684 v${ye} \u4E0D\u4E00\u81F4\uFF1A\u91CD\u8DD1 toolkit init \u53EF\u8865\u9F50`};let r=e.map(o=>`${o.file}\uFF08\u6807\u8BB0 ${n(o)}\uFF09`).join("\u3001");return{file:t.file,message:`\u5165\u53E3\u58F3\u6807\u8BB0\u4E0E\u5F53\u524D toolkit \u7684 v${ye} \u4E0D\u4E00\u81F4\uFF0C\u5171 ${e.length} \u5904\uFF1A${r}\uFF1B\u91CD\u8DD1 toolkit init \u53EF\u4E00\u6B21\u6027\u8865\u9F50`}}function Qn(e){let[t]=e;if(!t)return null;if(e.length===1)return{file:t.file,message:`\u5165\u53E3\u58F3 ${t.file} \u88AB gitignore \u8986\u76D6\uFF1A\u4E0D\u4F1A\u968F git \u5206\u53D1\uFF0C\u8BF7\u628A\u8BE5\u8DEF\u5F84\u4ECE\u5FFD\u7565\u89C4\u5219\u4E2D\u6392\u9664`};let n=e.map(r=>r.file).join("\u3001");return{file:t.file,message:`\u5165\u53E3\u58F3\u88AB gitignore \u8986\u76D6\uFF0C\u5171 ${e.length} \u5904\uFF1A${n}\uFF1B\u4E0D\u4F1A\u968F git \u5206\u53D1\uFF0C\u8BF7\u628A\u76F8\u5E94\u8DEF\u5F84\u4ECE\u5FFD\u7565\u89C4\u5219\u4E2D\u6392\u9664`}}var er=/待办|待实施|待核对|待确认|待开始|待评估|待排期|待做|TODO/,ls=/^[-*]\s*\[ \]\s/m,as=/^[-*]\s*\[ \]/,us=/^\d{4}-\d{1,2}-\d{1,2}(?:[T\s]\d{1,2}:\d{2}(?::\d{2})?)?$/,fs=/^\d{4}-\d{1,2}-\d{1,2}[T\s]\d{1,2}:\d{2}(?::\d{2})?$/,ds=/^\d{8}-[^-]+-.+\.md$/;function tr(e){let t=e.match(/^(\d{4})-?(\d{1,2})-?(\d{1,2})/);if(!t)return!1;let[,n,r,o]=t;if(!n||!r||!o)return!1;let s=+n,i=+r,l=+o;if(i<1||i>12||l<1||l>31)return!1;let c=new Date(Date.UTC(s,i-1,l));return c.getUTCFullYear()===s&&c.getUTCMonth()===i-1&&c.getUTCDate()===l}function Y(e,t,n){for(let r=0;r<t;r++)if((e[r]??"").trimStart().startsWith(`${n}:`))return r+1;return 1}function nr(e,t,n){let r=!1;for(let o=t;o<e.length;o++){let s=e[o]??"";if(!r&&/^# /.test(s)){r=!0;continue}if(n.test(s))return o+1}return t+1}function ps(e,t){let n=[];t.startsWith("\uFEFF")&&n.push({level:"warn",file:e,line:1,message:"\u6587\u4EF6\u542B UTF-8 BOM\uFF0C\u5EFA\u8BAE\u53BB\u9664\uFF08\u90E8\u5206\u89E3\u6790\u5DE5\u5177\u4F1A\u5F02\u5E38\uFF09"});let o=t.split(/\r?\n/).findIndex(i=>/[ \t]+$/.test(i));o>=0&&n.push({level:"warn",file:e,line:o+1,message:"\u884C\u5C3E\u6709\u591A\u4F59\u7A7A\u767D\uFF08\u7A7A\u683C\u6216\u5236\u8868\u7B26\uFF09\uFF0C\u5EFA\u8BAE\u53BB\u9664"});let s=-1;for(let i=0;i<t.length;i++)if(t[i]===`
|
|
66
66
|
`&&(i===0||t[i-1]!=="\r")){s=i;break}return s>=0&&t.includes(`\r
|
|
67
67
|
`)&&n.push({level:"warn",file:e,line:t.slice(0,s).split(`
|
|
68
68
|
`).length,message:"\u6362\u884C\u7B26\u6DF7\u7528\uFF08\u540C\u6587\u4EF6\u540C\u65F6\u542B CRLF \u4E0E LF\uFF09\uFF0C\u5EFA\u8BAE\u7EDF\u4E00\u4E3A LF"}),n}function Ft(e){let t=[],n=(0,j.basename)(e),r=(0,V.readFileSync)(e,"utf8");t.push(...ps(n,r));let o=W(r),s=o.split(/\r?\n/),i=Fe.exec(o)?.[0].split(/\r?\n/).length??0;if(!Fe.test(o))return t.push({level:"error",file:n,line:1,message:"\u7F3A\u5C11 frontmatter"}),t;let c=Oe(o);for(let a of Object.keys(c))Re.includes(a)||t.push({level:"warn",file:n,line:Y(s,i,a),message:`frontmatter \u542B\u672A\u77E5\u5B57\u6BB5\u300C${a}\u300D\uFF0C\u672C\u5DE5\u5177\u4E0D\u8BFB\u53D6\uFF08\u5F52\u6863\u4E0E\u5F52\u4E00\u5316\u4E0D\u4F1A\u4FDD\u7559\uFF0C\u8BF7\u81EA\u884C\u7EF4\u62A4\uFF09`});if(c.status?de.includes(c.status)||t.push({level:"error",file:n,line:Y(s,i,"status"),message:`status \u975E\u6CD5\u503C\u300C${c.status}\u300D\uFF0C\u5E94\u4E3A ${de.join(" / ")}`}):t.push({level:"error",file:n,line:Y(s,i,"status"),message:"frontmatter \u7F3A\u5C11 status \u5B57\u6BB5"}),ne.includes(c.status)&&!c.completed&&t.push({level:"error",file:n,line:Y(s,i,"completed"),message:`status \u4E3A\u300C${c.status}\u300D\u4F46\u7F3A\u5C11 completed \u5B8C\u6210\u65F6\u95F4`}),c.completed){let a=c.completed.trim(),d=Y(s,i,"completed");if(!us.test(a))t.push({level:"warn",file:n,line:d,message:`completed\u300C${c.completed}\u300D\u683C\u5F0F\u975E\u6CD5\uFF0C\u5E94\u4E3A YYYY-MM-DD HH:mm`});else{let g=a.match(/^\d{4}-\d{1,2}-\d{1,2}/)?.[0]??a;tr(g)?fs.test(a)?he(a)?t.push({level:"warn",file:n,line:d,message:`completed\u300C${c.completed}\u300D\u665A\u4E8E\u5F53\u524D\u7CFB\u7EDF\u65F6\u95F4 ${ge} \u5C0F\u65F6\u4EE5\u4E0A\uFF0C\u7591\u4F3C\u65F6\u95F4\u6E90\u9519\u8BEF\uFF0C\u8BF7\u5F53\u573A\u53D6\u7CFB\u7EDF\u65F6\u95F4\u6838\u5B9E`}):/(?:[T\s]00:00(?::00)?)$/.test(a)&&t.push({level:"warn",file:n,line:d,message:`completed\u300C${c.completed}\u300D\u6070\u4E3A\u96F6\u70B9\u6574\uFF0C\u7591\u4F3C\u53EA\u586B\u4E86\u65E5\u671F\u88AB\u8865\u96F6\uFF0C\u8BF7\u6838\u5B9E\u5B9E\u9645\u5B8C\u6210\u65F6\u95F4`}):t.push({level:"warn",file:n,line:d,message:`completed\u300C${c.completed}\u300D\u5EFA\u8BAE\u8865\u5168\u4E3A\u5B8C\u6574\u65F6\u95F4 YYYY-MM-DD HH:mm`}):t.push({level:"warn",file:n,line:d,message:`completed\u300C${c.completed}\u300D\u65E5\u671F\u4E0D\u5B58\u5728\uFF0C\u8BF7\u6838\u5BF9`})}}c.owner||t.push({level:"warn",file:n,line:Y(s,i,"owner"),message:"\u7F3A\u5C11 owner \u8D1F\u8D23\u4EBA\u5B57\u6BB5"}),c.created?/^\d{8}$/.test(c.created.trim())?tr(c.created.trim())||t.push({level:"warn",file:n,line:Y(s,i,"created"),message:`created\u300C${c.created}\u300D\u65E5\u671F\u4E0D\u5B58\u5728\uFF0C\u8BF7\u6838\u5BF9`}):t.push({level:"warn",file:n,line:Y(s,i,"created"),message:`created\u300C${c.created}\u300D\u683C\u5F0F\u975E\u6CD5\uFF0C\u5E94\u4E3A YYYYMMDD`}):t.push({level:"warn",file:n,line:Y(s,i,"created"),message:"\u7F3A\u5C11 created \u521B\u5EFA\u65E5\u671F\u5B57\u6BB5"}),c.updated&&c.created&&/^\d{8}$/.test(c.updated.trim())&&/^\d{8}$/.test(c.created.trim())&&c.updated.trim()<c.created.trim()&&t.push({level:"error",file:n,line:Y(s,i,"updated"),message:`updated ${c.updated.trim()} \u65E9\u4E8E created ${c.created.trim()}\uFF0C\u65F6\u95F4\u7EBF\u77DB\u76FE`});let f=n.match(/^(\d{8})-/);if(ds.test(n)?c.created&&/^\d{8}$/.test(c.created.trim())&&f&&c.created.trim()!==f[1]&&t.push({level:"warn",file:n,message:`\u6587\u4EF6\u540D\u65E5\u671F ${f[1]} \u4E0E created ${c.created.trim()} \u4E0D\u4E00\u81F4`}):t.push({level:"warn",file:n,message:"\u6587\u4EF6\u540D\u4E0D\u7B26\u5408\u89C4\u8303 {YYYYMMDD}-{\u8D1F\u8D23\u4EBA}-{\u7B80\u8FF0}.md"}),c.scope){let a=c.scope.trim(),d=Y(s,i,"scope");/[、,,]/.test(a)&&t.push({level:"warn",file:n,line:d,message:`scope\u300C${c.scope}\u300D\u542B\u987F\u53F7/\u9017\u53F7\u7591\u4F3C\u591A\u503C\u5206\u9694\uFF0C\u591A\u503C\u8BF7\u6539\u7528\u534A\u89D2\u52A0\u53F7\u8FDE\u63A5\uFF08\u5982 scope: web+server\uFF09`}),/[/\\]/.test(a)&&t.push({level:"warn",file:n,line:d,message:`scope\u300C${c.scope}\u300D\u542B\u8DEF\u5F84\u5206\u9694\u7B26\uFF0C\u591A\u503C\u8BF7\u6539\u7528\u534A\u89D2\u52A0\u53F7\u8FDE\u63A5\uFF08\u5982 scope: web+server\uFF09\uFF0C\u7AEF\u540D\u672C\u8EAB\u4E0D\u5F97\u542B\u5206\u9694\u7B26`}),/[()()]/.test(a)&&t.push({level:"warn",file:n,line:d,message:`scope\u300C${c.scope}\u300D\u542B\u62EC\u53F7\u7591\u4F3C\u6CE8\u91CA\u6027\u6587\u5B57\uFF0C\u8BF4\u660E\u8BF7\u79FB\u5165\u6B63\u6587`})}let p=Yt(Z(o)),h=se("check")?.pendingMarkers!==!1?p.match(er):null;return h&&t.push({level:"warn",file:n,line:nr(s,i,er),message:`\u6B63\u6587\u542B\u672A\u95ED\u5408\u5F85\u529E\u6807\u8BB0\u300C${h[0]}\u300D\uFF0C\u5EFA\u8BAE\u62C6\u5206\u4E3A\u72EC\u7ACB active \u4EFB\u52A1\u6216\u660E\u786E\u95ED\u73AF`}),se("check")?.includeCheckbox!==!1&&ls.test(p)&&t.push({level:"warn",file:n,line:nr(s,i,as),message:"\u6B63\u6587\u542B\u672A\u52FE\u9009\u5F85\u529E\u9879\u300C- [ ]\u300D\uFF0C\u5EFA\u8BAE\u62C6\u5206\u4E3A\u72EC\u7ACB active \u4EFB\u52A1\u6216\u52FE\u9009\u5B8C\u6210"}),t}function ms(e){let t=[];if(!(0,V.existsSync)(e))return t;for(let n of(0,V.readdirSync)(e,{withFileTypes:!0}))if(!(n.name==="active"||n.name==="archive")){if(n.isFile())n.name.endsWith(".md")&&/^\d{8}-/.test(n.name)&&t.push(n.name);else if(n.isDirectory())for(let r of(0,V.readdirSync)((0,j.join)(e,n.name)))r.endsWith(".md")&&/^\d{8}-/.test(r)&&t.push(`${n.name}/${r}`)}return t}function gs(e){let t=rn(e);if(!t)return[];let n=F(e,t),r=zt(t,e);return r.state==="not-a-repo"||r.state==="outside-repo"?[]:r.state==="unavailable"?[{level:"warn",file:n,message:`\u672C\u5730\u914D\u7F6E\u6587\u4EF6\u5FFD\u7565\u5224\u5B9A\u4E0D\u53EF\u7528\uFF08${r.detail??"\u672A\u77E5\u539F\u56E0"}\uFF09\uFF0C\u8BF7\u6838\u5B9E git \u73AF\u5883`}]:r.state==="tracked"?[{level:"warn",file:n,message:`\u672C\u5730\u914D\u7F6E\u6587\u4EF6\u5DF2\u88AB\u5FFD\u7565\u89C4\u5219\u8986\u76D6\u4F46\u4ECD\u88AB git \u8DDF\u8E2A\uFF08\u7591\u4F3C\u5386\u53F2 git add -f\uFF09\uFF1A\u6267\u884C git rm --cached ${n} \u540E\u624D\u4F1A\u771F\u6B63\u4E0D\u5165\u5E93`}]:r.state==="ignored"?[]:[{level:"warn",file:n,message:"\u672C\u5730\u914D\u7F6E\u6587\u4EF6\u672A\u88AB gitignore \u8986\u76D6\uFF0C\u53EF\u80FD\u968F git \u63D0\u4EA4\u6CC4\u9732\u4E2A\u4EBA\u914D\u7F6E\uFF1A\u91CD\u8DD1 toolkit init \u53EF\u81EA\u52A8\u8865\u5199\u5FFD\u7565\u884C"}]}function hs(e,t){let n=[],r=Ct(e);r.hasLegacy&&n.push({level:"warn",file:Ke,message:r.hasDir?"\u65E7\u5355\u6587\u4EF6\u89C4\u8303\u8F7D\u4F53\u5DF2\u88AB conventions/ \u76EE\u5F55\u5F62\u6001\u53D6\u4EE3\uFF0C\u5EFA\u8BAE\u6E05\u7406\uFF08\u4E24\u8005\u5E76\u5B58\u65F6\u4EE5\u76EE\u5F55\u5F62\u6001\u4E3A\u51C6\uFF09":"\u65E7\u5355\u6587\u4EF6\u89C4\u8303\u8F7D\u4F53\uFF0C\u5EFA\u8BAE\u8FC1\u79FB\u4E3A conventions/ \u76EE\u5F55\u5F62\u6001\uFF08index.md \u4F5C\u552F\u4E00\u5165\u53E3 + common.md / \u7AEF\u5206\u518C\u6309\u9700\u521B\u5EFA\uFF09"}),r.hasDir&&!r.hasIndex&&n.push({level:"warn",file:`conventions/${te}`,message:"\u89C4\u8303\u8F7D\u4F53\u7F3A index.md\uFF08\u552F\u4E00\u5165\u53E3\u4E0E\u552F\u4E00\u6743\u5A01\uFF09\uFF0C\u8BF7\u8865\u9F50"}),r.form==="abnormal"&&n.push({level:"warn",file:`conventions/${te}`,message:r.markerVersion===Le?`\u89C4\u8303\u8F7D\u4F53\u6807\u4E3A v${Le} \u4F46\u7F3A ${z} \u6216\u7D22\u5F15\u8868\u9996\u5217\u975E ${fe}\uFF0C\u8BF7\u8865\u9F50\u6216\u6267\u884C toolkit conventions upgrade`:`\u89C4\u8303\u8F7D\u4F53\u5B58\u5728 ${z} \u4F46\u7D22\u5F15\u8868\u9996\u5217\u4ECD\u975E ${fe}\uFF08\u5F62\u6001\u5F02\u5E38\uFF09\uFF0C\u8BF7\u4EBA\u5DE5\u786E\u8BA4`}),n.push(...bs(e,r));let o=Zn(t),s=Pt(t,o.map(l=>l.file)),i=[qn(o.filter(l=>l.version!==ye)),Qn(o.filter(l=>s.has(l.file)))];for(let l of i)l&&n.push({level:"warn",file:l.file,message:l.message});return n.push(...gs(t)),n}function bs(e,t){return Xn(t).map(n=>({level:"warn",file:F(e,n.file),...n.line===void 0?{}:{line:n.line},message:n.message}))}var rr=6;function ks(e){let t=[];for(let n of Kn(e)){let r=Vn(R(n));if(r.length===0)continue;let o=r.slice(0,rr).join("\u3001");t.push({level:"warn",file:F(e,n),line:r[0],message:`\u8868\u683C\u5B58\u5728\u5217\u5BF9\u9F50\u586B\u5145\uFF08\u504F\u79BB\u7D27\u51D1\u5F62\u6001\uFF09${r.length} \u884C\uFF08\u7B2C ${o}${r.length>rr?" \u2026":""} \u884C\uFF09\uFF1A\u6267\u884C toolkit conventions format \u5F52\u4E00`})}return t}function ys(e){if(Ct(e).form!=="v3")return[];let t=(0,j.join)(e,Ve,z);if(!(0,V.existsSync)(t))return[];let n=xe(R(t).split(/\r?\n/),Se);if(!n)return[];let r=n.rowLines.filter((o,s)=>!Un((n.rows[s]??[])[0]??""));return r.length===0?[]:[{level:"warn",file:F(e,t),line:(r[0]??0)+1,message:`\u6F14\u8FDB\u8BB0\u5F55\u6709 ${r.length} \u884C\u9996\u5217\u4E0D\u662F\u7A33\u5B9A ID\uFF08\u5E94\u8BB0\u884C\u5185\u4EE3\u7801\u5305\u88F9\u7684 C-<n>\uFF09\uFF1A\u8BF7\u4EBA\u5DE5\u6838\u5BF9\u8865\u5F55\uFF08\u5386\u53F2\u884C\u53EA\u8FFD\u52A0\uFF0C\u4E0D\u81EA\u52A8\u6539\u5199\uFF09`}]}function sr(e=".tasks",t=process.cwd()){let n=(0,j.join)(e,"active"),r=L(n),o=[];for(let c of r)o.push(...Ft(c)),(0,j.dirname)(c)===n&&o.push({level:"warn",file:(0,j.basename)(c),message:"active \u4EFB\u52A1\u5E94\u653E\u5165 {YYYYMM} \u6708\u4EFD\u5B50\u76EE\u5F55\uFF08\u5F53\u524D\u76F4\u653E active \u6839\u76EE\u5F55\uFF09"});for(let c of ms(e))o.push({level:"warn",file:c,message:"\u4EFB\u52A1\u6587\u4EF6\u6E38\u79BB\u4E8E active/ \u4E4B\u5916\uFF0Ctasks/check/archive \u5747\u4E0D\u4F1A\u8BFB\u53D6\uFF0C\u5E94\u79FB\u5165 active/{YYYYMM}/ \u6708\u4EFD\u5B50\u76EE\u5F55"});o.push(...hs(e,t)),o.push(...ks(e)),o.push(...ys(e));for(let c of ze(e))o.push({level:"warn",file:c.file,message:c.message});let s=new Map;for(let c of r){let f=(0,j.basename)(c,".md"),p=s.get(f);p?p.push(c):s.set(f,[c])}for(let[c,f]of s)f.length>1&&o.push({level:"warn",file:c,message:`\u5B58\u5728 ${f.length} \u4E2A\u540C\u540D\u4EFB\u52A1\u6587\u4EF6\uFF0C\u7591\u4F3C\u91CD\u590D\u5EFA\u6863`});o.push(...Ss(r,e));let i=o.filter(c=>c.level==="error").length,l=o.length-i;return{issues:o,errorCount:i,warnCount:l}}var or=new Map;function xs(e){let t=(0,V.statSync)(e),n=or.get(e);if(n&&n.mtimeMs===t.mtimeMs)return n.titles;let r=[],o=new Set;try{for(let s of N(R(e)).blocks)s.title&&!o.has(s.title)&&(o.add(s.title),r.push(s.title))}catch{}return or.set(e,{mtimeMs:t.mtimeMs,titles:r}),r}function Ss(e,t){let n=[],r=new Set(e.map(u=>(0,j.basename)(u,".md"))),o=new Map,s=u=>u.trim().replace(/\.md$/,"").trim();for(let u of e){let a=(0,j.basename)(u,".md"),d=R(u),g=Oe(d);o.set(a,je(g.depends_on).map(s))}if(![...o.values()].some(u=>u.length>0))return n;let i=null,l=u=>{if(!i){i=new Map;for(let a of L((0,j.join)(t,"archive")))for(let d of xs(a))i.has(d)||i.set(d,F(t,a))}return i.get(u)};for(let[u,a]of o)for(let d of a)if(!r.has(d)){let g=l(d);n.push({level:"warn",file:u,message:g?`\u4F9D\u8D56\u7684\u4EFB\u52A1\u300C${d}\u300D\u4E0D\u5728 active \u4E2D\uFF08\u5DF2\u5F52\u6863\u4E8E ${g}\uFF0C\u65E0\u9700\u518D\u4F9D\u8D56\uFF09`:`\u4F9D\u8D56\u7684\u4EFB\u52A1\u300C${d}\u300D\u4E0D\u5728 active \u4E2D\uFF08\u53EF\u80FD\u5DF2\u5F52\u6863\u6216\u6587\u4EF6\u540D\u62FC\u5199\u9519\u8BEF\uFF09`})}let c=0,f=1,p=2,m=new Map,h=(u,a)=>{m.set(u,f);for(let d of o.get(u)??[]){if(!r.has(d))continue;let g=m.get(d)??c;if(g===f)return[...a,d];if(g===c){let k=h(d,[...a,d]);if(k)return k}}return m.set(u,p),null};for(let u of o.keys())if((m.get(u)??c)===c){let a=h(u,[u]);if(a){n.push({level:"warn",file:u,message:`depends_on \u5B58\u5728\u5FAA\u73AF\u4F9D\u8D56\uFF1A${a.join(" \u2192 ")}`});break}}return n}var Ot={breaking:["\u91CD\u5927\uFF1A","Breaking:"],added:["\u65B0\u589E\uFF1A","Added:"],changed:["\u4FEE\u6539\uFF1A","Changed:"],improved:["\u4F18\u5316\uFF1A","Improved:"],fixed:["\u4FEE\u590D\uFF1A","Fixed:"],docs:["\u6587\u6863\uFF1A","Docs:"],removed:["\u6E05\u7406\uFF1A","Removed:"],deps:["\u4F9D\u8D56\uFF1A"],other:[]},Nt={"### \u{1F41B} \u8865\u4E01\u4FEE\u590D":"fixed"},et={zh:{groups:[{slot:"breaking",title:"### \u{1F6A8} \u91CD\u5927\u53D8\u66F4"},{slot:"added",title:"### \u2728 \u65B0\u589E\u529F\u80FD"},{slot:"changed",title:"### \u{1F527} \u529F\u80FD\u8C03\u6574"},{slot:"improved",title:"### \u26A1 \u4F18\u5316\u6539\u8FDB"},{slot:"fixed",title:"### \u{1F41B} \u95EE\u9898\u4FEE\u590D"},{slot:"docs",title:"### \u{1F4DD} \u6587\u6863\u66F4\u65B0"},{slot:"removed",title:"### \u{1F9F9} \u6E05\u7406\u79FB\u9664"},{slot:"deps",title:"### \u{1F517} \u4F9D\u8D56\u53D8\u66F4"},{slot:"other",title:"### \u{1F4E6} \u5176\u4ED6\u53D8\u66F4"}],replacements:{"### \u91CD\u5927\u53D8\u66F4":"### \u{1F6A8} \u91CD\u5927\u53D8\u66F4","### \u65B0\u589E\u529F\u80FD":"### \u2728 \u65B0\u589E\u529F\u80FD","### \u8865\u4E01\u4FEE\u590D":"### \u{1F41B} \u95EE\u9898\u4FEE\u590D","- Updated dependencies":"- \u66F4\u65B0\u4F9D\u8D56"},deps:"- \u66F4\u65B0\u4F9D\u8D56",released:"\u53D1\u5E03"},en:{groups:[{slot:"breaking",title:"### \u{1F6A8} Breaking Changes"},{slot:"added",title:"### \u2728 Added"},{slot:"changed",title:"### \u{1F527} Changed"},{slot:"improved",title:"### \u26A1 Improved"},{slot:"fixed",title:"### \u{1F41B} Fixed"},{slot:"docs",title:"### \u{1F4DD} Docs"},{slot:"removed",title:"### \u{1F9F9} Removed"},{slot:"deps",title:"### \u{1F517} Dependency Updates"},{slot:"other",title:"### \u{1F4E6} Other"}],replacements:{},deps:"- Updated dependencies",released:"released"}},Rs="zh";function vs(e,t,n){let r=e[t];return r?{lang:r}:{lang:e[n]??et[n],unknown:t}}var ir=require("fs"),Dt=require("path");function tt(e){let t=[],n=new Set(["node_modules",".git","dist","coverage"]),r=o=>{let s;try{s=(0,ir.readdirSync)(o,{withFileTypes:!0})}catch{return}for(let i of s)if(i.isDirectory()){if(n.has(i.name))continue;r((0,Dt.join)(o,i.name))}else i.name==="CHANGELOG.md"&&t.push((0,Dt.join)(o,i.name))};return r(e),t}var _e=require("fs");var nt=/^## \d+\.\d+\.\d+/,Mt={"### Major Changes":"breaking","### Minor Changes":"added","### Patch Changes":"other","### Dependent Changes":"deps"},$s="- Updated dependencies",ws=Object.values(et).map(e=>e.released);function ar(){return mn()}function jt(e,t,n,r=!0,o=!1){let s=(0,_e.readFileSync)(e,"utf8"),i=s.includes(`\r
|
package/dist/index.js
CHANGED
|
@@ -62,7 +62,7 @@ ${lt(Me)}
|
|
|
62
62
|
${gs}
|
|
63
63
|
|
|
64
64
|
${lt(je)}
|
|
65
|
-
`;import{existsSync as Ye}from"fs";import{basename as Tn}from"path";import{existsSync as hs,readdirSync as bs}from"fs";import{join as ks,relative as Yl}from"path";var ys=/^\s*(`{3,}|~{3,})/;function xs(e){let t=ys.exec(e)?.[1];return t?{char:t.charAt(0),len:t.length}:null}function Ss(e){return/^\s*/.exec(e)?.[0]??""}function Rs(e){return e.replace(/^(:?)-+(:?)$/,"$1---$2")}function vs(e){if(!X(e))return e;let t=U(e),n=be(e)?t.map(Rs):t;return`${Ss(e)}| ${n.join(" | ")} |`}function Be(e){let t=e.map(()=>!0),n=null;for(let r=0;r<e.length;r++){let o=xs(e[r]??"");if(n===null){o&&(n=o,t[r]=!1);continue}t[r]=!1,o&&o.char===n.char&&o.len>=n.len&&(n=null)}return t}function wn(e){let t=e.split(/\r?\n/),n=Be(t),r=[];for(let o=0;o<t.length;o++){if(!n[o])continue;let s=t[o]??"";X(s)&&vs(s)!==s&&r.push(o+1)}return r}function En(e){if(!hs(e))return[];let t=[],n=r=>{for(let o of bs(r,{withFileTypes:!0})){let s=ks(r,o.name);o.isDirectory()?n(s):o.isFile()&&o.name.endsWith(".md")&&t.push(s)}};return n(e),t.sort()}var $s=/^[-*]\s+(?:\*\*)?确立来源/,ws=/本次起入表|新立条目:|条文全文落/;function Cn(e,t){return e.length===t.length&&t.every((n,r)=>e[r]===n)}function He(e){return e.map(t=>`\u300C${t}\u300D`).join("")}function Es(e){return Cn(e.header,De)?[]:[{file:e.indexFile,message:`${W} \u7D22\u5F15\u8868\u5217\u96C6\u5408\u504F\u79BB v3 \u89C4\u8303\uFF1A\u5E94\u6070\u4E3A ${He(De)}\uFF0C\u5B9E\u4E3A ${He(e.header)}\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \u5F52\u4E00`}]}function Ts(e){let t=[],n=[[j,e.historyFile,Me,fe],[ke,e.retiredFile,je,it]];for(let[r,o,s,i]of n){if(!Ye(o))continue;let l=ue(v(o).split(/\r?\n/),i);!l||Cn(l.header,s)||t.push({file:o,line:l.headerLine+1,message:`${r} \u8868\u5934\u504F\u79BB v3 \u89C4\u8303\uFF1A\u5E94\u6070\u4E3A ${He(s)}\uFF0C\u5B9E\u4E3A ${He(l.header)}\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \u5F52\u4E00`})}return t}function Cs(e){let t=[],n=[...ut(e),e.historyFile,e.retiredFile];for(let r of n){if(!Ye(r))continue;let o=v(r).split(/\r?\n/),s=Be(o),i=o.map((p,m)=>s[m]?p:""),l=vn(i),c=l[0];if(c===void 0)continue;let f=l.length>1?`\uFF08\u53E6\u6709 ${l.length-1} \u5904\uFF09`:"";t.push({file:r,line:c.line,message:`${Tn(r)} \u7B2C ${c.line} \u884C\u8868\u5934\u4E0E\u5206\u9694\u884C\u5217\u6570\u4E0D\u4E00\u81F4\uFF08\u8868\u5934 ${c.headerCols} \u5217 / \u5206\u9694\u884C ${c.sepCols} \u5217\uFF09${f}\uFF1A\u8BF7\u6309 conventions-spec \u5F52\u4E00`})}return t}function As(e){let t=[],n=ut(e).filter(r=>r!==e.indexFile);for(let r of n){if(!Ye(r))continue;let o=v(r).split(/\r?\n/),s=Be(o),i=[];o.forEach((f,p)=>{s[p]&&$s.test(f)&&i.push(p+1)});let l=i[0];if(l===void 0)continue;let c=i.length>1?`\uFF08\u53E6\u6709 ${i.length-1} \u5904\uFF09`:"";t.push({file:r,line:l,message:`${Tn(r)} \u7B2C ${l} \u884C\u6B8B\u7559\u300C\u786E\u7ACB\u6765\u6E90\u300D\u5B50\u9879${c}\uFF1A\u6765\u6E90\u7531\u7D22\u5F15\u884C\u4E0E history.md / retired.md \u627F\u8F7D\uFF0C\u5206\u518C\u5185\u4E0D\u91CD\u590D\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \u5F52\u4E00`})}return t}function Ls(e){if(!Ye(e.historyFile))return[];let t=ue(v(e.historyFile).split(/\r?\n/),fe);if(!t)return[];let n=$n(t.header,st);if(n<0)return[];let r=[];t.rows.forEach((i,l)=>{let c=t.rowLines[l];c!==void 0&&ws.test(i[n]??"")&&r.push(c+1)});let o=r[0];if(o===void 0)return[];let s=r.length>1?`\uFF08\u53E6\u6709 ${r.length-1} \u5904\uFF09`:"";return[{file:e.historyFile,line:o,message:`${j} \u7B2C ${o} \u884C\u300C\u4FEE\u8BA2\u5185\u5BB9\u300D\u5217\u542B\u7981\u7528\u8BED\u6599${s}\uFF1A\u4E0D\u5F97\u5199\u81EA\u6307\u5957\u8BDD\uFF08\u5982\u300C\uFF08\u672C\u6B21\u8D77\u5165\u8868\uFF09\u300D\u300C\u65B0\u7ACB\u6761\u76EE\uFF1A\u300D\uFF09\u6216\u91CD\u590D\u7D22\u5F15\u5217\u7684\u6761\u6587\u53BB\u5411\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \xA73.2 \u5F52\u4E00`}]}function An(e){if(!e.hasIndex)return[];let t=[];return e.form==="v3"&&t.push(...Es(e),...Ts(e),...As(e),...Ls(e)),t.push(...Cs(e)),t}import{existsSync as Is}from"fs";import{join as Ln}from"path";var Fs="toolkit-conventions",_s="SKILL.md",Os=[".agents/skills",".trae/skills",".
|
|
65
|
+
`;import{existsSync as Ye}from"fs";import{basename as Tn}from"path";import{existsSync as hs,readdirSync as bs}from"fs";import{join as ks,relative as Yl}from"path";var ys=/^\s*(`{3,}|~{3,})/;function xs(e){let t=ys.exec(e)?.[1];return t?{char:t.charAt(0),len:t.length}:null}function Ss(e){return/^\s*/.exec(e)?.[0]??""}function Rs(e){return e.replace(/^(:?)-+(:?)$/,"$1---$2")}function vs(e){if(!X(e))return e;let t=U(e),n=be(e)?t.map(Rs):t;return`${Ss(e)}| ${n.join(" | ")} |`}function Be(e){let t=e.map(()=>!0),n=null;for(let r=0;r<e.length;r++){let o=xs(e[r]??"");if(n===null){o&&(n=o,t[r]=!1);continue}t[r]=!1,o&&o.char===n.char&&o.len>=n.len&&(n=null)}return t}function wn(e){let t=e.split(/\r?\n/),n=Be(t),r=[];for(let o=0;o<t.length;o++){if(!n[o])continue;let s=t[o]??"";X(s)&&vs(s)!==s&&r.push(o+1)}return r}function En(e){if(!hs(e))return[];let t=[],n=r=>{for(let o of bs(r,{withFileTypes:!0})){let s=ks(r,o.name);o.isDirectory()?n(s):o.isFile()&&o.name.endsWith(".md")&&t.push(s)}};return n(e),t.sort()}var $s=/^[-*]\s+(?:\*\*)?确立来源/,ws=/本次起入表|新立条目:|条文全文落/;function Cn(e,t){return e.length===t.length&&t.every((n,r)=>e[r]===n)}function He(e){return e.map(t=>`\u300C${t}\u300D`).join("")}function Es(e){return Cn(e.header,De)?[]:[{file:e.indexFile,message:`${W} \u7D22\u5F15\u8868\u5217\u96C6\u5408\u504F\u79BB v3 \u89C4\u8303\uFF1A\u5E94\u6070\u4E3A ${He(De)}\uFF0C\u5B9E\u4E3A ${He(e.header)}\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \u5F52\u4E00`}]}function Ts(e){let t=[],n=[[j,e.historyFile,Me,fe],[ke,e.retiredFile,je,it]];for(let[r,o,s,i]of n){if(!Ye(o))continue;let l=ue(v(o).split(/\r?\n/),i);!l||Cn(l.header,s)||t.push({file:o,line:l.headerLine+1,message:`${r} \u8868\u5934\u504F\u79BB v3 \u89C4\u8303\uFF1A\u5E94\u6070\u4E3A ${He(s)}\uFF0C\u5B9E\u4E3A ${He(l.header)}\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \u5F52\u4E00`})}return t}function Cs(e){let t=[],n=[...ut(e),e.historyFile,e.retiredFile];for(let r of n){if(!Ye(r))continue;let o=v(r).split(/\r?\n/),s=Be(o),i=o.map((p,m)=>s[m]?p:""),l=vn(i),c=l[0];if(c===void 0)continue;let f=l.length>1?`\uFF08\u53E6\u6709 ${l.length-1} \u5904\uFF09`:"";t.push({file:r,line:c.line,message:`${Tn(r)} \u7B2C ${c.line} \u884C\u8868\u5934\u4E0E\u5206\u9694\u884C\u5217\u6570\u4E0D\u4E00\u81F4\uFF08\u8868\u5934 ${c.headerCols} \u5217 / \u5206\u9694\u884C ${c.sepCols} \u5217\uFF09${f}\uFF1A\u8BF7\u6309 conventions-spec \u5F52\u4E00`})}return t}function As(e){let t=[],n=ut(e).filter(r=>r!==e.indexFile);for(let r of n){if(!Ye(r))continue;let o=v(r).split(/\r?\n/),s=Be(o),i=[];o.forEach((f,p)=>{s[p]&&$s.test(f)&&i.push(p+1)});let l=i[0];if(l===void 0)continue;let c=i.length>1?`\uFF08\u53E6\u6709 ${i.length-1} \u5904\uFF09`:"";t.push({file:r,line:l,message:`${Tn(r)} \u7B2C ${l} \u884C\u6B8B\u7559\u300C\u786E\u7ACB\u6765\u6E90\u300D\u5B50\u9879${c}\uFF1A\u6765\u6E90\u7531\u7D22\u5F15\u884C\u4E0E history.md / retired.md \u627F\u8F7D\uFF0C\u5206\u518C\u5185\u4E0D\u91CD\u590D\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \u5F52\u4E00`})}return t}function Ls(e){if(!Ye(e.historyFile))return[];let t=ue(v(e.historyFile).split(/\r?\n/),fe);if(!t)return[];let n=$n(t.header,st);if(n<0)return[];let r=[];t.rows.forEach((i,l)=>{let c=t.rowLines[l];c!==void 0&&ws.test(i[n]??"")&&r.push(c+1)});let o=r[0];if(o===void 0)return[];let s=r.length>1?`\uFF08\u53E6\u6709 ${r.length-1} \u5904\uFF09`:"";return[{file:e.historyFile,line:o,message:`${j} \u7B2C ${o} \u884C\u300C\u4FEE\u8BA2\u5185\u5BB9\u300D\u5217\u542B\u7981\u7528\u8BED\u6599${s}\uFF1A\u4E0D\u5F97\u5199\u81EA\u6307\u5957\u8BDD\uFF08\u5982\u300C\uFF08\u672C\u6B21\u8D77\u5165\u8868\uFF09\u300D\u300C\u65B0\u7ACB\u6761\u76EE\uFF1A\u300D\uFF09\u6216\u91CD\u590D\u7D22\u5F15\u5217\u7684\u6761\u6587\u53BB\u5411\uFF1B\u8BF7\u4EBA\u5DE5\u786E\u8BA4\u540E\u6309 conventions-spec \xA73.2 \u5F52\u4E00`}]}function An(e){if(!e.hasIndex)return[];let t=[];return e.form==="v3"&&t.push(...Es(e),...Ts(e),...As(e),...Ls(e)),t.push(...Cs(e)),t}import{existsSync as Is}from"fs";import{join as Ln}from"path";var Fs="toolkit-conventions",_s="SKILL.md",Os=[".agents/skills",".trae/skills",".claude/skills","agent/skills",".augment/skills",".codebuddy/skills",".continue/skills",".crush/skills",".devin/skills",".goose/skills",".grok/skills",".hermes/skills",".iflow/skills",".junie/skills",".kiro/skills",".openhands/skills",".qwen/skills",".roo/skills",".windsurf/skills"];function In(e){let t=[];for(let n of Os){let r=`${n}/${Fs}`,o=`${r}/${_s}`;Is(Ln(e,o))&&t.push({dir:r,file:o,version:Rn(v(Ln(e,o)))})}return t}function Fn(e){let[t]=e;if(!t)return null;let n=o=>o.version===null?"\u65E0":`v${o.version}`;if(e.length===1)return{file:t.file,message:`\u5165\u53E3\u58F3\u6807\u8BB0 ${n(t)}\uFF0C\u4E0E\u5F53\u524D toolkit \u7684 v${ae} \u4E0D\u4E00\u81F4\uFF1A\u91CD\u8DD1 toolkit init \u53EF\u8865\u9F50`};let r=e.map(o=>`${o.file}\uFF08\u6807\u8BB0 ${n(o)}\uFF09`).join("\u3001");return{file:t.file,message:`\u5165\u53E3\u58F3\u6807\u8BB0\u4E0E\u5F53\u524D toolkit \u7684 v${ae} \u4E0D\u4E00\u81F4\uFF0C\u5171 ${e.length} \u5904\uFF1A${r}\uFF1B\u91CD\u8DD1 toolkit init \u53EF\u4E00\u6B21\u6027\u8865\u9F50`}}function _n(e){let[t]=e;if(!t)return null;if(e.length===1)return{file:t.file,message:`\u5165\u53E3\u58F3 ${t.file} \u88AB gitignore \u8986\u76D6\uFF1A\u4E0D\u4F1A\u968F git \u5206\u53D1\uFF0C\u8BF7\u628A\u8BE5\u8DEF\u5F84\u4ECE\u5FFD\u7565\u89C4\u5219\u4E2D\u6392\u9664`};let n=e.map(r=>r.file).join("\u3001");return{file:t.file,message:`\u5165\u53E3\u58F3\u88AB gitignore \u8986\u76D6\uFF0C\u5171 ${e.length} \u5904\uFF1A${n}\uFF1B\u4E0D\u4F1A\u968F git \u5206\u53D1\uFF0C\u8BF7\u628A\u76F8\u5E94\u8DEF\u5F84\u4ECE\u5FFD\u7565\u89C4\u5219\u4E2D\u6392\u9664`}}var Nn=/待办|待实施|待核对|待确认|待开始|待评估|待排期|待做|TODO/,js=/^[-*]\s*\[ \]\s/m,Bs=/^[-*]\s*\[ \]/,Hs=/^\d{4}-\d{1,2}-\d{1,2}(?:[T\s]\d{1,2}:\d{2}(?::\d{2})?)?$/,Ys=/^\d{4}-\d{1,2}-\d{1,2}[T\s]\d{1,2}:\d{2}(?::\d{2})?$/,Us=/^\d{8}-[^-]+-.+\.md$/;function Dn(e){let t=e.match(/^(\d{4})-?(\d{1,2})-?(\d{1,2})/);if(!t)return!1;let[,n,r,o]=t;if(!n||!r||!o)return!1;let s=+n,i=+r,l=+o;if(i<1||i>12||l<1||l>31)return!1;let c=new Date(Date.UTC(s,i-1,l));return c.getUTCFullYear()===s&&c.getUTCMonth()===i-1&&c.getUTCDate()===l}function N(e,t,n){for(let r=0;r<t;r++)if((e[r]??"").trimStart().startsWith(`${n}:`))return r+1;return 1}function Mn(e,t,n){let r=!1;for(let o=t;o<e.length;o++){let s=e[o]??"";if(!r&&/^# /.test(s)){r=!0;continue}if(n.test(s))return o+1}return t+1}function Ws(e,t){let n=[];t.startsWith("\uFEFF")&&n.push({level:"warn",file:e,line:1,message:"\u6587\u4EF6\u542B UTF-8 BOM\uFF0C\u5EFA\u8BAE\u53BB\u9664\uFF08\u90E8\u5206\u89E3\u6790\u5DE5\u5177\u4F1A\u5F02\u5E38\uFF09"});let o=t.split(/\r?\n/).findIndex(i=>/[ \t]+$/.test(i));o>=0&&n.push({level:"warn",file:e,line:o+1,message:"\u884C\u5C3E\u6709\u591A\u4F59\u7A7A\u767D\uFF08\u7A7A\u683C\u6216\u5236\u8868\u7B26\uFF09\uFF0C\u5EFA\u8BAE\u53BB\u9664"});let s=-1;for(let i=0;i<t.length;i++)if(t[i]===`
|
|
66
66
|
`&&(i===0||t[i-1]!=="\r")){s=i;break}return s>=0&&t.includes(`\r
|
|
67
67
|
`)&&n.push({level:"warn",file:e,line:t.slice(0,s).split(`
|
|
68
68
|
`).length,message:"\u6362\u884C\u7B26\u6DF7\u7528\uFF08\u540C\u6587\u4EF6\u540C\u65F6\u542B CRLF \u4E0E LF\uFF09\uFF0C\u5EFA\u8BAE\u7EDF\u4E00\u4E3A LF"}),n}function Yn(e){let t=[],n=xe(e),r=Ds(e,"utf8");t.push(...Ws(n,r));let o=M(r),s=o.split(/\r?\n/),i=Re.exec(o)?.[0].split(/\r?\n/).length??0;if(!Re.test(o))return t.push({level:"error",file:n,line:1,message:"\u7F3A\u5C11 frontmatter"}),t;let c=ve(o);for(let a of Object.keys(c))Se.includes(a)||t.push({level:"warn",file:n,line:N(s,i,a),message:`frontmatter \u542B\u672A\u77E5\u5B57\u6BB5\u300C${a}\u300D\uFF0C\u672C\u5DE5\u5177\u4E0D\u8BFB\u53D6\uFF08\u5F52\u6863\u4E0E\u5F52\u4E00\u5316\u4E0D\u4F1A\u4FDD\u7559\uFF0C\u8BF7\u81EA\u884C\u7EF4\u62A4\uFF09`});if(c.status?de.includes(c.status)||t.push({level:"error",file:n,line:N(s,i,"status"),message:`status \u975E\u6CD5\u503C\u300C${c.status}\u300D\uFF0C\u5E94\u4E3A ${de.join(" / ")}`}):t.push({level:"error",file:n,line:N(s,i,"status"),message:"frontmatter \u7F3A\u5C11 status \u5B57\u6BB5"}),Z.includes(c.status)&&!c.completed&&t.push({level:"error",file:n,line:N(s,i,"completed"),message:`status \u4E3A\u300C${c.status}\u300D\u4F46\u7F3A\u5C11 completed \u5B8C\u6210\u65F6\u95F4`}),c.completed){let a=c.completed.trim(),d=N(s,i,"completed");if(!Hs.test(a))t.push({level:"warn",file:n,line:d,message:`completed\u300C${c.completed}\u300D\u683C\u5F0F\u975E\u6CD5\uFF0C\u5E94\u4E3A YYYY-MM-DD HH:mm`});else{let g=a.match(/^\d{4}-\d{1,2}-\d{1,2}/)?.[0]??a;Dn(g)?Ys.test(a)?ne(a)?t.push({level:"warn",file:n,line:d,message:`completed\u300C${c.completed}\u300D\u665A\u4E8E\u5F53\u524D\u7CFB\u7EDF\u65F6\u95F4 ${te} \u5C0F\u65F6\u4EE5\u4E0A\uFF0C\u7591\u4F3C\u65F6\u95F4\u6E90\u9519\u8BEF\uFF0C\u8BF7\u5F53\u573A\u53D6\u7CFB\u7EDF\u65F6\u95F4\u6838\u5B9E`}):/(?:[T\s]00:00(?::00)?)$/.test(a)&&t.push({level:"warn",file:n,line:d,message:`completed\u300C${c.completed}\u300D\u6070\u4E3A\u96F6\u70B9\u6574\uFF0C\u7591\u4F3C\u53EA\u586B\u4E86\u65E5\u671F\u88AB\u8865\u96F6\uFF0C\u8BF7\u6838\u5B9E\u5B9E\u9645\u5B8C\u6210\u65F6\u95F4`}):t.push({level:"warn",file:n,line:d,message:`completed\u300C${c.completed}\u300D\u5EFA\u8BAE\u8865\u5168\u4E3A\u5B8C\u6574\u65F6\u95F4 YYYY-MM-DD HH:mm`}):t.push({level:"warn",file:n,line:d,message:`completed\u300C${c.completed}\u300D\u65E5\u671F\u4E0D\u5B58\u5728\uFF0C\u8BF7\u6838\u5BF9`})}}c.owner||t.push({level:"warn",file:n,line:N(s,i,"owner"),message:"\u7F3A\u5C11 owner \u8D1F\u8D23\u4EBA\u5B57\u6BB5"}),c.created?/^\d{8}$/.test(c.created.trim())?Dn(c.created.trim())||t.push({level:"warn",file:n,line:N(s,i,"created"),message:`created\u300C${c.created}\u300D\u65E5\u671F\u4E0D\u5B58\u5728\uFF0C\u8BF7\u6838\u5BF9`}):t.push({level:"warn",file:n,line:N(s,i,"created"),message:`created\u300C${c.created}\u300D\u683C\u5F0F\u975E\u6CD5\uFF0C\u5E94\u4E3A YYYYMMDD`}):t.push({level:"warn",file:n,line:N(s,i,"created"),message:"\u7F3A\u5C11 created \u521B\u5EFA\u65E5\u671F\u5B57\u6BB5"}),c.updated&&c.created&&/^\d{8}$/.test(c.updated.trim())&&/^\d{8}$/.test(c.created.trim())&&c.updated.trim()<c.created.trim()&&t.push({level:"error",file:n,line:N(s,i,"updated"),message:`updated ${c.updated.trim()} \u65E9\u4E8E created ${c.created.trim()}\uFF0C\u65F6\u95F4\u7EBF\u77DB\u76FE`});let f=n.match(/^(\d{8})-/);if(Us.test(n)?c.created&&/^\d{8}$/.test(c.created.trim())&&f&&c.created.trim()!==f[1]&&t.push({level:"warn",file:n,message:`\u6587\u4EF6\u540D\u65E5\u671F ${f[1]} \u4E0E created ${c.created.trim()} \u4E0D\u4E00\u81F4`}):t.push({level:"warn",file:n,message:"\u6587\u4EF6\u540D\u4E0D\u7B26\u5408\u89C4\u8303 {YYYYMMDD}-{\u8D1F\u8D23\u4EBA}-{\u7B80\u8FF0}.md"}),c.scope){let a=c.scope.trim(),d=N(s,i,"scope");/[、,,]/.test(a)&&t.push({level:"warn",file:n,line:d,message:`scope\u300C${c.scope}\u300D\u542B\u987F\u53F7/\u9017\u53F7\u7591\u4F3C\u591A\u503C\u5206\u9694\uFF0C\u591A\u503C\u8BF7\u6539\u7528\u534A\u89D2\u52A0\u53F7\u8FDE\u63A5\uFF08\u5982 scope: web+server\uFF09`}),/[/\\]/.test(a)&&t.push({level:"warn",file:n,line:d,message:`scope\u300C${c.scope}\u300D\u542B\u8DEF\u5F84\u5206\u9694\u7B26\uFF0C\u591A\u503C\u8BF7\u6539\u7528\u534A\u89D2\u52A0\u53F7\u8FDE\u63A5\uFF08\u5982 scope: web+server\uFF09\uFF0C\u7AEF\u540D\u672C\u8EAB\u4E0D\u5F97\u542B\u5206\u9694\u7B26`}),/[()()]/.test(a)&&t.push({level:"warn",file:n,line:d,message:`scope\u300C${c.scope}\u300D\u542B\u62EC\u53F7\u7591\u4F3C\u6CE8\u91CA\u6027\u6587\u5B57\uFF0C\u8BF4\u660E\u8BF7\u79FB\u5165\u6B63\u6587`})}let p=gt(z(o)),h=Q("check")?.pendingMarkers!==!1?p.match(Nn):null;return h&&t.push({level:"warn",file:n,line:Mn(s,i,Nn),message:`\u6B63\u6587\u542B\u672A\u95ED\u5408\u5F85\u529E\u6807\u8BB0\u300C${h[0]}\u300D\uFF0C\u5EFA\u8BAE\u62C6\u5206\u4E3A\u72EC\u7ACB active \u4EFB\u52A1\u6216\u660E\u786E\u95ED\u73AF`}),Q("check")?.includeCheckbox!==!1&&js.test(p)&&t.push({level:"warn",file:n,line:Mn(s,i,Bs),message:"\u6B63\u6587\u542B\u672A\u52FE\u9009\u5F85\u529E\u9879\u300C- [ ]\u300D\uFF0C\u5EFA\u8BAE\u62C6\u5206\u4E3A\u72EC\u7ACB active \u4EFB\u52A1\u6216\u52FE\u9009\u5B8C\u6210"}),t}function Ps(e){let t=[];if(!Hn(e))return t;for(let n of On(e,{withFileTypes:!0}))if(!(n.name==="active"||n.name==="archive")){if(n.isFile())n.name.endsWith(".md")&&/^\d{8}-/.test(n.name)&&t.push(n.name);else if(n.isDirectory())for(let r of On(Ue(e,n.name)))r.endsWith(".md")&&/^\d{8}-/.test(r)&&t.push(`${n.name}/${r}`)}return t}function zs(e){let t=Lt(e);if(!t)return[];let n=I(e,t),r=xt(t,e);return r.state==="not-a-repo"||r.state==="outside-repo"?[]:r.state==="unavailable"?[{level:"warn",file:n,message:`\u672C\u5730\u914D\u7F6E\u6587\u4EF6\u5FFD\u7565\u5224\u5B9A\u4E0D\u53EF\u7528\uFF08${r.detail??"\u672A\u77E5\u539F\u56E0"}\uFF09\uFF0C\u8BF7\u6838\u5B9E git \u73AF\u5883`}]:r.state==="tracked"?[{level:"warn",file:n,message:`\u672C\u5730\u914D\u7F6E\u6587\u4EF6\u5DF2\u88AB\u5FFD\u7565\u89C4\u5219\u8986\u76D6\u4F46\u4ECD\u88AB git \u8DDF\u8E2A\uFF08\u7591\u4F3C\u5386\u53F2 git add -f\uFF09\uFF1A\u6267\u884C git rm --cached ${n} \u540E\u624D\u4F1A\u771F\u6B63\u4E0D\u5165\u5E93`}]:r.state==="ignored"?[]:[{level:"warn",file:n,message:"\u672C\u5730\u914D\u7F6E\u6587\u4EF6\u672A\u88AB gitignore \u8986\u76D6\uFF0C\u53EF\u80FD\u968F git \u63D0\u4EA4\u6CC4\u9732\u4E2A\u4EBA\u914D\u7F6E\uFF1A\u91CD\u8DD1 toolkit init \u53EF\u81EA\u52A8\u8865\u5199\u5FFD\u7565\u884C"}]}function Vs(e,t){let n=[],r=at(e);r.hasLegacy&&n.push({level:"warn",file:Ne,message:r.hasDir?"\u65E7\u5355\u6587\u4EF6\u89C4\u8303\u8F7D\u4F53\u5DF2\u88AB conventions/ \u76EE\u5F55\u5F62\u6001\u53D6\u4EE3\uFF0C\u5EFA\u8BAE\u6E05\u7406\uFF08\u4E24\u8005\u5E76\u5B58\u65F6\u4EE5\u76EE\u5F55\u5F62\u6001\u4E3A\u51C6\uFF09":"\u65E7\u5355\u6587\u4EF6\u89C4\u8303\u8F7D\u4F53\uFF0C\u5EFA\u8BAE\u8FC1\u79FB\u4E3A conventions/ \u76EE\u5F55\u5F62\u6001\uFF08index.md \u4F5C\u552F\u4E00\u5165\u53E3 + common.md / \u7AEF\u5206\u518C\u6309\u9700\u521B\u5EFA\uFF09"}),r.hasDir&&!r.hasIndex&&n.push({level:"warn",file:`conventions/${W}`,message:"\u89C4\u8303\u8F7D\u4F53\u7F3A index.md\uFF08\u552F\u4E00\u5165\u53E3\u4E0E\u552F\u4E00\u6743\u5A01\uFF09\uFF0C\u8BF7\u8865\u9F50"}),r.form==="abnormal"&&n.push({level:"warn",file:`conventions/${W}`,message:r.markerVersion===ye?`\u89C4\u8303\u8F7D\u4F53\u6807\u4E3A v${ye} \u4F46\u7F3A ${j} \u6216\u7D22\u5F15\u8868\u9996\u5217\u975E ${J}\uFF0C\u8BF7\u8865\u9F50\u6216\u6267\u884C toolkit conventions upgrade`:`\u89C4\u8303\u8F7D\u4F53\u5B58\u5728 ${j} \u4F46\u7D22\u5F15\u8868\u9996\u5217\u4ECD\u975E ${J}\uFF08\u5F62\u6001\u5F02\u5E38\uFF09\uFF0C\u8BF7\u4EBA\u5DE5\u786E\u8BA4`}),n.push(...Ks(e,r));let o=In(t),s=yt(t,o.map(l=>l.file)),i=[Fn(o.filter(l=>l.version!==ae)),_n(o.filter(l=>s.has(l.file)))];for(let l of i)l&&n.push({level:"warn",file:l.file,message:l.message});return n.push(...zs(t)),n}function Ks(e,t){return An(t).map(n=>({level:"warn",file:I(e,n.file),...n.line===void 0?{}:{line:n.line},message:n.message}))}var jn=6;function Gs(e){let t=[];for(let n of En(e)){let r=wn(v(n));if(r.length===0)continue;let o=r.slice(0,jn).join("\u3001");t.push({level:"warn",file:I(e,n),line:r[0],message:`\u8868\u683C\u5B58\u5728\u5217\u5BF9\u9F50\u586B\u5145\uFF08\u504F\u79BB\u7D27\u51D1\u5F62\u6001\uFF09${r.length} \u884C\uFF08\u7B2C ${o}${r.length>jn?" \u2026":""} \u884C\uFF09\uFF1A\u6267\u884C toolkit conventions format \u5F52\u4E00`})}return t}function Xs(e){if(at(e).form!=="v3")return[];let t=Ue(e,Oe,j);if(!Hn(t))return[];let n=ue(v(t).split(/\r?\n/),fe);if(!n)return[];let r=n.rowLines.filter((o,s)=>!Sn((n.rows[s]??[])[0]??""));return r.length===0?[]:[{level:"warn",file:I(e,t),line:(r[0]??0)+1,message:`\u6F14\u8FDB\u8BB0\u5F55\u6709 ${r.length} \u884C\u9996\u5217\u4E0D\u662F\u7A33\u5B9A ID\uFF08\u5E94\u8BB0\u884C\u5185\u4EE3\u7801\u5305\u88F9\u7684 C-<n>\uFF09\uFF1A\u8BF7\u4EBA\u5DE5\u6838\u5BF9\u8865\u5F55\uFF08\u5386\u53F2\u884C\u53EA\u8FFD\u52A0\uFF0C\u4E0D\u81EA\u52A8\u6539\u5199\uFF09`}]}function Js(e=".tasks",t=process.cwd()){let n=Ue(e,"active"),r=A(n),o=[];for(let c of r)o.push(...Yn(c)),Ms(c)===n&&o.push({level:"warn",file:xe(c),message:"active \u4EFB\u52A1\u5E94\u653E\u5165 {YYYYMM} \u6708\u4EFD\u5B50\u76EE\u5F55\uFF08\u5F53\u524D\u76F4\u653E active \u6839\u76EE\u5F55\uFF09"});for(let c of Ps(e))o.push({level:"warn",file:c,message:"\u4EFB\u52A1\u6587\u4EF6\u6E38\u79BB\u4E8E active/ \u4E4B\u5916\uFF0Ctasks/check/archive \u5747\u4E0D\u4F1A\u8BFB\u53D6\uFF0C\u5E94\u79FB\u5165 active/{YYYYMM}/ \u6708\u4EFD\u5B50\u76EE\u5F55"});o.push(...Vs(e,t)),o.push(...Gs(e)),o.push(...Xs(e));for(let c of ot(e))o.push({level:"warn",file:c.file,message:c.message});let s=new Map;for(let c of r){let f=xe(c,".md"),p=s.get(f);p?p.push(c):s.set(f,[c])}for(let[c,f]of s)f.length>1&&o.push({level:"warn",file:c,message:`\u5B58\u5728 ${f.length} \u4E2A\u540C\u540D\u4EFB\u52A1\u6587\u4EF6\uFF0C\u7591\u4F3C\u91CD\u590D\u5EFA\u6863`});o.push(...qs(r,e));let i=o.filter(c=>c.level==="error").length,l=o.length-i;return{issues:o,errorCount:i,warnCount:l}}var Bn=new Map;function Zs(e){let t=Ns(e),n=Bn.get(e);if(n&&n.mtimeMs===t.mtimeMs)return n.titles;let r=[],o=new Set;try{for(let s of F(v(e)).blocks)s.title&&!o.has(s.title)&&(o.add(s.title),r.push(s.title))}catch{}return Bn.set(e,{mtimeMs:t.mtimeMs,titles:r}),r}function qs(e,t){let n=[],r=new Set(e.map(u=>xe(u,".md"))),o=new Map,s=u=>u.trim().replace(/\.md$/,"").trim();for(let u of e){let a=xe(u,".md"),d=v(u),g=ve(d);o.set(a,Te(g.depends_on).map(s))}if(![...o.values()].some(u=>u.length>0))return n;let i=null,l=u=>{if(!i){i=new Map;for(let a of A(Ue(t,"archive")))for(let d of Zs(a))i.has(d)||i.set(d,I(t,a))}return i.get(u)};for(let[u,a]of o)for(let d of a)if(!r.has(d)){let g=l(d);n.push({level:"warn",file:u,message:g?`\u4F9D\u8D56\u7684\u4EFB\u52A1\u300C${d}\u300D\u4E0D\u5728 active \u4E2D\uFF08\u5DF2\u5F52\u6863\u4E8E ${g}\uFF0C\u65E0\u9700\u518D\u4F9D\u8D56\uFF09`:`\u4F9D\u8D56\u7684\u4EFB\u52A1\u300C${d}\u300D\u4E0D\u5728 active \u4E2D\uFF08\u53EF\u80FD\u5DF2\u5F52\u6863\u6216\u6587\u4EF6\u540D\u62FC\u5199\u9519\u8BEF\uFF09`})}let c=0,f=1,p=2,m=new Map,h=(u,a)=>{m.set(u,f);for(let d of o.get(u)??[]){if(!r.has(d))continue;let g=m.get(d)??c;if(g===f)return[...a,d];if(g===c){let k=h(d,[...a,d]);if(k)return k}}return m.set(u,p),null};for(let u of o.keys())if((m.get(u)??c)===c){let a=h(u,[u]);if(a){n.push({level:"warn",file:u,message:`depends_on \u5B58\u5728\u5FAA\u73AF\u4F9D\u8D56\uFF1A${a.join(" \u2192 ")}`});break}}return n}var Un={breaking:["\u91CD\u5927\uFF1A","Breaking:"],added:["\u65B0\u589E\uFF1A","Added:"],changed:["\u4FEE\u6539\uFF1A","Changed:"],improved:["\u4F18\u5316\uFF1A","Improved:"],fixed:["\u4FEE\u590D\uFF1A","Fixed:"],docs:["\u6587\u6863\uFF1A","Docs:"],removed:["\u6E05\u7406\uFF1A","Removed:"],deps:["\u4F9D\u8D56\uFF1A"],other:[]},Wn={"### \u{1F41B} \u8865\u4E01\u4FEE\u590D":"fixed"},ft={zh:{groups:[{slot:"breaking",title:"### \u{1F6A8} \u91CD\u5927\u53D8\u66F4"},{slot:"added",title:"### \u2728 \u65B0\u589E\u529F\u80FD"},{slot:"changed",title:"### \u{1F527} \u529F\u80FD\u8C03\u6574"},{slot:"improved",title:"### \u26A1 \u4F18\u5316\u6539\u8FDB"},{slot:"fixed",title:"### \u{1F41B} \u95EE\u9898\u4FEE\u590D"},{slot:"docs",title:"### \u{1F4DD} \u6587\u6863\u66F4\u65B0"},{slot:"removed",title:"### \u{1F9F9} \u6E05\u7406\u79FB\u9664"},{slot:"deps",title:"### \u{1F517} \u4F9D\u8D56\u53D8\u66F4"},{slot:"other",title:"### \u{1F4E6} \u5176\u4ED6\u53D8\u66F4"}],replacements:{"### \u91CD\u5927\u53D8\u66F4":"### \u{1F6A8} \u91CD\u5927\u53D8\u66F4","### \u65B0\u589E\u529F\u80FD":"### \u2728 \u65B0\u589E\u529F\u80FD","### \u8865\u4E01\u4FEE\u590D":"### \u{1F41B} \u95EE\u9898\u4FEE\u590D","- Updated dependencies":"- \u66F4\u65B0\u4F9D\u8D56"},deps:"- \u66F4\u65B0\u4F9D\u8D56",released:"\u53D1\u5E03"},en:{groups:[{slot:"breaking",title:"### \u{1F6A8} Breaking Changes"},{slot:"added",title:"### \u2728 Added"},{slot:"changed",title:"### \u{1F527} Changed"},{slot:"improved",title:"### \u26A1 Improved"},{slot:"fixed",title:"### \u{1F41B} Fixed"},{slot:"docs",title:"### \u{1F4DD} Docs"},{slot:"removed",title:"### \u{1F9F9} Removed"},{slot:"deps",title:"### \u{1F517} Dependency Updates"},{slot:"other",title:"### \u{1F4E6} Other"}],replacements:{},deps:"- Updated dependencies",released:"released"}},wa="zh";function Ea(e,t,n){let r=e[t];return r?{lang:r}:{lang:e[n]??ft[n],unknown:t}}import{readdirSync as Qs}from"fs";import{join as Pn}from"path";function dt(e){let t=[],n=new Set(["node_modules",".git","dist","coverage"]),r=o=>{let s;try{s=Qs(o,{withFileTypes:!0})}catch{return}for(let i of s)if(i.isDirectory()){if(n.has(i.name))continue;r(Pn(o,i.name))}else i.name==="CHANGELOG.md"&&t.push(Pn(o,i.name))};return r(e),t}import{readFileSync as ei,readdirSync as Oa,writeFileSync as ti}from"fs";var We=/^## \d+\.\d+\.\d+/,pt={"### Major Changes":"breaking","### Minor Changes":"added","### Patch Changes":"other","### Dependent Changes":"deps"},ni="- Updated dependencies",ri=Object.values(ft).map(e=>e.released);function oi(){return Ut()}function Kn(e,t,n,r=!0,o=!1){let s=ei(e,"utf8"),i=s.includes(`\r
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@fxri/toolkit",
|
|
3
|
-
"version": "1.12.
|
|
3
|
+
"version": "1.12.5",
|
|
4
4
|
"description": "专为多人 + AI 跨项目协作打造:任务管理 + 多语言 CHANGELOG。",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"author": {
|
|
@@ -41,25 +41,6 @@
|
|
|
41
41
|
"NOTICE",
|
|
42
42
|
"package.json"
|
|
43
43
|
],
|
|
44
|
-
"scripts": {
|
|
45
|
-
"dev": "pnpm build:debug && node ./dist/cli.js",
|
|
46
|
-
"build": "cross-env NODE_ENV=production tsup",
|
|
47
|
-
"build:debug": "cross-env NODE_ENV=development tsup --config tsup.dev.config.ts",
|
|
48
|
-
"typecheck": "tsc --noEmit -p tsconfig.typecheck.json",
|
|
49
|
-
"lint": "eslint . --cache",
|
|
50
|
-
"lint:fix": "eslint . --fix",
|
|
51
|
-
"test": "vitest run --exclude \"src/__tests__/warn-threshold.test.ts\"",
|
|
52
|
-
"test:watch": "vitest",
|
|
53
|
-
"test:coverage": "vitest run --coverage --exclude \"src/__tests__/warn-threshold.test.ts\"",
|
|
54
|
-
"test:repo-guard": "vitest run src/__tests__/warn-threshold.test.ts",
|
|
55
|
-
"verify": "node scripts/verify.mjs",
|
|
56
|
-
"changeset": "changeset",
|
|
57
|
-
"sync:changelog-doc": "node scripts/sync-changelog-doc.mjs",
|
|
58
|
-
"docs:dev": "vitepress dev docs",
|
|
59
|
-
"docs:build": "vitepress build docs",
|
|
60
|
-
"docs:preview": "vitepress preview docs",
|
|
61
|
-
"release": "pnpm build && pnpm publish"
|
|
62
|
-
},
|
|
63
44
|
"keywords": [
|
|
64
45
|
"toolkit",
|
|
65
46
|
"task",
|
|
@@ -84,12 +65,30 @@
|
|
|
84
65
|
"vitepress": "^1.6.4",
|
|
85
66
|
"vitest": "^4.1.11"
|
|
86
67
|
},
|
|
87
|
-
"packageManager": "pnpm@10.34.4",
|
|
88
68
|
"engines": {
|
|
89
69
|
"node": ">=20.19.0"
|
|
90
70
|
},
|
|
91
71
|
"publishConfig": {
|
|
92
72
|
"registry": "https://registry.npmjs.org/",
|
|
93
73
|
"access": "public"
|
|
74
|
+
},
|
|
75
|
+
"scripts": {
|
|
76
|
+
"dev": "pnpm build:debug && node ./dist/cli.js",
|
|
77
|
+
"build": "cross-env NODE_ENV=production tsup",
|
|
78
|
+
"build:debug": "cross-env NODE_ENV=development tsup --config tsup.dev.config.ts",
|
|
79
|
+
"typecheck": "tsc --noEmit -p tsconfig.typecheck.json",
|
|
80
|
+
"lint": "eslint . --cache",
|
|
81
|
+
"lint:fix": "eslint . --fix",
|
|
82
|
+
"test": "vitest run --exclude \"src/__tests__/warn-threshold.test.ts\"",
|
|
83
|
+
"test:watch": "vitest",
|
|
84
|
+
"test:coverage": "vitest run --coverage --exclude \"src/__tests__/warn-threshold.test.ts\"",
|
|
85
|
+
"test:repo-guard": "vitest run src/__tests__/warn-threshold.test.ts",
|
|
86
|
+
"verify": "node scripts/verify.mjs",
|
|
87
|
+
"changeset": "changeset",
|
|
88
|
+
"sync:changelog-doc": "node scripts/sync-changelog-doc.mjs",
|
|
89
|
+
"docs:dev": "vitepress dev docs",
|
|
90
|
+
"docs:build": "vitepress build docs",
|
|
91
|
+
"docs:preview": "vitepress preview docs",
|
|
92
|
+
"release": "pnpm build && pnpm publish"
|
|
94
93
|
}
|
|
95
|
-
}
|
|
94
|
+
}
|
package/skills/README.md
CHANGED
|
@@ -8,9 +8,9 @@
|
|
|
8
8
|
|
|
9
9
|
| 技能 | 版本 | 用途 |
|
|
10
10
|
| --- | --- | --- |
|
|
11
|
-
| [fxri-plan-to-task](./fxri-plan-to-task/SKILL.md) | 1.
|
|
12
|
-
| [fxri-release-changelog](./fxri-release-changelog/SKILL.md) | 1.1
|
|
13
|
-
| [fxri-session-recap](./fxri-session-recap/SKILL.md) | 1.
|
|
11
|
+
| [fxri-plan-to-task](./fxri-plan-to-task/SKILL.md) | 1.9.3 | 方案落盘:任务分解与纯展示计划表 → 逐仓逐任务建档 → 校验 → 归档 → 任务级规范沉淀(能力终点);规范载体迁移与升级 |
|
|
12
|
+
| [fxri-release-changelog](./fxri-release-changelog/SKILL.md) | 1.2.1 | changesets 发版与多语言 CHANGELOG 维护 |
|
|
13
|
+
| [fxri-session-recap](./fxri-session-recap/SKILL.md) | 1.6.0 | 会话收尾全量沉淀 + 规范沉淀 / 新会话三层恢复 / 历史任务时间批量修正 |
|
|
14
14
|
|
|
15
15
|
版本号取自各 SKILL.md 的 frontmatter `metadata.version`(`toolkit skills status` / `skills install` 打印的真源版本),与正文首部版本声明双写一致。
|
|
16
16
|
|
|
@@ -24,16 +24,16 @@
|
|
|
24
24
|
pnpm add -g @fxri/toolkit # 1. 装 CLI(npm 用户 npm i -g @fxri/toolkit)
|
|
25
25
|
toolkit skills install # 2. 把包内技能装到各 agent 的全局技能目录
|
|
26
26
|
# --scope project 换项目面:真源落 <仓库根>/.agents/skills/、其余候选目录落入口薄壳
|
|
27
|
-
toolkit skills status # 查现场状态(悬空 / 指向其他版本 / 副本漂移 / 缺失 /
|
|
27
|
+
toolkit skills status # 查现场状态(悬空 / 指向其他版本 / 副本漂移 / 缺失 / 同名冲突;历史落点残留单列提示;--scope project 查项目面)
|
|
28
28
|
# 前四类重跑 toolkit skills install 补齐,同名冲突需 toolkit skills install --force 覆盖
|
|
29
29
|
toolkit skills remove # 卸载本包装的产物(只清自己装的,不碰用户自装技能;--scope project 清项目面)
|
|
30
30
|
```
|
|
31
31
|
|
|
32
32
|
- 真源唯一:技能取自已装 CLI 包内的 `skills/`;软链锚在 pnpm 稳定入口,升级 CLI 后自动指向新版(副本形式需重跑 `toolkit skills install`)
|
|
33
|
-
- 目标三层:主目标 `~/.agents/skills/`(多家 agent
|
|
33
|
+
- 目标三层:主目标 `~/.agents/skills/`(多家 agent 共读:Cline、Codex、Dexto、Kimi Code CLI、Loaf、Pi、Sarvam Code、Warp、Zed、DeepSeek Harness)→ 内置表内**已安装**的各 agent 全局技能目录 → `--dir <path>` 兜底(可多次指定,给表外 agent 用;只在当次安装时写入,技能增删后不会自动同步,需带相同 `--dir` 重跑 `toolkit skills install`);共读 agent 的全局目录即主目标本身,写一次即全部覆盖,`toolkit skills status` 单列「经 canonical 共读的 agent」;升级前的 Codex / Pi 历史落点(`~/.codex/skills`、`~/.pi/agent/skills`)若仍有本包登记,`toolkit skills status` 会单列「历史落点残留」提示清理(只提示、不自动删除)
|
|
34
34
|
- 默认软链(锚在 pnpm 稳定入口,升级不失效);链接创建失败自动降级为副本并打印 ⚠️(如无权限建链);`--copy` 强制副本、`--dry-run` 预演、`--force` 覆盖同名非本包产物(不改本包已登记副本的形态)
|
|
35
35
|
- 产物记录在状态文件 `~/.agents/.toolkit-skills.json`;卸载 CLI 前先跑 `toolkit skills remove`,避免留下悬空链接(清理后目标目录若已空会一并回收)
|
|
36
|
-
- **项目面(`--scope project`)**:`--scope` 缺省时按 CLI 安装位置自动判定(项目内装 CLI → 项目面)。真源落 `<仓库根>/.agents/skills/`(完整副本),其余**已存在**的候选目录(`.trae/skills/`、`.
|
|
36
|
+
- **项目面(`--scope project`)**:`--scope` 缺省时按 CLI 安装位置自动判定(项目内装 CLI → 项目面)。真源落 `<仓库根>/.agents/skills/`(完整副本),其余**已存在**的候选目录(`.trae/skills/`、`.claude/skills/`、`agent/skills/`(eve)、`.augment/skills/`、`.codebuddy/skills/`、`.continue/skills/`、`.crush/skills/`、`.devin/skills/`、`.goose/skills/`、`.grok/skills/`、`.hermes/skills/`、`.iflow/skills/`、`.junie/skills/`、`.kiro/skills/`、`.openhands/skills/`、`.qwen/skills/`、`.roo/skills/`、`.windsurf/skills/`)各放每个技能一份入口薄壳指向真源;产物记录在 `<仓库根>/.toolkit/state.json`(与真源、薄壳一并入库)。`toolkit init` 会写入 `prepare` 刷新钩子,`pnpm install` 时自动补齐/刷新,队友 clone 即用;`--copy` 仅全局面生效,项目面恒为副本
|
|
37
37
|
|
|
38
38
|
### 方式二:上游安装器 `npx skills`(需锁定文件或覆盖表外 agent 时)
|
|
39
39
|
|
|
@@ -66,7 +66,7 @@ pnpm dlx skills add fxri-toolkit --global # npm 用户把 pnpm dlx 换成
|
|
|
66
66
|
|
|
67
67
|
- 已安装 `@fxri/toolkit` 的项目可直接使用包内自带的技能目录:`node_modules/@fxri/toolkit/skills/`,复制或软链到 agent 的 skills 目录即可
|
|
68
68
|
- 复制或软链技能目录到 agent 的 skills 目录(如 Claude Code 的 `.claude/skills/`)
|
|
69
|
-
- 支持自定义 rules 的工具(如 Trae
|
|
69
|
+
- 支持自定义 rules 的工具(如 Trae):**不要把 SKILL.md 链接为规则**——规则会常驻上下文,等于绕过按需加载;应放入技能目录(`toolkit skills install` 已覆盖 Trae 技能目录)。仅当确需该技能每轮常驻时,才考虑链接为规则。
|
|
70
70
|
- 通用兜底:在项目根 `AGENTS.md` 中引用本目录路径
|
|
71
71
|
|
|
72
72
|
复制副本以 frontmatter `metadata.version` 判断是否需要同步上游(`metadata.source` 指向本仓库)。
|
|
@@ -82,7 +82,7 @@ pnpm dlx skills add fxri-toolkit --global # npm 用户把 pnpm dlx 换成
|
|
|
82
82
|
|
|
83
83
|
## 与其他 skills 共存
|
|
84
84
|
|
|
85
|
-
|
|
85
|
+
每个技能是独立目录、独立激活单元:兼容 agent 会把各技能的 `description` 常驻上下文用于匹配触发,正文仅在触发时加载、`references/` 按需读取——不触发的技能只占 `description` 这一层,不占正文体积。唯一约束是目录名(即 `name`)不重复;`description` 已含反向排除,与常见通用技能重叠概率低。
|
|
86
86
|
|
|
87
87
|
## 命名约定
|
|
88
88
|
|
|
@@ -94,9 +94,9 @@ pnpm dlx skills add fxri-toolkit --global # npm 用户把 pnpm dlx 换成
|
|
|
94
94
|
- [ ] name:kebab-case、与目录名一致、≤64 字符
|
|
95
95
|
- [ ] description:≤1024 字符,含做什么 + 何时用 + 正向触发词 + 反向排除
|
|
96
96
|
- [ ] metadata.version:内容变更即递增,且与正文首部版本声明一致
|
|
97
|
-
- [ ] 主干 SKILL.md < 200
|
|
97
|
+
- [ ] 主干 SKILL.md < 200 行且 ≤ 8,000 字符,细节下沉 `references/`,可复制资产放 `assets/`
|
|
98
98
|
- [ ] 引用的 references / assets 相对路径有效
|
|
99
99
|
- [ ] 技能用途描述已同步 docs/guide 技能表与本文「技能列表」表(含版本标注)
|
|
100
|
-
- [ ] 涉规范载体(conventions)的改动:`fxri-session-recap/SKILL.md` 的 R3 压缩要点已与 `fxri-plan-to-task/references/conventions-spec.md`
|
|
100
|
+
- [ ] 涉规范载体(conventions)的改动:`fxri-session-recap/SKILL.md` 的 R3 压缩要点已与 `fxri-plan-to-task/references/conventions-spec.md` 同步(引用兄弟技能 references 时须用相对路径并给出包内真源兜底,两处不一致即失一致)
|
|
101
101
|
- [ ] 涉规范载体(conventions)的改动:`src/init.ts` 的 `index.md` / `history.md` 骨架模板与入口壳版本分流、`src/tasks/validate.ts` 的形态告警口径、`src/conventions/` 的形态识别与升级链路、`src/conventions/entry.ts` 的入口壳生成与版本告警已同步(CLI 侧与 skills 细则同源)
|
|
102
102
|
- [ ] 变更已走本仓库质量门:三方一致 + tasks check + pnpm test
|
|
@@ -1,16 +1,16 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: fxri-plan-to-task
|
|
3
|
-
description:
|
|
3
|
+
description: 将已确认的实施方案分解为可独立交付的任务并给出计划表,再落盘为标准任务文件并跟踪至归档:建档评估(查 active/archive 判同主题)、按模板建档、状态机更新、四级时间源取证、自查、任务级规范沉淀与归档。方案确认后表达「开始落地/登记记录」的意图,或即将改仓库文件时使用——含任务分解、建档、任务登记、落盘、归档、任务校验、规范载体迁移与升级(conventions 单文件升目录、v1 / v2 升 v3)等说法及口语近义表达(如按这个做吧、记一下、建个任务跟踪)均触发。不用于方案未确认的对话、会话收尾整场沉淀(fxri-session-recap 模式一)、与任务记录无关的普通 TODO、issue 管理或日常提交信息撰写。
|
|
4
4
|
license: MIT
|
|
5
5
|
metadata:
|
|
6
|
-
version: "1.
|
|
6
|
+
version: "1.9.3"
|
|
7
7
|
author: fxri
|
|
8
8
|
source: https://github.com/fxri-net/toolkit
|
|
9
9
|
---
|
|
10
10
|
|
|
11
11
|
# 方案落盘:任务建档与归档
|
|
12
12
|
|
|
13
|
-
> 本技能版本 1.
|
|
13
|
+
> 本技能版本 1.9.3(随 @fxri/toolkit 同批分发)。被问版本时即报此值(不读磁盘、不跑 CLI);与 `toolkit skills status` 的磁盘值不一致即说明会话上下文已过期,开新会话即可。
|
|
14
14
|
|
|
15
15
|
## 何时使用
|
|
16
16
|
|
|
@@ -21,7 +21,7 @@ metadata:
|
|
|
21
21
|
|
|
22
22
|
## 核心约定
|
|
23
23
|
|
|
24
|
-
任务文件规范(目录结构、命名、frontmatter
|
|
24
|
+
任务文件规范(目录结构、命名、frontmatter、归档格式、手工归档步骤、自查清单)以 `references/task-spec.md` 为准;规范载体(conventions)的结构、形态标记与稳定 ID、归属判定、分层读写、内容修订(含作废三层清理)、表格紧凑形态以 `references/conventions-spec.md` 为准。本文件只写流程,细则按场景读取——写任务文件前读 `task-spec.md`;读写或修订规范载体前读 `conventions-spec.md`;涉存量迁移、形态升级时读 `conventions-migration.md`;落笔条文、模板或文风偏离时才读 `conventions-templates.md`。不涉对应场景不读。
|
|
25
25
|
|
|
26
26
|
## 核心规则
|
|
27
27
|
|
|
@@ -40,11 +40,20 @@ metadata:
|
|
|
40
40
|
|
|
41
41
|
## 工作流
|
|
42
42
|
|
|
43
|
+
### 0. 任务分解与展示型计划表(方案确认后、建档前;两个及以上任务才出)
|
|
44
|
+
|
|
45
|
+
- 先按任务粒度拆解:一个任务 = 可独立验收、可独立回滚、单独提交后仓库自洽的最小交付单元,且不跨仓库(判据、判定顺序与反例见 `references/task-spec.md` 协作约定)
|
|
46
|
+
- 两个及以上任务时,在对话中给出唯一一张顺序计划表:列为「序号 | 仓库 | 任务 | 前置」,跨端、跨仓同表,按执行先后排列;单任务方案不出表
|
|
47
|
+
- 表只作展示与排序:不落档、不写入任务正文、不设状态列(状态以任务 frontmatter 为唯一真源);计划调整时先更新该表再继续
|
|
48
|
+
- 串行先后写在展示表与各任务正文的「批次 / 计划位置 / 前置」行,不写 `depends_on`(`depends_on` 只用于仍 active 的并行依赖)
|
|
49
|
+
|
|
43
50
|
### 1. 动手前置:建档评估(先查后写的流程落点,所有仓库文件改动前必做,防漏建档/重复建档)
|
|
44
51
|
|
|
45
52
|
- 无 `.tasks/` 任务区时先执行 `toolkit init` 建骨架(幂等,已存在不覆盖)
|
|
53
|
+
- **逐仓逐任务建档**:本次方案涉及多个仓库时,每个将产生仓库文件改动的仓库按展示表的任务清单各自独立建档,全部建档后再改第一处文件;只读参与的仓库不建档
|
|
54
|
+
- **触发建档的改动不含任务区自身**:`.tasks/` 下的读写不单独构成建档理由(避免建档本身成为改动依据、形成自证循环);archive 同主题判别仍按下方「仓库文件改动口径」(任务区自身计入)
|
|
46
55
|
- 列出任务目录 `active/` 下全部 `.md`(含一层 `{YYYYMM}/` 月份子目录),并核对 `archive/` 是否已有同主题任务
|
|
47
|
-
- 读 conventions
|
|
56
|
+
- 读 conventions 载体(存在时):常驻只读 `.tasks/conventions/index.md`,再按本任务 `scope` 加载端分册 / 分类标签分册并**恒叠加 `common`**;`history.md` / `retired.md` 属归档面、按需读;旧单文件 `.tasks/conventions.md` 兼容读取并提示可迁移(分层判定见 `references/conventions-spec.md`)。载体也可能经项目级技能入口壳(如 `.agents/skills/toolkit-conventions/`)引到此处;项目协作规范在建档与执行时须遵守;载体本身不属于任务,不为其建档
|
|
48
57
|
- **同主题判别表**(建档前必须按此决策):
|
|
49
58
|
| 现状 | 本次是否产生仓库文件改动 | 处理 |
|
|
50
59
|
| --- | --- | --- |
|
|
@@ -54,10 +63,10 @@ metadata:
|
|
|
54
63
|
| active 无、archive 有 | 是(延续 / 扩展 / 重新实现) | **重新建档**,正文首行标注来源链 `延续 {原归档任务名}(见 archive/{YYYYMM}/{YYYYMMDD}.md)` |
|
|
55
64
|
| active 无、archive 有 | 否,仅修正旧记录的时间/内容 | 走 fxri-session-recap 模式三(历史修正),**不是建档** |
|
|
56
65
|
| active 与 archive 均无 | — | **建档后再动手**(硬前置,不建档不许改文件) |
|
|
57
|
-
-
|
|
58
|
-
-
|
|
59
|
-
-
|
|
60
|
-
-
|
|
66
|
+
- **仓库文件改动口径**:需写入版本控制的工作区文件的增 / 改 / 删计入(源码、配置、文档、技能、任务区自身),纯读取 / 执行 / 汇报不计入;拿不准 → 列出差异问用户,不猜
|
|
67
|
+
- **动作不算,改动才算**:提交、发版、推送、部署等收尾动作及其固有产物(版本号、更新日志、标签)不构成任务、不单独建档;过程中若出现需改仓库文件才能解决的缺陷(如打包 / 发布渠道配置错误),该修复按普通任务建档
|
|
68
|
+
- **跨仓库改动各自归档(本仓自述)**:任务档只记本仓的改动与动机,同一会话涉及多仓时各仓各自建档归档;判据取**视角**(描述的是不是本仓的改动与动机),非词表——依赖包名 / 被调接口名等本仓事实照写
|
|
69
|
+
- **归档块不可变**:已归档块不追加新的工作内容(否则破坏完成时间 / 范围的可信度),延续需求走新任务。唯一例外是**事实更正**:后续核实推翻原块结论、或协作口径变更导致历史事实字段需更正时,正文末尾追加「修订记录」(保留原结论、附更正时刻与依据),可改受影响的事实字段(如 `scope`),但唯一键 / 完成时间 / 状态 / 负责人仍冻结
|
|
61
70
|
- 任务唯一键:`{YYYYMMDD}-{用户名}-{任务简述}`;多人对同一需求共用一个文件
|
|
62
71
|
|
|
63
72
|
### 2. 建档
|
|
@@ -91,13 +100,15 @@ metadata:
|
|
|
91
100
|
- 变更已有规范语义时,先在 `history.md` 追加一行留痕,再更新索引行「当前语义」(细则见 `references/conventions-spec.md`)
|
|
92
101
|
- **规则作废**:走「迁出 + 三层清理」——索引行删除并迁入 `retired.md`(冻结语义)、物理删除分册内该条小节、外部单一事实源同步删改;不把状态改个标记留在原位
|
|
93
102
|
- 一次性决策不进规范,留在任务正文
|
|
94
|
-
- **存量迁移与升级**:发现旧单文件 `conventions.md
|
|
103
|
+
- **存量迁移与升级**:发现旧单文件 `conventions.md`,或载体为 v1 / v2、`check` / `toolkit conventions status` 报形态告警时,按 `references/conventions-migration.md` 的迁移与升级链路处置(可中断不丢内容)
|
|
95
104
|
|
|
96
105
|
### 6. 收尾边界(硬约束到沉淀)
|
|
97
106
|
|
|
98
107
|
**归档 + 规范沉淀即本技能流程终点**(先归档、后沉淀)。提交、发版、推送不是必经步骤,是否执行取决于用户的全局 / 个人 / 项目规则;若提交代码,按「归档与沉淀 → 跑项目验收命令 → 提交」的顺序执行,任务归档文件与规范载体变更、代码变更落在**同一个 git 提交**(顺序不可颠倒),避免任务完成却滞留 `active/` 未归档,或归档单独成一条提交。
|
|
99
108
|
|
|
100
|
-
|
|
109
|
+
**逐任务交付**:按展示表顺序推进,前置未完成或阻塞未解除时下游不开工;每个任务完成即走完本仓的「归档 → 验收 → 提交」再进入下一个,不跨任务攒批(一个任务至少一次提交、允许多次;不得混入无关改动)。
|
|
110
|
+
|
|
111
|
+
⚠️ **验收须晚于归档**:归档会改写 `.tasks/`(写归档文件、删 active 源文件、清理空月份目录),而归档本身不做阻断式校验——早于归档跑验收就覆盖不到终态。同理,归档块「完成情况」只记改动事实与所用验证命令,不抄验收输出。
|
|
101
112
|
|
|
102
113
|
## 失败模式
|
|
103
114
|
|
|
@@ -106,18 +117,21 @@ metadata:
|
|
|
106
117
|
| active 下出现同名任务文件 | 重复建档,合并为一个后删除多余 |
|
|
107
118
|
| completed 日期与文件名创建日不一致 | 核对是否填错;确为跨天完成则以 completed 日期归档 |
|
|
108
119
|
| depends_on 引用的任务已归档 | 正常,依赖随之解除;引用拼写错误则修正 |
|
|
109
|
-
| 并发写归档文件互相覆盖 | 归档前确认无其他写者同时操作;多人同天归档 `pull`
|
|
120
|
+
| 并发写归档文件互相覆盖 | 归档前确认无其他写者同时操作;多人同天归档 `pull` 后残留 git 冲突标记时,跑 `toolkit tasks normalize --fix` 按并集去重 + 完成时间降序**确定性**解决(保留两侧任务块、丢弃 diff3 base 段与全部标记行) |
|
|
110
121
|
| completed 填了收尾时刻而非真实完成时刻 | 按四级时间源重新取证(git log / 聊天记录时间戳) |
|
|
122
|
+
| 一个方案只建了一个任务档,其余任务无记录 | 按展示表的任务清单逐仓逐任务补建,再继续执行 |
|
|
123
|
+
| 下游任务先于上游开工 | 以展示表顺序为准,前置未完成或阻塞未解除时暂停下游,先解除阻塞 |
|
|
124
|
+
| 把展示型计划表写进任务正文或 `.tasks/` | 计划表只在对话展示、不落档;任务正文只保留「批次 / 计划位置 / 前置」一行 |
|
|
111
125
|
|
|
112
126
|
## 可选加速(不构成依赖)
|
|
113
127
|
|
|
114
|
-
⚠️
|
|
128
|
+
⚠️ 先项目内后全局探测:`pnpm exec toolkit --help`(npm 项目用 `npx toolkit`)→ `toolkit --help`;都不可用即未安装,按各步手工继续,**不安装、不阻塞**。探测成功后用对应前缀执行:
|
|
115
129
|
|
|
116
|
-
- `toolkit tasks
|
|
130
|
+
- `toolkit tasks`:active 总览(替代第 1 步翻目录)
|
|
117
131
|
- `toolkit tasks check`:自动校验(替代第 4 步自查清单)
|
|
118
|
-
- `toolkit tasks archive`:自动归档(替代第 5
|
|
119
|
-
- `toolkit tasks normalize
|
|
120
|
-
- `toolkit conventions status
|
|
121
|
-
- `toolkit conventions upgrade`:v1 / v2 → v3
|
|
122
|
-
- `toolkit conventions format
|
|
132
|
+
- `toolkit tasks archive`:自动归档(替代第 5 步,排他锁防并发;`--dry-run` 预演)
|
|
133
|
+
- `toolkit tasks normalize`:归档后核验(元数据 / 日期漂移 / 排序 / 冲突标记),`--fix` 自动修复
|
|
134
|
+
- `toolkit conventions status`:只读体检载体形态与入口壳(替代第 1 步判形态、第 5.5 步沉淀前后自查)
|
|
135
|
+
- `toolkit conventions upgrade`:v1 / v2 → v3 升级(第 5.5 步,纯机械、幂等;`--dry-run` 预演)
|
|
136
|
+
- `toolkit conventions format`:表格归一为紧凑形态(只动空白层、不改语义;幂等、跳过代码块;`--dry-run` 预演)
|
|
123
137
|
- 任务目录非默认 `.tasks` 时加 `--dir <path>`
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
# 规范载体存量迁移
|
|
2
|
+
|
|
3
|
+
> 本文件为 `conventions-spec.md` 的配套规范,承载载体存量的形态迁移(v0 → v1、v1 → v2、v2 → v3)。仅在迁移存量载体或排查形态异常时加载;日常结构、读写判定与自查见 `conventions-spec.md`。
|
|
4
|
+
|
|
5
|
+
## 10.1 旧单文件 → 目录形态(v0 → v1)
|
|
6
|
+
|
|
7
|
+
触发:`toolkit tasks check` 报旧 `conventions.md` 存在;或用户直接要求迁移。
|
|
8
|
+
|
|
9
|
+
**三段式**(可中断,中途停下不丢内容):
|
|
10
|
+
|
|
11
|
+
1. **机器搬骨架**:建 `conventions/`,旧文件**整体**搬为 `index.md`(原文一字不丢),删除旧文件——此刻 `index.md` 是原文快照,功能上与旧文件等价
|
|
12
|
+
2. **AI 提归属建议**:读原有条目,逐条给出「`common` / 某端」建议与理由(旧文件无端信息,语义分流无法机械完成),形成待确认清单
|
|
13
|
+
3. **用户逐条确认**:确认后写索引行 + 把条文全文拆入对应分册;**未确认的条目保持原样留在 `index.md`**,不强推
|
|
14
|
+
|
|
15
|
+
补充要求:
|
|
16
|
+
|
|
17
|
+
- 迁移与内容重排分开做:先完成形态迁移(结构到位),再谈条目归属调整,避免一次变更混合两种风险
|
|
18
|
+
- 端清单在迁移时同步建立:从项目已有 `scope` 取值与实际子项目构成归纳,经用户确认写入端清单节
|
|
19
|
+
- 旧文件已不存在时不重复迁移
|
|
20
|
+
|
|
21
|
+
## 10.2 v1 → v2 结构升级
|
|
22
|
+
|
|
23
|
+
触发:`toolkit conventions status` 报「需升级」;`toolkit tasks check` 报形态告警(标为 v2 缺 `history.md` 或索引表首列非 `ID`;有 `history.md` 但首列仍是 `#`);或用户直接要求升级。
|
|
24
|
+
|
|
25
|
+
优先用 `toolkit conventions upgrade`(纯机械,可 `--dry-run` 预演),动作序:
|
|
26
|
+
|
|
27
|
+
1. **发 ID**:按现有条序 `1..n` 发 `C-1..C-n`,索引表首列由 `#` 改 `ID`
|
|
28
|
+
2. **切 `history.md`**:原 `index.md`「演进记录」节整表平移为独立 `history.md`(表头首格归一为 `ID`),`index.md` 撤该节;标题归一 `# 项目协作规范索引`,首行补形态标记(版本段写 `v2`)
|
|
29
|
+
3. **改内部引用**:裸「第 N 条」(仅 N ≤ 索引表最大序号者)改写为 `` `C-<n>` ``;带外部文档限定词前缀的引用(如 `AGENTS.md` 质量门第 5 条、`SPEC.md` 协作模型第 3 条、`task-spec.md` 第 6 节)一律不动;改写清单进报告
|
|
30
|
+
4. **分册小节归一**:分册小节标题改 `## C-<n>. {规则名}`
|
|
31
|
+
|
|
32
|
+
补充要求:
|
|
33
|
+
|
|
34
|
+
- **ID 映射不落盘**:映射由 `upgrade` 输出(实跑与 `--dry-run` 均打印);真值可由 git 历史复现(迁移提交的父提交即 v1 原件),故不落盘代价近零
|
|
35
|
+
- **先判后写**:遇形态异常(标记与结构不一致)拒绝执行并给非 0 退出码,**不写任何文件**,提示人工确认
|
|
36
|
+
- `upgrade` 幂等:已是 v2(或更高)时原样返回,不做二次改写
|
|
37
|
+
- **手工迁 v2 与工具升级的落点不同**:手工迁移按本节在首行写版本段为 `v2` 的形态标记、停在 v2;用 `toolkit conventions upgrade` 升级则不落 v2——工具从 v1 输入链式直达 v3(`v1 → v2 → v3`,见 §10.3),仅手工路径停在 v2
|
|
38
|
+
- 手动迁移时按同一动作序执行
|
|
39
|
+
|
|
40
|
+
## 10.3 v2 → v3 结构升级
|
|
41
|
+
|
|
42
|
+
触发:`toolkit conventions status` 报「需升级」;`toolkit tasks check` 报形态告警(标为 v3 缺 `history.md` 或索引表首列非 `ID`;有 `history.md` 但首列仍是 `#`);或用户直接要求升级。
|
|
43
|
+
|
|
44
|
+
优先用 `toolkit conventions upgrade`(纯机械,可 `--dry-run` 预演;v1 输入将链式升级 v1 → v2 → v3),动作序:
|
|
45
|
+
|
|
46
|
+
1. **索引表删两列**:删「状态」「确立来源任务」两列
|
|
47
|
+
2. **`history.md` 表头归一**:v2 存量 `history.md` 沿用「规则 ID / 名称」旧表头,首格归一为稳定 ID `ID`(与索引表首列同归一)
|
|
48
|
+
3. **退休条目迁出**:把原状态为 `已废弃` 的行迁入 `retired.md`(首部补 `# 规范退休记录`、元规则与 7 列表头),并从 Z1 索引表删除;同步删除 Z2 分册内对应小节(三层清理的索引 + 分册两层)
|
|
49
|
+
4. **`retired.md` 按需建**:无退休条目则不创建该文件
|
|
50
|
+
5. **来源 / ID 补录报告**:`history.md` 中 ID 列仍用规则名者、来源列含多任务者,输出人工复核报告——**不做全自动改写**(历史行只追加不改旧的元规则下,改写须人工确认)
|
|
51
|
+
6. **用法说明 / 写入纪律复核**:`index.md` 表外的自由文本(用法说明、写入纪律)若仍残留 v2 措辞(如「填『确立来源任务』」「把『状态』改为『已废弃』」),输出人工复核报告——升级只机械归一索引表列结构,不改写描述该表的自由文本
|
|
52
|
+
7. **标记升 v3**:`index.md` 首行改为 `<!-- toolkit-conventions: v3 -->`
|
|
53
|
+
|
|
54
|
+
补充要求:
|
|
55
|
+
|
|
56
|
+
- **先判后写**:遇形态异常(标记与结构不一致)拒绝执行并给非 0 退出码,**不写任何文件**,提示人工确认
|
|
57
|
+
- **dry-run 迁移报告**:`--dry-run` 打印将删的列、将迁出的条目与将删的分册小节、待人工复核项,供人工确认后再实跑
|
|
58
|
+
- `upgrade` 幂等:已是 v3 时原样返回,不做二次改写
|
|
59
|
+
- 手动迁移时按同一动作序执行
|