@oevery/rsp 4.0.0 → 4.2.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/chunk-AUZYUJ46.mjs +418 -0
- package/dist/chunk-DNRGBQS7.mjs +108 -0
- package/dist/chunk-LGDCIQYL.mjs +725 -0
- package/dist/chunk-P3KO3GZW.mjs +1023 -0
- package/dist/{chunk-HFSTLCCK.mjs → chunk-VDRXFKBP.mjs} +133 -1800
- package/dist/cli.mjs +286 -294
- package/dist/client-U2PN3VS4.mjs +108 -0
- package/dist/{entry-RIJQ2X46.mjs → entry-NDASTAI5.mjs} +13 -9
- package/dist/viewer/NOTICE.txt +299 -0
- package/dist/viewer/app.css +2 -0
- package/dist/viewer/app.js +670 -0
- package/dist/viewer/chunks/abnfDiagram-S7VZAUFO-K5EOZOEF.js +1 -0
- package/dist/viewer/chunks/architecture-WOLXFQ4H-UAT5D5BF.js +1 -0
- package/dist/viewer/chunks/architectureDiagram-YGSQEFNW-UNPSYM2L.js +36 -0
- package/dist/viewer/chunks/blockDiagram-APKKGZFW-2F7TTPAV.js +140 -0
- package/dist/viewer/chunks/bpmnIcons-APHXDYXF-ZWPFFN3O.js +1 -0
- package/dist/viewer/chunks/c4Diagram-KJ2TOQU5-KNLN6CME.js +38 -0
- package/dist/viewer/chunks/chunk-274PZN6B.js +1 -0
- package/dist/viewer/chunks/chunk-2VGDQLQD.js +1 -0
- package/dist/viewer/chunks/chunk-33XESOCS.js +1 -0
- package/dist/viewer/chunks/chunk-3ZSL2TGQ.js +1 -0
- package/dist/viewer/chunks/chunk-432I4U3B.js +1 -0
- package/dist/viewer/chunks/chunk-4PJNGS3V.js +1 -0
- package/dist/viewer/chunks/chunk-54NLSLTF.js +9 -0
- package/dist/viewer/chunks/chunk-6QRHYJ5Q.js +1 -0
- package/dist/viewer/chunks/chunk-6RCFKBVR.js +1 -0
- package/dist/viewer/chunks/chunk-6Y2HP7DC.js +213 -0
- package/dist/viewer/chunks/chunk-7MAT7NHP.js +1 -0
- package/dist/viewer/chunks/chunk-AKHBD6LT.js +2 -0
- package/dist/viewer/chunks/chunk-CZIM56BV.js +1 -0
- package/dist/viewer/chunks/chunk-DN4Y7LXJ.js +1 -0
- package/dist/viewer/chunks/chunk-E2UQN267.js +1 -0
- package/dist/viewer/chunks/chunk-GBARLDDT.js +1 -0
- package/dist/viewer/chunks/chunk-H4YEV7VR.js +1 -0
- package/dist/viewer/chunks/chunk-HUVVDQHZ.js +1 -0
- package/dist/viewer/chunks/chunk-IAKC32WV.js +72 -0
- package/dist/viewer/chunks/chunk-JTW4SY4L.js +1 -0
- package/dist/viewer/chunks/chunk-JZV675LF.js +1 -0
- package/dist/viewer/chunks/chunk-KDUDYTWO.js +1 -0
- package/dist/viewer/chunks/chunk-KHX3A5RZ.js +331 -0
- package/dist/viewer/chunks/chunk-KPXJJSUR.js +15 -0
- package/dist/viewer/chunks/chunk-LEGNM6PH.js +1 -0
- package/dist/viewer/chunks/chunk-LYY4ZY72.js +1 -0
- package/dist/viewer/chunks/chunk-MKDEK2LU.js +1 -0
- package/dist/viewer/chunks/chunk-MYJRFART.js +129 -0
- package/dist/viewer/chunks/chunk-NUXZBURC.js +1 -0
- package/dist/viewer/chunks/chunk-NXHT5I2L.js +1 -0
- package/dist/viewer/chunks/chunk-OF62XRVM.js +62 -0
- package/dist/viewer/chunks/chunk-ONCOEVBS.js +1 -0
- package/dist/viewer/chunks/chunk-P44SH3OO.js +1 -0
- package/dist/viewer/chunks/chunk-PDXKDBIX.js +1 -0
- package/dist/viewer/chunks/chunk-PHKIAKHS.js +1 -0
- package/dist/viewer/chunks/chunk-PJDMAGPE.js +2 -0
- package/dist/viewer/chunks/chunk-RC2NPHSX.js +88 -0
- package/dist/viewer/chunks/chunk-T6DM5RSK.js +10 -0
- package/dist/viewer/chunks/chunk-U5STX66M.js +2 -0
- package/dist/viewer/chunks/chunk-UIAJQPOF.js +1 -0
- package/dist/viewer/chunks/chunk-UX2S3LP3.js +1 -0
- package/dist/viewer/chunks/chunk-VEMTQQ7Y.js +2 -0
- package/dist/viewer/chunks/chunk-WKCPBR3C.js +1 -0
- package/dist/viewer/chunks/chunk-WMQ4Y2MS.js +32 -0
- package/dist/viewer/chunks/chunk-YPWIQAHX.js +3 -0
- package/dist/viewer/chunks/chunk-Z4ZDIMO2.js +136 -0
- package/dist/viewer/chunks/chunk-ZATQCNXH.js +1 -0
- package/dist/viewer/chunks/chunk-ZE5RDJX6.js +1 -0
- package/dist/viewer/chunks/chunk-ZO62R4L2.js +1 -0
- package/dist/viewer/chunks/classDiagram-v2-L25IHNXF-5F2M2CZ4.js +217 -0
- package/dist/viewer/chunks/cose-bilkent-JH36ORCC-S56HJ5WN.js +1 -0
- package/dist/viewer/chunks/cynefin-EF2NZ3EQ-6WY2NCLE.js +1 -0
- package/dist/viewer/chunks/cynefinDiagram-L36ESFBY-DE6PZNQA.js +62 -0
- package/dist/viewer/chunks/dagre-SPEB5RXH-QEOTKFV2.js +4 -0
- package/dist/viewer/chunks/diagram-3B7GL73J-RZPIU7FY.js +200 -0
- package/dist/viewer/chunks/diagram-DNEMPZML-YD26TJKC.js +24 -0
- package/dist/viewer/chunks/diagram-L3MUGCDN-TJUEX4QI.js +41 -0
- package/dist/viewer/chunks/diagram-LA4NIPWU-3PUQS6UW.js +24 -0
- package/dist/viewer/chunks/diagram-MHCOC4E2-YBTBD4PG.js +3 -0
- package/dist/viewer/chunks/diagram-XPFHEONP-VF2TQBNR.js +30 -0
- package/dist/viewer/chunks/ebnfDiagram-UZSYDL2S-QE7DIEME.js +1 -0
- package/dist/viewer/chunks/elk-XV6XMXQE-X5OZRIL3.js +27 -0
- package/dist/viewer/chunks/erDiagram-EYBAPDEH-5B2S7VB4.js +99 -0
- package/dist/viewer/chunks/eventmodeling-K75KTNOO-CHCQYZBI.js +1 -0
- package/dist/viewer/chunks/flowDiagram-MALGAFMO-XJFC5NTN.js +1 -0
- package/dist/viewer/chunks/ganttDiagram-23REXITY-TUUZ3QYO.js +292 -0
- package/dist/viewer/chunks/gitGraph-VSP46ZUC-VFZPJQ6A.js +1 -0
- package/dist/viewer/chunks/gitGraphDiagram-STJD7YCW-4CVV5LSH.js +106 -0
- package/dist/viewer/chunks/info-OHQRW6UA-P4744SJ6.js +1 -0
- package/dist/viewer/chunks/infoDiagram-KBXO4MBG-Q2WYYNNN.js +2 -0
- package/dist/viewer/chunks/ishikawaDiagram-M35NCXHK-PLQPTX2U.js +70 -0
- package/dist/viewer/chunks/journeyDiagram-OPLOXDXO-FB73RE6F.js +139 -0
- package/dist/viewer/chunks/kanban-definition-BZKZHSQY-6FU4TXYJ.js +89 -0
- package/dist/viewer/chunks/katex-IN4S3RHS.js +257 -0
- package/dist/viewer/chunks/mindmap-definition-I2QAS2VK-ZQ36ABVW.js +98 -0
- package/dist/viewer/chunks/packet-JDAUHWVQ-NYXIQQVA.js +1 -0
- package/dist/viewer/chunks/pegDiagram-FD4XPPHP-5XXVT6XN.js +1 -0
- package/dist/viewer/chunks/pie-XZMESJXO-32CUE6KZ.js +1 -0
- package/dist/viewer/chunks/pieDiagram-J4AKIIQI-WRTBDFM5.js +39 -0
- package/dist/viewer/chunks/quadrantDiagram-XTYBLID2-YPBDQIAK.js +7 -0
- package/dist/viewer/chunks/radar-ABXABTNO-272FILRO.js +1 -0
- package/dist/viewer/chunks/railroad-I3PHUGI6-6EGAH4XA.js +1 -0
- package/dist/viewer/chunks/railroad-abnf-LNEFI6M7-G6E7ATER.js +1 -0
- package/dist/viewer/chunks/railroad-ebnf-DWYD2UWJ-MR4P6BDR.js +1 -0
- package/dist/viewer/chunks/railroad-peg-JR7BVNR7-WXLQUGUO.js +1 -0
- package/dist/viewer/chunks/railroadDiagram-MRQ6NCDL-XHZQ2BLY.js +1 -0
- package/dist/viewer/chunks/requirementDiagram-Y7LWUY3S-W5FHRRML.js +84 -0
- package/dist/viewer/chunks/sankeyDiagram-WGJFYUXA-OJJIRVTI.js +40 -0
- package/dist/viewer/chunks/sequenceDiagram-5NDRBG5M-D6T4DRNG.js +169 -0
- package/dist/viewer/chunks/sizeCapture-INFHLROL-WL3FTUJX.js +1 -0
- package/dist/viewer/chunks/stateDiagram-v2-FJ4FJNEA-LAXL7KGG.js +291 -0
- package/dist/viewer/chunks/swimlanes-UMQ2AFYF-XIJBD726.js +1 -0
- package/dist/viewer/chunks/swimlanesDiagram-OMPLPG4O-7O7MHFW7.js +8 -0
- package/dist/viewer/chunks/timeline-definition-SEUHKTQE-BAZQA47I.js +120 -0
- package/dist/viewer/chunks/treeView-D4JQ5SDB-6YMDAAPA.js +1 -0
- package/dist/viewer/chunks/treemap-SAJKECNS-2X573PPS.js +1 -0
- package/dist/viewer/chunks/usecaseDiagram-AFA6YXN4-4YCEMWJB.js +370 -0
- package/dist/viewer/chunks/vennDiagram-NNMJR3RB-GEMROLAE.js +34 -0
- package/dist/viewer/chunks/wardley-7MLQ67FV-DGTGHYYC.js +1 -0
- package/dist/viewer/chunks/wardleyDiagram-S7YFUSEH-K4HVD3SS.js +78 -0
- package/dist/viewer/chunks/xychartDiagram-GGNKY7IX-HVLWCUEO.js +7 -0
- package/dist/viewer/mermaid.js +12 -0
- package/dist/viewer-build.json +1 -0
- package/dist/viewer-service.mjs +607 -0
- package/package.json +27 -8
- package/skills/rsp/SKILL.md +13 -10
- package/skills/rsp/references/architecture.md +39 -0
- package/skills/rsp/references/closeout.md +4 -4
- package/skills/rsp/references/durable-review.md +6 -9
- package/skills/rsp/references/focus-continuation.md +6 -2
- package/skills/rsp/references/setup-repair.md +11 -6
- package/skills/rsp/references/work-model.md +14 -4
- package/skills/rsp-commit/SKILL.md +2 -2
- package/skills/rsp-doc/SKILL.md +13 -10
- package/skills/rsp-doc/references/skill-authoring.md +2 -2
- package/skills/rsp-implement/SKILL.md +16 -12
- package/skills/rsp-review/SKILL.md +12 -12
- package/skills/rsp-review/references/code-review.md +11 -5
- package/skills/rsp-review/references/document-review.md +8 -10
- package/skills/rsp-shape/SKILL.md +3 -1
- package/skills/rsp-shape/references/planning.md +4 -4
- package/skills/rsp-verify/SKILL.md +9 -14
- package/skills/rsp-doc/references/artifact-lenses.md +0 -43
- package/skills/rsp-review/references/structural-review.md +0 -41
package/dist/cli.mjs
CHANGED
|
@@ -1,7 +1,78 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import {
|
|
3
|
-
|
|
3
|
+
ARCHITECTURE_FILE,
|
|
4
|
+
PROJECT_VERSION_PATH,
|
|
5
|
+
SOURCE_INVOCATION,
|
|
6
|
+
compareVersions,
|
|
7
|
+
exactInvocation,
|
|
8
|
+
guardProjectVersion,
|
|
9
|
+
isExactVersion,
|
|
10
|
+
queryArchitecture,
|
|
11
|
+
readProjectRuntime,
|
|
12
|
+
readProjectVersion,
|
|
13
|
+
selectProjectRuntime
|
|
14
|
+
} from "./chunk-AUZYUJ46.mjs";
|
|
15
|
+
import {
|
|
4
16
|
ArchiveHistoryError,
|
|
17
|
+
GROUP_BRIEF_FILENAME,
|
|
18
|
+
GROUP_REOPEN_COMPLETION_PREFIX,
|
|
19
|
+
HISTORY_DEFAULT_LIMIT,
|
|
20
|
+
HISTORY_MAX_LIMIT,
|
|
21
|
+
IssueRelationshipError,
|
|
22
|
+
WorkRefError,
|
|
23
|
+
buildDurableReviewGuidance,
|
|
24
|
+
collectArchiveReadiness,
|
|
25
|
+
createIssueRelationship,
|
|
26
|
+
generateGroupBriefContent,
|
|
27
|
+
getDurableReviewCandidateTargets,
|
|
28
|
+
getGroupReopenEvidence,
|
|
29
|
+
hasArchivedGroupBrief,
|
|
30
|
+
historyInspectionComplete,
|
|
31
|
+
inspectArchiveHistory,
|
|
32
|
+
inspectArchiveTree,
|
|
33
|
+
inspectChangeDependencies,
|
|
34
|
+
inspectChangeGroups,
|
|
35
|
+
inspectFocusTree,
|
|
36
|
+
inspectProjectStatus,
|
|
37
|
+
inspectWorkTree,
|
|
38
|
+
normalizeExecutableWorkRef,
|
|
39
|
+
normalizeWorkRefSegment,
|
|
40
|
+
parseIssueRelationships,
|
|
41
|
+
projectDependencyForest,
|
|
42
|
+
projectSpecsDetail,
|
|
43
|
+
projectSpecsSearch,
|
|
44
|
+
projectSpecsTree,
|
|
45
|
+
queryArchiveHistory,
|
|
46
|
+
readArchiveHistoryDetail,
|
|
47
|
+
resolveArchiveDirectory,
|
|
48
|
+
resolveExecutableChange,
|
|
49
|
+
resolveFocusMarkerPath,
|
|
50
|
+
resolveWorkRef,
|
|
51
|
+
selectArchiveHistoryRecord,
|
|
52
|
+
selectArchivedGroupBrief,
|
|
53
|
+
toArchiveReadinessOutput
|
|
54
|
+
} from "./chunk-VDRXFKBP.mjs";
|
|
55
|
+
import {
|
|
56
|
+
SPECS_DEFAULT_RESULT_LIMIT,
|
|
57
|
+
SPECS_DETAIL_CONTENT_CODE_POINTS,
|
|
58
|
+
SPECS_MAX_RESULT_LIMIT,
|
|
59
|
+
SpecsQueryError,
|
|
60
|
+
cleanupEmptyParentDirs,
|
|
61
|
+
detectProjectName,
|
|
62
|
+
emitJson,
|
|
63
|
+
guardRspInitialized,
|
|
64
|
+
inspectRspInitialization,
|
|
65
|
+
inspectSpecs,
|
|
66
|
+
inspectUnsupportedRules,
|
|
67
|
+
isRecognizedGeneratedSpecsIndex,
|
|
68
|
+
isValidSpecName,
|
|
69
|
+
normalizeLogicalPath,
|
|
70
|
+
specsInspectionComplete,
|
|
71
|
+
toErrorMessage,
|
|
72
|
+
walkMarkdownFiles
|
|
73
|
+
} from "./chunk-LGDCIQYL.mjs";
|
|
74
|
+
import {
|
|
75
|
+
ARCHIVES_DIR,
|
|
5
76
|
CHANGES_DIR,
|
|
6
77
|
CHANGE_DOCUMENT_SCHEMA,
|
|
7
78
|
CONFIG_PATH,
|
|
@@ -9,11 +80,6 @@ import {
|
|
|
9
80
|
DocumentSectionCardinalityError,
|
|
10
81
|
FOCUS_DIR,
|
|
11
82
|
GROUP_BRIEF_DOCUMENT_SCHEMA,
|
|
12
|
-
GROUP_BRIEF_FILENAME,
|
|
13
|
-
GROUP_REOPEN_COMPLETION_PREFIX,
|
|
14
|
-
HISTORY_DEFAULT_LIMIT,
|
|
15
|
-
HISTORY_MAX_LIMIT,
|
|
16
|
-
IssueRelationshipError,
|
|
17
83
|
LOCK_PATH,
|
|
18
84
|
MAX_FOCUS_CAPSULE_BYTES,
|
|
19
85
|
ManagedPathError,
|
|
@@ -21,94 +87,45 @@ import {
|
|
|
21
87
|
PKG_ROOT,
|
|
22
88
|
RSP_DIR,
|
|
23
89
|
RSP_RULES_PATH,
|
|
24
|
-
SPECS_DEFAULT_RESULT_LIMIT,
|
|
25
|
-
SPECS_DETAIL_CONTENT_CODE_POINTS,
|
|
26
|
-
SPECS_MAX_RESULT_LIMIT,
|
|
27
|
-
SpecsQueryError,
|
|
28
|
-
WorkRefError,
|
|
29
90
|
appendDocumentSectionItem,
|
|
30
|
-
buildDurableReviewGuidance,
|
|
31
|
-
cleanupEmptyParentDirs,
|
|
32
91
|
clearConfigCache,
|
|
33
|
-
collectArchiveReadiness,
|
|
34
92
|
countCheckboxes,
|
|
35
|
-
createIssueRelationship,
|
|
36
93
|
detectDeltaSections,
|
|
37
|
-
detectProjectName,
|
|
38
|
-
emitJson,
|
|
39
94
|
ensureManagedFile,
|
|
40
95
|
generateConfigTemplate,
|
|
41
|
-
generateGroupBriefContent,
|
|
42
96
|
getDocumentSectionDefinitionByHeading,
|
|
43
97
|
getDocumentSectionMarkdown,
|
|
44
98
|
getDocumentSections,
|
|
45
99
|
getDocumentTitles,
|
|
46
|
-
getDurableReviewCandidateTargets,
|
|
47
|
-
getGroupReopenEvidence,
|
|
48
100
|
getVersion,
|
|
49
101
|
getVisibleBodyLines,
|
|
50
|
-
guardRspInitialized,
|
|
51
|
-
hasArchivedGroupBrief,
|
|
52
102
|
hasMeaningfulBlockers,
|
|
53
|
-
historyInspectionComplete,
|
|
54
|
-
inspectArchiveHistory,
|
|
55
|
-
inspectArchiveTree,
|
|
56
|
-
inspectChangeDependencies,
|
|
57
|
-
inspectChangeGroups,
|
|
58
|
-
inspectFocusTree,
|
|
59
103
|
inspectManagedDirectory,
|
|
60
104
|
inspectManagedFile,
|
|
61
105
|
inspectManagedFileTree,
|
|
62
|
-
inspectProjectStatus,
|
|
63
106
|
inspectRspConfig,
|
|
64
|
-
inspectRspInitialization,
|
|
65
|
-
inspectSpecs,
|
|
66
|
-
inspectUnsupportedRules,
|
|
67
|
-
inspectWorkTree,
|
|
68
|
-
isRecognizedGeneratedSpecsIndex,
|
|
69
|
-
isValidSpecName,
|
|
70
107
|
loadRspConfig,
|
|
71
108
|
markdownProse,
|
|
72
109
|
markdownText,
|
|
73
110
|
markdownTopLevelComments,
|
|
74
|
-
normalizeExecutableWorkRef,
|
|
75
|
-
normalizeLogicalPath,
|
|
76
|
-
normalizeWorkRefSegment,
|
|
77
111
|
parseFrontmatter,
|
|
78
|
-
parseIssueRelationships,
|
|
79
112
|
parseMarkdown,
|
|
80
113
|
parseRspDocument,
|
|
81
114
|
parseScenarios,
|
|
82
115
|
pc,
|
|
83
|
-
projectDependencyForest,
|
|
84
|
-
projectSpecsDetail,
|
|
85
|
-
projectSpecsSearch,
|
|
86
|
-
projectSpecsTree,
|
|
87
|
-
queryArchiveHistory,
|
|
88
|
-
readArchiveHistoryDetail,
|
|
89
116
|
renderDocumentSectionHeading,
|
|
90
117
|
renderDocumentTitle,
|
|
91
118
|
requireManagedDirectory,
|
|
92
119
|
requireManagedFile,
|
|
93
|
-
resolveArchiveDirectory,
|
|
94
120
|
resolveDecisionRecordsPath,
|
|
95
|
-
resolveExecutableChange,
|
|
96
|
-
resolveFocusMarkerPath,
|
|
97
121
|
resolveKinds,
|
|
98
122
|
resolveLanguagePolicy,
|
|
99
123
|
resolveManagedDirectoryChain,
|
|
100
124
|
resolveRequiredSections,
|
|
101
|
-
resolveWorkRef,
|
|
102
125
|
resolveWorkflowPolicy,
|
|
103
|
-
selectArchiveHistoryRecord,
|
|
104
|
-
selectArchivedGroupBrief,
|
|
105
|
-
specsInspectionComplete,
|
|
106
|
-
toArchiveReadinessOutput,
|
|
107
|
-
toErrorMessage,
|
|
108
126
|
validateDecisionRecordsFilesystemPath,
|
|
109
|
-
walkMarkdownFiles,
|
|
110
127
|
writeManagedFile
|
|
111
|
-
} from "./chunk-
|
|
128
|
+
} from "./chunk-P3KO3GZW.mjs";
|
|
112
129
|
|
|
113
130
|
// src/cli.ts
|
|
114
131
|
import { resolve as resolve2 } from "path";
|
|
@@ -117,6 +134,7 @@ import { runMain } from "citty";
|
|
|
117
134
|
|
|
118
135
|
// src/cli/capabilities.ts
|
|
119
136
|
var CLI_COMMAND_CAPABILITIES = {
|
|
137
|
+
"architecture": { json: true, compact: true },
|
|
120
138
|
"config": { json: true, compact: true },
|
|
121
139
|
"status": { json: true, compact: true },
|
|
122
140
|
"show": { json: true, compact: true },
|
|
@@ -150,10 +168,56 @@ function supportsCompact(command) {
|
|
|
150
168
|
}
|
|
151
169
|
|
|
152
170
|
// src/cli/registry.ts
|
|
153
|
-
import { defineCommand as
|
|
171
|
+
import { defineCommand as defineCommand6 } from "citty";
|
|
154
172
|
|
|
155
|
-
// src/cli/commands/
|
|
173
|
+
// src/cli/commands/architecture.ts
|
|
156
174
|
import { defineCommand } from "citty";
|
|
175
|
+
var architectureCommand = defineCommand({
|
|
176
|
+
meta: { name: "architecture", description: "Read full or selected architecture structure without document bodies" },
|
|
177
|
+
args: { node: { type: "string", description: "Node and descendants" }, view: { type: "string", description: "Explicit view selection" }, ...compactJsonArgs },
|
|
178
|
+
async run({ args }) {
|
|
179
|
+
const unknown = Object.keys(args).filter((key) => !["node", "view", "json", "compact", "_"].includes(key));
|
|
180
|
+
if (unknown.length || args._.length)
|
|
181
|
+
throw new Error(`Unsupported architecture options/arguments: ${[...unknown, ...args._].join(", ")}`);
|
|
182
|
+
const result = await queryArchitecture({ node: args.node, view: args.view });
|
|
183
|
+
if (args.json) {
|
|
184
|
+
console.log(JSON.stringify(result, null, args.compact ? void 0 : 2));
|
|
185
|
+
} else {
|
|
186
|
+
console.log(`Architecture: ${result.configured ? result.source.root : "not configured"}
|
|
187
|
+
Selection: ${result.selection.kind}${result.selection.id ? ` ${result.selection.id}` : ""}`);
|
|
188
|
+
for (const node of result.nodes) {
|
|
189
|
+
console.log(`${node.boundary ? "[boundary] " : ""}${node.id}: ${node.title} \u2014 ${node.description}${node.parent ? ` (parent: ${node.parent})` : ""}`);
|
|
190
|
+
for (const binding of node.bindings) console.log(` ${binding.file}${binding.headings ? ` > ${binding.headings.join(" > ")}` : ""} (scope: ${binding.scope}; ${binding.inherited ? `inherited from ${binding.origin}` : `direct on ${binding.origin}`})`);
|
|
191
|
+
}
|
|
192
|
+
for (const edge of result.relations) console.log(`Relation ${edge.id}: ${edge.source} -> ${edge.target} [${edge.type}]${edge.label ? ` ${edge.label}` : ""}: ${edge.description}`);
|
|
193
|
+
for (const view of result.views) {
|
|
194
|
+
console.log(`View ${view.id}: ${view.title} (owner: ${view.node}; include: ${view.include.join(", ")})`);
|
|
195
|
+
if (view.relationTypes || view.relationIds || view.boundary)
|
|
196
|
+
console.log(` Filters: types=${view.relationTypes?.join(", ") ?? "*"}; relations=${view.relationIds?.join(", ") ?? "*"}; boundary=${view.boundary ?? "include"}`);
|
|
197
|
+
for (const participant of view.scenario?.participants ?? [])
|
|
198
|
+
console.log(` Participant ${participant.id}: ${participant.node}${participant.title ? ` (${participant.title})` : ""}`);
|
|
199
|
+
view.scenario?.steps.forEach((step, index) => console.log(` ${index + 1}. ${step.id}: ${step.source} -> ${step.target} [${step.type}] ${step.label}${step.replyTo ? ` (reply to ${step.replyTo})` : ""}${step.description ? ` \u2014 ${step.description}` : ""}`));
|
|
200
|
+
}
|
|
201
|
+
for (const diagnostic of result.diagnostics) console.log(`${diagnostic.code}: ${diagnostic.message}`);
|
|
202
|
+
if (result.configured)
|
|
203
|
+
console.log(`Source: ${result.source.file} @ ${result.source.revision}`);
|
|
204
|
+
}
|
|
205
|
+
}
|
|
206
|
+
});
|
|
207
|
+
var viewCommand = defineCommand({
|
|
208
|
+
meta: { name: "view", description: "Open the shared local architecture viewer, inspect or stop its service" },
|
|
209
|
+
args: { action: { type: "positional", required: false, description: "status or stop; omit to open" }, open: { type: "boolean", default: true, description: "Open browser (use --no-open to print URL only)" } },
|
|
210
|
+
async run({ args }) {
|
|
211
|
+
const unknown = Object.keys(args).filter((key) => !["action", "open", "_"].includes(key));
|
|
212
|
+
if (unknown.length || args._.length > 1 || args.action && !args.open)
|
|
213
|
+
throw new Error("rsp view accepts only an optional status/stop action or --no-open");
|
|
214
|
+
const { runView } = await import("./client-U2PN3VS4.mjs");
|
|
215
|
+
await runView(args.action, args.open);
|
|
216
|
+
}
|
|
217
|
+
});
|
|
218
|
+
|
|
219
|
+
// src/cli/commands/inspection.ts
|
|
220
|
+
import { defineCommand as defineCommand2 } from "citty";
|
|
157
221
|
|
|
158
222
|
// src/commands/check.ts
|
|
159
223
|
import { readFile } from "fs/promises";
|
|
@@ -255,7 +319,6 @@ function inspectChangeDocument(content, options) {
|
|
|
255
319
|
}
|
|
256
320
|
|
|
257
321
|
// src/core/focus-capsule.ts
|
|
258
|
-
import { Buffer } from "buffer";
|
|
259
322
|
import { TextDecoder } from "util";
|
|
260
323
|
var FOCUS_CAPSULE_VERSION = "<!-- rsp-focus:v1 -->";
|
|
261
324
|
var LEGACY_WARNING = "legacy focus capsule has no structured recovery projection";
|
|
@@ -273,15 +336,6 @@ function inspectFocusCapsuleBytes(bytes) {
|
|
|
273
336
|
} catch {
|
|
274
337
|
return { kind: "invalid", code: "focus_capsule_invalid_utf8", message: "focus capsule must contain valid UTF-8" };
|
|
275
338
|
}
|
|
276
|
-
if (Buffer.byteLength(content, "utf-8") > MAX_FOCUS_CAPSULE_BYTES) {
|
|
277
|
-
return {
|
|
278
|
-
kind: "invalid",
|
|
279
|
-
code: "focus_capsule_too_large",
|
|
280
|
-
message: `focus capsule exceeds ${MAX_FOCUS_CAPSULE_BYTES} UTF-8 bytes`
|
|
281
|
-
};
|
|
282
|
-
}
|
|
283
|
-
if (content.length === 0)
|
|
284
|
-
return { kind: "empty", content: "" };
|
|
285
339
|
return parseFocusCapsule(content);
|
|
286
340
|
}
|
|
287
341
|
function parseFocusCapsule(content) {
|
|
@@ -637,109 +691,8 @@ async function showConfig() {
|
|
|
637
691
|
|
|
638
692
|
// src/commands/doctor.ts
|
|
639
693
|
import { existsSync } from "fs";
|
|
640
|
-
import { readdir as readdir2, readFile as
|
|
641
|
-
import { basename, join as
|
|
642
|
-
|
|
643
|
-
// src/core/project-version.ts
|
|
644
|
-
import { readFile as readFile2, realpath } from "fs/promises";
|
|
645
|
-
import { join } from "path";
|
|
646
|
-
var PROJECT_VERSION_PATH = ".rsp/version";
|
|
647
|
-
var PROJECT_SOURCE_PATH = ".rsp/source";
|
|
648
|
-
var SOURCE_INVOCATION = "mise exec -- node dist/cli.mjs";
|
|
649
|
-
function isExactVersion(value) {
|
|
650
|
-
return /^(?:0|[1-9]\d*)\.(?:0|[1-9]\d*)\.(?:0|[1-9]\d*)(?:-(?:0|[1-9]\d*|\d*[a-z-][\da-z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-z-][\da-z-]*))*)?(?:\+[\da-z-]+(?:\.[\da-z-]+)*)?$/i.test(value);
|
|
651
|
-
}
|
|
652
|
-
function exactInvocation(version) {
|
|
653
|
-
if (!isExactVersion(version))
|
|
654
|
-
throw new Error(`Invalid exact RSP version: ${version}`);
|
|
655
|
-
return `npx -y @oevery/rsp@${version}`;
|
|
656
|
-
}
|
|
657
|
-
async function readProjectVersion(projectRoot = ".") {
|
|
658
|
-
const directory = inspectManagedDirectory(join(projectRoot, RSP_DIR), "RSP root", { allowMissing: true });
|
|
659
|
-
if (directory.issue)
|
|
660
|
-
throw directory.issue;
|
|
661
|
-
if (!directory.exists)
|
|
662
|
-
return null;
|
|
663
|
-
const path = join(projectRoot, PROJECT_VERSION_PATH);
|
|
664
|
-
const inspection = inspectManagedFile(path, "project CLI version", { allowMissing: true });
|
|
665
|
-
if (inspection.issue)
|
|
666
|
-
throw inspection.issue;
|
|
667
|
-
if (!inspection.exists)
|
|
668
|
-
return null;
|
|
669
|
-
const version = (await readFile2(path, "utf8")).trim();
|
|
670
|
-
if (!isExactVersion(version))
|
|
671
|
-
throw new Error(`${PROJECT_VERSION_PATH} must contain one exact package version, not a tag or range`);
|
|
672
|
-
return version;
|
|
673
|
-
}
|
|
674
|
-
async function readProjectRuntime(projectRoot = ".") {
|
|
675
|
-
const version = await readProjectVersion(projectRoot);
|
|
676
|
-
const source = inspectManagedFile(join(projectRoot, PROJECT_SOURCE_PATH), "project source selection", { allowMissing: true });
|
|
677
|
-
if (source.issue)
|
|
678
|
-
throw source.issue;
|
|
679
|
-
if (!source.exists)
|
|
680
|
-
return { mode: "package", version };
|
|
681
|
-
if (version !== null)
|
|
682
|
-
throw new Error(`${PROJECT_SOURCE_PATH} and ${PROJECT_VERSION_PATH} are mutually exclusive; explicitly select one runtime.`);
|
|
683
|
-
if ((await readFile2(join(projectRoot, PROJECT_SOURCE_PATH), "utf8")).trim() !== ".")
|
|
684
|
-
throw new Error(`${PROJECT_SOURCE_PATH} must contain . to select this RSP source checkout.`);
|
|
685
|
-
if (await realpath(projectRoot) !== await realpath(PKG_ROOT))
|
|
686
|
-
throw new Error(`Source mode requires this checkout's local CLI. Build here, then use ${SOURCE_INVOCATION} <command>; a registry package or another checkout cannot substitute.`);
|
|
687
|
-
const sourceDirectory = inspectManagedDirectory(join(projectRoot, "src"), "RSP source directory");
|
|
688
|
-
const sourceEntry = inspectManagedFile(join(projectRoot, "src/cli.ts"), "RSP source entry");
|
|
689
|
-
if (sourceDirectory.issue || sourceEntry.issue)
|
|
690
|
-
throw sourceDirectory.issue ?? sourceEntry.issue;
|
|
691
|
-
return { mode: "source" };
|
|
692
|
-
}
|
|
693
|
-
async function selectProjectRuntime(operation = "ordinary") {
|
|
694
|
-
const version = await getVersion();
|
|
695
|
-
exactInvocation(version);
|
|
696
|
-
const selected = await readProjectRuntime();
|
|
697
|
-
if (selected.mode === "source")
|
|
698
|
-
return { mode: "source", version };
|
|
699
|
-
if (selected.version && selected.version !== version && operation !== "update") {
|
|
700
|
-
throw new Error(`Project pins RSP ${selected.version}; running CLI is ${version}. Use ${exactInvocation(selected.version)} <command>. To migrate deliberately, inspect the target version and run ${exactInvocation(version)} update.`);
|
|
701
|
-
}
|
|
702
|
-
if (selected.version && operation === "update" && compareVersions(version, selected.version) < 0)
|
|
703
|
-
throw new Error(`Downgrading RSP from ${selected.version} to ${version} is unsupported. Use ${exactInvocation(selected.version)} <command>.`);
|
|
704
|
-
return { mode: "package", version };
|
|
705
|
-
}
|
|
706
|
-
function compareVersions(left, right) {
|
|
707
|
-
const parts = (value) => {
|
|
708
|
-
const [core, ...pre] = value.split("+", 1)[0].split("-");
|
|
709
|
-
return { core: core.split(".").map(BigInt), pre: pre.length ? pre.join("-").split(".") : [] };
|
|
710
|
-
};
|
|
711
|
-
const a = parts(left);
|
|
712
|
-
const b = parts(right);
|
|
713
|
-
for (let i = 0; i < 3; i++) {
|
|
714
|
-
if (a.core[i] !== b.core[i])
|
|
715
|
-
return a.core[i] > b.core[i] ? 1 : -1;
|
|
716
|
-
}
|
|
717
|
-
if (!a.pre.length || !b.pre.length)
|
|
718
|
-
return Number(!a.pre.length) - Number(!b.pre.length);
|
|
719
|
-
for (let i = 0; i < Math.max(a.pre.length, b.pre.length); i++) {
|
|
720
|
-
const x = a.pre[i];
|
|
721
|
-
const y = b.pre[i];
|
|
722
|
-
if (x === y)
|
|
723
|
-
continue;
|
|
724
|
-
if (x === void 0 || y === void 0)
|
|
725
|
-
return x === void 0 ? -1 : 1;
|
|
726
|
-
const nx = /^\d+$/.test(x);
|
|
727
|
-
const ny = /^\d+$/.test(y);
|
|
728
|
-
if (nx && ny)
|
|
729
|
-
return BigInt(x) > BigInt(y) ? 1 : -1;
|
|
730
|
-
if (nx !== ny)
|
|
731
|
-
return nx ? -1 : 1;
|
|
732
|
-
return x > y ? 1 : -1;
|
|
733
|
-
}
|
|
734
|
-
return 0;
|
|
735
|
-
}
|
|
736
|
-
async function guardProjectVersion(rawArgs) {
|
|
737
|
-
if (rawArgs.some((arg) => ["--help", "-h"].includes(arg)) || rawArgs.length === 1 && ["--version", "-v"].includes(rawArgs[0]))
|
|
738
|
-
return;
|
|
739
|
-
if (["doctor", "config", "update"].includes(rawArgs[0] ?? ""))
|
|
740
|
-
return;
|
|
741
|
-
await selectProjectRuntime();
|
|
742
|
-
}
|
|
694
|
+
import { readdir as readdir2, readFile as readFile3, stat } from "fs/promises";
|
|
695
|
+
import { basename, join as join2, relative as relative2 } from "path";
|
|
743
696
|
|
|
744
697
|
// src/core/artifacts.ts
|
|
745
698
|
var RSP_AGENTS_BEGIN = "<!-- rsp:begin -->";
|
|
@@ -802,8 +755,8 @@ ${changeSectionHeading("verify")}
|
|
|
802
755
|
### Optional
|
|
803
756
|
- Manual or environment:
|
|
804
757
|
- [ ] ${placeholder}
|
|
805
|
-
|
|
806
|
-
|
|
758
|
+
### Conclusions
|
|
759
|
+
- ${placeholder}
|
|
807
760
|
|
|
808
761
|
${changeSectionHeading("blockers")}
|
|
809
762
|
- none
|
|
@@ -853,8 +806,8 @@ ${changeSectionHeading("verify")}
|
|
|
853
806
|
### Optional
|
|
854
807
|
- Manual or environment:
|
|
855
808
|
- [ ] ${template.manualVerify}
|
|
856
|
-
|
|
857
|
-
|
|
809
|
+
### Conclusions
|
|
810
|
+
- ${placeholder}
|
|
858
811
|
|
|
859
812
|
${changeSectionHeading("blockers")}
|
|
860
813
|
- none
|
|
@@ -895,9 +848,9 @@ function changeSectionHeading(sectionId) {
|
|
|
895
848
|
const guidance = {
|
|
896
849
|
proposal: "State the intended outcome, why it matters, scope, and non-goals; do not narrate execution.",
|
|
897
850
|
spec: "Describe the contract delta and acceptance conditions, referencing affected existing Specs; do not copy the full baseline or implementation steps.",
|
|
898
|
-
design: "Explain the approach,
|
|
899
|
-
tasks: "
|
|
900
|
-
verify: "
|
|
851
|
+
design: "Explain the current approach, boundaries, and necessary tradeoffs; replace obsolete plans while preserving decision reasons and useful outcome comparisons.",
|
|
852
|
+
tasks: "Keep current checkable work and actual completion; revise or reopen invalidated tasks within authorized scope. Do not append routine attempts, fixes, retries, or check runs.",
|
|
853
|
+
verify: "Use Required/Optional checklists and an optional short, non-nested Conclusions list only. Uncheck failed, unrun or invalidated evidence. Keep current limits, applicability conditions or required failure dispositions; replace stale conclusions. No prose paragraphs, tables, repeated results or repair history. Remove Conclusions when unnecessary.",
|
|
901
854
|
blockers: "Name unresolved decisions or dependencies that prevent progress; use none when there are no blockers."
|
|
902
855
|
};
|
|
903
856
|
return `${renderDocumentSectionHeading(CHANGE_DOCUMENT_SCHEMA, sectionId)}
|
|
@@ -911,14 +864,13 @@ function renderRspAgentsBlock(runtime) {
|
|
|
911
864
|
|
|
912
865
|
RSP tracks current work, stable specs, and archives under \`.rsp/\`.
|
|
913
866
|
|
|
914
|
-
|
|
867
|
+
Use supplied or confirmed paths; discover only missing paths or applicable ancestor instructions, without overlapping whole-tree scans:
|
|
915
868
|
1. Nearest \`AGENTS.md\` for project or module instructions.
|
|
916
869
|
2. Root \`CONTEXT.md\` if present, then the relevant nearest \`CONTEXT.md\` for domain language, relationships, and navigation. If a legacy \`CONTEXT-MAP.md\` remains, retain its relevant context and use Core's context-migration branch; discovery alone does not authorize migration.
|
|
917
|
-
3.
|
|
918
|
-
4. \`.rsp/focus.d
|
|
919
|
-
5. Only the relevant Specs and Decision Records under the configured authoritative path.
|
|
870
|
+
3. Establish the request's scope, authority and existing owner. A clear bounded request selecting one capability with sufficient owner facts loads that project Skill directly from \`.agents/skills/\`, without a Core or Focus preflight. For tracked work read the selected Change; for grouped work read its sibling Group Brief first. Read only relevant Specs and Decision Records under the configured authoritative path.
|
|
871
|
+
4. Load \`rsp\` at \`.agents/skills/rsp/SKILL.md\` for unresolved routing or ownership, actual cross-capability coordination, or lifecycle operations. Read \`.rsp/focus.d/\` only when needed to resolve or recover the owner; marker paths are open-work candidates and optional bounded Markdown is recovery guidance, not authority. An explicit WorkRef or the user's mentioned Change selects first; otherwise use current status and dependency evidence.
|
|
920
872
|
|
|
921
|
-
|
|
873
|
+
Direct capability invocation does not make tracked work untracked. Preserve existing Changes, required tracking prerequisites, Group dependencies, independent review and permission boundaries; missing prerequisites stop dependent work. Skills are the only workflow: hosts may discover them or read them directly, but a missing or unusable required Skill stops dependent work and must be reported as an incomplete installation. Do not use retired Rules or install implicitly.
|
|
922
874
|
Do not treat \`.rsp/specs/\` or \`.rsp/changes/\` as replacements for nearest \`AGENTS.md\` or \`CONTEXT.md\`.
|
|
923
875
|
|
|
924
876
|
${selection}
|
|
@@ -1031,8 +983,8 @@ async function checkForUpdates(current) {
|
|
|
1031
983
|
|
|
1032
984
|
// src/commands/skills.ts
|
|
1033
985
|
import { lstatSync, realpathSync } from "fs";
|
|
1034
|
-
import { chmod, copyFile, mkdir, mkdtemp, readdir, readFile as
|
|
1035
|
-
import { dirname, join
|
|
986
|
+
import { chmod, copyFile, mkdir, mkdtemp, readdir, readFile as readFile2, rename, rm } from "fs/promises";
|
|
987
|
+
import { dirname, join, relative } from "path";
|
|
1036
988
|
var DEFAULT_PACKAGED_SKILL_NAMES = [
|
|
1037
989
|
"rsp",
|
|
1038
990
|
"rsp-shape",
|
|
@@ -1057,7 +1009,7 @@ function unsupportedEntry(path, label) {
|
|
|
1057
1009
|
return new ManagedPathError(path, `unsupported entry in the ${label} tree: ${path}`);
|
|
1058
1010
|
}
|
|
1059
1011
|
async function inspectPackagedSkills(packageRoot) {
|
|
1060
|
-
const skillsRoot =
|
|
1012
|
+
const skillsRoot = join(packageRoot, "skills");
|
|
1061
1013
|
const rootInspection = inspectManagedDirectory(skillsRoot, "packaged Skills root");
|
|
1062
1014
|
if (rootInspection.issue)
|
|
1063
1015
|
throw rootInspection.issue;
|
|
@@ -1066,7 +1018,7 @@ async function inspectPackagedSkills(packageRoot) {
|
|
|
1066
1018
|
for (const entry of entries.sort((a, b) => a.name.localeCompare(b.name))) {
|
|
1067
1019
|
if (entry.name.startsWith("."))
|
|
1068
1020
|
continue;
|
|
1069
|
-
const root =
|
|
1021
|
+
const root = join(skillsRoot, entry.name);
|
|
1070
1022
|
if (!entry.isDirectory())
|
|
1071
1023
|
throw unsupportedEntry(root, "packaged Skills");
|
|
1072
1024
|
const inspection = await inspectManagedFileTree(root, `packaged Skill ${entry.name}`, { includeHidden: true });
|
|
@@ -1118,14 +1070,14 @@ async function treesEqual(source, targetRoot) {
|
|
|
1118
1070
|
if (source.files.length !== targetFiles.length || source.files.some((path, index) => path !== targetFiles[index]))
|
|
1119
1071
|
return false;
|
|
1120
1072
|
for (const path of source.files) {
|
|
1121
|
-
const sourcePath =
|
|
1122
|
-
const targetPath =
|
|
1073
|
+
const sourcePath = join(source.root, path);
|
|
1074
|
+
const targetPath = join(targetRoot, path);
|
|
1123
1075
|
const [sourceStats, targetStats] = [lstatSync(sourcePath), lstatSync(targetPath)];
|
|
1124
1076
|
if (!sourceStats.isFile() || !targetStats.isFile())
|
|
1125
1077
|
throw unsupportedEntry(!sourceStats.isFile() ? sourcePath : targetPath, `Skill ${source.name}`);
|
|
1126
1078
|
if ((sourceStats.mode & 511) !== (targetStats.mode & 511))
|
|
1127
1079
|
return false;
|
|
1128
|
-
const [sourceContent, targetContent] = await Promise.all([
|
|
1080
|
+
const [sourceContent, targetContent] = await Promise.all([readFile2(sourcePath), readFile2(targetPath)]);
|
|
1129
1081
|
if (!sourceContent.equals(targetContent))
|
|
1130
1082
|
return false;
|
|
1131
1083
|
}
|
|
@@ -1139,14 +1091,14 @@ async function inspectPackagedSkillInventory(options = {}) {
|
|
|
1139
1091
|
const missingDefaults = DEFAULT_PACKAGED_SKILL_NAMES.filter((name) => !packagedNames.has(name));
|
|
1140
1092
|
if (missingDefaults.length > 0)
|
|
1141
1093
|
throw new Error(`packaged Skills missing default Skills: ${missingDefaults.join(", ")}`);
|
|
1142
|
-
const manifest = JSON.parse(await
|
|
1094
|
+
const manifest = JSON.parse(await readFile2(join(packageRoot, "package.json"), "utf8"));
|
|
1143
1095
|
if (typeof manifest.name !== "string" || typeof manifest.version !== "string")
|
|
1144
1096
|
throw new Error("package.json must contain string name and version fields");
|
|
1145
1097
|
const targetRoot = resolveManagedDirectoryChain(projectRoot, [".agents", "skills"], "project Skills root");
|
|
1146
1098
|
const defaults = new Set(DEFAULT_PACKAGED_SKILL_NAMES);
|
|
1147
1099
|
const skills = [];
|
|
1148
1100
|
for (const skill of packagedSkills) {
|
|
1149
|
-
const target =
|
|
1101
|
+
const target = join(targetRoot, skill.name);
|
|
1150
1102
|
const targetStatus = inspectInventoryTarget(target);
|
|
1151
1103
|
skills.push({
|
|
1152
1104
|
name: skill.name,
|
|
@@ -1154,7 +1106,7 @@ async function inspectPackagedSkillInventory(options = {}) {
|
|
|
1154
1106
|
status: targetStatus === "missing" ? "missing" : targetStatus === "divergent" ? isCanonicalSourceProjection(skill.root, target) ? "unchanged" : "divergent" : await treesEqual(skill, target) ? "unchanged" : "divergent"
|
|
1155
1107
|
});
|
|
1156
1108
|
}
|
|
1157
|
-
const retired = RETIRED_PACKAGED_SKILL_NAMES.filter((name) => inspectInventoryTarget(
|
|
1109
|
+
const retired = RETIRED_PACKAGED_SKILL_NAMES.filter((name) => inspectInventoryTarget(join(targetRoot, name)) !== "missing");
|
|
1158
1110
|
return {
|
|
1159
1111
|
retired,
|
|
1160
1112
|
package: { name: manifest.name, version: manifest.version },
|
|
@@ -1165,8 +1117,8 @@ async function inspectPackagedSkillInventory(options = {}) {
|
|
|
1165
1117
|
async function copySkillTree(source, targetRoot) {
|
|
1166
1118
|
await mkdir(targetRoot, { recursive: true });
|
|
1167
1119
|
for (const path of source.files) {
|
|
1168
|
-
const sourcePath =
|
|
1169
|
-
const targetPath =
|
|
1120
|
+
const sourcePath = join(source.root, path);
|
|
1121
|
+
const targetPath = join(targetRoot, path);
|
|
1170
1122
|
const stats = lstatSync(sourcePath);
|
|
1171
1123
|
if (!stats.isFile())
|
|
1172
1124
|
throw unsupportedEntry(sourcePath, `packaged Skill ${source.name}`);
|
|
@@ -1189,7 +1141,7 @@ async function updatePackagedSkills(options = {}) {
|
|
|
1189
1141
|
const targetRoot = resolveManagedDirectoryChain(projectRoot, [".agents", "skills"], "project Skills root");
|
|
1190
1142
|
const result = { installed: [], removed: [], unchanged: [], replaced: [] };
|
|
1191
1143
|
for (const skill of skills) {
|
|
1192
|
-
const target =
|
|
1144
|
+
const target = join(targetRoot, skill.name);
|
|
1193
1145
|
if (isCanonicalSourceProjection(skill.root, target))
|
|
1194
1146
|
result.unchanged.push(skill.name);
|
|
1195
1147
|
else if (inspectTarget(target, skill.name) === "missing")
|
|
@@ -1200,35 +1152,35 @@ async function updatePackagedSkills(options = {}) {
|
|
|
1200
1152
|
result.replaced.push(skill.name);
|
|
1201
1153
|
}
|
|
1202
1154
|
for (const name of RETIRED_PACKAGED_SKILL_NAMES) {
|
|
1203
|
-
if (inspectTarget(
|
|
1155
|
+
if (inspectTarget(join(targetRoot, name), name) !== "missing")
|
|
1204
1156
|
result.removed.push(name);
|
|
1205
1157
|
}
|
|
1206
1158
|
if (options.dryRun || result.installed.length + result.replaced.length + result.removed.length === 0)
|
|
1207
1159
|
return result;
|
|
1208
1160
|
await mkdir(targetRoot, { recursive: true });
|
|
1209
1161
|
resolveManagedDirectoryChain(projectRoot, [".agents", "skills"], "project Skills root");
|
|
1210
|
-
const staging = await mkdtemp(
|
|
1162
|
+
const staging = await mkdtemp(join(targetRoot, ".rsp-skills-"));
|
|
1211
1163
|
const completed = [];
|
|
1212
1164
|
let failure2;
|
|
1213
1165
|
try {
|
|
1214
1166
|
for (const skill of skills) {
|
|
1215
1167
|
if (!result.unchanged.includes(skill.name))
|
|
1216
|
-
await copySkillTree(skill,
|
|
1168
|
+
await copySkillTree(skill, join(staging, skill.name));
|
|
1217
1169
|
}
|
|
1218
1170
|
for (const name of result.removed) {
|
|
1219
1171
|
resolveManagedDirectoryChain(projectRoot, [".agents", "skills"], "project Skills root");
|
|
1220
|
-
inspectTarget(
|
|
1221
|
-
await rm(
|
|
1172
|
+
inspectTarget(join(targetRoot, name), name);
|
|
1173
|
+
await rm(join(targetRoot, name), { recursive: true, force: true });
|
|
1222
1174
|
completed.push(`removed ${name}`);
|
|
1223
1175
|
}
|
|
1224
1176
|
for (const skill of skills) {
|
|
1225
1177
|
if (result.unchanged.includes(skill.name))
|
|
1226
1178
|
continue;
|
|
1227
1179
|
resolveManagedDirectoryChain(projectRoot, [".agents", "skills"], "project Skills root");
|
|
1228
|
-
const target =
|
|
1180
|
+
const target = join(targetRoot, skill.name);
|
|
1229
1181
|
inspectTarget(target, skill.name);
|
|
1230
1182
|
await rm(target, { recursive: true, force: true });
|
|
1231
|
-
await renamePath(
|
|
1183
|
+
await renamePath(join(staging, skill.name), target);
|
|
1232
1184
|
completed.push(`installed ${skill.name}`);
|
|
1233
1185
|
}
|
|
1234
1186
|
} catch (error) {
|
|
@@ -1275,14 +1227,16 @@ async function runDoctor(options = {}) {
|
|
|
1275
1227
|
hint: "Use Core context migration. Retain relevant legacy context until an authorized merge updates CONTEXT.md and active references; update does not migrate or delete it."
|
|
1276
1228
|
});
|
|
1277
1229
|
}
|
|
1278
|
-
await checkSpecsTree(checks, reportRuntime);
|
|
1279
1230
|
await checkArchiveNaming(checks);
|
|
1280
|
-
const
|
|
1281
|
-
if (
|
|
1231
|
+
const configValid = await checkConfigSemantics(checks, reportRuntime);
|
|
1232
|
+
if (configValid) {
|
|
1233
|
+
await checkSpecsTree(checks, reportRuntime);
|
|
1282
1234
|
await checkDecisionRecordsDirectory(checks, reportRuntime);
|
|
1283
1235
|
await checkInactiveDefaultDecisionRecords(checks, reportRuntime);
|
|
1284
1236
|
}
|
|
1285
1237
|
await checkActiveChangeConsistency(checks);
|
|
1238
|
+
if (configValid)
|
|
1239
|
+
await checkArchitecture(checks);
|
|
1286
1240
|
const result = {
|
|
1287
1241
|
command: "doctor",
|
|
1288
1242
|
ok: checks.every((check) => check.status !== "issue"),
|
|
@@ -1294,6 +1248,42 @@ async function runDoctor(options = {}) {
|
|
|
1294
1248
|
};
|
|
1295
1249
|
return result;
|
|
1296
1250
|
}
|
|
1251
|
+
async function checkArchitecture(checks) {
|
|
1252
|
+
try {
|
|
1253
|
+
const architecture = await queryArchitecture();
|
|
1254
|
+
if (!architecture.configured) {
|
|
1255
|
+
checks.push({
|
|
1256
|
+
status: "info",
|
|
1257
|
+
code: "architecture_not_configured",
|
|
1258
|
+
label: ARCHITECTURE_FILE,
|
|
1259
|
+
message: "Optional architecture model is not configured."
|
|
1260
|
+
});
|
|
1261
|
+
} else if (architecture.diagnostics.length) {
|
|
1262
|
+
for (const diagnostic of architecture.diagnostics) {
|
|
1263
|
+
checks.push({
|
|
1264
|
+
status: "issue",
|
|
1265
|
+
code: `architecture_${diagnostic.code}`,
|
|
1266
|
+
label: `architecture binding: ${diagnostic.file ?? ARCHITECTURE_FILE}`,
|
|
1267
|
+
message: `${diagnostic.file ?? ARCHITECTURE_FILE}: ${diagnostic.message}`
|
|
1268
|
+
});
|
|
1269
|
+
}
|
|
1270
|
+
} else {
|
|
1271
|
+
checks.push({
|
|
1272
|
+
status: "ok",
|
|
1273
|
+
code: "architecture_valid",
|
|
1274
|
+
label: "architecture structure and document bindings",
|
|
1275
|
+
message: `${architecture.nodes.length} nodes, ${architecture.relations.length} relations, ${architecture.views.length} views. Structural and reference validity does not establish semantic agreement with implementation.`
|
|
1276
|
+
});
|
|
1277
|
+
}
|
|
1278
|
+
} catch (error) {
|
|
1279
|
+
checks.push({
|
|
1280
|
+
status: "issue",
|
|
1281
|
+
code: "architecture_inspection_failed",
|
|
1282
|
+
label: ARCHITECTURE_FILE,
|
|
1283
|
+
message: `${ARCHITECTURE_FILE}: ${toErrorMessage(error)}`
|
|
1284
|
+
});
|
|
1285
|
+
}
|
|
1286
|
+
}
|
|
1297
1287
|
async function reportProjectRuntime(checks) {
|
|
1298
1288
|
let sourceMode = false;
|
|
1299
1289
|
try {
|
|
@@ -1389,7 +1379,7 @@ async function checkAgents(checks, reportRuntime) {
|
|
|
1389
1379
|
}
|
|
1390
1380
|
let agents;
|
|
1391
1381
|
try {
|
|
1392
|
-
agents = await
|
|
1382
|
+
agents = await readFile3("AGENTS.md", "utf-8");
|
|
1393
1383
|
} catch (error) {
|
|
1394
1384
|
reportRuntime({
|
|
1395
1385
|
code: "agents_read_failed",
|
|
@@ -1448,7 +1438,7 @@ async function checkSpecsTree(checks, reportRuntime) {
|
|
|
1448
1438
|
}
|
|
1449
1439
|
}
|
|
1450
1440
|
async function checkArchiveNaming(checks) {
|
|
1451
|
-
const archivesDir =
|
|
1441
|
+
const archivesDir = join2(RSP_DIR, "archives");
|
|
1452
1442
|
const inspection = await inspectArchiveTree({ archivesDir });
|
|
1453
1443
|
if (inspection.diagnostics.length > 0) {
|
|
1454
1444
|
checks.push({
|
|
@@ -1812,7 +1802,7 @@ function emptyCollectionSummary() {
|
|
|
1812
1802
|
}
|
|
1813
1803
|
|
|
1814
1804
|
// src/commands/ready.ts
|
|
1815
|
-
import { readFile as
|
|
1805
|
+
import { readFile as readFile4 } from "fs/promises";
|
|
1816
1806
|
function readyError(name, error, kind) {
|
|
1817
1807
|
return { command: "ready", ok: false, change: name || null, path: null, warnings: [], runtime: [], error, kind };
|
|
1818
1808
|
}
|
|
@@ -1832,7 +1822,7 @@ async function showReady(name) {
|
|
|
1832
1822
|
const runtime = [];
|
|
1833
1823
|
let content;
|
|
1834
1824
|
try {
|
|
1835
|
-
content = await
|
|
1825
|
+
content = await readFile4(srcPath, "utf-8");
|
|
1836
1826
|
} catch {
|
|
1837
1827
|
return readyError(name, { code: "change_read_failed", message: `unable to read .rsp/changes/${name}.md` }, "read");
|
|
1838
1828
|
}
|
|
@@ -1876,7 +1866,7 @@ async function showReady(name) {
|
|
|
1876
1866
|
}
|
|
1877
1867
|
|
|
1878
1868
|
// src/commands/show.ts
|
|
1879
|
-
import { readFile as
|
|
1869
|
+
import { readFile as readFile5 } from "fs/promises";
|
|
1880
1870
|
function showError(error, runtime = []) {
|
|
1881
1871
|
const nextActions = error.code === "no_focused_change" ? ["Run: rsp status", "Run: rsp focus <name>", "Or run: rsp create <name>"] : [];
|
|
1882
1872
|
return { command: "show", ok: false, change: null, contextPaths: [], runtime, nextActions, error };
|
|
@@ -1920,7 +1910,7 @@ async function showChange(nameOrFocused, options = {}) {
|
|
|
1920
1910
|
const srcPath = workRef.path;
|
|
1921
1911
|
let content;
|
|
1922
1912
|
try {
|
|
1923
|
-
content = await
|
|
1913
|
+
content = await readFile5(srcPath, "utf-8");
|
|
1924
1914
|
} catch {
|
|
1925
1915
|
return showError({ code: "change_read_failed", message: `unable to read .rsp/changes/${name}.md` }, runtime);
|
|
1926
1916
|
}
|
|
@@ -1949,7 +1939,7 @@ async function showChange(nameOrFocused, options = {}) {
|
|
|
1949
1939
|
const markerPath = focusMarkers.get(name);
|
|
1950
1940
|
let markerContent;
|
|
1951
1941
|
try {
|
|
1952
|
-
markerContent = await
|
|
1942
|
+
markerContent = await readFile5(markerPath);
|
|
1953
1943
|
} catch (error) {
|
|
1954
1944
|
reportRuntime({
|
|
1955
1945
|
code: "focus_marker_read_failed",
|
|
@@ -2850,7 +2840,7 @@ function formatArchiveReady(value) {
|
|
|
2850
2840
|
}
|
|
2851
2841
|
|
|
2852
2842
|
// src/cli/commands/inspection.ts
|
|
2853
|
-
var configCommand =
|
|
2843
|
+
var configCommand = defineCommand2({
|
|
2854
2844
|
meta: {
|
|
2855
2845
|
name: "config",
|
|
2856
2846
|
description: "Inspect effective project configuration without scanning work state"
|
|
@@ -2866,7 +2856,7 @@ var configCommand = defineCommand({
|
|
|
2866
2856
|
}, args);
|
|
2867
2857
|
}
|
|
2868
2858
|
});
|
|
2869
|
-
var specsCommand =
|
|
2859
|
+
var specsCommand = defineCommand2({
|
|
2870
2860
|
meta: {
|
|
2871
2861
|
name: "specs",
|
|
2872
2862
|
description: "Inspect current Specs and Decision Records or run bounded literal search"
|
|
@@ -2905,7 +2895,7 @@ var specsCommand = defineCommand({
|
|
|
2905
2895
|
}, args);
|
|
2906
2896
|
}
|
|
2907
2897
|
});
|
|
2908
|
-
var statusCommand =
|
|
2898
|
+
var statusCommand = defineCommand2({
|
|
2909
2899
|
meta: {
|
|
2910
2900
|
name: "status",
|
|
2911
2901
|
description: "Show project status summary with current focus information"
|
|
@@ -2953,7 +2943,7 @@ var statusCommand = defineCommand({
|
|
|
2953
2943
|
}, args);
|
|
2954
2944
|
}
|
|
2955
2945
|
});
|
|
2956
|
-
var checkCommand =
|
|
2946
|
+
var checkCommand = defineCommand2({
|
|
2957
2947
|
meta: {
|
|
2958
2948
|
name: "check",
|
|
2959
2949
|
description: "Validate changes (frontmatter, sections, template text, deltas, scenarios)"
|
|
@@ -2979,7 +2969,7 @@ var checkCommand = defineCommand({
|
|
|
2979
2969
|
}, args);
|
|
2980
2970
|
}
|
|
2981
2971
|
});
|
|
2982
|
-
var doctorCommand =
|
|
2972
|
+
var doctorCommand = defineCommand2({
|
|
2983
2973
|
meta: {
|
|
2984
2974
|
name: "doctor",
|
|
2985
2975
|
description: "Check RSP setup health and common integration issues"
|
|
@@ -3007,7 +2997,7 @@ var doctorCommand = defineCommand({
|
|
|
3007
2997
|
}, args);
|
|
3008
2998
|
}
|
|
3009
2999
|
});
|
|
3010
|
-
var readyCommand =
|
|
3000
|
+
var readyCommand = defineCommand2({
|
|
3011
3001
|
meta: {
|
|
3012
3002
|
name: "ready",
|
|
3013
3003
|
description: "Preview archive readiness for a change without moving it"
|
|
@@ -3033,7 +3023,7 @@ var readyCommand = defineCommand({
|
|
|
3033
3023
|
}, args);
|
|
3034
3024
|
}
|
|
3035
3025
|
});
|
|
3036
|
-
var showCommand =
|
|
3026
|
+
var showCommand = defineCommand2({
|
|
3037
3027
|
meta: {
|
|
3038
3028
|
name: "show",
|
|
3039
3029
|
description: "Show change context with readiness signals and relevant paths"
|
|
@@ -3064,7 +3054,7 @@ var showCommand = defineCommand({
|
|
|
3064
3054
|
}, args);
|
|
3065
3055
|
}
|
|
3066
3056
|
});
|
|
3067
|
-
var historyCommand =
|
|
3057
|
+
var historyCommand = defineCommand2({
|
|
3068
3058
|
meta: {
|
|
3069
3059
|
name: "history",
|
|
3070
3060
|
description: "Query bounded archived Change summaries or one exact archived WorkRef"
|
|
@@ -3130,14 +3120,14 @@ var inspectionCommands = {
|
|
|
3130
3120
|
};
|
|
3131
3121
|
|
|
3132
3122
|
// src/cli/commands/setup.ts
|
|
3133
|
-
import { defineCommand as
|
|
3123
|
+
import { defineCommand as defineCommand3 } from "citty";
|
|
3134
3124
|
|
|
3135
3125
|
// src/commands/add-spec.ts
|
|
3136
3126
|
import { mkdir as mkdir3, writeFile as writeFile2 } from "fs/promises";
|
|
3137
|
-
import { join as
|
|
3127
|
+
import { join as join3 } from "path";
|
|
3138
3128
|
|
|
3139
3129
|
// src/core/lock.ts
|
|
3140
|
-
import { mkdir as mkdir2, readFile as
|
|
3130
|
+
import { mkdir as mkdir2, readFile as readFile6, unlink, writeFile } from "fs/promises";
|
|
3141
3131
|
async function withRspLock(operation, fn) {
|
|
3142
3132
|
requireManagedDirectory(RSP_DIR, "RSP root", { allowMissing: true });
|
|
3143
3133
|
await mkdir2(RSP_DIR, { recursive: true });
|
|
@@ -3162,7 +3152,7 @@ ${(/* @__PURE__ */ new Date()).toISOString()}`, { flag: "wx" });
|
|
|
3162
3152
|
}
|
|
3163
3153
|
async function handleStaleLock(operation) {
|
|
3164
3154
|
try {
|
|
3165
|
-
const content = await
|
|
3155
|
+
const content = await readFile6(LOCK_PATH, "utf-8");
|
|
3166
3156
|
const lines = content.trim().split("\n");
|
|
3167
3157
|
const pid = Number(lines[0]);
|
|
3168
3158
|
if (pid && Number.isFinite(pid)) {
|
|
@@ -3220,10 +3210,10 @@ async function addSpec(name, projectName = "project") {
|
|
|
3220
3210
|
return { ok: false, message: `.rsp/config.yaml could not be parsed: ${toErrorMessage(error)}` };
|
|
3221
3211
|
}
|
|
3222
3212
|
return withRspLock("add-spec", async () => {
|
|
3223
|
-
const specsDir =
|
|
3213
|
+
const specsDir = join3(RSP_DIR, "specs");
|
|
3224
3214
|
const segments = name.split("/");
|
|
3225
3215
|
const parent = resolveManagedDirectoryChain(specsDir, segments.slice(0, -1), "spec path");
|
|
3226
|
-
const path =
|
|
3216
|
+
const path = join3(parent, `${segments.at(-1)}.md`);
|
|
3227
3217
|
const inspection = await inspectManagedFileTree(specsDir, "Specs");
|
|
3228
3218
|
if (inspection.issues.length > 0)
|
|
3229
3219
|
throw inspection.issues[0];
|
|
@@ -3243,30 +3233,30 @@ async function addSpec(name, projectName = "project") {
|
|
|
3243
3233
|
|
|
3244
3234
|
// src/commands/init.ts
|
|
3245
3235
|
import { existsSync as existsSync2 } from "fs";
|
|
3246
|
-
import { mkdir as mkdir4, readdir as readdir3, readFile as
|
|
3247
|
-
import { join as
|
|
3236
|
+
import { mkdir as mkdir4, readdir as readdir3, readFile as readFile8 } from "fs/promises";
|
|
3237
|
+
import { join as join5 } from "path";
|
|
3248
3238
|
|
|
3249
3239
|
// src/core/setup-files.ts
|
|
3250
3240
|
import { constants } from "fs";
|
|
3251
|
-
import { access, chmod as chmod2, link, mkdtemp as mkdtemp2, readFile as
|
|
3252
|
-
import { dirname as dirname2, join as
|
|
3241
|
+
import { access, chmod as chmod2, link, mkdtemp as mkdtemp2, readFile as readFile7, rename as rename2, rm as rm2, stat as stat2, writeFile as writeFile3 } from "fs/promises";
|
|
3242
|
+
import { dirname as dirname2, join as join4 } from "path";
|
|
3253
3243
|
async function updateSetupFile(path, render) {
|
|
3254
3244
|
const exists = requireManagedFile(path, "setup file", { allowMissing: true });
|
|
3255
|
-
const current = exists ? await
|
|
3245
|
+
const current = exists ? await readFile7(path, "utf8") : null;
|
|
3256
3246
|
const next = render(current);
|
|
3257
3247
|
if (next === current)
|
|
3258
3248
|
return false;
|
|
3259
3249
|
if (exists)
|
|
3260
3250
|
await access(path, constants.W_OK);
|
|
3261
|
-
const temporary = await mkdtemp2(
|
|
3262
|
-
const prepared =
|
|
3251
|
+
const temporary = await mkdtemp2(join4(dirname2(path), ".rsp-write-"));
|
|
3252
|
+
const prepared = join4(temporary, "next");
|
|
3263
3253
|
let failure2;
|
|
3264
3254
|
try {
|
|
3265
3255
|
await writeFile3(prepared, next, { flag: "wx" });
|
|
3266
3256
|
if (exists)
|
|
3267
3257
|
await chmod2(prepared, (await stat2(path)).mode & 511);
|
|
3268
3258
|
const stillExists = requireManagedFile(path, "setup file", { allowMissing: true });
|
|
3269
|
-
if (stillExists !== exists || stillExists && await
|
|
3259
|
+
if (stillExists !== exists || stillExists && await readFile7(path, "utf8") !== current)
|
|
3270
3260
|
throw new Error(`Setup file changed during update: ${path}`);
|
|
3271
3261
|
if (exists)
|
|
3272
3262
|
await rename2(prepared, path);
|
|
@@ -3307,7 +3297,7 @@ async function initProject(args = {}) {
|
|
|
3307
3297
|
const pathIssue = await validateDecisionRecordsFilesystemPath(decisionRecordsPath);
|
|
3308
3298
|
if (pathIssue)
|
|
3309
3299
|
throw new Error(pathIssue);
|
|
3310
|
-
const dirs = [
|
|
3300
|
+
const dirs = [join5(RSP_DIR, "specs"), CHANGES_DIR, FOCUS_DIR, join5(RSP_DIR, "archives"), decisionRecordsPath];
|
|
3311
3301
|
for (const path of dirs)
|
|
3312
3302
|
resolveManagedDirectoryChain(process.cwd(), path.split("/"), "project directory");
|
|
3313
3303
|
const completed = [];
|
|
@@ -3327,12 +3317,12 @@ async function initProject(args = {}) {
|
|
|
3327
3317
|
}
|
|
3328
3318
|
await ensureFile(CONFIG_PATH, generateConfigTemplate());
|
|
3329
3319
|
clearConfigCache();
|
|
3330
|
-
await ensureFile(
|
|
3320
|
+
await ensureFile(join5(RSP_DIR, "specs/design.md"), generateDesignContent(projectName));
|
|
3331
3321
|
if ((await readdir3(decisionRecordsPath)).length === 0)
|
|
3332
|
-
await ensureFile(
|
|
3333
|
-
await ensureFile(
|
|
3334
|
-
await ensureFile(
|
|
3335
|
-
await ensureFile(
|
|
3322
|
+
await ensureFile(join5(decisionRecordsPath, ".gitkeep"), "");
|
|
3323
|
+
await ensureFile(join5(CHANGES_DIR, ".gitkeep"), "");
|
|
3324
|
+
await ensureFile(join5(FOCUS_DIR, ".gitkeep"), "");
|
|
3325
|
+
await ensureFile(join5(RSP_DIR, ".gitignore"), "# Transient files that should not be committed\n.lock\n");
|
|
3336
3326
|
if (args.withProjectSetup) {
|
|
3337
3327
|
const work = resolveWorkRef("project-setup", { executable: true });
|
|
3338
3328
|
await ensureFile(work.path, generateChangeContent("project-setup"));
|
|
@@ -3347,7 +3337,7 @@ async function initProject(args = {}) {
|
|
|
3347
3337
|
if (runtime.mode === "package" && await updateSetupFile(PROJECT_VERSION_PATH, () => `${version}
|
|
3348
3338
|
`))
|
|
3349
3339
|
completed.push(`pinned ${version}`);
|
|
3350
|
-
return { ok: true, isNew, created: completed.length > 0, decisionRecordsPath, withProjectSetup: Boolean(args.withProjectSetup), agentsUpdated, skills, managedAgents: mode === "print" ? await
|
|
3340
|
+
return { ok: true, isNew, created: completed.length > 0, decisionRecordsPath, withProjectSetup: Boolean(args.withProjectSetup), agentsUpdated, skills, managedAgents: mode === "print" ? await readFile8("AGENTS.md", "utf8") : void 0 };
|
|
3351
3341
|
} catch (error) {
|
|
3352
3342
|
throw new Error(`Init stopped; completed: ${completed.join(", ") || "none"}. No rollback was attempted. Fix the cause and rerun init with the same target CLI. ${error instanceof Error ? error.message : String(error)}`, { cause: error });
|
|
3353
3343
|
}
|
|
@@ -3356,17 +3346,17 @@ async function initProject(args = {}) {
|
|
|
3356
3346
|
|
|
3357
3347
|
// src/commands/update.ts
|
|
3358
3348
|
import { existsSync as existsSync3 } from "fs";
|
|
3359
|
-
import { readFile as
|
|
3360
|
-
import { join as
|
|
3349
|
+
import { readFile as readFile11, unlink as unlink3 } from "fs/promises";
|
|
3350
|
+
import { join as join7 } from "path";
|
|
3361
3351
|
|
|
3362
3352
|
// src/commands/archive-index-migration.ts
|
|
3363
|
-
import { readFile as
|
|
3364
|
-
import { join as
|
|
3353
|
+
import { readFile as readFile9 } from "fs/promises";
|
|
3354
|
+
import { join as join6 } from "path";
|
|
3365
3355
|
async function isLegacyArchiveIndex() {
|
|
3366
|
-
const path =
|
|
3356
|
+
const path = join6(ARCHIVES_DIR, "INDEX.md");
|
|
3367
3357
|
if (!requireManagedFile(path, "legacy archive index", { allowMissing: true }))
|
|
3368
3358
|
return false;
|
|
3369
|
-
return isLegacyArchiveIndexContent(await
|
|
3359
|
+
return isLegacyArchiveIndexContent(await readFile9(path, "utf-8"));
|
|
3370
3360
|
}
|
|
3371
3361
|
function isLegacyArchiveIndexContent(content) {
|
|
3372
3362
|
try {
|
|
@@ -3378,7 +3368,7 @@ function isLegacyArchiveIndexContent(content) {
|
|
|
3378
3368
|
}
|
|
3379
3369
|
|
|
3380
3370
|
// src/commands/specs-index-migration.ts
|
|
3381
|
-
import { readFile as
|
|
3371
|
+
import { readFile as readFile10, unlink as unlink2 } from "fs/promises";
|
|
3382
3372
|
import { dirname as dirname3, resolve } from "path";
|
|
3383
3373
|
async function inspectGeneratedSpecsIndexMigration(cwd = process.cwd()) {
|
|
3384
3374
|
const inspection = await inspectSpecs({ cwd, allowMissingDecisionRecords: true });
|
|
@@ -3393,7 +3383,7 @@ async function removeGeneratedSpecsIndex(path) {
|
|
|
3393
3383
|
resolveManagedDirectoryChain(process.cwd(), dirname3(path).split("/"), "Specs parent");
|
|
3394
3384
|
if (!requireManagedFile(path, "generated Specs index", { allowMissing: true }))
|
|
3395
3385
|
return false;
|
|
3396
|
-
if (!isRecognizedGeneratedSpecsIndex(await
|
|
3386
|
+
if (!isRecognizedGeneratedSpecsIndex(await readFile10(resolve(path), "utf8"), path))
|
|
3397
3387
|
throw new Error(`Specs index is no longer generated; left untouched: ${path}`);
|
|
3398
3388
|
await unlink2(path);
|
|
3399
3389
|
return true;
|
|
@@ -3418,12 +3408,12 @@ async function updateProject(options = {}) {
|
|
|
3418
3408
|
return { ok: false, actions: [], updated: false, events: [{ type: "migration-diagnostics", diagnostics: rules.diagnostics }], migration };
|
|
3419
3409
|
requireManagedFile("AGENTS.md", "AGENTS.md", { allowMissing: true });
|
|
3420
3410
|
resolveManagedDirectoryChain(process.cwd(), [RSP_DIR, "archives"], "archive parent");
|
|
3421
|
-
requireManagedFile(
|
|
3411
|
+
requireManagedFile(join7(RSP_DIR, "archives/INDEX.md"), "archive index", { allowMissing: true });
|
|
3422
3412
|
const plan = await inspectGeneratedSpecsIndexMigration();
|
|
3423
3413
|
if (!plan.inspectionComplete || plan.ownerControlled.length)
|
|
3424
3414
|
throw new Error(`Generated Specs-index migration requires owner review before update: ${[...plan.ownerControlled, ...plan.diagnostics].join("; ")}`);
|
|
3425
3415
|
const projectName = await detectProjectName();
|
|
3426
|
-
const agents = requireManagedFile("AGENTS.md", "AGENTS.md", { allowMissing: true }) ? await
|
|
3416
|
+
const agents = requireManagedFile("AGENTS.md", "AGENTS.md", { allowMissing: true }) ? await readFile11("AGENTS.md", "utf8") : null;
|
|
3427
3417
|
const refreshAgents = (current) => upsertRspAgentsBlock(current ?? `# ${projectName}
|
|
3428
3418
|
|
|
3429
3419
|
`, runtime).content;
|
|
@@ -3464,7 +3454,7 @@ async function updateProject(options = {}) {
|
|
|
3464
3454
|
record(`generated Specs index removed: ${path}`);
|
|
3465
3455
|
}
|
|
3466
3456
|
if (await isLegacyArchiveIndex()) {
|
|
3467
|
-
await unlink3(
|
|
3457
|
+
await unlink3(join7(RSP_DIR, "archives/INDEX.md"));
|
|
3468
3458
|
record("legacy Archive Index removed");
|
|
3469
3459
|
}
|
|
3470
3460
|
if (await updateSetupFile("AGENTS.md", refreshAgents))
|
|
@@ -3578,7 +3568,7 @@ function presentUpdate(result, dryRun = false) {
|
|
|
3578
3568
|
}
|
|
3579
3569
|
|
|
3580
3570
|
// src/cli/commands/setup.ts
|
|
3581
|
-
var initCommand =
|
|
3571
|
+
var initCommand = defineCommand3({
|
|
3582
3572
|
meta: {
|
|
3583
3573
|
name: "init",
|
|
3584
3574
|
description: "Scaffold .rsp/ and ensure AGENTS.md contains the RSP entry block"
|
|
@@ -3606,7 +3596,7 @@ var initCommand = defineCommand2({
|
|
|
3606
3596
|
}, args);
|
|
3607
3597
|
}
|
|
3608
3598
|
});
|
|
3609
|
-
var addSpecCommand =
|
|
3599
|
+
var addSpecCommand = defineCommand3({
|
|
3610
3600
|
meta: {
|
|
3611
3601
|
name: "spec",
|
|
3612
3602
|
description: "Create .rsp/specs/<name>.md for direct Specs queries"
|
|
@@ -3626,7 +3616,7 @@ var addSpecCommand = defineCommand2({
|
|
|
3626
3616
|
}, args);
|
|
3627
3617
|
}
|
|
3628
3618
|
});
|
|
3629
|
-
var addCommand =
|
|
3619
|
+
var addCommand = defineCommand3({
|
|
3630
3620
|
meta: {
|
|
3631
3621
|
name: "add",
|
|
3632
3622
|
description: "Add an optional durable spec file"
|
|
@@ -3635,7 +3625,7 @@ var addCommand = defineCommand2({
|
|
|
3635
3625
|
spec: addSpecCommand
|
|
3636
3626
|
}
|
|
3637
3627
|
});
|
|
3638
|
-
var updateCommand =
|
|
3628
|
+
var updateCommand = defineCommand3({
|
|
3639
3629
|
meta: {
|
|
3640
3630
|
name: "update",
|
|
3641
3631
|
description: "Update the complete pinned environment and remove retired managed assets"
|
|
@@ -3660,7 +3650,7 @@ var setupCommands = {
|
|
|
3660
3650
|
};
|
|
3661
3651
|
|
|
3662
3652
|
// src/cli/commands/skills.ts
|
|
3663
|
-
import { defineCommand as
|
|
3653
|
+
import { defineCommand as defineCommand4 } from "citty";
|
|
3664
3654
|
|
|
3665
3655
|
// src/cli/presenters/skills.ts
|
|
3666
3656
|
function presentPackagedSkillInventory(inventory, json = false) {
|
|
@@ -3678,7 +3668,7 @@ function presentPackagedSkillInventory(inventory, json = false) {
|
|
|
3678
3668
|
}
|
|
3679
3669
|
|
|
3680
3670
|
// src/cli/commands/skills.ts
|
|
3681
|
-
var skillsListCommand =
|
|
3671
|
+
var skillsListCommand = defineCommand4({
|
|
3682
3672
|
meta: { name: "list", description: "Inspect the complete package-owned Skill inventory" },
|
|
3683
3673
|
args: { ...jsonArgs },
|
|
3684
3674
|
async run({ args }) {
|
|
@@ -3689,19 +3679,19 @@ var skillsListCommand = defineCommand3({
|
|
|
3689
3679
|
}
|
|
3690
3680
|
});
|
|
3691
3681
|
var skillsCommands = {
|
|
3692
|
-
skills:
|
|
3682
|
+
skills: defineCommand4({
|
|
3693
3683
|
meta: { name: "skills", description: "Inspect Skills; use init or update to manage the complete environment" },
|
|
3694
3684
|
subCommands: { list: skillsListCommand }
|
|
3695
3685
|
})
|
|
3696
3686
|
};
|
|
3697
3687
|
|
|
3698
3688
|
// src/cli/commands/work.ts
|
|
3699
|
-
import { defineCommand as
|
|
3689
|
+
import { defineCommand as defineCommand5 } from "citty";
|
|
3700
3690
|
|
|
3701
3691
|
// src/commands/archive.ts
|
|
3702
3692
|
import { existsSync as existsSync4, readdirSync } from "fs";
|
|
3703
|
-
import { mkdir as mkdir5, readFile as
|
|
3704
|
-
import { basename as basename2, join as
|
|
3693
|
+
import { mkdir as mkdir5, readFile as readFile12, rename as rename3, unlink as unlink4 } from "fs/promises";
|
|
3694
|
+
import { basename as basename2, join as join8 } from "path";
|
|
3705
3695
|
async function archiveChange(name) {
|
|
3706
3696
|
if (!name) {
|
|
3707
3697
|
return { ok: false, kind: "usage", message: "rsp archive <name>" };
|
|
@@ -3718,7 +3708,7 @@ async function archiveChange(name) {
|
|
|
3718
3708
|
const date = (/* @__PURE__ */ new Date()).toISOString().slice(0, 10);
|
|
3719
3709
|
const base = basename2(workRef.name);
|
|
3720
3710
|
const archiveName = resolveArchiveName(archiveSubdir, date, base);
|
|
3721
|
-
const content = await
|
|
3711
|
+
const content = await readFile12(srcPath, "utf-8");
|
|
3722
3712
|
const configInspection = await inspectRspConfig();
|
|
3723
3713
|
if (configInspection.issues.length > 0) {
|
|
3724
3714
|
return {
|
|
@@ -3747,7 +3737,7 @@ async function archiveChange(name) {
|
|
|
3747
3737
|
};
|
|
3748
3738
|
}
|
|
3749
3739
|
await mkdir5(archiveSubdir, { recursive: true });
|
|
3750
|
-
await rename3(srcPath,
|
|
3740
|
+
await rename3(srcPath, join8(archiveSubdir, archiveName));
|
|
3751
3741
|
const postArchiveWarnings = [];
|
|
3752
3742
|
let focusCleared = false;
|
|
3753
3743
|
if (existsSync4(focusEntry)) {
|
|
@@ -3862,11 +3852,11 @@ async function createChange(name, summary = "", kind, options = {}) {
|
|
|
3862
3852
|
}
|
|
3863
3853
|
|
|
3864
3854
|
// src/commands/focus.ts
|
|
3865
|
-
import { Buffer
|
|
3855
|
+
import { Buffer } from "buffer";
|
|
3866
3856
|
import { randomUUID } from "crypto";
|
|
3867
3857
|
import { existsSync as existsSync6 } from "fs";
|
|
3868
3858
|
import { mkdir as mkdir7, open, rename as rename4, unlink as unlink6 } from "fs/promises";
|
|
3869
|
-
import { basename as basename3, dirname as dirname5, join as
|
|
3859
|
+
import { basename as basename3, dirname as dirname5, join as join9 } from "path";
|
|
3870
3860
|
async function focusChange(name, options = {}) {
|
|
3871
3861
|
if (!name) {
|
|
3872
3862
|
return { ok: false, kind: "usage", message: "rsp focus <name>" };
|
|
@@ -3901,7 +3891,7 @@ async function readCapsule(source) {
|
|
|
3901
3891
|
}
|
|
3902
3892
|
async function replaceFocusCapsule(path, content) {
|
|
3903
3893
|
requireManagedFile(path, "focus marker", { allowMissing: true });
|
|
3904
|
-
const temporaryPath =
|
|
3894
|
+
const temporaryPath = join9(dirname5(path), `.${basename3(path)}.${randomUUID()}.tmp`);
|
|
3905
3895
|
let handle;
|
|
3906
3896
|
try {
|
|
3907
3897
|
handle = await open(temporaryPath, "wx");
|
|
@@ -3934,13 +3924,13 @@ async function readBoundedStdin() {
|
|
|
3934
3924
|
const chunks = [];
|
|
3935
3925
|
let size = 0;
|
|
3936
3926
|
for await (const chunk of process.stdin) {
|
|
3937
|
-
const buffer =
|
|
3927
|
+
const buffer = Buffer.isBuffer(chunk) ? chunk : Buffer.from(chunk);
|
|
3938
3928
|
size += buffer.byteLength;
|
|
3939
3929
|
if (size > MAX_FOCUS_CAPSULE_BYTES)
|
|
3940
3930
|
throw new Error(`focus capsule exceeds ${MAX_FOCUS_CAPSULE_BYTES} UTF-8 bytes`);
|
|
3941
3931
|
chunks.push(buffer);
|
|
3942
3932
|
}
|
|
3943
|
-
return
|
|
3933
|
+
return Buffer.concat(chunks, size);
|
|
3944
3934
|
}
|
|
3945
3935
|
async function unfocusChange(name) {
|
|
3946
3936
|
if (!name) {
|
|
@@ -3975,8 +3965,8 @@ function workRefFailure(error) {
|
|
|
3975
3965
|
// src/commands/group.ts
|
|
3976
3966
|
import { randomUUID as randomUUID2 } from "crypto";
|
|
3977
3967
|
import { existsSync as existsSync7 } from "fs";
|
|
3978
|
-
import { link as link2, mkdir as mkdir8, readdir as readdir4, readFile as
|
|
3979
|
-
import { join as
|
|
3968
|
+
import { link as link2, mkdir as mkdir8, readdir as readdir4, readFile as readFile13, rename as rename5, unlink as unlink7, writeFile as writeFile5 } from "fs/promises";
|
|
3969
|
+
import { join as join10 } from "path";
|
|
3980
3970
|
var ChangeGroupError = class extends Error {
|
|
3981
3971
|
name = "ChangeGroupError";
|
|
3982
3972
|
};
|
|
@@ -4037,14 +4027,14 @@ async function closeChangeGroup(name) {
|
|
|
4037
4027
|
const date = (/* @__PURE__ */ new Date()).toISOString().slice(0, 10);
|
|
4038
4028
|
const archiveName = resolveArchiveName(archiveDirectory, date, "brief");
|
|
4039
4029
|
await mkdir8(archiveDirectory, { recursive: true });
|
|
4040
|
-
await rename5(ref.path,
|
|
4030
|
+
await rename5(ref.path, join10(archiveDirectory, archiveName));
|
|
4041
4031
|
const warnings = [];
|
|
4042
4032
|
try {
|
|
4043
4033
|
await cleanupEmptyParentDirs(ref.path, CHANGES_DIR);
|
|
4044
4034
|
} catch (error) {
|
|
4045
4035
|
warnings.push(`changes directory cleanup failed: ${toErrorMessage(error)}`);
|
|
4046
4036
|
}
|
|
4047
|
-
return { ok: true, action: "close", groupName, archivePath:
|
|
4037
|
+
return { ok: true, action: "close", groupName, archivePath: join10(archiveDirectory, archiveName), warnings };
|
|
4048
4038
|
});
|
|
4049
4039
|
} catch (error) {
|
|
4050
4040
|
if (error instanceof WorkRefError || error instanceof ChangeGroupError) {
|
|
@@ -4068,8 +4058,8 @@ async function reopenChangeGroup(name, options) {
|
|
|
4068
4058
|
return await withRspLock("reopen-change-group", async () => {
|
|
4069
4059
|
const warnings = [];
|
|
4070
4060
|
const groupName = normalizeWorkRefSegment(name);
|
|
4071
|
-
await requireEmptyGroupRecoverySubtree(
|
|
4072
|
-
await requireEmptyGroupRecoverySubtree(
|
|
4061
|
+
await requireEmptyGroupRecoverySubtree(join10(CHANGES_DIR, groupName), `Change Group work subtree for ${groupName}`);
|
|
4062
|
+
await requireEmptyGroupRecoverySubtree(join10(FOCUS_DIR, groupName), `Change Group focus subtree for ${groupName}`);
|
|
4073
4063
|
const ref = resolveWorkRef(`${groupName}/brief`);
|
|
4074
4064
|
if (ref.kind !== "group-brief")
|
|
4075
4065
|
throw new ChangeGroupError(`invalid Change Group name: ${name}`);
|
|
@@ -4092,13 +4082,13 @@ async function reopenChangeGroup(name, options) {
|
|
|
4092
4082
|
}
|
|
4093
4083
|
if (existsSync7(ref.path))
|
|
4094
4084
|
throw new ArchiveHistoryError("open_group_exists", `open Change Group already exists: ${groupName}`);
|
|
4095
|
-
const archivedContent = await
|
|
4085
|
+
const archivedContent = await readFile13(record.sourcePath, "utf-8");
|
|
4096
4086
|
const document = parseRspDocument(archivedContent, GROUP_BRIEF_DOCUMENT_SCHEMA);
|
|
4097
4087
|
validateArchivedGroupBrief(document, groupName);
|
|
4098
4088
|
const evidenceKey = `${GROUP_REOPEN_COMPLETION_PREFIX} \`${record.path}\`: ${reason}`;
|
|
4099
4089
|
const retainedEvidence = /* @__PURE__ */ new Set();
|
|
4100
4090
|
for (const retained of inspection.groupBriefs.filter((candidate) => candidate.group === groupName)) {
|
|
4101
|
-
const retainedDocument = retained.sourcePath === record.sourcePath ? document : parseRspDocument(await
|
|
4091
|
+
const retainedDocument = retained.sourcePath === record.sourcePath ? document : parseRspDocument(await readFile13(retained.sourcePath, "utf-8"), GROUP_BRIEF_DOCUMENT_SCHEMA);
|
|
4102
4092
|
for (const item of getGroupReopenEvidence(retainedDocument))
|
|
4103
4093
|
retainedEvidence.add(item.key);
|
|
4104
4094
|
}
|
|
@@ -4115,7 +4105,7 @@ async function reopenChangeGroup(name, options) {
|
|
|
4115
4105
|
);
|
|
4116
4106
|
const groupDirectory = resolveManagedDirectoryChain(CHANGES_DIR, [groupName], "Change Group path");
|
|
4117
4107
|
await mkdir8(groupDirectory, { recursive: true });
|
|
4118
|
-
const temporaryPath =
|
|
4108
|
+
const temporaryPath = join10(RSP_DIR, `.group-reopen-${process.pid}-${randomUUID2()}.tmp`);
|
|
4119
4109
|
let mutationError;
|
|
4120
4110
|
try {
|
|
4121
4111
|
await writeFile5(temporaryPath, reopenedContent, { flag: "wx" });
|
|
@@ -4200,7 +4190,7 @@ function collectCloseReasons(group, errors) {
|
|
|
4200
4190
|
|
|
4201
4191
|
// src/commands/reopen.ts
|
|
4202
4192
|
import { existsSync as existsSync8 } from "fs";
|
|
4203
|
-
import { mkdir as mkdir9, readFile as
|
|
4193
|
+
import { mkdir as mkdir9, readFile as readFile14, unlink as unlink8, writeFile as writeFile6 } from "fs/promises";
|
|
4204
4194
|
import { dirname as dirname6 } from "path";
|
|
4205
4195
|
async function reopenChange(name, options) {
|
|
4206
4196
|
if (!name) {
|
|
@@ -4250,7 +4240,7 @@ async function reopenChange(name, options) {
|
|
|
4250
4240
|
const focusEntry = resolveFocusMarkerPath(workRef);
|
|
4251
4241
|
if (existsSync8(focusEntry))
|
|
4252
4242
|
throw new ArchiveHistoryError("focus_marker_exists", `focus marker already exists for non-open Change: ${name}; run rsp doctor`);
|
|
4253
|
-
const archivedContent = await
|
|
4243
|
+
const archivedContent = await readFile14(record.sourcePath, "utf-8");
|
|
4254
4244
|
const reopenedContent = appendChecklistItem(
|
|
4255
4245
|
appendChecklistItem(archivedContent, "tasks", `- [ ] Resolve reopened concern: ${reason}`),
|
|
4256
4246
|
"verify",
|
|
@@ -4420,7 +4410,7 @@ function presentReopen(result) {
|
|
|
4420
4410
|
|
|
4421
4411
|
// src/cli/commands/work.ts
|
|
4422
4412
|
function createCreateCommand(deprecatedLite) {
|
|
4423
|
-
return
|
|
4413
|
+
return defineCommand5({
|
|
4424
4414
|
meta: {
|
|
4425
4415
|
name: "create",
|
|
4426
4416
|
description: "Create .rsp/changes/<name>.md [summary]"
|
|
@@ -4445,7 +4435,7 @@ function createCreateCommand(deprecatedLite) {
|
|
|
4445
4435
|
}
|
|
4446
4436
|
},
|
|
4447
4437
|
async run({ args }) {
|
|
4448
|
-
const summary =
|
|
4438
|
+
const summary = args._.slice(1).join(" ");
|
|
4449
4439
|
await executeCliCommand({
|
|
4450
4440
|
execute: () => createChange(args.name, summary, args.kind, {
|
|
4451
4441
|
issue: args.issue,
|
|
@@ -4458,7 +4448,7 @@ function createCreateCommand(deprecatedLite) {
|
|
|
4458
4448
|
}
|
|
4459
4449
|
});
|
|
4460
4450
|
}
|
|
4461
|
-
var groupCreateCommand =
|
|
4451
|
+
var groupCreateCommand = defineCommand5({
|
|
4462
4452
|
meta: {
|
|
4463
4453
|
name: "create",
|
|
4464
4454
|
description: "Create an unfocused .rsp/changes/<group>/00-brief.md"
|
|
@@ -4471,18 +4461,18 @@ var groupCreateCommand = defineCommand4({
|
|
|
4471
4461
|
}
|
|
4472
4462
|
},
|
|
4473
4463
|
async run({ args }) {
|
|
4474
|
-
const goal =
|
|
4464
|
+
const goal = args._.slice(1).join(" ");
|
|
4475
4465
|
await executeCliCommand({ execute: () => createChangeGroup(args.name, goal), present: presentGroup, exitCode: (result) => result.ok ? void 0 : 1 }, args);
|
|
4476
4466
|
}
|
|
4477
4467
|
});
|
|
4478
|
-
var groupCommand =
|
|
4468
|
+
var groupCommand = defineCommand5({
|
|
4479
4469
|
meta: {
|
|
4480
4470
|
name: "group",
|
|
4481
4471
|
description: "Create, close, and explicitly reopen shallow Change Groups"
|
|
4482
4472
|
},
|
|
4483
4473
|
subCommands: {
|
|
4484
4474
|
create: groupCreateCommand,
|
|
4485
|
-
close:
|
|
4475
|
+
close: defineCommand5({
|
|
4486
4476
|
meta: {
|
|
4487
4477
|
name: "close",
|
|
4488
4478
|
description: "Archive a completed Group Brief after all child Changes are archived"
|
|
@@ -4498,7 +4488,7 @@ var groupCommand = defineCommand4({
|
|
|
4498
4488
|
await executeCliCommand({ execute: () => closeChangeGroup(args.name), present: presentGroup, exitCode: (result) => result.ok ? void 0 : 1 }, args);
|
|
4499
4489
|
}
|
|
4500
4490
|
}),
|
|
4501
|
-
reopen:
|
|
4491
|
+
reopen: defineCommand5({
|
|
4502
4492
|
meta: {
|
|
4503
4493
|
name: "reopen",
|
|
4504
4494
|
description: "Restore one archived Group Brief while retaining history"
|
|
@@ -4525,7 +4515,7 @@ var groupCommand = defineCommand4({
|
|
|
4525
4515
|
})
|
|
4526
4516
|
}
|
|
4527
4517
|
});
|
|
4528
|
-
var archiveCommand =
|
|
4518
|
+
var archiveCommand = defineCommand5({
|
|
4529
4519
|
meta: {
|
|
4530
4520
|
name: "archive",
|
|
4531
4521
|
description: "Archive an open change into .rsp/archives/"
|
|
@@ -4549,7 +4539,7 @@ var archiveCommand = defineCommand4({
|
|
|
4549
4539
|
await executeCliCommand({ execute: () => archiveChange(args.name), present: presentArchive, exitCode: (result) => result.ok ? void 0 : 1 }, args);
|
|
4550
4540
|
}
|
|
4551
4541
|
});
|
|
4552
|
-
var reopenCommand =
|
|
4542
|
+
var reopenCommand = defineCommand5({
|
|
4553
4543
|
meta: {
|
|
4554
4544
|
name: "reopen",
|
|
4555
4545
|
description: "Restore one archived Change as focused open work while retaining history"
|
|
@@ -4574,7 +4564,7 @@ var reopenCommand = defineCommand4({
|
|
|
4574
4564
|
await executeCliCommand({ execute: () => reopenChange(args.name, { from: args.from, reason: args.reason }), present: presentReopen, exitCode: (result) => result.ok ? void 0 : 1 }, args);
|
|
4575
4565
|
}
|
|
4576
4566
|
});
|
|
4577
|
-
var focusCommand =
|
|
4567
|
+
var focusCommand = defineCommand5({
|
|
4578
4568
|
meta: {
|
|
4579
4569
|
name: "focus",
|
|
4580
4570
|
description: "Mark an existing change as currently focused in .rsp/focus.d/"
|
|
@@ -4594,7 +4584,7 @@ var focusCommand = defineCommand4({
|
|
|
4594
4584
|
await executeCliCommand({ execute: () => focusChange(args.name, { capsuleFile: args["capsule-file"] }), present: presentFocus, exitCode: (result) => result.ok ? void 0 : 1 }, args);
|
|
4595
4585
|
}
|
|
4596
4586
|
});
|
|
4597
|
-
var unfocusCommand =
|
|
4587
|
+
var unfocusCommand = defineCommand5({
|
|
4598
4588
|
meta: {
|
|
4599
4589
|
name: "unfocus",
|
|
4600
4590
|
description: "Remove a change from the current focus set in .rsp/focus.d/"
|
|
@@ -4624,13 +4614,15 @@ function createWorkCommands(deprecatedLite) {
|
|
|
4624
4614
|
// src/cli/registry.ts
|
|
4625
4615
|
function createRootCommand(options) {
|
|
4626
4616
|
const workCommands = createWorkCommands(options.deprecatedLite);
|
|
4627
|
-
return
|
|
4617
|
+
return defineCommand6({
|
|
4628
4618
|
meta: {
|
|
4629
4619
|
name: "rsp",
|
|
4630
4620
|
version: options.version,
|
|
4631
4621
|
description: "RSP (Reliable Software Practice), a repository-native engineering workflow for humans and AI agents"
|
|
4632
4622
|
},
|
|
4633
4623
|
subCommands: {
|
|
4624
|
+
architecture: architectureCommand,
|
|
4625
|
+
view: viewCommand,
|
|
4634
4626
|
init: setupCommands.init,
|
|
4635
4627
|
add: setupCommands.add,
|
|
4636
4628
|
specs: inspectionCommands.specs,
|
|
@@ -4715,7 +4707,7 @@ async function runCli(rawArgs = process.argv.slice(2)) {
|
|
|
4715
4707
|
} else {
|
|
4716
4708
|
const { resolveUiLocale } = await import("./locale-HT44UIUP.mjs");
|
|
4717
4709
|
const locale = resolveUiLocale(lang, process.env.RSP_UI_LANG, process.env.LC_ALL ?? process.env.LC_MESSAGES ?? process.env.LANG ?? new Intl.DateTimeFormat().resolvedOptions().locale);
|
|
4718
|
-
const { runTui } = await import("./entry-
|
|
4710
|
+
const { runTui } = await import("./entry-NDASTAI5.mjs");
|
|
4719
4711
|
const exitCode = await runTui(locale);
|
|
4720
4712
|
if (exitCode !== 0)
|
|
4721
4713
|
process.exitCode = exitCode;
|