outfitter 0.3.3 → 0.4.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/actions/add.d.ts +1 -1
- package/dist/actions/add.js +6 -5
- package/dist/actions/check-automation.d.ts +4 -2
- package/dist/actions/check-automation.js +13 -9
- package/dist/actions/check.d.ts +2 -2
- package/dist/actions/check.js +6 -6
- package/dist/actions/demo.d.ts +1 -1
- package/dist/actions/demo.js +3 -4
- package/dist/actions/docs.d.ts +7 -7
- package/dist/actions/docs.js +12 -13
- package/dist/actions/doctor.d.ts +1 -1
- package/dist/actions/doctor.js +8 -7
- package/dist/actions/init.d.ts +9 -7
- package/dist/actions/init.js +12 -10
- package/dist/actions/scaffold.d.ts +1 -1
- package/dist/actions/scaffold.js +14 -12
- package/dist/actions/shared.d.ts +1 -20
- package/dist/actions/shared.js +1 -5
- package/dist/actions/upgrade.d.ts +10 -2
- package/dist/actions/upgrade.js +15 -8
- package/dist/actions.js +51 -48
- package/dist/cli.js +51 -48
- package/dist/commands/add.js +4 -3
- package/dist/commands/check-action-ceremony.d.ts +1 -1
- package/dist/commands/check-action-ceremony.js +2 -2
- package/dist/commands/check-action-registry.d.ts +52 -0
- package/dist/commands/check-action-registry.js +13 -0
- package/dist/commands/check-docs-sentinel.d.ts +1 -1
- package/dist/commands/check-docs-sentinel.js +2 -2
- package/dist/commands/check-orchestrator.d.ts +1 -1
- package/dist/commands/check-orchestrator.js +2 -2
- package/dist/commands/check-preset-versions.d.ts +4 -2
- package/dist/commands/check-preset-versions.js +8 -3
- package/dist/commands/check-publish-guardrails.d.ts +1 -1
- package/dist/commands/check-publish-guardrails.js +2 -2
- package/dist/commands/check-surface-map-format.d.ts +1 -1
- package/dist/commands/check-surface-map-format.js +2 -2
- package/dist/commands/check-surface-map.d.ts +1 -1
- package/dist/commands/check-surface-map.js +2 -2
- package/dist/commands/check-tsdoc.d.ts +2 -2
- package/dist/commands/check.js +3 -3
- package/dist/commands/demo.d.ts +1 -1
- package/dist/commands/demo.js +1 -1
- package/dist/commands/docs-api.d.ts +3 -3
- package/dist/commands/docs-api.js +2 -2
- package/dist/commands/docs-export.d.ts +2 -2
- package/dist/commands/docs-export.js +2 -2
- package/dist/commands/docs-list.d.ts +2 -2
- package/dist/commands/docs-list.js +2 -2
- package/dist/commands/docs-search.d.ts +2 -2
- package/dist/commands/docs-search.js +2 -2
- package/dist/commands/docs-show.d.ts +2 -2
- package/dist/commands/docs-show.js +2 -2
- package/dist/commands/doctor.js +6 -5
- package/dist/commands/init-execution.d.ts +5 -5
- package/dist/commands/init-execution.js +6 -4
- package/dist/commands/init-option-resolution.d.ts +3 -3
- package/dist/commands/init-option-resolution.js +1 -1
- package/dist/commands/init-output.d.ts +5 -5
- package/dist/commands/init-output.js +3 -3
- package/dist/commands/init.d.ts +5 -5
- package/dist/commands/init.js +9 -9
- package/dist/commands/scaffold-output.js +3 -3
- package/dist/commands/scaffold-planning.d.ts +9 -10
- package/dist/commands/scaffold-planning.js +6 -4
- package/dist/commands/scaffold.js +12 -10
- package/dist/commands/shared-deps.js +2 -2
- package/dist/commands/upgrade-codemod-builder.d.ts +45 -0
- package/dist/commands/upgrade-codemod-builder.js +14 -0
- package/dist/commands/upgrade-output.js +2 -2
- package/dist/commands/upgrade-workspace.js +5 -1
- package/dist/commands/upgrade.js +9 -5
- package/dist/create/index.d.ts +1 -1
- package/dist/create/planner.js +1 -1
- package/dist/engine/blocks.d.ts +2 -2
- package/dist/engine/blocks.js +5 -4
- package/dist/engine/config.d.ts +2 -2
- package/dist/engine/config.js +6 -5
- package/dist/engine/dependency-versions.d.ts +11 -3
- package/dist/engine/dependency-versions.js +6 -2
- package/dist/engine/executor.d.ts +2 -2
- package/dist/engine/executor.js +23 -10
- package/dist/engine/index.d.ts +8 -9
- package/dist/engine/index.js +1 -5
- package/dist/engine/package-json.d.ts +3 -0
- package/dist/engine/package-json.js +10 -0
- package/dist/engine/post-scaffold.js +1 -1
- package/dist/engine/preset.d.ts +3 -3
- package/dist/engine/preset.js +4 -2
- package/dist/engine/render-plan.js +2 -2
- package/dist/engine/types.d.ts +1 -1
- package/dist/engine/workspace.d.ts +2 -2
- package/dist/engine/workspace.js +3 -2
- package/dist/index.d.ts +7 -7
- package/dist/manifest.js +1 -1
- package/dist/output-mode.d.ts +2 -2
- package/dist/output-mode.js +2 -4
- package/dist/scaffold-e2e/cli.d.ts +19 -0
- package/dist/scaffold-e2e/cli.js +14 -0
- package/dist/scaffold-e2e/config.d.ts +6 -0
- package/dist/scaffold-e2e/config.js +14 -0
- package/dist/scaffold-e2e/runner.d.ts +29 -0
- package/dist/scaffold-e2e/runner.js +17 -0
- package/dist/scaffold-e2e/template-guardrails.d.ts +25 -0
- package/dist/scaffold-e2e/template-guardrails.js +183 -0
- package/dist/scaffold-e2e/workspace.d.ts +27 -0
- package/dist/scaffold-e2e/workspace.js +18 -0
- package/dist/scripts/scaffold-e2e.js +78 -0
- package/dist/shared/{outfitter-qsrx7m4w.js → outfitter-00wxeg2g.js} +8 -8
- package/dist/shared/{outfitter-ex8gn945.js → outfitter-0cspz333.js} +4 -6
- package/dist/shared/{outfitter-rp89dafm.js → outfitter-0xp447gf.js} +55 -8
- package/dist/shared/outfitter-0zs8makw.js +94 -0
- package/dist/shared/{outfitter-5d9wbzhh.d.ts → outfitter-11r5ny73.d.ts} +2 -2
- package/dist/shared/{outfitter-gyayfx5r.js → outfitter-18s82np1.js} +1 -1
- package/dist/shared/{outfitter-954y4mzx.d.ts → outfitter-1dekqnaw.d.ts} +1 -1
- package/dist/shared/{outfitter-6t7xeyg1.js → outfitter-1t8gjzw6.js} +91 -3
- package/dist/shared/{outfitter-tqznjgbm.js → outfitter-23159bef.js} +6 -3
- package/dist/shared/{outfitter-y6ee0k45.d.ts → outfitter-232ean4v.d.ts} +1 -1
- package/dist/shared/{outfitter-3rcrvva8.js → outfitter-247et71q.js} +8 -8
- package/dist/shared/{outfitter-xs94pkfe.js → outfitter-3f261xh0.js} +5 -7
- package/dist/shared/outfitter-4bs5a2n4.js +31 -0
- package/dist/shared/{outfitter-76k25svs.js → outfitter-4c4q091c.js} +6 -28
- package/dist/shared/{outfitter-738z4c37.js → outfitter-4t818mq5.js} +21 -9
- package/dist/shared/{outfitter-4s9meh3j.js → outfitter-4w9sc6bw.js} +24 -0
- package/dist/shared/outfitter-5gaptj9b.js +83 -0
- package/dist/shared/{outfitter-2ysjerp6.d.ts → outfitter-5rc4hxdn.d.ts} +2 -2
- package/dist/shared/{outfitter-ttjr95y9.js → outfitter-7krhbg3b.js} +3 -3
- package/dist/shared/{outfitter-7n7vsz95.js → outfitter-7t7ces1x.js} +1 -42
- package/dist/shared/{outfitter-gdc7b7de.d.ts → outfitter-8231g70k.d.ts} +1 -1
- package/dist/shared/{outfitter-yhb23pjc.js → outfitter-8jd1sak0.js} +4 -4
- package/dist/shared/{outfitter-wkt0a0ra.js → outfitter-93e1shd4.js} +4 -6
- package/dist/shared/{outfitter-wyg1tpp5.d.ts → outfitter-a93yanw6.d.ts} +1 -1
- package/dist/shared/{outfitter-mstr60zz.js → outfitter-aa5nzw14.js} +47 -22
- package/dist/shared/{outfitter-fxry5n58.js → outfitter-b05mvbmx.js} +4 -4
- package/dist/shared/{outfitter-1fy7byz5.js → outfitter-bsjq8gkk.js} +6 -4
- package/dist/shared/{outfitter-ssrtakh3.js → outfitter-c50y6yr3.js} +4 -4
- package/dist/shared/{outfitter-cyvr4r8d.d.ts → outfitter-crxe5gth.d.ts} +4 -0
- package/dist/shared/{outfitter-fj2v5ffz.js → outfitter-d5kz9x7g.js} +1 -1
- package/dist/shared/{outfitter-k6zyvg2n.js → outfitter-dna8exj2.js} +19 -10
- package/dist/shared/{outfitter-940h0x7b.js → outfitter-e44qcs0w.js} +3 -3
- package/dist/shared/{outfitter-r2awqszh.d.ts → outfitter-e5x0ybqt.d.ts} +12 -3
- package/dist/shared/{outfitter-3tx3adgj.js → outfitter-ez7qffv5.js} +8 -6
- package/dist/shared/outfitter-fgrqt6aq.js +179 -0
- package/dist/shared/outfitter-fhahf9f3.d.ts +14 -0
- package/dist/shared/{outfitter-c7sbs7es.js → outfitter-g6r9avgz.js} +3 -3
- package/dist/shared/{outfitter-ssynegbs.js → outfitter-ga59fa45.js} +1 -1
- package/dist/shared/{outfitter-tavatb5p.js → outfitter-gna739c3.js} +86 -31
- package/dist/shared/{outfitter-nxvjxrmw.d.ts → outfitter-grt5ngqq.d.ts} +1 -1
- package/dist/shared/{outfitter-58rn1sj1.d.ts → outfitter-gsjbcta2.d.ts} +1 -1
- package/dist/shared/{outfitter-q1g58t85.js → outfitter-gvpwpqnc.js} +0 -1
- package/dist/shared/{outfitter-x39awx8g.js → outfitter-hr4cvmjy.js} +47 -25
- package/dist/shared/{outfitter-84chvazx.js → outfitter-hw9f0zq9.js} +75 -31
- package/dist/shared/{outfitter-ksyvwmb5.js → outfitter-jhpcjeg1.js} +5 -5
- package/dist/shared/outfitter-kc46jq69.d.ts +12 -0
- package/dist/shared/{outfitter-px5sv5gn.js → outfitter-ksg34wka.js} +5 -5
- package/dist/shared/{outfitter-wrcqq29p.js → outfitter-n63ygpv3.js} +30 -23
- package/dist/shared/{outfitter-qsd5638j.js → outfitter-n9jp1abt.js} +16 -40
- package/dist/shared/{outfitter-d0kqashd.d.ts → outfitter-nhft74pe.d.ts} +4 -2
- package/dist/shared/{outfitter-8kmak0wc.d.ts → outfitter-nx1sywpb.d.ts} +1 -1
- package/dist/shared/{outfitter-5r6q2749.d.ts → outfitter-pw74st5t.d.ts} +1 -1
- package/dist/shared/{outfitter-h0wmtxw8.d.ts → outfitter-qka1skyw.d.ts} +1 -1
- package/dist/shared/{outfitter-6mpkh3zn.js → outfitter-qps83547.js} +30 -23
- package/dist/shared/outfitter-qzd5djgx.js +88 -0
- package/dist/shared/{outfitter-hf5bj2gq.js → outfitter-sh015v8k.js} +4 -4
- package/dist/shared/{outfitter-ypcvwg1s.js → outfitter-srznx3hj.js} +1 -1
- package/dist/shared/{outfitter-n0ed012k.js → outfitter-ssq33ym3.js} +8 -8
- package/dist/shared/outfitter-sxf8jjjn.js +7 -0
- package/dist/shared/{outfitter-p2wn07b7.js → outfitter-t535h0mw.js} +1 -1
- package/dist/shared/{outfitter-znbqe5zy.d.ts → outfitter-t8dg4tg5.d.ts} +1 -1
- package/dist/shared/{outfitter-ydw7x6bh.js → outfitter-t8mvabed.js} +1 -1
- package/dist/shared/{outfitter-6ddf91vh.js → outfitter-t9xkn37g.js} +11 -12
- package/dist/shared/{outfitter-x4cc5xsq.js → outfitter-wmgzyymq.js} +4 -4
- package/dist/shared/outfitter-wna6gp2t.js +56 -0
- package/dist/shared/outfitter-x0r7mfvy.js +142 -0
- package/dist/shared/{outfitter-b9cpnr7e.js → outfitter-x4f8v5vf.js} +1 -1
- package/dist/shared/{outfitter-x8w5sjnd.d.ts → outfitter-x6322tjp.d.ts} +1 -1
- package/dist/shared/{outfitter-6rtcemk7.d.ts → outfitter-xa4915yp.d.ts} +3 -2
- package/dist/shared/{outfitter-2z61gp5w.js → outfitter-xg5yryp2.js} +1 -1
- package/dist/shared/{outfitter-rdpw2sbp.d.ts → outfitter-xn5km042.d.ts} +6 -0
- package/dist/shared/{outfitter-cyhzstz0.js → outfitter-xqr4fp1n.js} +4 -4
- package/dist/shared/outfitter-z6tg0swx.js +87 -0
- package/dist/shared/{outfitter-dx4hn4ta.js → outfitter-zmzrsvcn.js} +17 -21
- package/dist/shared/{outfitter-8ggmja91.js → outfitter-zqj1nte1.js} +66 -67
- package/dist/targets/index.d.ts +2 -2
- package/dist/targets/registry.d.ts +2 -2
- package/dist/targets/registry.js +13 -1
- package/dist/targets/types.d.ts +1 -1
- package/package.json +85 -39
- package/dist/actions/docs-output-mode.d.ts +0 -4
- package/dist/actions/docs-output-mode.js +0 -8
- package/dist/engine/template.d.ts +0 -4
- package/dist/engine/template.js +0 -34
- package/dist/shared/outfitter-7r12fj7f.js +0 -30
- package/dist/shared/outfitter-a79xrm12.d.ts +0 -17
- package/dist/shared/outfitter-ec83h4v2.js +0 -17
- package/dist/shared/outfitter-fbvfd5zq.d.ts +0 -13
- package/dist/shared/outfitter-jkct38dh.js +0 -53
|
@@ -0,0 +1,142 @@
|
|
|
1
|
+
// @bun
|
|
2
|
+
import {
|
|
3
|
+
DEFAULT_SCAFFOLD_E2E_PRESETS,
|
|
4
|
+
resolveScaffoldE2EProfile
|
|
5
|
+
} from "./outfitter-4bs5a2n4.js";
|
|
6
|
+
import {
|
|
7
|
+
isValidInitPreset
|
|
8
|
+
} from "./outfitter-xg5yryp2.js";
|
|
9
|
+
|
|
10
|
+
// apps/outfitter/src/scaffold-e2e/runner.ts
|
|
11
|
+
import { existsSync } from "fs";
|
|
12
|
+
import { join } from "path";
|
|
13
|
+
function resolveScaffoldCliEntry(baseDir, fileExists = existsSync) {
|
|
14
|
+
const sourceEntry = join(baseDir, "..", "cli.ts");
|
|
15
|
+
if (fileExists(sourceEntry)) {
|
|
16
|
+
return sourceEntry;
|
|
17
|
+
}
|
|
18
|
+
const builtEntry = join(baseDir, "..", "cli.js");
|
|
19
|
+
if (fileExists(builtEntry)) {
|
|
20
|
+
return builtEntry;
|
|
21
|
+
}
|
|
22
|
+
throw new Error(`Unable to resolve outfitter CLI entry from ${baseDir}`);
|
|
23
|
+
}
|
|
24
|
+
var cliEntry = resolveScaffoldCliEntry(import.meta.dir);
|
|
25
|
+
var repoRoot = join(import.meta.dir, "..", "..", "..", "..");
|
|
26
|
+
function createProjectName(preset) {
|
|
27
|
+
return `scaffold-e2e-${preset}`;
|
|
28
|
+
}
|
|
29
|
+
function resolveScaffoldE2EPresets(values) {
|
|
30
|
+
if (!values || values.length === 0) {
|
|
31
|
+
return DEFAULT_SCAFFOLD_E2E_PRESETS;
|
|
32
|
+
}
|
|
33
|
+
const presets = values.flatMap((value) => value.split(",").map((part) => part.trim()).filter((part) => part.length > 0));
|
|
34
|
+
const invalid = presets.filter((preset) => !isValidInitPreset(preset));
|
|
35
|
+
if (invalid.length > 0) {
|
|
36
|
+
throw new Error(`Unknown scaffold E2E preset(s): ${invalid.join(", ")}. Available presets: ${DEFAULT_SCAFFOLD_E2E_PRESETS.join(", ")}`);
|
|
37
|
+
}
|
|
38
|
+
return [...new Set(presets)];
|
|
39
|
+
}
|
|
40
|
+
async function runCommand(cwd, command, timeoutMs) {
|
|
41
|
+
const proc = Bun.spawn([...command], {
|
|
42
|
+
cwd,
|
|
43
|
+
stdout: "pipe",
|
|
44
|
+
stderr: "pipe"
|
|
45
|
+
});
|
|
46
|
+
const timeout = new Promise((resolveTimeout) => {
|
|
47
|
+
const timer = setTimeout(() => resolveTimeout("timeout"), timeoutMs);
|
|
48
|
+
proc.exited.finally(() => clearTimeout(timer));
|
|
49
|
+
});
|
|
50
|
+
const race = await Promise.race([proc.exited.then(() => "exit"), timeout]);
|
|
51
|
+
if (race === "timeout") {
|
|
52
|
+
proc.kill("SIGKILL");
|
|
53
|
+
}
|
|
54
|
+
const [exitCode, stdout, stderr] = await Promise.all([
|
|
55
|
+
proc.exited,
|
|
56
|
+
new Response(proc.stdout).text(),
|
|
57
|
+
new Response(proc.stderr).text()
|
|
58
|
+
]);
|
|
59
|
+
return {
|
|
60
|
+
exitCode,
|
|
61
|
+
stdout,
|
|
62
|
+
stderr,
|
|
63
|
+
timedOut: race === "timeout"
|
|
64
|
+
};
|
|
65
|
+
}
|
|
66
|
+
function assertCommandSuccess(preset, step, result) {
|
|
67
|
+
if (result.timedOut) {
|
|
68
|
+
throw new Error(`[${preset}] ${step} timed out.
|
|
69
|
+
stdout:
|
|
70
|
+
${result.stdout}
|
|
71
|
+
stderr:
|
|
72
|
+
${result.stderr}`);
|
|
73
|
+
}
|
|
74
|
+
if (result.exitCode !== 0) {
|
|
75
|
+
throw new Error(`[${preset}] ${step} failed with exit code ${result.exitCode}.
|
|
76
|
+
stdout:
|
|
77
|
+
${result.stdout}
|
|
78
|
+
stderr:
|
|
79
|
+
${result.stderr}`);
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
async function runInitViaCli(targetDir, name, preset, timeoutMs) {
|
|
83
|
+
return runCommand(repoRoot, [
|
|
84
|
+
"bun",
|
|
85
|
+
cliEntry,
|
|
86
|
+
"init",
|
|
87
|
+
targetDir,
|
|
88
|
+
"--name",
|
|
89
|
+
name,
|
|
90
|
+
"--preset",
|
|
91
|
+
preset,
|
|
92
|
+
"--yes",
|
|
93
|
+
"--skip-install",
|
|
94
|
+
"--skip-git",
|
|
95
|
+
"--skip-commit"
|
|
96
|
+
], timeoutMs);
|
|
97
|
+
}
|
|
98
|
+
async function runScaffoldE2ESuite(options) {
|
|
99
|
+
const profile = resolveScaffoldE2EProfile(options.profile);
|
|
100
|
+
const timeoutMs = options.timeoutMs ?? profile.commandTimeoutMs;
|
|
101
|
+
const presets = options.presets ?? profile.presets;
|
|
102
|
+
const results = [];
|
|
103
|
+
for (const preset of presets) {
|
|
104
|
+
const presetStartedAt = Date.now();
|
|
105
|
+
process.stderr.write(`[scaffold-e2e] starting preset: ${preset}
|
|
106
|
+
`);
|
|
107
|
+
const targetDir = join(options.runDir, preset);
|
|
108
|
+
const steps = [];
|
|
109
|
+
const initStartedAt = Date.now();
|
|
110
|
+
const init = await runInitViaCli(targetDir, createProjectName(preset), preset, timeoutMs);
|
|
111
|
+
assertCommandSuccess(preset, "outfitter init", init);
|
|
112
|
+
steps.push({
|
|
113
|
+
command: "outfitter init",
|
|
114
|
+
durationMs: Date.now() - initStartedAt
|
|
115
|
+
});
|
|
116
|
+
const installStartedAt = Date.now();
|
|
117
|
+
const install = await runCommand(targetDir, ["bun", "install"], timeoutMs);
|
|
118
|
+
assertCommandSuccess(preset, "bun install", install);
|
|
119
|
+
steps.push({
|
|
120
|
+
command: "bun install",
|
|
121
|
+
durationMs: Date.now() - installStartedAt
|
|
122
|
+
});
|
|
123
|
+
const verifyStartedAt = Date.now();
|
|
124
|
+
const verify = await runCommand(targetDir, ["bun", "run", "verify:ci"], timeoutMs);
|
|
125
|
+
assertCommandSuccess(preset, "bun run verify:ci", verify);
|
|
126
|
+
steps.push({
|
|
127
|
+
command: "bun run verify:ci",
|
|
128
|
+
durationMs: Date.now() - verifyStartedAt
|
|
129
|
+
});
|
|
130
|
+
results.push({
|
|
131
|
+
preset,
|
|
132
|
+
targetDir,
|
|
133
|
+
steps
|
|
134
|
+
});
|
|
135
|
+
const presetDurationMs = Date.now() - presetStartedAt;
|
|
136
|
+
process.stderr.write(`[scaffold-e2e] completed preset: ${preset} (${presetDurationMs}ms)
|
|
137
|
+
`);
|
|
138
|
+
}
|
|
139
|
+
return results;
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
export { resolveScaffoldCliEntry, resolveScaffoldE2EPresets, runScaffoldE2ESuite };
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { CliOutputMode } from "./outfitter-
|
|
1
|
+
import { CliOutputMode } from "./outfitter-fhahf9f3.js";
|
|
2
2
|
import { DocsExportTarget, loadDocsModule } from "./outfitter-1tfa9hke.js";
|
|
3
3
|
import { InternalError, Result } from "@outfitter/contracts";
|
|
4
4
|
/** Validated input for the docs.action handler. */
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { EngineOptions, PlaceholderValues, ScaffoldError } from "./outfitter-
|
|
1
|
+
import { EngineOptions, PlaceholderValues, ScaffoldError } from "./outfitter-crxe5gth.js";
|
|
2
2
|
import { Result } from "@outfitter/contracts";
|
|
3
3
|
/**
|
|
4
4
|
* Get the directory containing scaffold preset files.
|
|
@@ -8,6 +8,7 @@ declare function getPresetsBaseDir(): string;
|
|
|
8
8
|
declare function getOutputFilename(templateFilename: string): string;
|
|
9
9
|
declare function isBinaryFile(filename: string): boolean;
|
|
10
10
|
declare function replacePlaceholders(content: string, values: PlaceholderValues): string;
|
|
11
|
+
declare function sortLeadingImports(filePath: string, content: string): string;
|
|
11
12
|
declare function copyPresetFiles(presetDir: string, targetDir: string, values: PlaceholderValues, options: EngineOptions, copyOptions?: {
|
|
12
13
|
readonly allowOverwrite?: boolean;
|
|
13
14
|
readonly overwritablePaths?: ReadonlySet<string>;
|
|
@@ -15,4 +16,4 @@ declare function copyPresetFiles(presetDir: string, targetDir: string, values: P
|
|
|
15
16
|
readonly skipFilter?: (relativePath: string) => boolean;
|
|
16
17
|
readonly relativePrefix?: string;
|
|
17
18
|
}): Result<void, ScaffoldError>;
|
|
18
|
-
export { getPresetsBaseDir, getOutputFilename, isBinaryFile, replacePlaceholders, copyPresetFiles };
|
|
19
|
+
export { getPresetsBaseDir, getOutputFilename, isBinaryFile, replacePlaceholders, sortLeadingImports, copyPresetFiles };
|
|
@@ -12,7 +12,7 @@ function isBinaryPreset(preset) {
|
|
|
12
12
|
return preset === "cli" || preset === "daemon";
|
|
13
13
|
}
|
|
14
14
|
function isValidInitPreset(value) {
|
|
15
|
-
return value === "minimal" || value === "cli" || value === "mcp" || value === "daemon" || value === "library" || value === "full-stack";
|
|
15
|
+
return value === "minimal" || value === "basic" || value === "cli" || value === "mcp" || value === "daemon" || value === "library" || value === "full-stack";
|
|
16
16
|
}
|
|
17
17
|
function resolvePresetFromFlags(presetFromFlag, availablePresetIds) {
|
|
18
18
|
if (!presetFromFlag) {
|
|
@@ -2,6 +2,7 @@ import { OutputMode } from "@outfitter/cli/types";
|
|
|
2
2
|
import { Result } from "@outfitter/contracts";
|
|
3
3
|
/** Check bundle mode controlling which steps are included and whether a clean tree is enforced. */
|
|
4
4
|
type CheckOrchestratorMode = "all" | "ci" | "pre-commit" | "pre-push";
|
|
5
|
+
type CheckOrchestratorCommandProfile = "default" | "hook";
|
|
5
6
|
interface CheckOrchestratorStep {
|
|
6
7
|
readonly command: readonly string[];
|
|
7
8
|
readonly id: string;
|
|
@@ -9,11 +10,15 @@ interface CheckOrchestratorStep {
|
|
|
9
10
|
}
|
|
10
11
|
/** Options controlling which checks the orchestrator runs. */
|
|
11
12
|
interface CheckOrchestratorOptions {
|
|
13
|
+
/** Command profile for nested tool invocations. */
|
|
14
|
+
readonly commandProfile?: CheckOrchestratorCommandProfile;
|
|
12
15
|
/** Workspace root for resolving commands and tree-clean detection. */
|
|
13
16
|
readonly cwd: string;
|
|
14
17
|
readonly mode: CheckOrchestratorMode;
|
|
15
18
|
/** Staged file paths for pre-commit scoping. Ignored by other modes. */
|
|
16
19
|
readonly stagedFiles?: readonly string[];
|
|
20
|
+
/** Stream child process output to the terminal as each step runs. */
|
|
21
|
+
readonly streamOutput?: boolean;
|
|
17
22
|
}
|
|
18
23
|
interface CheckOrchestratorStepResult {
|
|
19
24
|
readonly command: readonly string[];
|
|
@@ -64,6 +69,7 @@ declare function parseTreePaths(statusOutput: string): string[];
|
|
|
64
69
|
declare function runCheckOrchestrator(options: CheckOrchestratorOptions): Promise<Result<CheckOrchestratorResult, CheckOrchestratorError>>;
|
|
65
70
|
interface PrintCheckOrchestratorResultsOptions {
|
|
66
71
|
readonly compact?: boolean;
|
|
72
|
+
readonly liveOutput?: boolean;
|
|
67
73
|
readonly mode?: OutputMode;
|
|
68
74
|
}
|
|
69
75
|
/**
|
|
@@ -7,7 +7,7 @@ import {
|
|
|
7
7
|
} from "./outfitter-5vx1bp7h.js";
|
|
8
8
|
import {
|
|
9
9
|
resolveStructuredOutputMode
|
|
10
|
-
} from "./outfitter-
|
|
10
|
+
} from "./outfitter-sxf8jjjn.js";
|
|
11
11
|
|
|
12
12
|
// apps/outfitter/src/commands/docs-api.ts
|
|
13
13
|
import { relative } from "path";
|
|
@@ -50,7 +50,7 @@ async function printDocsApiResults(result, options) {
|
|
|
50
50
|
});
|
|
51
51
|
process.stdout.write(filtered);
|
|
52
52
|
} else {
|
|
53
|
-
await output(result,
|
|
53
|
+
await output(result, structuredMode);
|
|
54
54
|
}
|
|
55
55
|
return;
|
|
56
56
|
}
|
|
@@ -59,7 +59,7 @@ async function printDocsApiResults(result, options) {
|
|
|
59
59
|
const totalDeclarations = result.summary.total;
|
|
60
60
|
if (totalDeclarations === 0) {
|
|
61
61
|
lines.push(theme.muted("No API declarations found."));
|
|
62
|
-
await output(lines,
|
|
62
|
+
await output(lines, "human");
|
|
63
63
|
return;
|
|
64
64
|
}
|
|
65
65
|
lines.push("");
|
|
@@ -87,7 +87,7 @@ async function printDocsApiResults(result, options) {
|
|
|
87
87
|
}
|
|
88
88
|
}
|
|
89
89
|
lines.push("");
|
|
90
|
-
await output(lines,
|
|
90
|
+
await output(lines, "human");
|
|
91
91
|
}
|
|
92
92
|
|
|
93
93
|
export { runDocsApi, printDocsApiResults };
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
// @bun
|
|
2
|
+
// apps/outfitter/src/scaffold-e2e/workspace.ts
|
|
3
|
+
import { existsSync, mkdirSync, readdirSync, rmSync } from "fs";
|
|
4
|
+
import { tmpdir } from "os";
|
|
5
|
+
import { join, resolve } from "path";
|
|
6
|
+
var SCAFFOLD_E2E_ROOT_NAME = "outfitter-scaffold-e2e";
|
|
7
|
+
var DEFAULT_SCAFFOLD_E2E_RETENTION_MS = 24 * 60 * 60 * 1000;
|
|
8
|
+
var RUN_DIR_NAME_PATTERN = /^(?<year>\d{4})(?<month>\d{2})(?<day>\d{2})T(?<hour>\d{2})(?<minute>\d{2})(?<second>\d{2})-(?<label>[a-z0-9-]+?)(?:-[0-9a-f-]+)?$/u;
|
|
9
|
+
function pad(value) {
|
|
10
|
+
return value.toString().padStart(2, "0");
|
|
11
|
+
}
|
|
12
|
+
function formatTimestamp(now) {
|
|
13
|
+
const date = new Date(now);
|
|
14
|
+
return [
|
|
15
|
+
date.getUTCFullYear().toString(),
|
|
16
|
+
pad(date.getUTCMonth() + 1),
|
|
17
|
+
pad(date.getUTCDate()),
|
|
18
|
+
"T",
|
|
19
|
+
pad(date.getUTCHours()),
|
|
20
|
+
pad(date.getUTCMinutes()),
|
|
21
|
+
pad(date.getUTCSeconds())
|
|
22
|
+
].join("");
|
|
23
|
+
}
|
|
24
|
+
function slugifyLabel(label) {
|
|
25
|
+
const normalized = (label ?? "run").toLowerCase().replace(/[^a-z0-9]+/gu, "-").replace(/^-+|-+$/gu, "");
|
|
26
|
+
return normalized.length > 0 ? normalized : "run";
|
|
27
|
+
}
|
|
28
|
+
function parseRunStart(name) {
|
|
29
|
+
const match = RUN_DIR_NAME_PATTERN.exec(name);
|
|
30
|
+
if (!match?.groups) {
|
|
31
|
+
return;
|
|
32
|
+
}
|
|
33
|
+
const { year, month, day, hour, minute, second } = match.groups;
|
|
34
|
+
return Date.UTC(Number(year), Number(month) - 1, Number(day), Number(hour), Number(minute), Number(second));
|
|
35
|
+
}
|
|
36
|
+
function resolveScaffoldE2ERoot(rootDir) {
|
|
37
|
+
return resolve(rootDir ?? join(tmpdir(), SCAFFOLD_E2E_ROOT_NAME));
|
|
38
|
+
}
|
|
39
|
+
function createScaffoldE2ERunDir(options = {}) {
|
|
40
|
+
const rootDir = resolveScaffoldE2ERoot(options.rootDir);
|
|
41
|
+
const timestamp = formatTimestamp(options.now ?? Date.now());
|
|
42
|
+
const label = slugifyLabel(options.runLabel);
|
|
43
|
+
const runId = Bun.randomUUIDv7().toLowerCase();
|
|
44
|
+
const runDir = join(rootDir, `${timestamp}-${label}-${runId}`);
|
|
45
|
+
mkdirSync(runDir, { recursive: true });
|
|
46
|
+
return runDir;
|
|
47
|
+
}
|
|
48
|
+
function cleanupScaffoldE2ERunDir(runDir) {
|
|
49
|
+
if (existsSync(runDir)) {
|
|
50
|
+
rmSync(runDir, { recursive: true, force: true });
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
function pruneScaffoldE2ERuns(options = {}) {
|
|
54
|
+
const rootDir = resolveScaffoldE2ERoot(options.rootDir);
|
|
55
|
+
const now = options.now ?? Date.now();
|
|
56
|
+
const maxAgeMs = options.maxAgeMs ?? DEFAULT_SCAFFOLD_E2E_RETENTION_MS;
|
|
57
|
+
const removed = [];
|
|
58
|
+
const kept = [];
|
|
59
|
+
if (!existsSync(rootDir)) {
|
|
60
|
+
return { rootDir, removed, kept };
|
|
61
|
+
}
|
|
62
|
+
for (const entry of readdirSync(rootDir, { withFileTypes: true })) {
|
|
63
|
+
if (!entry.isDirectory()) {
|
|
64
|
+
continue;
|
|
65
|
+
}
|
|
66
|
+
const startedAt = parseRunStart(entry.name);
|
|
67
|
+
if (startedAt === undefined) {
|
|
68
|
+
continue;
|
|
69
|
+
}
|
|
70
|
+
const path = join(rootDir, entry.name);
|
|
71
|
+
const ageMs = Math.max(0, now - startedAt);
|
|
72
|
+
const shouldRemove = options.removeAll === true || ageMs > maxAgeMs;
|
|
73
|
+
if (shouldRemove) {
|
|
74
|
+
cleanupScaffoldE2ERunDir(path);
|
|
75
|
+
removed.push({ path, ageMs });
|
|
76
|
+
continue;
|
|
77
|
+
}
|
|
78
|
+
kept.push({ path, ageMs });
|
|
79
|
+
}
|
|
80
|
+
return {
|
|
81
|
+
rootDir,
|
|
82
|
+
removed: removed.toSorted((left, right) => left.path.localeCompare(right.path)),
|
|
83
|
+
kept: kept.toSorted((left, right) => left.path.localeCompare(right.path))
|
|
84
|
+
};
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
export { SCAFFOLD_E2E_ROOT_NAME, DEFAULT_SCAFFOLD_E2E_RETENTION_MS, resolveScaffoldE2ERoot, createScaffoldE2ERunDir, cleanupScaffoldE2ERunDir, pruneScaffoldE2ERuns };
|
|
@@ -1,39 +1,40 @@
|
|
|
1
1
|
// @bun
|
|
2
2
|
import {
|
|
3
3
|
checkTsdocOutputSchema
|
|
4
|
-
} from "./outfitter-
|
|
5
|
-
import {
|
|
6
|
-
resolveDocsOutputMode
|
|
7
|
-
} from "./outfitter-ec83h4v2.js";
|
|
4
|
+
} from "./outfitter-dna8exj2.js";
|
|
8
5
|
import {
|
|
9
6
|
outputModeSchema,
|
|
10
7
|
resolveCwdFromPreset,
|
|
11
8
|
resolveStringFlag
|
|
12
|
-
} from "./outfitter-
|
|
9
|
+
} from "./outfitter-7t7ces1x.js";
|
|
13
10
|
import {
|
|
14
11
|
printDocsListResults,
|
|
15
12
|
runDocsList
|
|
16
|
-
} from "./outfitter-
|
|
13
|
+
} from "./outfitter-8jd1sak0.js";
|
|
17
14
|
import {
|
|
18
15
|
printDocsApiResults,
|
|
19
16
|
runDocsApi
|
|
20
|
-
} from "./outfitter-
|
|
17
|
+
} from "./outfitter-xqr4fp1n.js";
|
|
21
18
|
import {
|
|
22
19
|
printDocsSearchResults,
|
|
23
20
|
runDocsSearch
|
|
24
|
-
} from "./outfitter-
|
|
21
|
+
} from "./outfitter-sh015v8k.js";
|
|
25
22
|
import {
|
|
26
23
|
printDocsExportResults,
|
|
27
24
|
runDocsExport
|
|
28
|
-
} from "./outfitter-
|
|
25
|
+
} from "./outfitter-e44qcs0w.js";
|
|
29
26
|
import {
|
|
30
27
|
printDocsShowResults,
|
|
31
28
|
runDocsShow
|
|
32
|
-
} from "./outfitter-
|
|
29
|
+
} from "./outfitter-g6r9avgz.js";
|
|
33
30
|
|
|
34
31
|
// apps/outfitter/src/actions/docs.ts
|
|
35
32
|
import { cwdPreset } from "@outfitter/cli/flags";
|
|
36
|
-
import {
|
|
33
|
+
import {
|
|
34
|
+
jqPreset,
|
|
35
|
+
outputModePreset,
|
|
36
|
+
resolveOutputMode
|
|
37
|
+
} from "@outfitter/cli/query";
|
|
37
38
|
import { defineAction, Result } from "@outfitter/contracts";
|
|
38
39
|
import { z } from "zod";
|
|
39
40
|
var docsListInputSchema = z.object({
|
|
@@ -69,9 +70,8 @@ var docsListAction = defineAction({
|
|
|
69
70
|
...docsListCwd.options
|
|
70
71
|
],
|
|
71
72
|
mapInput: (context) => {
|
|
72
|
-
const { outputMode: presetOutputMode } = docsListOutputMode.resolve(context.flags);
|
|
73
73
|
const { jq } = docsListJq.resolve(context.flags);
|
|
74
|
-
const outputMode =
|
|
74
|
+
const { mode: outputMode } = resolveOutputMode(context.flags);
|
|
75
75
|
const kind = resolveStringFlag(context.flags["kind"]);
|
|
76
76
|
const pkg = resolveStringFlag(context.flags["package"]);
|
|
77
77
|
return {
|
|
@@ -117,9 +117,8 @@ var docsShowAction = defineAction({
|
|
|
117
117
|
...docsShowCwd.options
|
|
118
118
|
],
|
|
119
119
|
mapInput: (context) => {
|
|
120
|
-
const { outputMode: presetOutputMode } = docsShowOutputMode.resolve(context.flags);
|
|
121
120
|
const { jq } = docsShowJq.resolve(context.flags);
|
|
122
|
-
const outputMode =
|
|
121
|
+
const { mode: outputMode } = resolveOutputMode(context.flags);
|
|
123
122
|
return {
|
|
124
123
|
id: context.args[0],
|
|
125
124
|
cwd: resolveCwdFromPreset(context.flags, docsShowCwd),
|
|
@@ -172,9 +171,8 @@ var docsSearchAction = defineAction({
|
|
|
172
171
|
...docsSearchCwd.options
|
|
173
172
|
],
|
|
174
173
|
mapInput: (context) => {
|
|
175
|
-
const { outputMode: presetOutputMode } = docsSearchOutputMode.resolve(context.flags);
|
|
176
174
|
const { jq } = docsSearchJq.resolve(context.flags);
|
|
177
|
-
const outputMode =
|
|
175
|
+
const { mode: outputMode } = resolveOutputMode(context.flags);
|
|
178
176
|
const kind = resolveStringFlag(context.flags["kind"]);
|
|
179
177
|
const pkg = resolveStringFlag(context.flags["package"]);
|
|
180
178
|
return {
|
|
@@ -231,9 +229,8 @@ var docsApiAction = defineAction({
|
|
|
231
229
|
...docsApiCwd.options
|
|
232
230
|
],
|
|
233
231
|
mapInput: (context) => {
|
|
234
|
-
const { outputMode: presetOutputMode } = docsApiOutputMode.resolve(context.flags);
|
|
235
232
|
const { jq } = docsApiJq.resolve(context.flags);
|
|
236
|
-
const outputMode =
|
|
233
|
+
const { mode: outputMode } = resolveOutputMode(context.flags);
|
|
237
234
|
const levelRaw = context.flags["level"];
|
|
238
235
|
const validLevels = new Set(["documented", "partial", "undocumented"]);
|
|
239
236
|
const level = typeof levelRaw === "string" && validLevels.has(levelRaw) ? levelRaw : undefined;
|
|
@@ -300,8 +297,7 @@ var docsExportAction = defineAction({
|
|
|
300
297
|
...docsExportCwd.options
|
|
301
298
|
],
|
|
302
299
|
mapInput: (context) => {
|
|
303
|
-
const {
|
|
304
|
-
const outputMode = resolveDocsOutputMode(context.flags, presetOutputMode);
|
|
300
|
+
const { mode: outputMode } = resolveOutputMode(context.flags);
|
|
305
301
|
const targetRaw = resolveStringFlag(context.flags["target"]);
|
|
306
302
|
const target = targetRaw ?? "all";
|
|
307
303
|
return {
|
|
@@ -1,20 +1,20 @@
|
|
|
1
1
|
// @bun
|
|
2
2
|
import {
|
|
3
3
|
resolveStructuredOutputMode
|
|
4
|
-
} from "./outfitter-
|
|
4
|
+
} from "./outfitter-sxf8jjjn.js";
|
|
5
|
+
import {
|
|
6
|
+
DEPENDENCY_SECTIONS,
|
|
7
|
+
normalizeVersionRange
|
|
8
|
+
} from "./outfitter-hr4cvmjy.js";
|
|
5
9
|
|
|
6
10
|
// apps/outfitter/src/commands/check-preset-versions.ts
|
|
7
11
|
import { existsSync, readFileSync } from "fs";
|
|
8
12
|
import { join, resolve } from "path";
|
|
9
|
-
import { Result } from "@outfitter/contracts";
|
|
13
|
+
import { extractMessage, Result } from "@outfitter/contracts";
|
|
10
14
|
import { getResolvedVersions } from "@outfitter/presets";
|
|
11
15
|
import { isTypesBunVersionCompatible } from "@outfitter/tooling";
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
"devDependencies",
|
|
15
|
-
"peerDependencies",
|
|
16
|
-
"optionalDependencies"
|
|
17
|
-
];
|
|
16
|
+
import { isPlainObject } from "@outfitter/types";
|
|
17
|
+
var EXTERNAL_TEMPLATE_VERSION = "catalog:";
|
|
18
18
|
|
|
19
19
|
class CheckPresetVersionsError extends Error {
|
|
20
20
|
_tag = "CheckPresetVersionsError";
|
|
@@ -23,61 +23,49 @@ class CheckPresetVersionsError extends Error {
|
|
|
23
23
|
this.name = "CheckPresetVersionsError";
|
|
24
24
|
}
|
|
25
25
|
}
|
|
26
|
-
function isRecord(value) {
|
|
27
|
-
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
28
|
-
}
|
|
29
|
-
function normalizeVersionRange(version) {
|
|
30
|
-
const trimmed = version.trim();
|
|
31
|
-
const semverMatch = trimmed.match(/\d+\.\d+\.\d+(?:-[0-9A-Za-z.-]+)?/);
|
|
32
|
-
if (semverMatch) {
|
|
33
|
-
return semverMatch[0];
|
|
34
|
-
}
|
|
35
|
-
return trimmed.replace(/^[\^~>=<]+/, "");
|
|
36
|
-
}
|
|
37
26
|
function validatePresetDeps(workspaceRoot, resolvedVersions, problems) {
|
|
38
|
-
const
|
|
27
|
+
const presetRoot = "packages/presets/presets";
|
|
39
28
|
const glob = new Bun.Glob("**/package.json.template");
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
29
|
+
const absoluteRoot = join(workspaceRoot, presetRoot);
|
|
30
|
+
if (!existsSync(absoluteRoot)) {
|
|
31
|
+
problems.push(`Canonical presets root not found: ${presetRoot}`);
|
|
32
|
+
return;
|
|
33
|
+
}
|
|
34
|
+
for (const relativePath of glob.scanSync({
|
|
35
|
+
cwd: absoluteRoot,
|
|
36
|
+
absolute: false
|
|
37
|
+
})) {
|
|
38
|
+
const templatePath = join(presetRoot, relativePath);
|
|
39
|
+
const absoluteTemplatePath = join(absoluteRoot, relativePath);
|
|
40
|
+
const parsed = JSON.parse(readFileSync(absoluteTemplatePath, "utf-8"));
|
|
41
|
+
if (!isPlainObject(parsed)) {
|
|
43
42
|
continue;
|
|
44
43
|
}
|
|
45
|
-
for (const
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
})) {
|
|
49
|
-
const templatePath = join(rootPath, relativePath);
|
|
50
|
-
const absoluteTemplatePath = join(absoluteRoot, relativePath);
|
|
51
|
-
const parsed = JSON.parse(readFileSync(absoluteTemplatePath, "utf-8"));
|
|
52
|
-
if (!isRecord(parsed)) {
|
|
44
|
+
for (const section of DEPENDENCY_SECTIONS) {
|
|
45
|
+
const deps = parsed[section];
|
|
46
|
+
if (!isPlainObject(deps)) {
|
|
53
47
|
continue;
|
|
54
48
|
}
|
|
55
|
-
for (const
|
|
56
|
-
|
|
57
|
-
if (!isRecord(deps)) {
|
|
49
|
+
for (const [name, value] of Object.entries(deps)) {
|
|
50
|
+
if (typeof value !== "string") {
|
|
58
51
|
continue;
|
|
59
52
|
}
|
|
60
|
-
|
|
61
|
-
if (
|
|
62
|
-
|
|
63
|
-
}
|
|
64
|
-
if (name.startsWith("@outfitter/")) {
|
|
65
|
-
if (value !== "workspace:*") {
|
|
66
|
-
problems.push(`${templatePath}: ${name} must use workspace:* (found ${value})`);
|
|
67
|
-
}
|
|
68
|
-
continue;
|
|
69
|
-
}
|
|
70
|
-
if (name.includes("{{") || value.startsWith("workspace:")) {
|
|
71
|
-
continue;
|
|
72
|
-
}
|
|
73
|
-
const expected = resolvedVersions[name];
|
|
74
|
-
if (!expected) {
|
|
75
|
-
problems.push(`${templatePath}: external dependency "${name}" is not declared in @outfitter/presets`);
|
|
76
|
-
continue;
|
|
77
|
-
}
|
|
78
|
-
if (normalizeVersionRange(value) !== normalizeVersionRange(expected)) {
|
|
79
|
-
problems.push(`${templatePath}: ${name} expected ${expected} (found ${value})`);
|
|
53
|
+
if (name.startsWith("@outfitter/")) {
|
|
54
|
+
if (value !== "workspace:*") {
|
|
55
|
+
problems.push(`${templatePath}: ${name} must use workspace:* (found ${value})`);
|
|
80
56
|
}
|
|
57
|
+
continue;
|
|
58
|
+
}
|
|
59
|
+
if (name.includes("{{") || value.startsWith("workspace:")) {
|
|
60
|
+
continue;
|
|
61
|
+
}
|
|
62
|
+
const expected = resolvedVersions[name];
|
|
63
|
+
if (!expected) {
|
|
64
|
+
problems.push(`${templatePath}: external dependency "${name}" is not declared in @outfitter/presets`);
|
|
65
|
+
continue;
|
|
66
|
+
}
|
|
67
|
+
if (value !== EXTERNAL_TEMPLATE_VERSION) {
|
|
68
|
+
problems.push(`${templatePath}: ${name} must use ${EXTERNAL_TEMPLATE_VERSION} (found ${value})`);
|
|
81
69
|
}
|
|
82
70
|
}
|
|
83
71
|
}
|
|
@@ -93,20 +81,20 @@ function validateRegistryVersions(workspaceRoot, resolvedVersions, problems) {
|
|
|
93
81
|
problems.push(`Registry not found or unreadable: ${registryPath}`);
|
|
94
82
|
return;
|
|
95
83
|
}
|
|
96
|
-
if (!
|
|
84
|
+
if (!isPlainObject(registry)) {
|
|
97
85
|
problems.push(`Registry has invalid shape (expected object): ${registryPath}`);
|
|
98
86
|
return;
|
|
99
87
|
}
|
|
100
|
-
if (!
|
|
88
|
+
if (!isPlainObject(registry["blocks"])) {
|
|
101
89
|
problems.push(`Registry has invalid shape (missing object "blocks" field): ${registryPath}`);
|
|
102
90
|
return;
|
|
103
91
|
}
|
|
104
92
|
for (const [blockName, block] of Object.entries(registry["blocks"])) {
|
|
105
|
-
if (!
|
|
93
|
+
if (!isPlainObject(block)) {
|
|
106
94
|
continue;
|
|
107
95
|
}
|
|
108
96
|
const devDeps = block["devDependencies"];
|
|
109
|
-
if (!
|
|
97
|
+
if (!isPlainObject(devDeps)) {
|
|
110
98
|
continue;
|
|
111
99
|
}
|
|
112
100
|
for (const [name, value] of Object.entries(devDeps)) {
|
|
@@ -125,7 +113,7 @@ function validateRegistryVersions(workspaceRoot, resolvedVersions, problems) {
|
|
|
125
113
|
}
|
|
126
114
|
function readDependencyVersion(packageJson, section, name) {
|
|
127
115
|
const container = packageJson[section];
|
|
128
|
-
if (!
|
|
116
|
+
if (!isPlainObject(container)) {
|
|
129
117
|
return;
|
|
130
118
|
}
|
|
131
119
|
const value = container[name];
|
|
@@ -133,14 +121,26 @@ function readDependencyVersion(packageJson, section, name) {
|
|
|
133
121
|
}
|
|
134
122
|
function validateBunVersionConsistency(workspaceRoot, problems) {
|
|
135
123
|
const bunVersionPath = join(workspaceRoot, ".bun-version");
|
|
136
|
-
|
|
124
|
+
let bunVersionFile;
|
|
125
|
+
try {
|
|
126
|
+
bunVersionFile = readFileSync(bunVersionPath, "utf-8").trim();
|
|
127
|
+
} catch (error) {
|
|
128
|
+
problems.push(`.bun-version not found or unreadable: ${extractMessage(error)}`);
|
|
129
|
+
return;
|
|
130
|
+
}
|
|
137
131
|
const rootPackagePath = join(workspaceRoot, "package.json");
|
|
138
|
-
|
|
139
|
-
|
|
132
|
+
let parsedRootPackage;
|
|
133
|
+
try {
|
|
134
|
+
parsedRootPackage = JSON.parse(readFileSync(rootPackagePath, "utf-8"));
|
|
135
|
+
} catch (error) {
|
|
136
|
+
problems.push(`Root package.json could not be read or parsed: ${extractMessage(error)}`);
|
|
137
|
+
return;
|
|
138
|
+
}
|
|
139
|
+
if (!isPlainObject(parsedRootPackage)) {
|
|
140
140
|
return;
|
|
141
141
|
}
|
|
142
142
|
const engines = parsedRootPackage["engines"];
|
|
143
|
-
if (
|
|
143
|
+
if (isPlainObject(engines) && typeof engines["bun"] === "string") {
|
|
144
144
|
const engineBun = normalizeVersionRange(engines["bun"]);
|
|
145
145
|
if (engineBun !== bunVersionFile) {
|
|
146
146
|
problems.push(`Bun version drift: .bun-version is ${bunVersionFile} but engines.bun is ${engines["bun"]}`);
|
|
@@ -155,7 +155,7 @@ function validateBunVersionConsistency(workspaceRoot, problems) {
|
|
|
155
155
|
}
|
|
156
156
|
let bunTypesVersion;
|
|
157
157
|
const catalog = parsedRootPackage["catalog"];
|
|
158
|
-
if (
|
|
158
|
+
if (isPlainObject(catalog) && typeof catalog["@types/bun"] === "string") {
|
|
159
159
|
bunTypesVersion = catalog["@types/bun"];
|
|
160
160
|
}
|
|
161
161
|
if (!bunTypesVersion) {
|
|
@@ -219,8 +219,7 @@ async function runCheckPresetVersions(options) {
|
|
|
219
219
|
ok: problems.length === 0
|
|
220
220
|
});
|
|
221
221
|
} catch (error) {
|
|
222
|
-
|
|
223
|
-
return Result.err(new CheckPresetVersionsError(message));
|
|
222
|
+
return Result.err(new CheckPresetVersionsError(extractMessage(error)));
|
|
224
223
|
}
|
|
225
224
|
}
|
|
226
225
|
async function printCheckPresetVersionsResult(result, options) {
|
|
@@ -298,4 +297,4 @@ if (import.meta.main) {
|
|
|
298
297
|
});
|
|
299
298
|
}
|
|
300
299
|
|
|
301
|
-
export { CheckPresetVersionsError, runCheckPresetVersions, printCheckPresetVersionsResult, runCheckPresetVersionsFromArgv };
|
|
300
|
+
export { EXTERNAL_TEMPLATE_VERSION, CheckPresetVersionsError, validatePresetDeps, runCheckPresetVersions, printCheckPresetVersionsResult, runCheckPresetVersionsFromArgv };
|
package/dist/targets/index.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import "../shared/outfitter-y784nh31.js";
|
|
2
|
-
import { INIT_TARGET_IDS, READY_TARGET_IDS, SCAFFOLD_TARGET_IDS, TARGET_IDS, TARGET_REGISTRY, getInitTarget, getReadyTarget, getScaffoldTarget, getTarget, listTargets, resolvePlacement } from "../shared/outfitter-
|
|
3
|
-
import { TargetCategory, TargetDefinition, TargetId, TargetScope, TargetStatus } from "../shared/outfitter-
|
|
2
|
+
import { INIT_TARGET_IDS, READY_TARGET_IDS, SCAFFOLD_TARGET_IDS, TARGET_IDS, TARGET_REGISTRY, getInitTarget, getReadyTarget, getScaffoldTarget, getTarget, listTargets, resolvePlacement } from "../shared/outfitter-pw74st5t.js";
|
|
3
|
+
import { TargetCategory, TargetDefinition, TargetId, TargetScope, TargetStatus } from "../shared/outfitter-gsjbcta2.js";
|
|
4
4
|
export { resolvePlacement, listTargets, getTarget, getScaffoldTarget, getReadyTarget, getInitTarget, TargetStatus, TargetScope, TargetId, TargetDefinition, TargetCategory, TARGET_REGISTRY, TARGET_IDS, SCAFFOLD_TARGET_IDS, READY_TARGET_IDS, INIT_TARGET_IDS };
|