@prd-improve/cli 1.0.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/README.md +38 -0
- package/dist/anchor-slicer.d.ts +18 -0
- package/dist/anchor-slicer.js +114 -0
- package/dist/anchor-slicer.js.map +1 -0
- package/dist/api/client.d.ts +68 -0
- package/dist/api/client.js +175 -0
- package/dist/api/client.js.map +1 -0
- package/dist/changelog.d.ts +9 -0
- package/dist/changelog.js +34 -0
- package/dist/changelog.js.map +1 -0
- package/dist/cli.d.ts +2 -0
- package/dist/cli.js +258 -0
- package/dist/cli.js.map +1 -0
- package/dist/commands/admin/_adminJson.d.ts +18 -0
- package/dist/commands/admin/_adminJson.js +27 -0
- package/dist/commands/admin/_adminJson.js.map +1 -0
- package/dist/commands/admin/_authResolve.d.ts +8 -0
- package/dist/commands/admin/_authResolve.js +56 -0
- package/dist/commands/admin/_authResolve.js.map +1 -0
- package/dist/commands/admin/index.d.ts +22 -0
- package/dist/commands/admin/index.js +100 -0
- package/dist/commands/admin/index.js.map +1 -0
- package/dist/commands/admin/io.d.ts +15 -0
- package/dist/commands/admin/io.js +30 -0
- package/dist/commands/admin/io.js.map +1 -0
- package/dist/commands/admin/member.d.ts +43 -0
- package/dist/commands/admin/member.js +362 -0
- package/dist/commands/admin/member.js.map +1 -0
- package/dist/commands/admin/project.d.ts +40 -0
- package/dist/commands/admin/project.js +182 -0
- package/dist/commands/admin/project.js.map +1 -0
- package/dist/commands/admin/team.d.ts +31 -0
- package/dist/commands/admin/team.js +157 -0
- package/dist/commands/admin/team.js.map +1 -0
- package/dist/commands/admin/teamMember.d.ts +33 -0
- package/dist/commands/admin/teamMember.js +262 -0
- package/dist/commands/admin/teamMember.js.map +1 -0
- package/dist/commands/admin/token.d.ts +29 -0
- package/dist/commands/admin/token.js +125 -0
- package/dist/commands/admin/token.js.map +1 -0
- package/dist/commands/admin/user.d.ts +2 -0
- package/dist/commands/admin/user.js +85 -0
- package/dist/commands/admin/user.js.map +1 -0
- package/dist/commands/config.d.ts +9 -0
- package/dist/commands/config.js +178 -0
- package/dist/commands/config.js.map +1 -0
- package/dist/commands/context.d.ts +11 -0
- package/dist/commands/context.js +235 -0
- package/dist/commands/context.js.map +1 -0
- package/dist/commands/diff.d.ts +6 -0
- package/dist/commands/diff.js +208 -0
- package/dist/commands/diff.js.map +1 -0
- package/dist/commands/freeze.d.ts +10 -0
- package/dist/commands/freeze.js +269 -0
- package/dist/commands/freeze.js.map +1 -0
- package/dist/commands/init.d.ts +24 -0
- package/dist/commands/init.js +229 -0
- package/dist/commands/init.js.map +1 -0
- package/dist/commands/login.d.ts +26 -0
- package/dist/commands/login.js +241 -0
- package/dist/commands/login.js.map +1 -0
- package/dist/commands/logout.d.ts +6 -0
- package/dist/commands/logout.js +75 -0
- package/dist/commands/logout.js.map +1 -0
- package/dist/commands/migrate-yaml.d.ts +17 -0
- package/dist/commands/migrate-yaml.js +288 -0
- package/dist/commands/migrate-yaml.js.map +1 -0
- package/dist/commands/project.d.ts +7 -0
- package/dist/commands/project.js +87 -0
- package/dist/commands/project.js.map +1 -0
- package/dist/commands/pull.d.ts +16 -0
- package/dist/commands/pull.js +197 -0
- package/dist/commands/pull.js.map +1 -0
- package/dist/commands/push.d.ts +9 -0
- package/dist/commands/push.js +392 -0
- package/dist/commands/push.js.map +1 -0
- package/dist/commands/refresh.d.ts +9 -0
- package/dist/commands/refresh.js +123 -0
- package/dist/commands/refresh.js.map +1 -0
- package/dist/commands/status.d.ts +7 -0
- package/dist/commands/status.js +190 -0
- package/dist/commands/status.js.map +1 -0
- package/dist/commands/team.d.ts +6 -0
- package/dist/commands/team.js +84 -0
- package/dist/commands/team.js.map +1 -0
- package/dist/commands/validate.d.ts +5 -0
- package/dist/commands/validate.js +129 -0
- package/dist/commands/validate.js.map +1 -0
- package/dist/commands/whoami.d.ts +6 -0
- package/dist/commands/whoami.js +81 -0
- package/dist/commands/whoami.js.map +1 -0
- package/dist/config/adminBackend.d.ts +43 -0
- package/dist/config/adminBackend.js +33 -0
- package/dist/config/adminBackend.js.map +1 -0
- package/dist/config/rc.d.ts +70 -0
- package/dist/config/rc.js +148 -0
- package/dist/config/rc.js.map +1 -0
- package/dist/config/schema.d.ts +132 -0
- package/dist/config/schema.js +36 -0
- package/dist/config/schema.js.map +1 -0
- package/dist/diff/engine.d.ts +35 -0
- package/dist/diff/engine.js +305 -0
- package/dist/diff/engine.js.map +1 -0
- package/dist/diff/render.d.ts +18 -0
- package/dist/diff/render.js +129 -0
- package/dist/diff/render.js.map +1 -0
- package/dist/formatter/colors.d.ts +17 -0
- package/dist/formatter/colors.js +35 -0
- package/dist/formatter/colors.js.map +1 -0
- package/dist/formatter/human.d.ts +7 -0
- package/dist/formatter/human.js +70 -0
- package/dist/formatter/human.js.map +1 -0
- package/dist/fs/atomicWrite.d.ts +7 -0
- package/dist/fs/atomicWrite.js +37 -0
- package/dist/fs/atomicWrite.js.map +1 -0
- package/dist/i18n/dispatch.d.ts +19 -0
- package/dist/i18n/dispatch.js +27 -0
- package/dist/i18n/dispatch.js.map +1 -0
- package/dist/i18n/en.d.ts +3 -0
- package/dist/i18n/en.js +275 -0
- package/dist/i18n/en.js.map +1 -0
- package/dist/i18n/help.d.ts +3 -0
- package/dist/i18n/help.en.d.ts +149 -0
- package/dist/i18n/help.en.js +150 -0
- package/dist/i18n/help.en.js.map +1 -0
- package/dist/i18n/help.js +7 -0
- package/dist/i18n/help.js.map +1 -0
- package/dist/i18n/help.zh.d.ts +149 -0
- package/dist/i18n/help.zh.js +150 -0
- package/dist/i18n/help.zh.js.map +1 -0
- package/dist/i18n/helpFormat.d.ts +7 -0
- package/dist/i18n/helpFormat.js +51 -0
- package/dist/i18n/helpFormat.js.map +1 -0
- package/dist/i18n/helpGroups.d.ts +3 -0
- package/dist/i18n/helpGroups.js +11 -0
- package/dist/i18n/helpGroups.js.map +1 -0
- package/dist/i18n/index.d.ts +16 -0
- package/dist/i18n/index.js +46 -0
- package/dist/i18n/index.js.map +1 -0
- package/dist/i18n/peekLang.d.ts +1 -0
- package/dist/i18n/peekLang.js +16 -0
- package/dist/i18n/peekLang.js.map +1 -0
- package/dist/i18n/zh.d.ts +680 -0
- package/dist/i18n/zh.js +288 -0
- package/dist/i18n/zh.js.map +1 -0
- package/dist/parser/discover.d.ts +2 -0
- package/dist/parser/discover.js +69 -0
- package/dist/parser/discover.js.map +1 -0
- package/dist/parser/load-yaml.d.ts +11 -0
- package/dist/parser/load-yaml.js +25 -0
- package/dist/parser/load-yaml.js.map +1 -0
- package/dist/pkgVersion.d.ts +9 -0
- package/dist/pkgVersion.js +22 -0
- package/dist/pkgVersion.js.map +1 -0
- package/dist/renderer/context-md.d.ts +27 -0
- package/dist/renderer/context-md.js +444 -0
- package/dist/renderer/context-md.js.map +1 -0
- package/dist/renderer/refresh-md.d.ts +18 -0
- package/dist/renderer/refresh-md.js +93 -0
- package/dist/renderer/refresh-md.js.map +1 -0
- package/dist/schema/index.d.ts +2 -0
- package/dist/schema/index.js +3 -0
- package/dist/schema/index.js.map +1 -0
- package/dist/schema/modules.d.ts +461 -0
- package/dist/schema/modules.js +184 -0
- package/dist/schema/modules.js.map +1 -0
- package/dist/schema/prd.d.ts +1018 -0
- package/dist/schema/prd.js +65 -0
- package/dist/schema/prd.js.map +1 -0
- package/dist/sync/cliRcHelpers.d.ts +25 -0
- package/dist/sync/cliRcHelpers.js +62 -0
- package/dist/sync/cliRcHelpers.js.map +1 -0
- package/dist/sync/conflicts.d.ts +7 -0
- package/dist/sync/conflicts.js +72 -0
- package/dist/sync/conflicts.js.map +1 -0
- package/dist/sync/headProbe.d.ts +1 -0
- package/dist/sync/headProbe.js +95 -0
- package/dist/sync/headProbe.js.map +1 -0
- package/dist/sync/normalize.d.ts +10 -0
- package/dist/sync/normalize.js +13 -0
- package/dist/sync/normalize.js.map +1 -0
- package/dist/sync/syncJson.d.ts +18 -0
- package/dist/sync/syncJson.js +42 -0
- package/dist/sync/syncJson.js.map +1 -0
- package/dist/types.d.ts +70 -0
- package/dist/types.js +21 -0
- package/dist/types.js.map +1 -0
- package/dist/validators/blocking.d.ts +2 -0
- package/dist/validators/blocking.js +25 -0
- package/dist/validators/blocking.js.map +1 -0
- package/dist/validators/duplicate-ids.d.ts +2 -0
- package/dist/validators/duplicate-ids.js +58 -0
- package/dist/validators/duplicate-ids.js.map +1 -0
- package/dist/validators/references.d.ts +5 -0
- package/dist/validators/references.js +165 -0
- package/dist/validators/references.js.map +1 -0
- package/dist/validators/required-modules.d.ts +8 -0
- package/dist/validators/required-modules.js +59 -0
- package/dist/validators/required-modules.js.map +1 -0
- package/dist/validators/runner.d.ts +11 -0
- package/dist/validators/runner.js +73 -0
- package/dist/validators/runner.js.map +1 -0
- package/dist/workspace.d.ts +32 -0
- package/dist/workspace.js +37 -0
- package/dist/workspace.js.map +1 -0
- package/dist/yaml-indexer.d.ts +15 -0
- package/dist/yaml-indexer.js +112 -0
- package/dist/yaml-indexer.js.map +1 -0
- package/package.json +50 -0
|
@@ -0,0 +1,208 @@
|
|
|
1
|
+
import { existsSync, readFileSync } from "node:fs";
|
|
2
|
+
import { join } from "node:path";
|
|
3
|
+
import { load as yamlLoad } from "js-yaml";
|
|
4
|
+
import { getMessages, readLocale } from "../i18n/index.js";
|
|
5
|
+
import { renderError } from "../i18n/dispatch.js";
|
|
6
|
+
import * as c from "../formatter/colors.js";
|
|
7
|
+
import { VERSION_REGEX, readManifest, listExistingVersions, } from "../workspace.js";
|
|
8
|
+
import { diffPRDs } from "../diff/engine.js";
|
|
9
|
+
import { renderDiff } from "../diff/render.js";
|
|
10
|
+
import { asyncHeadProbe } from "../sync/headProbe.js";
|
|
11
|
+
function parseRef(s) {
|
|
12
|
+
if (s === "working")
|
|
13
|
+
return { kind: "working" };
|
|
14
|
+
if (VERSION_REGEX.test(s))
|
|
15
|
+
return { kind: "frozen", version: s };
|
|
16
|
+
return null;
|
|
17
|
+
}
|
|
18
|
+
function readSnapshotFrozenAt(snapshotPath) {
|
|
19
|
+
if (!existsSync(snapshotPath))
|
|
20
|
+
return undefined;
|
|
21
|
+
try {
|
|
22
|
+
const data = JSON.parse(readFileSync(snapshotPath, "utf8"));
|
|
23
|
+
return typeof data.frozen_at === "string" ? data.frozen_at : undefined;
|
|
24
|
+
}
|
|
25
|
+
catch {
|
|
26
|
+
return undefined;
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
function resolveRef(refStr, isFromSide, slug, cwd, manifest) {
|
|
30
|
+
const featureDir = join(cwd, ".prd/features", slug);
|
|
31
|
+
if (!refStr) {
|
|
32
|
+
if (isFromSide) {
|
|
33
|
+
const featureEntry = manifest.features.find((f) => f.slug === slug);
|
|
34
|
+
if (!featureEntry || !featureEntry.latest_frozen_version) {
|
|
35
|
+
return {
|
|
36
|
+
ok: false,
|
|
37
|
+
fail: {
|
|
38
|
+
errorKey: "diff_feature_not_frozen_default",
|
|
39
|
+
details: { slug },
|
|
40
|
+
exitCode: 1,
|
|
41
|
+
},
|
|
42
|
+
};
|
|
43
|
+
}
|
|
44
|
+
const version = featureEntry.latest_frozen_version;
|
|
45
|
+
const path = join(featureDir, "frozen", version, "prd.yaml");
|
|
46
|
+
if (!existsSync(path)) {
|
|
47
|
+
return {
|
|
48
|
+
ok: false,
|
|
49
|
+
fail: {
|
|
50
|
+
errorKey: "diff_manifest_disk_mismatch",
|
|
51
|
+
details: { slug, version },
|
|
52
|
+
exitCode: 2,
|
|
53
|
+
},
|
|
54
|
+
};
|
|
55
|
+
}
|
|
56
|
+
return {
|
|
57
|
+
ok: true,
|
|
58
|
+
src: {
|
|
59
|
+
path,
|
|
60
|
+
refLabel: version,
|
|
61
|
+
frozenAt: readSnapshotFrozenAt(join(featureDir, "frozen", version, "snapshot.json")),
|
|
62
|
+
},
|
|
63
|
+
};
|
|
64
|
+
}
|
|
65
|
+
const path = join(featureDir, "working/prd.yaml");
|
|
66
|
+
if (!existsSync(path)) {
|
|
67
|
+
return {
|
|
68
|
+
ok: false,
|
|
69
|
+
fail: {
|
|
70
|
+
errorKey: "diff_working_not_found",
|
|
71
|
+
details: { slug },
|
|
72
|
+
exitCode: 1,
|
|
73
|
+
},
|
|
74
|
+
};
|
|
75
|
+
}
|
|
76
|
+
return { ok: true, src: { path, refLabel: "working" } };
|
|
77
|
+
}
|
|
78
|
+
const parsed = parseRef(refStr);
|
|
79
|
+
if (!parsed) {
|
|
80
|
+
return {
|
|
81
|
+
ok: false,
|
|
82
|
+
fail: {
|
|
83
|
+
errorKey: "diff_invalid_ref",
|
|
84
|
+
details: { value: refStr },
|
|
85
|
+
exitCode: 1,
|
|
86
|
+
},
|
|
87
|
+
};
|
|
88
|
+
}
|
|
89
|
+
if (parsed.kind === "working") {
|
|
90
|
+
const path = join(featureDir, "working/prd.yaml");
|
|
91
|
+
if (!existsSync(path)) {
|
|
92
|
+
return {
|
|
93
|
+
ok: false,
|
|
94
|
+
fail: {
|
|
95
|
+
errorKey: "diff_working_not_found",
|
|
96
|
+
details: { slug },
|
|
97
|
+
exitCode: 1,
|
|
98
|
+
},
|
|
99
|
+
};
|
|
100
|
+
}
|
|
101
|
+
return { ok: true, src: { path, refLabel: "working" } };
|
|
102
|
+
}
|
|
103
|
+
const versionDir = join(featureDir, "frozen", parsed.version);
|
|
104
|
+
const path = join(versionDir, "prd.yaml");
|
|
105
|
+
if (!existsSync(path)) {
|
|
106
|
+
const existing = listExistingVersions(join(featureDir, "frozen"));
|
|
107
|
+
return {
|
|
108
|
+
ok: false,
|
|
109
|
+
fail: {
|
|
110
|
+
errorKey: "diff_version_not_found",
|
|
111
|
+
details: {
|
|
112
|
+
version: parsed.version,
|
|
113
|
+
existing: existing.length === 0 ? "(无)" : existing.join(", "),
|
|
114
|
+
},
|
|
115
|
+
exitCode: 1,
|
|
116
|
+
},
|
|
117
|
+
};
|
|
118
|
+
}
|
|
119
|
+
return {
|
|
120
|
+
ok: true,
|
|
121
|
+
src: {
|
|
122
|
+
path,
|
|
123
|
+
refLabel: parsed.version,
|
|
124
|
+
frozenAt: readSnapshotFrozenAt(join(versionDir, "snapshot.json")),
|
|
125
|
+
},
|
|
126
|
+
};
|
|
127
|
+
}
|
|
128
|
+
function loadYamlOrFail(path) {
|
|
129
|
+
let text;
|
|
130
|
+
try {
|
|
131
|
+
text = readFileSync(path, "utf8");
|
|
132
|
+
}
|
|
133
|
+
catch (e) {
|
|
134
|
+
return {
|
|
135
|
+
ok: false,
|
|
136
|
+
errorKey: "diff_fs_error",
|
|
137
|
+
details: { operation: `read ${path}`, message: e.message },
|
|
138
|
+
exitCode: 2,
|
|
139
|
+
};
|
|
140
|
+
}
|
|
141
|
+
try {
|
|
142
|
+
return { ok: true, data: yamlLoad(text) };
|
|
143
|
+
}
|
|
144
|
+
catch (e) {
|
|
145
|
+
return {
|
|
146
|
+
ok: false,
|
|
147
|
+
errorKey: "diff_yaml_parse_error",
|
|
148
|
+
details: { path, message: e.message },
|
|
149
|
+
exitCode: 2,
|
|
150
|
+
};
|
|
151
|
+
}
|
|
152
|
+
}
|
|
153
|
+
export function runDiffCommand(opts, cwd) {
|
|
154
|
+
const locale = readLocale();
|
|
155
|
+
const m = getMessages(locale);
|
|
156
|
+
if (!opts.feature) {
|
|
157
|
+
process.stderr.write(c.fail("✗ ") + m.diff_feature_required + "\n");
|
|
158
|
+
return 1;
|
|
159
|
+
}
|
|
160
|
+
// T6: HEAD probe (fire-and-forget; design §6.10).
|
|
161
|
+
void asyncHeadProbe(opts.feature, cwd);
|
|
162
|
+
const manifestPath = join(cwd, ".prd/manifest.json");
|
|
163
|
+
const manifestRead = readManifest(manifestPath);
|
|
164
|
+
if (!manifestRead.ok) {
|
|
165
|
+
process.stderr.write(c.fail("✗ ") + m.diff_workspace_not_init + "\n");
|
|
166
|
+
return 1;
|
|
167
|
+
}
|
|
168
|
+
const fromR = resolveRef(opts.from, true, opts.feature, cwd, manifestRead.data);
|
|
169
|
+
if (!fromR.ok) {
|
|
170
|
+
process.stderr.write(c.fail("✗ ") +
|
|
171
|
+
renderError(m, fromR.fail.errorKey, fromR.fail.details ?? {}) +
|
|
172
|
+
"\n");
|
|
173
|
+
return fromR.fail.exitCode;
|
|
174
|
+
}
|
|
175
|
+
const toR = resolveRef(opts.to, false, opts.feature, cwd, manifestRead.data);
|
|
176
|
+
if (!toR.ok) {
|
|
177
|
+
process.stderr.write(c.fail("✗ ") +
|
|
178
|
+
renderError(m, toR.fail.errorKey, toR.fail.details ?? {}) +
|
|
179
|
+
"\n");
|
|
180
|
+
return toR.fail.exitCode;
|
|
181
|
+
}
|
|
182
|
+
const leftLoad = loadYamlOrFail(fromR.src.path);
|
|
183
|
+
if (!leftLoad.ok) {
|
|
184
|
+
process.stderr.write(c.fail("✗ ") +
|
|
185
|
+
renderError(m, leftLoad.errorKey, leftLoad.details) +
|
|
186
|
+
"\n");
|
|
187
|
+
return leftLoad.exitCode;
|
|
188
|
+
}
|
|
189
|
+
const rightLoad = loadYamlOrFail(toR.src.path);
|
|
190
|
+
if (!rightLoad.ok) {
|
|
191
|
+
process.stderr.write(c.fail("✗ ") +
|
|
192
|
+
renderError(m, rightLoad.errorKey, rightLoad.details) +
|
|
193
|
+
"\n");
|
|
194
|
+
return rightLoad.exitCode;
|
|
195
|
+
}
|
|
196
|
+
const result = diffPRDs(leftLoad.data, rightLoad.data);
|
|
197
|
+
const text = renderDiff(result, {
|
|
198
|
+
feature: opts.feature,
|
|
199
|
+
from: { ref: fromR.src.refLabel, frozen_at: fromR.src.frozenAt },
|
|
200
|
+
to: { ref: toR.src.refLabel, frozen_at: toR.src.frozenAt },
|
|
201
|
+
}, {
|
|
202
|
+
color: c.colorEnabled(),
|
|
203
|
+
locale,
|
|
204
|
+
});
|
|
205
|
+
process.stdout.write(text);
|
|
206
|
+
return 0;
|
|
207
|
+
}
|
|
208
|
+
//# sourceMappingURL=diff.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"diff.js","sourceRoot":"","sources":["../../src/commands/diff.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
export interface FreezeOptions {
|
|
2
|
+
feature?: string;
|
|
3
|
+
version?: string;
|
|
4
|
+
auto?: boolean;
|
|
5
|
+
}
|
|
6
|
+
export declare function nextAutoVersion(existing: string[]): string;
|
|
7
|
+
/**
|
|
8
|
+
* freeze 命令主逻辑。返回退出码,由调用方负责 process.exit。
|
|
9
|
+
*/
|
|
10
|
+
export declare function runFreezeCommand(opts: FreezeOptions, cwd: string): number;
|
|
@@ -0,0 +1,269 @@
|
|
|
1
|
+
import { copyFileSync, existsSync, mkdirSync, readFileSync, writeFileSync, } from "node:fs";
|
|
2
|
+
import { join } from "node:path";
|
|
3
|
+
import { createHash } from "node:crypto";
|
|
4
|
+
import { getMessages, readLocale } from "../i18n/index.js";
|
|
5
|
+
import { renderError } from "../i18n/dispatch.js";
|
|
6
|
+
import * as c from "../formatter/colors.js";
|
|
7
|
+
import { runValidateCommand } from "./validate.js";
|
|
8
|
+
import { promoteUnreleasedSection } from "../changelog.js";
|
|
9
|
+
import { VERSION_REGEX, readManifest, listExistingVersions, } from "../workspace.js";
|
|
10
|
+
import { asyncHeadProbe } from "../sync/headProbe.js";
|
|
11
|
+
function resolveVersion(opts, existingVersions) {
|
|
12
|
+
const hasVersion = typeof opts.version === "string" && opts.version !== "";
|
|
13
|
+
const hasAuto = opts.auto === true;
|
|
14
|
+
if (hasVersion && hasAuto) {
|
|
15
|
+
return { ok: false, errorKey: "freeze_version_auto_conflict" };
|
|
16
|
+
}
|
|
17
|
+
if (!hasVersion && !hasAuto) {
|
|
18
|
+
return { ok: false, errorKey: "freeze_version_or_auto_required" };
|
|
19
|
+
}
|
|
20
|
+
if (hasVersion) {
|
|
21
|
+
if (!VERSION_REGEX.test(opts.version)) {
|
|
22
|
+
return {
|
|
23
|
+
ok: false,
|
|
24
|
+
errorKey: "freeze_invalid_version",
|
|
25
|
+
details: { value: opts.version },
|
|
26
|
+
};
|
|
27
|
+
}
|
|
28
|
+
return { ok: true, version: opts.version };
|
|
29
|
+
}
|
|
30
|
+
// --auto
|
|
31
|
+
return { ok: true, version: nextAutoVersion(existingVersions) };
|
|
32
|
+
}
|
|
33
|
+
/**
|
|
34
|
+
* 数值比较(忽略段数差异:v1.0 == v1.0.0)。当语义等价时返回 0;
|
|
35
|
+
* 调用方对此 case 的稳定性依赖 V8 stable sort + readdirSync 顺序,接受非确定性(spec 4.x)。
|
|
36
|
+
*/
|
|
37
|
+
function versionCompare(a, b) {
|
|
38
|
+
const segs = (s) => s.slice(1).split(".").map(Number);
|
|
39
|
+
const sa = segs(a);
|
|
40
|
+
const sb = segs(b);
|
|
41
|
+
for (let i = 0; i < Math.max(sa.length, sb.length); i++) {
|
|
42
|
+
const da = sa[i] ?? 0;
|
|
43
|
+
const db = sb[i] ?? 0;
|
|
44
|
+
if (da !== db)
|
|
45
|
+
return da - db;
|
|
46
|
+
}
|
|
47
|
+
return 0;
|
|
48
|
+
}
|
|
49
|
+
export function nextAutoVersion(existing) {
|
|
50
|
+
if (existing.length === 0)
|
|
51
|
+
return "v1.0";
|
|
52
|
+
const sorted = [...existing].sort(versionCompare);
|
|
53
|
+
const max = sorted[sorted.length - 1];
|
|
54
|
+
const segments = max.slice(1).split(".").map(Number);
|
|
55
|
+
segments[segments.length - 1]++;
|
|
56
|
+
return "v" + segments.join(".");
|
|
57
|
+
}
|
|
58
|
+
function upsertFeature(manifest, slug, version, frozenAt) {
|
|
59
|
+
const idx = manifest.features.findIndex((f) => f.slug === slug);
|
|
60
|
+
const entry = {
|
|
61
|
+
slug,
|
|
62
|
+
latest_frozen_version: version,
|
|
63
|
+
frozen_at: frozenAt,
|
|
64
|
+
};
|
|
65
|
+
if (idx >= 0) {
|
|
66
|
+
manifest.features[idx] = entry;
|
|
67
|
+
}
|
|
68
|
+
else {
|
|
69
|
+
manifest.features.push(entry);
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
/**
|
|
73
|
+
* freeze 命令主逻辑。返回退出码,由调用方负责 process.exit。
|
|
74
|
+
*/
|
|
75
|
+
export function runFreezeCommand(opts, cwd) {
|
|
76
|
+
const locale = readLocale();
|
|
77
|
+
const m = getMessages(locale);
|
|
78
|
+
// 1. --feature 必填
|
|
79
|
+
if (!opts.feature) {
|
|
80
|
+
process.stderr.write(c.fail("✗ ") + m.freeze_feature_required + "\n");
|
|
81
|
+
return 1;
|
|
82
|
+
}
|
|
83
|
+
// T6: HEAD probe (fire-and-forget; design §6.10).
|
|
84
|
+
void asyncHeadProbe(opts.feature, cwd);
|
|
85
|
+
// 2. workspace 已 init?
|
|
86
|
+
const manifestPath = join(cwd, ".prd/manifest.json");
|
|
87
|
+
const manifestRead = readManifest(manifestPath);
|
|
88
|
+
if (!manifestRead.ok) {
|
|
89
|
+
process.stderr.write(c.fail("✗ ") + m.freeze_workspace_not_init + "\n");
|
|
90
|
+
return 1;
|
|
91
|
+
}
|
|
92
|
+
// 3. feature 目录存在?(working 目录可能空但目录本身要存在)
|
|
93
|
+
const featureDir = join(cwd, ".prd/features", opts.feature);
|
|
94
|
+
const workingPath = join(featureDir, "working/prd.yaml");
|
|
95
|
+
if (!existsSync(workingPath)) {
|
|
96
|
+
process.stderr.write(c.fail("✗ ") + m.freeze_working_not_found({ slug: opts.feature }) + "\n");
|
|
97
|
+
return 1;
|
|
98
|
+
}
|
|
99
|
+
// 4. 解析版本号
|
|
100
|
+
const frozenDir = join(featureDir, "frozen");
|
|
101
|
+
const existingVersions = listExistingVersions(frozenDir);
|
|
102
|
+
const verResult = resolveVersion(opts, existingVersions);
|
|
103
|
+
if (!verResult.ok) {
|
|
104
|
+
process.stderr.write(c.fail("✗ ") +
|
|
105
|
+
renderError(m, verResult.errorKey, verResult.details ?? {}) +
|
|
106
|
+
"\n");
|
|
107
|
+
return 1;
|
|
108
|
+
}
|
|
109
|
+
const version = verResult.version;
|
|
110
|
+
// 5. 版本已存在?
|
|
111
|
+
const versionDir = join(frozenDir, version);
|
|
112
|
+
const existingSnapshotPath = join(versionDir, "snapshot.json");
|
|
113
|
+
if (existsSync(versionDir)) {
|
|
114
|
+
let frozenAt = "(unknown)";
|
|
115
|
+
if (existsSync(existingSnapshotPath)) {
|
|
116
|
+
try {
|
|
117
|
+
frozenAt = JSON.parse(readFileSync(existingSnapshotPath, "utf8")).frozen_at;
|
|
118
|
+
}
|
|
119
|
+
catch {
|
|
120
|
+
// ignore, use placeholder
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
process.stderr.write(c.fail("✗ ") +
|
|
124
|
+
m.freeze_version_exists({ version, frozen_at: frozenAt }) +
|
|
125
|
+
"\n");
|
|
126
|
+
return 1;
|
|
127
|
+
}
|
|
128
|
+
// 6. pre-validate(复用 runValidateCommand)
|
|
129
|
+
process.stdout.write(m.freeze_prevalidating({ slug: opts.feature }) + "\n");
|
|
130
|
+
const validateCode = runValidateCommand({ feature: opts.feature }, cwd);
|
|
131
|
+
if (validateCode !== 0) {
|
|
132
|
+
process.stderr.write(c.fail("✗ ") + m.freeze_prevalidate_fail + "\n");
|
|
133
|
+
return 1;
|
|
134
|
+
}
|
|
135
|
+
process.stdout.write(c.pass(m.freeze_prevalidate_pass) + "\n\n");
|
|
136
|
+
// 7. 读 working yaml
|
|
137
|
+
let yamlText;
|
|
138
|
+
try {
|
|
139
|
+
yamlText = readFileSync(workingPath, "utf8");
|
|
140
|
+
}
|
|
141
|
+
catch (e) {
|
|
142
|
+
process.stderr.write(c.fail("✗ ") +
|
|
143
|
+
m.freeze_fs_error({
|
|
144
|
+
operation: "read working/prd.yaml",
|
|
145
|
+
message: e.message,
|
|
146
|
+
}) +
|
|
147
|
+
"\n");
|
|
148
|
+
return 2;
|
|
149
|
+
}
|
|
150
|
+
// 8. source_hash
|
|
151
|
+
const sourceHash = "sha256:" + createHash("sha256").update(yamlText).digest("hex");
|
|
152
|
+
// 9. 写 frozen/<version>/
|
|
153
|
+
try {
|
|
154
|
+
mkdirSync(versionDir, { recursive: true });
|
|
155
|
+
}
|
|
156
|
+
catch (e) {
|
|
157
|
+
process.stderr.write(c.fail("✗ ") +
|
|
158
|
+
m.freeze_fs_error({
|
|
159
|
+
operation: `mkdir ${versionDir}`,
|
|
160
|
+
message: e.message,
|
|
161
|
+
}) +
|
|
162
|
+
"\n");
|
|
163
|
+
return 2;
|
|
164
|
+
}
|
|
165
|
+
try {
|
|
166
|
+
writeFileSync(join(versionDir, "prd.yaml"), yamlText, "utf8");
|
|
167
|
+
}
|
|
168
|
+
catch (e) {
|
|
169
|
+
process.stderr.write(c.fail("✗ ") +
|
|
170
|
+
m.freeze_fs_error({
|
|
171
|
+
operation: "write prd.yaml",
|
|
172
|
+
message: e.message,
|
|
173
|
+
}) +
|
|
174
|
+
"\n");
|
|
175
|
+
process.stderr.write(m.freeze_partial_recovery_hint({ dir: versionDir }) + "\n");
|
|
176
|
+
return 2;
|
|
177
|
+
}
|
|
178
|
+
const frozenAt = new Date().toISOString();
|
|
179
|
+
// 9.5 CHANGELOG.md 联动(设计 doc Section 5.5)
|
|
180
|
+
const workingDir = join(featureDir, "working");
|
|
181
|
+
const workingChangelogPath = join(workingDir, "CHANGELOG.md");
|
|
182
|
+
const frozenChangelogPath = join(versionDir, "CHANGELOG.md");
|
|
183
|
+
if (existsSync(workingChangelogPath)) {
|
|
184
|
+
// Step 1: byte-for-byte copy to frozen/
|
|
185
|
+
try {
|
|
186
|
+
copyFileSync(workingChangelogPath, frozenChangelogPath);
|
|
187
|
+
process.stdout.write(c.pass("✓ ") +
|
|
188
|
+
m.freeze_changelog_copied({ path: frozenChangelogPath }) +
|
|
189
|
+
"\n");
|
|
190
|
+
}
|
|
191
|
+
catch (e) {
|
|
192
|
+
process.stderr.write(c.fail("✗ ") +
|
|
193
|
+
m.freeze_changelog_copy_failed({ message: e.message }) +
|
|
194
|
+
"\n");
|
|
195
|
+
process.stderr.write(m.freeze_partial_recovery_hint({ dir: versionDir }) + "\n");
|
|
196
|
+
return 2;
|
|
197
|
+
}
|
|
198
|
+
// Step 2: promote working [Unreleased] → versioned + insert new [Unreleased]
|
|
199
|
+
try {
|
|
200
|
+
const content = readFileSync(workingChangelogPath, "utf8");
|
|
201
|
+
const promoted = promoteUnreleasedSection(content, version, frozenAt);
|
|
202
|
+
if (promoted !== content) {
|
|
203
|
+
writeFileSync(workingChangelogPath, promoted, "utf8");
|
|
204
|
+
process.stdout.write(c.pass("✓ ") +
|
|
205
|
+
m.freeze_changelog_unreleased_promoted({ version }) +
|
|
206
|
+
"\n");
|
|
207
|
+
process.stdout.write(c.pass("✓ ") +
|
|
208
|
+
m.freeze_changelog_new_unreleased_inserted() +
|
|
209
|
+
"\n");
|
|
210
|
+
}
|
|
211
|
+
}
|
|
212
|
+
catch (e) {
|
|
213
|
+
process.stderr.write(c.fail("✗ ") +
|
|
214
|
+
m.freeze_changelog_rewrite_failed({ message: e.message }) +
|
|
215
|
+
"\n");
|
|
216
|
+
process.stderr.write(m.freeze_changelog_recovery_sed_hint({ version, frozenAt }) + "\n");
|
|
217
|
+
return 2;
|
|
218
|
+
}
|
|
219
|
+
}
|
|
220
|
+
const snapshot = {
|
|
221
|
+
schema_version: "v0.1",
|
|
222
|
+
version,
|
|
223
|
+
feature: opts.feature,
|
|
224
|
+
frozen_at: frozenAt,
|
|
225
|
+
cli_version: manifestRead.data.cli_version,
|
|
226
|
+
source_hash: sourceHash,
|
|
227
|
+
};
|
|
228
|
+
try {
|
|
229
|
+
writeFileSync(join(versionDir, "snapshot.json"), JSON.stringify(snapshot, null, 2) + "\n", "utf8");
|
|
230
|
+
}
|
|
231
|
+
catch (e) {
|
|
232
|
+
process.stderr.write(c.fail("✗ ") +
|
|
233
|
+
m.freeze_fs_error({
|
|
234
|
+
operation: "write snapshot.json",
|
|
235
|
+
message: e.message,
|
|
236
|
+
}) +
|
|
237
|
+
"\n");
|
|
238
|
+
process.stderr.write(m.freeze_partial_recovery_hint({ dir: versionDir }) + "\n");
|
|
239
|
+
return 2;
|
|
240
|
+
}
|
|
241
|
+
// 10. 更新 manifest
|
|
242
|
+
upsertFeature(manifestRead.data, opts.feature, version, frozenAt);
|
|
243
|
+
try {
|
|
244
|
+
writeFileSync(manifestPath, JSON.stringify(manifestRead.data, null, 2) + "\n", "utf8");
|
|
245
|
+
}
|
|
246
|
+
catch (e) {
|
|
247
|
+
process.stderr.write(c.fail("✗ ") +
|
|
248
|
+
m.freeze_fs_error({
|
|
249
|
+
operation: "write manifest.json",
|
|
250
|
+
message: e.message,
|
|
251
|
+
}) +
|
|
252
|
+
"\n");
|
|
253
|
+
process.stderr.write(m.freeze_partial_recovery_hint({ dir: versionDir }) + "\n");
|
|
254
|
+
return 2;
|
|
255
|
+
}
|
|
256
|
+
// 11. 渲染成功
|
|
257
|
+
process.stdout.write(c.pass("✓ ") +
|
|
258
|
+
m.freeze_success_yaml({ slug: opts.feature, version }) +
|
|
259
|
+
"\n");
|
|
260
|
+
process.stdout.write(c.pass("✓ ") +
|
|
261
|
+
m.freeze_success_snapshot({ slug: opts.feature, version }) +
|
|
262
|
+
"\n");
|
|
263
|
+
process.stdout.write(c.pass("✓ ") +
|
|
264
|
+
m.freeze_success_manifest({ slug: opts.feature, version }) +
|
|
265
|
+
"\n");
|
|
266
|
+
process.stdout.write("\n" + m.freeze_success_summary({ slug: opts.feature, version }) + "\n");
|
|
267
|
+
return 0;
|
|
268
|
+
}
|
|
269
|
+
//# sourceMappingURL=freeze.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"freeze.js","sourceRoot":"","sources":["../../src/commands/freeze.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
export interface InitOptions {
|
|
2
|
+
workspace?: string;
|
|
3
|
+
/**
|
|
4
|
+
* v1.1 §6.3 — optional feature slug. When provided (with --team and
|
|
5
|
+
* --project resolved), init also writes a v0.2 yaml stub at
|
|
6
|
+
* `.prd/features/<slug>/working/prd.yaml` so the user can go straight from
|
|
7
|
+
* `prd init` to `prd push --allow-create <slug>` without hand-authoring the
|
|
8
|
+
* meta block. Q1 boundary: `prd push --allow-create` will refuse if this
|
|
9
|
+
* yaml is missing — `prd init <slug>` is the supported way to create it.
|
|
10
|
+
*/
|
|
11
|
+
slug?: string;
|
|
12
|
+
/** v1.1 — workspace-level team slug for the new yaml stub. */
|
|
13
|
+
team?: string;
|
|
14
|
+
/** v1.1 — workspace-level project slug for the new yaml stub. */
|
|
15
|
+
project?: string;
|
|
16
|
+
/** Test seam — point rc reader at an isolated path. */
|
|
17
|
+
rcPath?: string;
|
|
18
|
+
/** v1.1 — backend name for .prdrc default lookup. */
|
|
19
|
+
backend?: string;
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* init 命令主逻辑。返回退出码,由调用方负责 process.exit。
|
|
23
|
+
*/
|
|
24
|
+
export declare function runInitCommand(opts: InitOptions, cwd: string): number;
|