@geenius/release-toolkit 0.10.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/CHANGELOG.md +335 -0
- package/LICENSE +88 -0
- package/README.md +104 -0
- package/bin/geenius-release.js +5 -0
- package/dist/cli.js +6226 -0
- package/dist/cli.js.map +1 -0
- package/dist/index.d.ts +1401 -0
- package/dist/index.js +5256 -0
- package/dist/index.js.map +1 -0
- package/package.json +88 -0
- package/templates/husky/pre-push +11 -0
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,1401 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Public report shapes. Stable across versions — schema changes require a minor
|
|
5
|
+
* bump and an explicit CHANGELOG entry. Downstream consumers (CI integrations,
|
|
6
|
+
* coverage aggregators, gauntlet runners) parse these reports directly.
|
|
7
|
+
*/
|
|
8
|
+
type StepStatus = "passed" | "failed" | "skipped" | "missing" | "unauthenticated";
|
|
9
|
+
type CommandStatus = "passed" | "failed" | "skipped";
|
|
10
|
+
interface StepReport {
|
|
11
|
+
/** Human-readable step name, e.g. `"pnpm audit"`, `"osv-scanner"`, `"smoke @geenius/ai-magic/react"`. */
|
|
12
|
+
name: string;
|
|
13
|
+
status: StepStatus;
|
|
14
|
+
/** Short reason for non-passed states. */
|
|
15
|
+
reason?: string;
|
|
16
|
+
durationMs: number;
|
|
17
|
+
/** Last 4 KB of combined stdout/stderr; useful for triage without re-running. */
|
|
18
|
+
output?: string;
|
|
19
|
+
}
|
|
20
|
+
interface CommandReport {
|
|
21
|
+
/** Canonical command name (e.g. `"supply-chain"`, `"license"`). */
|
|
22
|
+
command: string;
|
|
23
|
+
status: CommandStatus;
|
|
24
|
+
/** ISO 8601 timestamp when the command started. */
|
|
25
|
+
startedAt: string;
|
|
26
|
+
durationMs: number;
|
|
27
|
+
steps: StepReport[];
|
|
28
|
+
/** Free-form metadata: package name, fixture id, version, etc. */
|
|
29
|
+
meta?: Record<string, unknown>;
|
|
30
|
+
}
|
|
31
|
+
/** Per-scanner runtime state. Distinct from `StepStatus` because a `missing`
|
|
32
|
+
* scanner is data, not failure, and the same `missing` value can map to
|
|
33
|
+
* different downstream behavior (`passed`/`skipped`/`failed`) depending on
|
|
34
|
+
* the scanner's `required` configuration.
|
|
35
|
+
*/
|
|
36
|
+
type ScannerState = {
|
|
37
|
+
kind: "passed";
|
|
38
|
+
output?: string;
|
|
39
|
+
} | {
|
|
40
|
+
kind: "failed";
|
|
41
|
+
reason: string;
|
|
42
|
+
output?: string;
|
|
43
|
+
} | {
|
|
44
|
+
kind: "missing";
|
|
45
|
+
reason: string;
|
|
46
|
+
} | {
|
|
47
|
+
kind: "unauthenticated";
|
|
48
|
+
reason: string;
|
|
49
|
+
};
|
|
50
|
+
|
|
51
|
+
/**
|
|
52
|
+
* `geenius-release a11y-report` — aggregate axe-core results that the package's
|
|
53
|
+
* a11y test run produced. Replaces 28 copies of `a11y-report.mjs`.
|
|
54
|
+
*
|
|
55
|
+
* Looks for a single JSON file at `.eval/a11y/results.json` (or the path
|
|
56
|
+
* passed via `--results`) containing the axe output. Reports the count of
|
|
57
|
+
* violations by severity. Fails when any violation at or above
|
|
58
|
+
* `failThreshold` exists (default: `serious`).
|
|
59
|
+
*/
|
|
60
|
+
|
|
61
|
+
type A11ySeverity = "minor" | "moderate" | "serious" | "critical";
|
|
62
|
+
interface RunA11yReportOptions {
|
|
63
|
+
cwd?: string;
|
|
64
|
+
/** Path to the axe results JSON. Default: `.eval/a11y/results.json`. */
|
|
65
|
+
resultsPath?: string;
|
|
66
|
+
/** Lowest severity that fails the report. Default: `serious`. */
|
|
67
|
+
failThreshold?: A11ySeverity;
|
|
68
|
+
/** Whether absent results is `failed` or `skipped`. */
|
|
69
|
+
optional?: boolean;
|
|
70
|
+
quiet?: boolean;
|
|
71
|
+
}
|
|
72
|
+
declare function runA11yReport(opts?: RunA11yReportOptions): Promise<CommandReport>;
|
|
73
|
+
|
|
74
|
+
/**
|
|
75
|
+
* `geenius-release attw` — run @arethetypeswrong/cli against the packed tarball.
|
|
76
|
+
* Replaces ~13 scripts across 3 filename variations (`run-attw.mjs`,
|
|
77
|
+
* `attw-packed.mjs`, `attw-check.mjs`).
|
|
78
|
+
*/
|
|
79
|
+
|
|
80
|
+
interface RunAttwOptions {
|
|
81
|
+
cwd?: string;
|
|
82
|
+
/** Allow attw to be missing without failing. */
|
|
83
|
+
optional?: boolean;
|
|
84
|
+
/** Comma list of attw `--ignore-rules` (e.g. `cjs-resolves-to-esm`). */
|
|
85
|
+
ignoreRules?: readonly string[];
|
|
86
|
+
/** Reuse a stable directory (relative to packageRoot) for the tarball
|
|
87
|
+
* instead of `mkdtempSync(os.tmpdir())`. Useful when concurrent pnpm
|
|
88
|
+
* installs in the global cache thrash mkdtemp creations. Default:
|
|
89
|
+
* undefined (use os.tmpdir). Common value: `.eval/attw-pack`. */
|
|
90
|
+
safePackDir?: string;
|
|
91
|
+
quiet?: boolean;
|
|
92
|
+
}
|
|
93
|
+
declare function runAttw(opts?: RunAttwOptions): Promise<CommandReport>;
|
|
94
|
+
|
|
95
|
+
/**
|
|
96
|
+
* `geenius-release bundle-budgets` — variants.json-native gzip bundle budgets.
|
|
97
|
+
*
|
|
98
|
+
* Replaces `scripts/check-bundle-budgets.mjs` (currently 1 copy in perf, but
|
|
99
|
+
* 8 packages declare `bundleBudget` in their variants.json: perf, agent,
|
|
100
|
+
* ai-magic, devtools, errors, onboarding, ui, tools-legacy — so the pattern
|
|
101
|
+
* is genuinely shared).
|
|
102
|
+
*
|
|
103
|
+
* For every implemented variant declaring `bundleBudget: "<n><unit>"`:
|
|
104
|
+
* 1. Gzip-sum every declared runtime asset (default: index.js + index.css)
|
|
105
|
+
* in <packageDir>/dist.
|
|
106
|
+
* 2. Compare against the parsed budget (b / kb / mb units).
|
|
107
|
+
* 3. Fail with a per-variant overshoot list on any violation.
|
|
108
|
+
*
|
|
109
|
+
* Distinct from `size-check` (which uses the external `size-limit` tool with
|
|
110
|
+
* its own config) and from `size-limit-config` (which generates a size-limit
|
|
111
|
+
* config from variants.json). This command is the lightweight, zero-extra-
|
|
112
|
+
* dependency path that just reads the manifest and the dist tree.
|
|
113
|
+
*/
|
|
114
|
+
interface RunBundleBudgetsOptions {
|
|
115
|
+
cwd?: string;
|
|
116
|
+
/** Runtime asset basenames to gzip-sum per variant (default: index.js, index.css). */
|
|
117
|
+
assets?: string[];
|
|
118
|
+
/** Only include variants flagged `implemented: true` (default: true). */
|
|
119
|
+
implementedOnly?: boolean;
|
|
120
|
+
/** Skip silently when no variant declares a budget. */
|
|
121
|
+
optional?: boolean;
|
|
122
|
+
}
|
|
123
|
+
interface BundleBudgetsResult {
|
|
124
|
+
status: "passed" | "failed" | "skipped";
|
|
125
|
+
exitCode: number;
|
|
126
|
+
rows: BudgetRow[];
|
|
127
|
+
failures: string[];
|
|
128
|
+
}
|
|
129
|
+
interface BudgetRow {
|
|
130
|
+
name: string;
|
|
131
|
+
packageDir: string;
|
|
132
|
+
budgetBytes: number;
|
|
133
|
+
gzipBytes: number;
|
|
134
|
+
uncompressedBytes: number;
|
|
135
|
+
assets: string[];
|
|
136
|
+
}
|
|
137
|
+
declare function runBundleBudgets(opts?: RunBundleBudgetsOptions): Promise<BundleBudgetsResult>;
|
|
138
|
+
|
|
139
|
+
/**
|
|
140
|
+
* `geenius-release convex-build` — build a Convex sub-package.
|
|
141
|
+
*
|
|
142
|
+
* Replaces the per-package `build: "node ../../scripts/geenius-convex-codegen.mjs --src src && tsup"`
|
|
143
|
+
* pattern (repeated across the 16 Convex-bearing packages).
|
|
144
|
+
*
|
|
145
|
+
* Equivalent to:
|
|
146
|
+
* geenius-release convex-codegen --src <src> # default: src/
|
|
147
|
+
* tsup
|
|
148
|
+
*
|
|
149
|
+
* Flags:
|
|
150
|
+
* --src <dir> Convex source dir (default: src)
|
|
151
|
+
* --no-codegen Skip codegen, just run tsup
|
|
152
|
+
* --no-build Run codegen only
|
|
153
|
+
* --clean Clean _generated/ instead of building
|
|
154
|
+
*/
|
|
155
|
+
interface RunConvexBuildOptions {
|
|
156
|
+
cwd?: string;
|
|
157
|
+
src?: string;
|
|
158
|
+
noCodegen?: boolean;
|
|
159
|
+
noBuild?: boolean;
|
|
160
|
+
clean?: boolean;
|
|
161
|
+
/** Builder to invoke (default: "tsup"). */
|
|
162
|
+
builder?: "tsup" | "tsc";
|
|
163
|
+
/** Extra args forwarded to the builder. */
|
|
164
|
+
passthrough?: string[];
|
|
165
|
+
}
|
|
166
|
+
interface ConvexBuildResult {
|
|
167
|
+
status: "passed" | "failed";
|
|
168
|
+
exitCode: number;
|
|
169
|
+
steps: {
|
|
170
|
+
name: string;
|
|
171
|
+
exitCode: number;
|
|
172
|
+
}[];
|
|
173
|
+
}
|
|
174
|
+
declare function runConvexBuild(opts?: RunConvexBuildOptions): Promise<ConvexBuildResult>;
|
|
175
|
+
|
|
176
|
+
/**
|
|
177
|
+
* `geenius-release convex-codegen` — generate `_generated/` shims for Convex
|
|
178
|
+
* variants.
|
|
179
|
+
*
|
|
180
|
+
* Promotes the standalone `geenius-convex-codegen` script (vendored in
|
|
181
|
+
* geenius-payments and shipped as a bin from geenius-db's convex subpackage)
|
|
182
|
+
* into a first-class toolkit command. All Convex-bearing packages can drop
|
|
183
|
+
* their per-package copy and call this instead.
|
|
184
|
+
*
|
|
185
|
+
* Behaviour:
|
|
186
|
+
* - Discovers the convex source dir by trying (in order):
|
|
187
|
+
* opts.src → packages/convex/src → src → cwd
|
|
188
|
+
* - Generates: server.js, server.d.ts, dataModel.d.ts, api.js, api.d.ts
|
|
189
|
+
* - `--check` mode: verify files are up to date; exit 1 if not.
|
|
190
|
+
* - `--clean` mode: delete `_generated/` and exit.
|
|
191
|
+
*/
|
|
192
|
+
interface RunConvexCodegenOptions {
|
|
193
|
+
cwd?: string;
|
|
194
|
+
/** Override source directory. */
|
|
195
|
+
src?: string;
|
|
196
|
+
/** Check-only — exit 1 if any file would be written/changed. */
|
|
197
|
+
check?: boolean;
|
|
198
|
+
/** Delete the _generated/ directory. */
|
|
199
|
+
clean?: boolean;
|
|
200
|
+
}
|
|
201
|
+
interface ConvexCodegenResult {
|
|
202
|
+
status: "passed" | "failed" | "skipped";
|
|
203
|
+
exitCode: number;
|
|
204
|
+
srcDir: string;
|
|
205
|
+
files: {
|
|
206
|
+
name: string;
|
|
207
|
+
status: "new" | "changed" | "unchanged";
|
|
208
|
+
}[];
|
|
209
|
+
modules: string[];
|
|
210
|
+
warnings: string[];
|
|
211
|
+
}
|
|
212
|
+
declare function runConvexCodegen(opts?: RunConvexCodegenOptions): Promise<ConvexCodegenResult>;
|
|
213
|
+
|
|
214
|
+
/**
|
|
215
|
+
* `geenius-release coverage` — canonical vitest --coverage runner.
|
|
216
|
+
*
|
|
217
|
+
* Collapses run-coverage.mjs (5) and the various ad-hoc vitest invocations.
|
|
218
|
+
*
|
|
219
|
+
* Behaviour:
|
|
220
|
+
* 1. Clean root + per-variant coverage/ directories.
|
|
221
|
+
* 2. Run `vitest run --coverage` at the root, excluding tests from any
|
|
222
|
+
* variant packages flagged as `separateCoverage: true` (or matching
|
|
223
|
+
* `--separate-coverage <framework>`).
|
|
224
|
+
* 3. For each separate-coverage package, run vitest inside that package
|
|
225
|
+
* directory so its own coverage report is emitted.
|
|
226
|
+
*
|
|
227
|
+
* Emits the same JSON shape downstream `coverage-report` expects.
|
|
228
|
+
*/
|
|
229
|
+
interface RunCoverageOptions {
|
|
230
|
+
cwd?: string;
|
|
231
|
+
/** Run separate vitest passes for variants whose framework matches. */
|
|
232
|
+
separateFrameworks?: string[];
|
|
233
|
+
/** Explicit list of packageDirs to run separately (overrides framework match). */
|
|
234
|
+
separatePackageDirs?: string[];
|
|
235
|
+
/** Skip the cleanup phase. */
|
|
236
|
+
noClean?: boolean;
|
|
237
|
+
/** Strict mode flag forwarded to tests via GEENIUS_COVERAGE_STRICT. */
|
|
238
|
+
strict?: boolean;
|
|
239
|
+
/** Extra args appended to every vitest call. */
|
|
240
|
+
passthrough?: string[];
|
|
241
|
+
}
|
|
242
|
+
interface CoverageResult {
|
|
243
|
+
status: "passed" | "failed" | "skipped";
|
|
244
|
+
exitCode: number;
|
|
245
|
+
passes: {
|
|
246
|
+
label: string;
|
|
247
|
+
cwd: string;
|
|
248
|
+
exitCode: number;
|
|
249
|
+
}[];
|
|
250
|
+
}
|
|
251
|
+
declare function runCoverage(opts?: RunCoverageOptions): Promise<CoverageResult>;
|
|
252
|
+
|
|
253
|
+
/**
|
|
254
|
+
* `geenius-release coverage-report` — aggregate the coverage summary that
|
|
255
|
+
* vitest (or any tool writing coverage-summary.json / coverage-final.json)
|
|
256
|
+
* produced. Replaces 36 copies of `coverage-report.mjs`.
|
|
257
|
+
*
|
|
258
|
+
* Reads `coverage/coverage-summary.json` (default v8/istanbul output path).
|
|
259
|
+
* Optional thresholds: minimum % lines / branches / functions / statements.
|
|
260
|
+
*/
|
|
261
|
+
|
|
262
|
+
interface CoverageThresholds {
|
|
263
|
+
lines?: number;
|
|
264
|
+
branches?: number;
|
|
265
|
+
functions?: number;
|
|
266
|
+
statements?: number;
|
|
267
|
+
}
|
|
268
|
+
interface RunCoverageReportOptions {
|
|
269
|
+
cwd?: string;
|
|
270
|
+
/** Path to coverage-summary.json. Default: `coverage/coverage-summary.json`. */
|
|
271
|
+
summaryPath?: string;
|
|
272
|
+
/** Minimum percentages. Default: pull from `coverage-thresholds.json` if present
|
|
273
|
+
* (legacy flat shape). When `thresholdFile` is set, the per-subpackage shape
|
|
274
|
+
* there takes precedence. */
|
|
275
|
+
thresholds?: CoverageThresholds;
|
|
276
|
+
/** Path to a richer per-subpackage threshold JSON (shape:
|
|
277
|
+
* `{ subpackages: { <name>: { thresholds: { lines, statements, branches, functions }, required?, kind? } } }`).
|
|
278
|
+
* When set, the toolkit emits per-subpackage results in addition to the
|
|
279
|
+
* totals row. Subpackages keyed by name look for `coverage/coverage-summary.json`
|
|
280
|
+
* files at `packages/<name>/coverage/`, `<name>/coverage/`, or matching prefix
|
|
281
|
+
* inside the root summary. */
|
|
282
|
+
thresholdFile?: string;
|
|
283
|
+
/** Write a Markdown report to this path. */
|
|
284
|
+
output?: string;
|
|
285
|
+
/** Write a structured JSON report to this path. */
|
|
286
|
+
json?: string;
|
|
287
|
+
/** Treat any subpackage below threshold as a failure (default: true when
|
|
288
|
+
* `thresholdFile` is set, false otherwise — matches legacy --fail-on-gaps
|
|
289
|
+
* flag in per-package scripts). */
|
|
290
|
+
failOnGaps?: boolean;
|
|
291
|
+
/** Whether absent coverage is `failed` (default) or `skipped`. */
|
|
292
|
+
optional?: boolean;
|
|
293
|
+
quiet?: boolean;
|
|
294
|
+
}
|
|
295
|
+
declare function runCoverageReport(opts?: RunCoverageReportOptions): Promise<CommandReport>;
|
|
296
|
+
|
|
297
|
+
/**
|
|
298
|
+
* `geenius-release db-migrations` — run migration tests across db-provider
|
|
299
|
+
* variants.
|
|
300
|
+
*
|
|
301
|
+
* Collapses db-migrations-check.mjs (4 packages). For every variant with
|
|
302
|
+
* kind `db-provider` and `tests.migrations: true`, runs:
|
|
303
|
+
* pnpm --filter ./<packageDir> test -- -t migration
|
|
304
|
+
*
|
|
305
|
+
* Fails fast on the first non-zero status by default.
|
|
306
|
+
*/
|
|
307
|
+
interface RunDbMigrationsOptions {
|
|
308
|
+
cwd?: string;
|
|
309
|
+
/** Only run providers whose name matches one of these. */
|
|
310
|
+
only?: string[];
|
|
311
|
+
/** Don't bail on first failure. */
|
|
312
|
+
continueOnFailure?: boolean;
|
|
313
|
+
/** Test-name pattern passed to vitest (default: "migration"). */
|
|
314
|
+
pattern?: string;
|
|
315
|
+
}
|
|
316
|
+
interface DbMigrationsResult {
|
|
317
|
+
status: "passed" | "failed" | "skipped";
|
|
318
|
+
exitCode: number;
|
|
319
|
+
ran: {
|
|
320
|
+
name: string;
|
|
321
|
+
packageDir: string;
|
|
322
|
+
exitCode: number;
|
|
323
|
+
}[];
|
|
324
|
+
}
|
|
325
|
+
declare function runDbMigrations(opts?: RunDbMigrationsOptions): Promise<DbMigrationsResult>;
|
|
326
|
+
|
|
327
|
+
/**
|
|
328
|
+
* `geenius-release diff-coverage` — changed-line coverage diff against a base
|
|
329
|
+
* git ref. Replaces 22 copies of `diff-coverage.mjs`.
|
|
330
|
+
*
|
|
331
|
+
* Computes which source lines were added or modified between `--base` (default
|
|
332
|
+
* `origin/main`) and `HEAD`, then walks the latest `coverage-final.json` to
|
|
333
|
+
* check whether every such line was hit. Fails if the changed-line coverage
|
|
334
|
+
* percentage falls below `--min`.
|
|
335
|
+
*/
|
|
336
|
+
|
|
337
|
+
interface RunDiffCoverageOptions {
|
|
338
|
+
cwd?: string;
|
|
339
|
+
/** Git ref to diff against. Default: `origin/main`. */
|
|
340
|
+
base?: string;
|
|
341
|
+
/** Path to vitest's coverage-final.json. Default: `coverage/coverage-final.json`. */
|
|
342
|
+
coveragePath?: string;
|
|
343
|
+
/** Minimum changed-line coverage % required to pass. Default: 80. */
|
|
344
|
+
min?: number;
|
|
345
|
+
/** When `process.env.CI === "true"`, use this threshold instead of `min`. */
|
|
346
|
+
minCi?: number;
|
|
347
|
+
/** When `process.env.CI` is unset/falsy, use this threshold. Overrides `min`
|
|
348
|
+
* for local runs. Common pattern: 0 locally + strict in CI. */
|
|
349
|
+
minLocal?: number;
|
|
350
|
+
/** Skip if coverage hasn't been run. Default: false. */
|
|
351
|
+
optional?: boolean;
|
|
352
|
+
quiet?: boolean;
|
|
353
|
+
}
|
|
354
|
+
declare function runDiffCoverage(opts?: RunDiffCoverageOptions): Promise<CommandReport>;
|
|
355
|
+
|
|
356
|
+
/**
|
|
357
|
+
* `geenius-release e2e` — canonical Playwright runner.
|
|
358
|
+
*
|
|
359
|
+
* Collapses e2e-runner.mjs (5) + playwright-projects.mjs (2).
|
|
360
|
+
*
|
|
361
|
+
* Responsibilities:
|
|
362
|
+
* 1. Reserve ephemeral ports per UI harness variant and inject them as
|
|
363
|
+
* `<PACKAGE>_E2E_<VARIANT>_PORT` env vars (mirroring the existing
|
|
364
|
+
* per-package e2e-runner pattern).
|
|
365
|
+
* 2. Derive `--project=<variantName>-<browser>` filters from variants.json
|
|
366
|
+
* when callers pass `--projects` or `--all-browsers`.
|
|
367
|
+
* 3. Forward all other args to `pnpm exec playwright test`.
|
|
368
|
+
*/
|
|
369
|
+
interface RunE2EOptions {
|
|
370
|
+
cwd?: string;
|
|
371
|
+
/** Emit `--project=<variant>-<browser>` projects for every e2e variant. */
|
|
372
|
+
projects?: boolean;
|
|
373
|
+
/** When true with projects, include every browser declared on each variant. */
|
|
374
|
+
allBrowsers?: boolean;
|
|
375
|
+
/** Specific browser to use (default: chromium) when --projects. */
|
|
376
|
+
browser?: string;
|
|
377
|
+
/** Env prefix for port vars. Default: derived from package.json name. */
|
|
378
|
+
envPrefix?: string;
|
|
379
|
+
/** Extra args forwarded to `playwright test`. */
|
|
380
|
+
passthrough?: string[];
|
|
381
|
+
/** Print resolved env + command and exit. */
|
|
382
|
+
print?: boolean;
|
|
383
|
+
}
|
|
384
|
+
interface E2EResult {
|
|
385
|
+
status: "passed" | "failed" | "skipped";
|
|
386
|
+
exitCode: number;
|
|
387
|
+
ports: Record<string, string>;
|
|
388
|
+
projects: string[];
|
|
389
|
+
}
|
|
390
|
+
declare function runE2E(opts?: RunE2EOptions): Promise<E2EResult>;
|
|
391
|
+
|
|
392
|
+
/**
|
|
393
|
+
* Configuration: schema, defaults, loader.
|
|
394
|
+
*
|
|
395
|
+
* The single Zod schema below is the source of truth for `release-toolkit.config.json`.
|
|
396
|
+
* Defaults are applied per-field so that an absent config file is equivalent to
|
|
397
|
+
* an empty `{}` — every consumer gets sensible behaviour out of the box.
|
|
398
|
+
*/
|
|
399
|
+
|
|
400
|
+
declare const ConfigSchema: z.ZodObject<{
|
|
401
|
+
$schema: z.ZodOptional<z.ZodString>;
|
|
402
|
+
variants: z.ZodDefault<z.ZodObject<{
|
|
403
|
+
include: z.ZodOptional<z.ZodArray<z.ZodString>>;
|
|
404
|
+
exclude: z.ZodOptional<z.ZodArray<z.ZodString>>;
|
|
405
|
+
}, z.core.$strict>>;
|
|
406
|
+
supplyChain: z.ZodDefault<z.ZodObject<{
|
|
407
|
+
scanners: z.ZodDefault<z.ZodObject<{
|
|
408
|
+
pnpmAudit: z.ZodDefault<z.ZodObject<{
|
|
409
|
+
required: z.ZodDefault<z.ZodBoolean>;
|
|
410
|
+
auditLevel: z.ZodDefault<z.ZodEnum<{
|
|
411
|
+
low: "low";
|
|
412
|
+
moderate: "moderate";
|
|
413
|
+
high: "high";
|
|
414
|
+
critical: "critical";
|
|
415
|
+
}>>;
|
|
416
|
+
scope: z.ZodDefault<z.ZodEnum<{
|
|
417
|
+
prod: "prod";
|
|
418
|
+
all: "all";
|
|
419
|
+
}>>;
|
|
420
|
+
skipIfMissing: z.ZodOptional<z.ZodEnum<{
|
|
421
|
+
silent: "silent";
|
|
422
|
+
info: "info";
|
|
423
|
+
warn: "warn";
|
|
424
|
+
}>>;
|
|
425
|
+
skipIfUnauthenticated: z.ZodOptional<z.ZodEnum<{
|
|
426
|
+
silent: "silent";
|
|
427
|
+
info: "info";
|
|
428
|
+
warn: "warn";
|
|
429
|
+
}>>;
|
|
430
|
+
}, z.core.$strict>>;
|
|
431
|
+
osvScanner: z.ZodDefault<z.ZodObject<{
|
|
432
|
+
required: z.ZodDefault<z.ZodBoolean>;
|
|
433
|
+
skipIfMissing: z.ZodDefault<z.ZodEnum<{
|
|
434
|
+
silent: "silent";
|
|
435
|
+
info: "info";
|
|
436
|
+
warn: "warn";
|
|
437
|
+
}>>;
|
|
438
|
+
skipIfUnauthenticated: z.ZodOptional<z.ZodEnum<{
|
|
439
|
+
silent: "silent";
|
|
440
|
+
info: "info";
|
|
441
|
+
warn: "warn";
|
|
442
|
+
}>>;
|
|
443
|
+
}, z.core.$strict>>;
|
|
444
|
+
socket: z.ZodDefault<z.ZodObject<{
|
|
445
|
+
required: z.ZodDefault<z.ZodBoolean>;
|
|
446
|
+
skipIfMissing: z.ZodDefault<z.ZodEnum<{
|
|
447
|
+
silent: "silent";
|
|
448
|
+
info: "info";
|
|
449
|
+
warn: "warn";
|
|
450
|
+
}>>;
|
|
451
|
+
skipIfUnauthenticated: z.ZodDefault<z.ZodEnum<{
|
|
452
|
+
silent: "silent";
|
|
453
|
+
info: "info";
|
|
454
|
+
warn: "warn";
|
|
455
|
+
}>>;
|
|
456
|
+
}, z.core.$strict>>;
|
|
457
|
+
license: z.ZodDefault<z.ZodObject<{
|
|
458
|
+
required: z.ZodDefault<z.ZodBoolean>;
|
|
459
|
+
skipIfMissing: z.ZodOptional<z.ZodEnum<{
|
|
460
|
+
silent: "silent";
|
|
461
|
+
info: "info";
|
|
462
|
+
warn: "warn";
|
|
463
|
+
}>>;
|
|
464
|
+
skipIfUnauthenticated: z.ZodOptional<z.ZodEnum<{
|
|
465
|
+
silent: "silent";
|
|
466
|
+
info: "info";
|
|
467
|
+
warn: "warn";
|
|
468
|
+
}>>;
|
|
469
|
+
}, z.core.$strict>>;
|
|
470
|
+
}, z.core.$strict>>;
|
|
471
|
+
}, z.core.$strict>>;
|
|
472
|
+
license: z.ZodDefault<z.ZodObject<{
|
|
473
|
+
scope: z.ZodDefault<z.ZodEnum<{
|
|
474
|
+
prod: "prod";
|
|
475
|
+
all: "all";
|
|
476
|
+
}>>;
|
|
477
|
+
forbidden: z.ZodDefault<z.ZodArray<z.ZodString>>;
|
|
478
|
+
allowlist: z.ZodDefault<z.ZodArray<z.ZodString>>;
|
|
479
|
+
unknownPolicy: z.ZodDefault<z.ZodEnum<{
|
|
480
|
+
warn: "warn";
|
|
481
|
+
pass: "pass";
|
|
482
|
+
fail: "fail";
|
|
483
|
+
}>>;
|
|
484
|
+
}, z.core.$strict>>;
|
|
485
|
+
sbom: z.ZodDefault<z.ZodObject<{
|
|
486
|
+
format: z.ZodDefault<z.ZodEnum<{
|
|
487
|
+
"cyclonedx-json": "cyclonedx-json";
|
|
488
|
+
"spdx-json": "spdx-json";
|
|
489
|
+
}>>;
|
|
490
|
+
out: z.ZodDefault<z.ZodString>;
|
|
491
|
+
}, z.core.$strict>>;
|
|
492
|
+
smokePacked: z.ZodDefault<z.ZodObject<{
|
|
493
|
+
subpathsFromExports: z.ZodDefault<z.ZodBoolean>;
|
|
494
|
+
extraSubpaths: z.ZodDefault<z.ZodArray<z.ZodString>>;
|
|
495
|
+
timeoutMs: z.ZodDefault<z.ZodNumber>;
|
|
496
|
+
checkExportsOnDisk: z.ZodDefault<z.ZodBoolean>;
|
|
497
|
+
checkTarballPurity: z.ZodDefault<z.ZodString>;
|
|
498
|
+
checkStylesheets: z.ZodDefault<z.ZodBoolean>;
|
|
499
|
+
browserConditions: z.ZodDefault<z.ZodBoolean>;
|
|
500
|
+
domStubs: z.ZodDefault<z.ZodBoolean>;
|
|
501
|
+
injectDeps: z.ZodDefault<z.ZodArray<z.ZodString>>;
|
|
502
|
+
}, z.core.$strict>>;
|
|
503
|
+
publint: z.ZodDefault<z.ZodObject<{
|
|
504
|
+
allowSourceTimeLinks: z.ZodDefault<z.ZodBoolean>;
|
|
505
|
+
sourceLinkScope: z.ZodDefault<z.ZodString>;
|
|
506
|
+
}, z.core.$strict>>;
|
|
507
|
+
rewriteImports: z.ZodDefault<z.ZodObject<{
|
|
508
|
+
rules: z.ZodDefault<z.ZodArray<z.ZodObject<{
|
|
509
|
+
match: z.ZodString;
|
|
510
|
+
replaceWith: z.ZodString;
|
|
511
|
+
literal: z.ZodOptional<z.ZodBoolean>;
|
|
512
|
+
quoted: z.ZodOptional<z.ZodBoolean>;
|
|
513
|
+
}, z.core.$strict>>>;
|
|
514
|
+
frameworkDetect: z.ZodDefault<z.ZodRecord<z.ZodString, z.ZodString>>;
|
|
515
|
+
extensions: z.ZodDefault<z.ZodArray<z.ZodString>>;
|
|
516
|
+
deriveFromExports: z.ZodDefault<z.ZodBoolean>;
|
|
517
|
+
}, z.core.$strict>>;
|
|
518
|
+
gauntlet: z.ZodDefault<z.ZodObject<{
|
|
519
|
+
steps: z.ZodDefault<z.ZodArray<z.ZodString>>;
|
|
520
|
+
continueOnFailure: z.ZodDefault<z.ZodBoolean>;
|
|
521
|
+
siblingDistFreshness: z.ZodDefault<z.ZodEnum<{
|
|
522
|
+
check: "check";
|
|
523
|
+
off: "off";
|
|
524
|
+
build: "build";
|
|
525
|
+
}>>;
|
|
526
|
+
}, z.core.$strict>>;
|
|
527
|
+
}, z.core.$strict>;
|
|
528
|
+
type Config = z.infer<typeof ConfigSchema>;
|
|
529
|
+
interface LoadedConfig {
|
|
530
|
+
config: Config;
|
|
531
|
+
/** Absolute path to the config file that was read, or `null` if defaults were used. */
|
|
532
|
+
filePath: string | null;
|
|
533
|
+
}
|
|
534
|
+
/**
|
|
535
|
+
* Read `release-toolkit.config.json` if present; merge with defaults via Zod's
|
|
536
|
+
* `default()` mechanism. Missing config file is not an error.
|
|
537
|
+
*/
|
|
538
|
+
declare function loadConfig(packageRoot: string): LoadedConfig;
|
|
539
|
+
|
|
540
|
+
/**
|
|
541
|
+
* `geenius-release gauntlet` — compose the configured step sequence.
|
|
542
|
+
*
|
|
543
|
+
* External steps (`lint`, `type-check`, `test:unit`, anything else) shell out
|
|
544
|
+
* to `pnpm <step>` so existing per-package scripts continue to work.
|
|
545
|
+
*
|
|
546
|
+
* Internal steps (`supply-chain`, `license`, `sbom`, `smoke-packed`) call the
|
|
547
|
+
* toolkit's `runX` functions directly — no `pnpm` overhead, full structured
|
|
548
|
+
* report aggregation.
|
|
549
|
+
*/
|
|
550
|
+
|
|
551
|
+
interface RunGauntletOptions {
|
|
552
|
+
cwd?: string;
|
|
553
|
+
config?: Config;
|
|
554
|
+
/** Override the step list. */
|
|
555
|
+
steps?: readonly string[];
|
|
556
|
+
/** Continue running remaining steps after a failure. */
|
|
557
|
+
continueOnFailure?: boolean;
|
|
558
|
+
quiet?: boolean;
|
|
559
|
+
}
|
|
560
|
+
declare function runGauntlet(opts?: RunGauntletOptions): Promise<CommandReport>;
|
|
561
|
+
|
|
562
|
+
/**
|
|
563
|
+
* `geenius-release license` — forbidden-license scan over installed dependencies.
|
|
564
|
+
* Replaces the 36 copies of `license-check.mjs` across the ecosystem.
|
|
565
|
+
*/
|
|
566
|
+
|
|
567
|
+
interface RunLicenseOptions {
|
|
568
|
+
/** Defaults to `process.cwd()` if omitted. */
|
|
569
|
+
cwd?: string;
|
|
570
|
+
/** Override loaded config. */
|
|
571
|
+
config?: Config["license"];
|
|
572
|
+
/** Override the dependency scope. */
|
|
573
|
+
scope?: "prod" | "all";
|
|
574
|
+
/** Suppress console output (for gauntlet composition). */
|
|
575
|
+
quiet?: boolean;
|
|
576
|
+
}
|
|
577
|
+
declare function runLicense(opts?: RunLicenseOptions): Promise<CommandReport>;
|
|
578
|
+
|
|
579
|
+
/**
|
|
580
|
+
* `geenius-release lint` — single canonical lint entry point.
|
|
581
|
+
*
|
|
582
|
+
* Collapses run-lint.mjs (9 pkgs) + lint-apps.mjs (4) + lint-scope.mjs (3) +
|
|
583
|
+
* biome-scope.mjs (5) + lint-pub.mjs (7) etc.
|
|
584
|
+
*
|
|
585
|
+
* Modes:
|
|
586
|
+
* default (root): root files + every in-scope variant's packageDir, plus
|
|
587
|
+
* discovered apps/ directories if any exist.
|
|
588
|
+
* --scope package: root files + variant packageDirs only.
|
|
589
|
+
* --scope apps: apps/* dirs derived from ui+storybook+e2e variants only.
|
|
590
|
+
* --scope all: everything (default behaviour, kept explicit).
|
|
591
|
+
* --apps: shortcut for --scope apps.
|
|
592
|
+
*
|
|
593
|
+
* Always invokes `biome check` (or `biome lint`/`biome format` via --command).
|
|
594
|
+
* Extra args after `--` (collected into passthrough) are forwarded.
|
|
595
|
+
*/
|
|
596
|
+
type LintScope = "package" | "apps" | "all";
|
|
597
|
+
interface RunLintOptions {
|
|
598
|
+
cwd?: string;
|
|
599
|
+
scope?: LintScope;
|
|
600
|
+
/** Biome subcommand (default "check"). */
|
|
601
|
+
command?: "check" | "lint" | "format" | "ci";
|
|
602
|
+
/** Apply autofixes (`--write`). */
|
|
603
|
+
fix?: boolean;
|
|
604
|
+
/** Extra args forwarded to biome after the path list. */
|
|
605
|
+
passthrough?: string[];
|
|
606
|
+
/** Print the resolved command and exit. */
|
|
607
|
+
print?: boolean;
|
|
608
|
+
/** Limit variant collection to `implemented: true` variants. */
|
|
609
|
+
implementedOnly?: boolean;
|
|
610
|
+
}
|
|
611
|
+
interface LintResult {
|
|
612
|
+
status: "passed" | "failed" | "skipped";
|
|
613
|
+
command: string;
|
|
614
|
+
paths: string[];
|
|
615
|
+
exitCode: number;
|
|
616
|
+
}
|
|
617
|
+
declare function runLint(opts?: RunLintOptions): Promise<LintResult>;
|
|
618
|
+
|
|
619
|
+
/**
|
|
620
|
+
* `geenius-release manifest-contract` — verify that every `package.json:exports`
|
|
621
|
+
* target file exists on disk, that `files` patterns cover every export target,
|
|
622
|
+
* and that `bin` entries exist + are executable.
|
|
623
|
+
*
|
|
624
|
+
* Absorbs the inline `test -f dist/index.js && test -f dist/index.d.ts` checks
|
|
625
|
+
* scattered across packages (e.g. tools/devtools' `test:dist-contract`).
|
|
626
|
+
*/
|
|
627
|
+
|
|
628
|
+
interface RunManifestContractOptions {
|
|
629
|
+
cwd?: string;
|
|
630
|
+
quiet?: boolean;
|
|
631
|
+
}
|
|
632
|
+
declare function runManifestContract(opts?: RunManifestContractOptions): Promise<CommandReport>;
|
|
633
|
+
|
|
634
|
+
/**
|
|
635
|
+
* `geenius-release mutation-report` — Stryker driver. Replaces 36 copies of
|
|
636
|
+
* `mutation-report.mjs`. Optional by default: if Stryker isn't installed or
|
|
637
|
+
* configured, the command skips cleanly.
|
|
638
|
+
*/
|
|
639
|
+
|
|
640
|
+
interface RunMutationReportOptions {
|
|
641
|
+
cwd?: string;
|
|
642
|
+
/** When true (default), missing Stryker config → skipped (not failed). */
|
|
643
|
+
optional?: boolean;
|
|
644
|
+
/** Minimum mutation score required to pass (0-100). */
|
|
645
|
+
minScore?: number;
|
|
646
|
+
/** Just verify a Stryker config exists; do not invoke Stryker. */
|
|
647
|
+
checkConfigOnly?: boolean;
|
|
648
|
+
/** Fall back to `pnpm dlx --package <spec> -c "stryker run"` when the
|
|
649
|
+
* package's local @stryker-mutator/core isn't installed. Common form:
|
|
650
|
+
* `@stryker-mutator/core@9.5.0`. */
|
|
651
|
+
dlxSpec?: string;
|
|
652
|
+
/** Write a Markdown summary to this path. */
|
|
653
|
+
markdownOut?: string;
|
|
654
|
+
/** Write a structured JSON summary to this path. */
|
|
655
|
+
jsonOut?: string;
|
|
656
|
+
/** Where Stryker writes its raw report. Used to compute a fallback score
|
|
657
|
+
* if the run didn't print "Final mutation testing score" on stdout.
|
|
658
|
+
* Default: `.eval/mutation/mutation.json`. */
|
|
659
|
+
reportJsonPath?: string;
|
|
660
|
+
quiet?: boolean;
|
|
661
|
+
}
|
|
662
|
+
declare function runMutationReport(opts?: RunMutationReportOptions): Promise<CommandReport>;
|
|
663
|
+
|
|
664
|
+
/**
|
|
665
|
+
* `geenius-release pack-contract` — run `pnpm pack --json`, capture the
|
|
666
|
+
* resulting manifest into a temp directory, expose the path via
|
|
667
|
+
* `PACK_CONTRACT_JSON`, then run a consumer-supplied vitest config that
|
|
668
|
+
* asserts on the packed contents (files included, exports targets, README
|
|
669
|
+
* present, etc.).
|
|
670
|
+
*
|
|
671
|
+
* Generic harness — the actual contract tests are package-specific. The
|
|
672
|
+
* caller passes `--test-config <vitest.pack-contract.config.ts>`.
|
|
673
|
+
*
|
|
674
|
+
* Replaces local `scripts/pack-contract.mjs` shims.
|
|
675
|
+
*/
|
|
676
|
+
interface RunPackContractOptions {
|
|
677
|
+
cwd?: string;
|
|
678
|
+
/** Vitest config that runs the contract assertions. Required. */
|
|
679
|
+
testConfig: string;
|
|
680
|
+
/** Pass an existing pack JSON instead of running `pnpm pack` first. */
|
|
681
|
+
packJson?: string;
|
|
682
|
+
/** Tests to run (passed to vitest as positional args). */
|
|
683
|
+
testFiles?: readonly string[];
|
|
684
|
+
}
|
|
685
|
+
interface PackContractResult {
|
|
686
|
+
status: number;
|
|
687
|
+
packJsonPath: string;
|
|
688
|
+
}
|
|
689
|
+
declare function runPackContract(opts: RunPackContractOptions): PackContractResult;
|
|
690
|
+
|
|
691
|
+
/**
|
|
692
|
+
* `geenius-release patch-dts` — post-build patcher for dist outputs.
|
|
693
|
+
*
|
|
694
|
+
* Collapses patch-dts-imports.mjs (4) + patch-solid-web-import.mjs (2) +
|
|
695
|
+
* the `--fix-solid-jsx-runtime` flag previously embedded in sanitize-dist.
|
|
696
|
+
*
|
|
697
|
+
* Operations (composable; pass any combination):
|
|
698
|
+
* --rewrite <from=to> Plain string replaceAll in .d.ts files (repeatable).
|
|
699
|
+
* --solid Rewrite solid-js/web → solid-js/web/dist/web.js and
|
|
700
|
+
* gate delegateEvents() on a window check, in .js files.
|
|
701
|
+
* --solid-jsx Rewrite solid-js/jsx-runtime → solid-js/h/jsx-runtime
|
|
702
|
+
* in .js files.
|
|
703
|
+
* --files <list> Operate on an explicit file list instead of walking
|
|
704
|
+
* a directory.
|
|
705
|
+
*
|
|
706
|
+
* Default directory is `dist/`. Walks recursively; only touches `.d.ts` for
|
|
707
|
+
* --rewrite, only `.js`/`.mjs`/`.cjs` for the --solid* flags.
|
|
708
|
+
*/
|
|
709
|
+
interface DtsRewriteRule {
|
|
710
|
+
from: string;
|
|
711
|
+
to: string;
|
|
712
|
+
}
|
|
713
|
+
interface RunPatchDtsOptions {
|
|
714
|
+
cwd?: string;
|
|
715
|
+
/** Directory to walk (default: "dist"). Ignored when `files` is provided. */
|
|
716
|
+
dir?: string;
|
|
717
|
+
/** Explicit file list (absolute or relative to cwd). */
|
|
718
|
+
files?: string[];
|
|
719
|
+
/** Plain string replacements applied to .d.ts files. */
|
|
720
|
+
rewrites?: DtsRewriteRule[];
|
|
721
|
+
/** Apply Solid web import + delegateEvents patch to .js files. */
|
|
722
|
+
solid?: boolean;
|
|
723
|
+
/** Rewrite solid-js/jsx-runtime → solid-js/h/jsx-runtime in .js files. */
|
|
724
|
+
solidJsx?: boolean;
|
|
725
|
+
}
|
|
726
|
+
interface PatchDtsResult {
|
|
727
|
+
status: "passed" | "skipped";
|
|
728
|
+
filesChanged: number;
|
|
729
|
+
filesScanned: number;
|
|
730
|
+
}
|
|
731
|
+
declare function runPatchDts(opts?: RunPatchDtsOptions): Promise<PatchDtsResult>;
|
|
732
|
+
|
|
733
|
+
/**
|
|
734
|
+
* `geenius-release perf-smoke` — perf-budget harness wrapper.
|
|
735
|
+
* Absorbs 7 copies of `perf-smoke.mjs`.
|
|
736
|
+
*
|
|
737
|
+
* Reads `.eval/perf/results.json` produced by the package's perf harness
|
|
738
|
+
* (Storybook perf stories, vitest perf suite, custom Playwright harness — the
|
|
739
|
+
* toolkit doesn't care how the file got there) and enforces budgets from
|
|
740
|
+
* `release-toolkit.config.json:perf` or `perf-budgets.json` at the package
|
|
741
|
+
* root.
|
|
742
|
+
*/
|
|
743
|
+
|
|
744
|
+
interface PerfBudget {
|
|
745
|
+
/** Symbolic metric name; matches the result file's `metric` field. */
|
|
746
|
+
metric: string;
|
|
747
|
+
/** Numerical maximum (e.g. 250 for "max 250 ms"). */
|
|
748
|
+
max: number;
|
|
749
|
+
/** Optional unit label for the report, e.g. "ms", "ops/s". */
|
|
750
|
+
unit?: string;
|
|
751
|
+
/** When set, this metric is a minimum (e.g. ops/sec) rather than a maximum. */
|
|
752
|
+
isMinimum?: boolean;
|
|
753
|
+
}
|
|
754
|
+
interface RunPerfSmokeOptions {
|
|
755
|
+
cwd?: string;
|
|
756
|
+
/** Path to the perf results JSON. Default: `.eval/perf/results.json`. */
|
|
757
|
+
resultsPath?: string;
|
|
758
|
+
/** Budget list. If absent, the toolkit reads `perf-budgets.json` at the
|
|
759
|
+
* package root, then falls back to "no enforced budgets". */
|
|
760
|
+
budgets?: readonly PerfBudget[];
|
|
761
|
+
/** Whether absent results is `failed` or `skipped`. */
|
|
762
|
+
optional?: boolean;
|
|
763
|
+
quiet?: boolean;
|
|
764
|
+
}
|
|
765
|
+
declare function runPerfSmoke(opts?: RunPerfSmokeOptions): Promise<CommandReport>;
|
|
766
|
+
|
|
767
|
+
/**
|
|
768
|
+
* `geenius-release pnpm-filters` — run a per-package script across the variant
|
|
769
|
+
* matrix.
|
|
770
|
+
*
|
|
771
|
+
* **The name is historical.** Earlier versions shelled out to
|
|
772
|
+
* `pnpm -r --filter ... <task>`. This version skips pnpm entirely and spawns
|
|
773
|
+
* each variant's `scripts.<task>` directly via `/bin/sh -c <cmd>`, which:
|
|
774
|
+
*
|
|
775
|
+
* - eliminates the ~100-300ms pnpm bootstrap per package (critical when
|
|
776
|
+
* fanning out 16 variants × 20 parallel agents);
|
|
777
|
+
* - keeps `package.json` script semantics intact (shell pipes, &&, env
|
|
778
|
+
* substitution all work because we hand the raw command to sh);
|
|
779
|
+
* - augments PATH with each variant's `node_modules/.bin` and every
|
|
780
|
+
* ancestor `node_modules/.bin` so locally-installed tools resolve the
|
|
781
|
+
* same way pnpm exec would have resolved them.
|
|
782
|
+
*
|
|
783
|
+
* Execution modes (CLI surface is unchanged from the pnpm-era):
|
|
784
|
+
* - **parallel** (default): launch all variants concurrently, optionally
|
|
785
|
+
* capped by `--workspace-concurrency=N`. Stdout/stderr prefixed per pkg.
|
|
786
|
+
* - **sequential**: one variant at a time, optional shared-first + kind
|
|
787
|
+
* tiering + heartbeat.
|
|
788
|
+
* - **shared-then-parallel**: shared first sequentially, then everything
|
|
789
|
+
* else in parallel.
|
|
790
|
+
*
|
|
791
|
+
* `--prebuild <dir>` runs `<dir>`'s `build` script (always `build`, not the
|
|
792
|
+
* requested task) before the main fan-out, and removes `<dir>` from the main
|
|
793
|
+
* fan-out when task is also build.
|
|
794
|
+
*/
|
|
795
|
+
interface RunPnpmFiltersOptions {
|
|
796
|
+
cwd?: string;
|
|
797
|
+
task: string;
|
|
798
|
+
includeMissing?: boolean;
|
|
799
|
+
/** Limit fan-out to variants flagged `implemented: true`. */
|
|
800
|
+
implementedOnly?: boolean;
|
|
801
|
+
/** Skip variants whose package.json has no entry for `task` (default: true). */
|
|
802
|
+
ifPresent?: boolean;
|
|
803
|
+
/** Force unbounded parallelism (alias for `workspaceConcurrency: undefined`). */
|
|
804
|
+
parallel?: boolean;
|
|
805
|
+
/** Cap concurrent in-flight spawns in parallel mode (string for CLI parity). */
|
|
806
|
+
workspaceConcurrency?: string;
|
|
807
|
+
/** Print the resolved per-variant invocations and exit (no spawns). */
|
|
808
|
+
print?: boolean;
|
|
809
|
+
kinds?: readonly string[];
|
|
810
|
+
/** Forward extra arguments after the script body. Joined with space and
|
|
811
|
+
* appended; the package script receives them via `$@`-like shell expansion. */
|
|
812
|
+
passthrough?: readonly string[];
|
|
813
|
+
/** Filter variants to those declaring `variant.tests.<key> === true`. */
|
|
814
|
+
requires?: readonly string[];
|
|
815
|
+
/** Sequential mode (one variant at a time). Overrides --parallel. */
|
|
816
|
+
sequential?: boolean;
|
|
817
|
+
/** Execution mode (takes precedence over `sequential`/`parallel`). */
|
|
818
|
+
mode?: "parallel" | "sequential" | "shared-then-parallel";
|
|
819
|
+
/** When sequential or shared-then-parallel, run this packageDir first. */
|
|
820
|
+
sharedFirst?: string;
|
|
821
|
+
/** Heartbeat interval (ms) when sequential, so CI doesn't kill a quiet job. */
|
|
822
|
+
heartbeatMs?: number;
|
|
823
|
+
/** Order variant kinds into tiers (sequential mode only). */
|
|
824
|
+
sequentialKindOrder?: readonly (readonly string[])[];
|
|
825
|
+
/** Build `<dir>` (always `build`, not the requested task) before main fan-out.
|
|
826
|
+
* When `task === "build"`, the main fan-out excludes `<dir>`. */
|
|
827
|
+
prebuild?: string;
|
|
828
|
+
}
|
|
829
|
+
interface PnpmFiltersResult {
|
|
830
|
+
status: number;
|
|
831
|
+
/** Per-variant resolved invocations. Each entry: `[label, command]`. */
|
|
832
|
+
invocations: {
|
|
833
|
+
label: string;
|
|
834
|
+
cwd: string;
|
|
835
|
+
command: string;
|
|
836
|
+
}[];
|
|
837
|
+
}
|
|
838
|
+
declare function runPnpmFilters(opts: RunPnpmFiltersOptions): Promise<PnpmFiltersResult>;
|
|
839
|
+
|
|
840
|
+
/**
|
|
841
|
+
* `geenius-release publint` — run publint against the package's packed tarball.
|
|
842
|
+
* Replaces ~17 scripts across 4 filename variations in the legacy tree
|
|
843
|
+
* (`publint-package.mjs`, `publint-packed.mjs`, `publint-check.mjs`, `publint.mjs`).
|
|
844
|
+
*
|
|
845
|
+
* publint is resolved from the package's local `node_modules/.bin` and spawned
|
|
846
|
+
* directly (skipping `pnpm exec`'s ~300ms bootstrap). If the binary isn't
|
|
847
|
+
* reachable, we report `missing` and let the config decide whether that's an
|
|
848
|
+
* optional skip.
|
|
849
|
+
*/
|
|
850
|
+
|
|
851
|
+
interface RunPublintOptions {
|
|
852
|
+
cwd?: string;
|
|
853
|
+
/** Allow publint to be missing without failing. Default: false (publint should always pass). */
|
|
854
|
+
optional?: boolean;
|
|
855
|
+
/** Tolerance config for source-time `link:` deps. */
|
|
856
|
+
config?: Config["publint"];
|
|
857
|
+
quiet?: boolean;
|
|
858
|
+
}
|
|
859
|
+
declare function runPublint(opts?: RunPublintOptions): Promise<CommandReport>;
|
|
860
|
+
|
|
861
|
+
/**
|
|
862
|
+
* `geenius-release rewrite-imports` — post-build codemod that rewrites
|
|
863
|
+
* private subpath imports in a variant's built `dist/` so packed tarballs
|
|
864
|
+
* don't need to advertise internal `./shared` (or similar) exports.
|
|
865
|
+
*
|
|
866
|
+
* Replaces ~36 copies of `rewrite-private-imports.mjs`. Rules are
|
|
867
|
+
* config-driven and token-aware (`${packageName}`, `${framework}`,
|
|
868
|
+
* `${variant}`) so the same toolkit serves every Geenius package that
|
|
869
|
+
* keeps shared code under `packages/shared/` and per-framework variants
|
|
870
|
+
* under `packages/<variant>/`.
|
|
871
|
+
*/
|
|
872
|
+
|
|
873
|
+
interface RewriteRule {
|
|
874
|
+
/** Literal specifier to find. Token-expanded before matching. */
|
|
875
|
+
match: string;
|
|
876
|
+
/** Replacement. Token-expanded. When `literal` is false (default), treated
|
|
877
|
+
* as a path relative to packageRoot and converted into a module specifier
|
|
878
|
+
* relative to the variant's `dist/`. When `literal` is true, used as-is —
|
|
879
|
+
* useful for JSDoc / comment cleanup ("internal-name → public-name"). */
|
|
880
|
+
replaceWith: string;
|
|
881
|
+
/** If true, `replaceWith` is used as literal text (no path resolution). */
|
|
882
|
+
literal?: boolean;
|
|
883
|
+
/** If true, only quoted occurrences are matched (both `"<match>"` and
|
|
884
|
+
* `'<match>'`). Use this for import-specifier rewrites that must not
|
|
885
|
+
* touch identical strings in JSDoc / comments. */
|
|
886
|
+
quoted?: boolean;
|
|
887
|
+
}
|
|
888
|
+
interface RunRewriteImportsOptions {
|
|
889
|
+
cwd?: string;
|
|
890
|
+
/** Variant directory, relative to packageRoot (e.g. `packages/react`). */
|
|
891
|
+
variantDir: string;
|
|
892
|
+
/** Override config rules. */
|
|
893
|
+
rules?: readonly RewriteRule[];
|
|
894
|
+
/** Override framework detection. Map of framework name → variant-basename regex. */
|
|
895
|
+
frameworkDetect?: Record<string, string>;
|
|
896
|
+
/** Explicit framework name (skips detection). */
|
|
897
|
+
framework?: string;
|
|
898
|
+
/** File extensions to rewrite. Default: `[".js", ".d.ts"]`. */
|
|
899
|
+
extensions?: readonly string[];
|
|
900
|
+
/** If true, generate additional literal rules from the root manifest's
|
|
901
|
+
* `exports` map: for every `packages/<name>` referenced from an exports
|
|
902
|
+
* target, map the private workspace name (read from `packages/<name>/
|
|
903
|
+
* package.json`) to the public root-subpath specifier. Useful when
|
|
904
|
+
* consumers must not see internal workspace package names in published
|
|
905
|
+
* declaration files. Added after any explicitly configured rules. */
|
|
906
|
+
deriveFromExports?: boolean;
|
|
907
|
+
/** Built-in preset names to layer on. Currently: `solid-web` (rewrite
|
|
908
|
+
* `solid-js/web` to `solid-js/web/dist/web.js` so Node ESM consumers can
|
|
909
|
+
* resolve it without subpath redirects). Presets append to the rule list. */
|
|
910
|
+
presets?: readonly "solid-web"[];
|
|
911
|
+
config?: Config["rewriteImports"];
|
|
912
|
+
quiet?: boolean;
|
|
913
|
+
}
|
|
914
|
+
declare function runRewriteImports(opts: RunRewriteImportsOptions): Promise<CommandReport>;
|
|
915
|
+
|
|
916
|
+
/**
|
|
917
|
+
* `geenius-release run-scripts <s1> <s2> …` — run multiple top-level
|
|
918
|
+
* `package.json` scripts sequentially in the package root, with PATH
|
|
919
|
+
* augmented to include `node_modules/.bin`. Stops on the first failure
|
|
920
|
+
* and propagates the failing exit code.
|
|
921
|
+
*
|
|
922
|
+
* Replaces local `_run-root-scripts.mjs` shims that exist in adapters and
|
|
923
|
+
* similar packages, where a single command needs to chain build → tests
|
|
924
|
+
* → exports → dist-contract in the same shell context.
|
|
925
|
+
*/
|
|
926
|
+
interface RunScriptsOptions {
|
|
927
|
+
cwd?: string;
|
|
928
|
+
scripts: readonly string[];
|
|
929
|
+
/** Stop on first failure (default: true). */
|
|
930
|
+
stopOnFailure?: boolean;
|
|
931
|
+
/** Don't actually spawn; print the command list. */
|
|
932
|
+
print?: boolean;
|
|
933
|
+
}
|
|
934
|
+
interface RunScriptsResult {
|
|
935
|
+
status: number;
|
|
936
|
+
/** Names of scripts that ran (including the failing one if applicable). */
|
|
937
|
+
ran: string[];
|
|
938
|
+
/** Name of the failing script, if any. */
|
|
939
|
+
failedAt?: string;
|
|
940
|
+
}
|
|
941
|
+
declare function runScripts(opts: RunScriptsOptions): Promise<RunScriptsResult>;
|
|
942
|
+
|
|
943
|
+
/**
|
|
944
|
+
* `geenius-release sanitize-dist` — strip leaky tsup artifacts from built JS.
|
|
945
|
+
*
|
|
946
|
+
* Collapses sanitize-dist-comments.mjs (3) + sanitize-dist.mjs (2).
|
|
947
|
+
*
|
|
948
|
+
* Operations (composable):
|
|
949
|
+
* --comments (default on) Strip `// src/...` / `// .../src/...` comments tsup leaves at
|
|
950
|
+
* the top of bundled chunks (they expose workspace
|
|
951
|
+
* source paths).
|
|
952
|
+
* --maps Strip `//# sourceMappingURL=` comments.
|
|
953
|
+
* --fix-solid-jsx-runtime Rewrite solid-js/jsx-runtime → solid-js/h/jsx-runtime.
|
|
954
|
+
*
|
|
955
|
+
* Walks `dist/` (override with `dir`) and only touches `.js`, `.cjs`, `.mjs`.
|
|
956
|
+
*/
|
|
957
|
+
interface RunSanitizeDistOptions {
|
|
958
|
+
cwd?: string;
|
|
959
|
+
dir?: string;
|
|
960
|
+
/** Default true. Strip `// .../src/...` source-path comments. */
|
|
961
|
+
comments?: boolean;
|
|
962
|
+
/** Default false. Strip sourceMappingURL comments. */
|
|
963
|
+
maps?: boolean;
|
|
964
|
+
/** Default false. Rewrite solid-js/jsx-runtime to runtime/h variant. */
|
|
965
|
+
fixSolidJsxRuntime?: boolean;
|
|
966
|
+
}
|
|
967
|
+
interface SanitizeDistResult {
|
|
968
|
+
status: "passed" | "skipped";
|
|
969
|
+
filesScanned: number;
|
|
970
|
+
filesChanged: number;
|
|
971
|
+
}
|
|
972
|
+
declare function runSanitizeDist(opts?: RunSanitizeDistOptions): Promise<SanitizeDistResult>;
|
|
973
|
+
|
|
974
|
+
/**
|
|
975
|
+
* `geenius-release sbom` — emit a CycloneDX 1.5 JSON SBOM from pnpm-lock.yaml.
|
|
976
|
+
* Replaces the 36 copies of `sbom.mjs`.
|
|
977
|
+
*
|
|
978
|
+
* Implementation strategy: parse the lockfile YAML by line (no dependency on a
|
|
979
|
+
* full YAML parser — pnpm-lock.yaml has a stable, simple shape since v9).
|
|
980
|
+
* For SPDX format we shell out to `syft` if available; otherwise we report
|
|
981
|
+
* SPDX as `missing` per the optional-scanner policy.
|
|
982
|
+
*/
|
|
983
|
+
|
|
984
|
+
interface RunSbomOptions {
|
|
985
|
+
cwd?: string;
|
|
986
|
+
config?: Config["sbom"];
|
|
987
|
+
/** Override output path. */
|
|
988
|
+
out?: string;
|
|
989
|
+
/** Override format. */
|
|
990
|
+
format?: "cyclonedx-json" | "spdx-json";
|
|
991
|
+
quiet?: boolean;
|
|
992
|
+
}
|
|
993
|
+
declare function runSbom(opts?: RunSbomOptions): Promise<CommandReport>;
|
|
994
|
+
|
|
995
|
+
/**
|
|
996
|
+
* `geenius-release size-check` — size-limit driver. Replaces 13 copies of
|
|
997
|
+
* `size-check.mjs`. Reads the package's `size-limit` config (either from
|
|
998
|
+
* `package.json:size-limit` or `size-limit.config.{js,mjs,ts}`) and runs the
|
|
999
|
+
* `size-limit` binary; passing means every entry is under its budget.
|
|
1000
|
+
*/
|
|
1001
|
+
|
|
1002
|
+
interface RunSizeCheckOptions {
|
|
1003
|
+
cwd?: string;
|
|
1004
|
+
/** When the size-limit binary or config is absent: `false` → step is `missing`
|
|
1005
|
+
* and command fails. `true` (default) → step is `skipped` and command passes.
|
|
1006
|
+
* This mirrors `mutation-report` — size-limit is opt-in tooling, not every
|
|
1007
|
+
* package adopts it. */
|
|
1008
|
+
optional?: boolean;
|
|
1009
|
+
/** Additional flags to pass to size-limit (e.g. `--why`). */
|
|
1010
|
+
extraArgs?: readonly string[];
|
|
1011
|
+
quiet?: boolean;
|
|
1012
|
+
}
|
|
1013
|
+
declare function runSizeCheck(opts?: RunSizeCheckOptions): Promise<CommandReport>;
|
|
1014
|
+
|
|
1015
|
+
/**
|
|
1016
|
+
* `geenius-release size-limit-config` — generate size-limit entries from
|
|
1017
|
+
* `variants.json` and the root manifest's `exports` map.
|
|
1018
|
+
*
|
|
1019
|
+
* For every variant whose `packageDir` is referenced in `root.exports` (i.e.
|
|
1020
|
+
* actually shipped) and that declares `budget.gzip`, emit a size-limit entry:
|
|
1021
|
+
* { name, path: "<packageDir>/dist/index.js", ignore: [...peerDeps], limit }
|
|
1022
|
+
*
|
|
1023
|
+
* Variants without `budget.gzip` cause an error when they're in the exported
|
|
1024
|
+
* set — this is the same invariant adapters' local `size-limit-config.mjs`
|
|
1025
|
+
* enforces. Replaces ~5 copies across the ecosystem.
|
|
1026
|
+
*
|
|
1027
|
+
* Emits JSON to stdout; consumers pipe it into their `.size-limit.cjs` /
|
|
1028
|
+
* `size-limit.config.mjs` (typically `module.exports = JSON.parse(read(...))`).
|
|
1029
|
+
*/
|
|
1030
|
+
interface RunSizeLimitConfigOptions {
|
|
1031
|
+
cwd?: string;
|
|
1032
|
+
/** Pretty-print JSON. Default: true. */
|
|
1033
|
+
pretty?: boolean;
|
|
1034
|
+
/** Match variants by exact `packageDir`. Default: derive from root exports. */
|
|
1035
|
+
packageDirs?: readonly string[];
|
|
1036
|
+
}
|
|
1037
|
+
interface SizeLimitEntry {
|
|
1038
|
+
name: string;
|
|
1039
|
+
path: string;
|
|
1040
|
+
ignore: string[];
|
|
1041
|
+
limit: string;
|
|
1042
|
+
}
|
|
1043
|
+
declare function runSizeLimitConfig(opts?: RunSizeLimitConfigOptions): {
|
|
1044
|
+
ok: boolean;
|
|
1045
|
+
entries: SizeLimitEntry[];
|
|
1046
|
+
output: string;
|
|
1047
|
+
};
|
|
1048
|
+
|
|
1049
|
+
/**
|
|
1050
|
+
* `geenius-release smoke-packed` — pack the package, install the tarball into
|
|
1051
|
+
* an ephemeral tmpdir, and dynamic-import every subpath in `package.json:exports`.
|
|
1052
|
+
*
|
|
1053
|
+
* Replaces the 36 copies of `smoke-packed-imports.mjs` (the heaviest legacy
|
|
1054
|
+
* script at ~286 LOC/copy = 10,318 total LOC absorbed).
|
|
1055
|
+
*/
|
|
1056
|
+
|
|
1057
|
+
interface RunSmokePackedOptions {
|
|
1058
|
+
cwd?: string;
|
|
1059
|
+
config?: Config["smokePacked"];
|
|
1060
|
+
/** Limit to a subset of subpaths. */
|
|
1061
|
+
subpaths?: readonly string[];
|
|
1062
|
+
quiet?: boolean;
|
|
1063
|
+
/** CLI-only overrides (mirror config fields). */
|
|
1064
|
+
checkExportsOnDisk?: boolean;
|
|
1065
|
+
checkTarballPurity?: string;
|
|
1066
|
+
checkStylesheets?: boolean;
|
|
1067
|
+
browserConditions?: boolean;
|
|
1068
|
+
domStubs?: boolean;
|
|
1069
|
+
injectDeps?: readonly string[];
|
|
1070
|
+
}
|
|
1071
|
+
declare function runSmokePacked(opts?: RunSmokePackedOptions): Promise<CommandReport>;
|
|
1072
|
+
|
|
1073
|
+
/**
|
|
1074
|
+
* `geenius-release storybook` — build + test-runner orchestration for every
|
|
1075
|
+
* Storybook app declared in `release-toolkit.config.json:storybook.apps`.
|
|
1076
|
+
*
|
|
1077
|
+
* Absorbs ~28 scripts across 5 filename variations (`storybook-runner.mjs`,
|
|
1078
|
+
* `storybook-test-runner.mjs`, `test-storybook-static.mjs`, `storybook-build.mjs`,
|
|
1079
|
+
* `storybook-apps.mjs`).
|
|
1080
|
+
*
|
|
1081
|
+
* Each app is identified by a relative path to its directory; the toolkit
|
|
1082
|
+
* invokes `pnpm --dir <path> <action>` for each. Actions are configurable
|
|
1083
|
+
* (default: build then test:storybook).
|
|
1084
|
+
*/
|
|
1085
|
+
|
|
1086
|
+
interface RunStorybookOptions {
|
|
1087
|
+
cwd?: string;
|
|
1088
|
+
/** Relative paths to Storybook app directories. If omitted, falls back to
|
|
1089
|
+
* globbing `apps/storybook-*` at the package root. */
|
|
1090
|
+
apps?: readonly string[];
|
|
1091
|
+
/** Lifecycle action to run per app. Default: `["build", "test:storybook"]`. */
|
|
1092
|
+
actions?: readonly string[];
|
|
1093
|
+
/** Limit to a subset of apps via a substring filter. */
|
|
1094
|
+
filter?: string;
|
|
1095
|
+
/** Soft-skip apps that don't have the requested script. Default: true. */
|
|
1096
|
+
skipIfMissingScript?: boolean;
|
|
1097
|
+
/** Continue with the next app after a failure. */
|
|
1098
|
+
continueOnFailure?: boolean;
|
|
1099
|
+
/** When set, run the toolkit's built-in static smoke (Playwright + http
|
|
1100
|
+
* server) instead of (or after) shelling out to `pnpm test:storybook`.
|
|
1101
|
+
* `replace` skips per-app `test:storybook`, `after` runs it then smoke,
|
|
1102
|
+
* `only` skips `build` too. Default: undefined (legacy behavior). */
|
|
1103
|
+
staticSmoke?: "replace" | "after" | "only";
|
|
1104
|
+
/** Per-app runner. `static-smoke` is the toolkit's built-in Playwright +
|
|
1105
|
+
* http-server smoke (equivalent to `staticSmoke: "replace"`).
|
|
1106
|
+
* `test-runner` invokes `@storybook/test-runner` against a served
|
|
1107
|
+
* built Storybook. `vitest` runs the app's `test:storybook` script
|
|
1108
|
+
* (which typically points at a Vitest browser-mode config).
|
|
1109
|
+
* When set, `staticSmoke` is ignored and a single build step runs
|
|
1110
|
+
* before the chosen runner. */
|
|
1111
|
+
runner?: "static-smoke" | "test-runner" | "vitest";
|
|
1112
|
+
/** Story ids every Storybook must include during static smoke. */
|
|
1113
|
+
requiredStoryIds?: readonly string[];
|
|
1114
|
+
/** Discover apps from variants.json instead of auto-globbing apps/storybook-*.
|
|
1115
|
+
* Reads variants where `storybook` field is set; respects `published` if
|
|
1116
|
+
* `fromVariantsScope: "published"` is also set. */
|
|
1117
|
+
fromVariants?: boolean;
|
|
1118
|
+
/** When `fromVariants` is true: `all` (default) includes every variant
|
|
1119
|
+
* with a `storybook` field; `published` includes only variants with
|
|
1120
|
+
* `published: true`. */
|
|
1121
|
+
fromVariantsScope?: "all" | "published";
|
|
1122
|
+
/** When set, assert per-app structural shape (required + forbidden files,
|
|
1123
|
+
* required story titles in the built index.json). Same intent as the
|
|
1124
|
+
* per-package `scripts/storybook-app-smoke.mjs` shim. */
|
|
1125
|
+
checkShape?: StorybookShapeSpec;
|
|
1126
|
+
quiet?: boolean;
|
|
1127
|
+
}
|
|
1128
|
+
interface StorybookShapeSpec {
|
|
1129
|
+
/** Paths (relative to the app dir) that must exist. */
|
|
1130
|
+
requiredFiles?: readonly string[];
|
|
1131
|
+
/** Paths (relative to the app dir) that must NOT exist. */
|
|
1132
|
+
forbiddenFiles?: readonly string[];
|
|
1133
|
+
/** Story titles (from index.json `entries[].title`) that must be present. */
|
|
1134
|
+
requiredTitles?: readonly string[];
|
|
1135
|
+
}
|
|
1136
|
+
declare function runStorybook(opts?: RunStorybookOptions): Promise<CommandReport>;
|
|
1137
|
+
|
|
1138
|
+
/**
|
|
1139
|
+
* `geenius-release supply-chain` — pnpm audit + osv-scanner + Socket + license,
|
|
1140
|
+
* all configurable required/optional. Replaces the 26 scripts across 7
|
|
1141
|
+
* filename variations in the legacy tree.
|
|
1142
|
+
*/
|
|
1143
|
+
|
|
1144
|
+
interface RunSupplyChainOptions {
|
|
1145
|
+
cwd?: string;
|
|
1146
|
+
config?: Config["supplyChain"];
|
|
1147
|
+
/** Inherited from the parent License command settings, when invoked from gauntlet. */
|
|
1148
|
+
licenseConfig?: Config["license"];
|
|
1149
|
+
quiet?: boolean;
|
|
1150
|
+
}
|
|
1151
|
+
declare function runSupplyChain(opts?: RunSupplyChainOptions): Promise<CommandReport>;
|
|
1152
|
+
|
|
1153
|
+
/**
|
|
1154
|
+
* `geenius-release type-check` — run a per-variant type-check command,
|
|
1155
|
+
* with a fallback chain. For each variant declaring a `packageDir`:
|
|
1156
|
+
*
|
|
1157
|
+
* 1. If the variant's `package.json` has a `type-check` script, run it.
|
|
1158
|
+
* 2. Otherwise, if it has a `lint` script, run that.
|
|
1159
|
+
* 3. Otherwise, run `tsc --noEmit` from the variant directory.
|
|
1160
|
+
*
|
|
1161
|
+
* PATH is augmented to include both the variant's and root's `node_modules/.bin`
|
|
1162
|
+
* so locally-installed `tsc` resolves correctly. Replaces
|
|
1163
|
+
* `scripts/type-check-packages.mjs` (78 LOC × several packages).
|
|
1164
|
+
*/
|
|
1165
|
+
interface RunTypeCheckOptions {
|
|
1166
|
+
cwd?: string;
|
|
1167
|
+
/** Continue with the next variant after a failure (default: false). */
|
|
1168
|
+
continueOnFailure?: boolean;
|
|
1169
|
+
/** Include variants marked inScope:false (default: true — type-checking
|
|
1170
|
+
* out-of-scope code surfaces drift early). */
|
|
1171
|
+
includeOutOfScope?: boolean;
|
|
1172
|
+
/** Run this packageDir first (typical: packages/shared). Default: undefined. */
|
|
1173
|
+
sharedFirst?: string;
|
|
1174
|
+
/** Don't spawn; print the resolved command list. */
|
|
1175
|
+
print?: boolean;
|
|
1176
|
+
}
|
|
1177
|
+
interface TypeCheckResult {
|
|
1178
|
+
status: number;
|
|
1179
|
+
results: {
|
|
1180
|
+
packageDir: string;
|
|
1181
|
+
command: string;
|
|
1182
|
+
status: number;
|
|
1183
|
+
}[];
|
|
1184
|
+
}
|
|
1185
|
+
declare function runTypeCheck(opts?: RunTypeCheckOptions): Promise<TypeCheckResult>;
|
|
1186
|
+
|
|
1187
|
+
/**
|
|
1188
|
+
* `geenius-release variants` — print the package's variant matrix.
|
|
1189
|
+
*
|
|
1190
|
+
* Subcommands:
|
|
1191
|
+
* - list (default) Emit `manifest.variants` as JSON.
|
|
1192
|
+
* - missing Emit only required variants whose `packageDir` is absent.
|
|
1193
|
+
* - published-subpaths Emit `{variant,subpath}[]` for every published subpath.
|
|
1194
|
+
* - ui Emit only UI-kind variants.
|
|
1195
|
+
* - db Emit only db-provider variants.
|
|
1196
|
+
* - storybook-apps Emit `{variant,app,appDir}[]` for every Storybook host.
|
|
1197
|
+
*
|
|
1198
|
+
* Replaces 43 copies of `scripts/_variants.mjs`.
|
|
1199
|
+
*/
|
|
1200
|
+
interface RunVariantsOptions {
|
|
1201
|
+
cwd?: string;
|
|
1202
|
+
subcommand?: "list" | "missing" | "published-subpaths" | "ui" | "db" | "storybook-apps" | "check";
|
|
1203
|
+
includeOutOfScope?: boolean;
|
|
1204
|
+
/** Pretty-print JSON. Default: true. */
|
|
1205
|
+
pretty?: boolean;
|
|
1206
|
+
/** `check` subcommand: require every entry with `required: true` (or
|
|
1207
|
+
* unspecified `required`) to have a `packageDir` that exists on disk. */
|
|
1208
|
+
requireAll?: boolean;
|
|
1209
|
+
}
|
|
1210
|
+
declare function runVariants(opts?: RunVariantsOptions): {
|
|
1211
|
+
ok: boolean;
|
|
1212
|
+
output: string;
|
|
1213
|
+
};
|
|
1214
|
+
|
|
1215
|
+
/**
|
|
1216
|
+
* `geenius-release vitest-browser-prepare` — vitest browser-mode prepare plugin.
|
|
1217
|
+
*
|
|
1218
|
+
* Collapses vitest-browser-prepare-retry.ts copies across 4 packages.
|
|
1219
|
+
*
|
|
1220
|
+
* Exposed both as a programmatic plugin factory (for `vitest.config.ts`) and as
|
|
1221
|
+
* a CLI command that prints the plugin source for ad-hoc copy/integration. In
|
|
1222
|
+
* practice every package should import the factory, not the CLI; the CLI is
|
|
1223
|
+
* just an inspection escape hatch.
|
|
1224
|
+
*/
|
|
1225
|
+
interface VitestBrowserPreparePlugin {
|
|
1226
|
+
name: string;
|
|
1227
|
+
transformIndexHtml: {
|
|
1228
|
+
order: "pre";
|
|
1229
|
+
handler: () => {
|
|
1230
|
+
tag: string;
|
|
1231
|
+
injectTo: "head-prepend";
|
|
1232
|
+
children: string;
|
|
1233
|
+
}[];
|
|
1234
|
+
};
|
|
1235
|
+
}
|
|
1236
|
+
/**
|
|
1237
|
+
* Returns a Vitest browser-mode plugin that proxies `BroadcastChannel`
|
|
1238
|
+
* construction inside the harness iframe so prepare/execute/cleanup messages
|
|
1239
|
+
* emitted before the iframe's listener is attached are still delivered.
|
|
1240
|
+
*
|
|
1241
|
+
* Mirrors the per-package `vitestBrowserPrepareRetry()` factory verbatim so
|
|
1242
|
+
* existing vitest configs can swap `from "./scripts/..."` for `from
|
|
1243
|
+
* "@geenius/release-toolkit/vitest"` without behavioural drift.
|
|
1244
|
+
*/
|
|
1245
|
+
declare function vitestBrowserPrepareRetry(): VitestBrowserPreparePlugin;
|
|
1246
|
+
interface RunVitestBrowserPrepareOptions {
|
|
1247
|
+
/** Print the injected script body to stdout (CLI inspection). */
|
|
1248
|
+
print?: boolean;
|
|
1249
|
+
}
|
|
1250
|
+
declare function runVitestBrowserPrepare(opts?: RunVitestBrowserPrepareOptions): {
|
|
1251
|
+
status: "passed";
|
|
1252
|
+
source: string;
|
|
1253
|
+
};
|
|
1254
|
+
|
|
1255
|
+
/**
|
|
1256
|
+
* Centralized environment detection. Every subcommand reads its strictness
|
|
1257
|
+
* dials from here instead of inspecting `process.env` ad-hoc.
|
|
1258
|
+
*/
|
|
1259
|
+
interface EnvSnapshot {
|
|
1260
|
+
/** True if `CI` is set to a truthy value (`"1"`, `"true"`, `"yes"`). */
|
|
1261
|
+
ci: boolean;
|
|
1262
|
+
/** True when `SOCKET_API_TOKEN` is set; informs the supply-chain scanner. */
|
|
1263
|
+
socketTokenPresent: boolean;
|
|
1264
|
+
/** Coarse strictness override, parsed from `GEENIUS_RELEASE_STRICTNESS`.
|
|
1265
|
+
* - `"strict"`: every optional/skipIfX policy escalates one level.
|
|
1266
|
+
* - `"lenient"`: every optional/skipIfX policy de-escalates one level.
|
|
1267
|
+
* - `undefined`: use configured defaults. */
|
|
1268
|
+
strictness: "strict" | "lenient" | undefined;
|
|
1269
|
+
/** Per-scanner override: `GEENIUS_SUPPLY_CHAIN_<NAME>=off|optional|required`. */
|
|
1270
|
+
supplyChainOverrides: Record<string, "off" | "optional" | "required">;
|
|
1271
|
+
}
|
|
1272
|
+
/**
|
|
1273
|
+
* Read the environment once. Pure with respect to `env`; callers in tests can
|
|
1274
|
+
* pass a custom object instead of `process.env`.
|
|
1275
|
+
*/
|
|
1276
|
+
declare function readEnv(env?: NodeJS.ProcessEnv): EnvSnapshot;
|
|
1277
|
+
|
|
1278
|
+
/**
|
|
1279
|
+
* Canonical exit codes. Stable across versions — adding a new code is a major
|
|
1280
|
+
* bump. CI integrations rely on these.
|
|
1281
|
+
*/
|
|
1282
|
+
declare const ExitCode: {
|
|
1283
|
+
readonly OK: 0;
|
|
1284
|
+
readonly REQUIRED_FAILURE: 1;
|
|
1285
|
+
readonly CONFIG_ERROR: 2;
|
|
1286
|
+
readonly ENV_ERROR: 3;
|
|
1287
|
+
readonly INTERNAL_BUG: 4;
|
|
1288
|
+
};
|
|
1289
|
+
type ExitCode = (typeof ExitCode)[keyof typeof ExitCode];
|
|
1290
|
+
/**
|
|
1291
|
+
* Errors the CLI knows how to translate into a non-zero exit code. Any other
|
|
1292
|
+
* thrown value is an unexpected failure (exit code 4).
|
|
1293
|
+
*/
|
|
1294
|
+
declare class ReleaseToolkitError extends Error {
|
|
1295
|
+
readonly code: ExitCode;
|
|
1296
|
+
readonly hint?: string | undefined;
|
|
1297
|
+
constructor(message: string, code: ExitCode, hint?: string | undefined);
|
|
1298
|
+
}
|
|
1299
|
+
|
|
1300
|
+
/**
|
|
1301
|
+
* Canonical path resolution. Every command and lib reads paths through here so
|
|
1302
|
+
* relocating the report directory or the lockfile name is a one-line edit.
|
|
1303
|
+
*/
|
|
1304
|
+
interface ResolvedPaths {
|
|
1305
|
+
/** Absolute path to the package root (the directory containing package.json). */
|
|
1306
|
+
packageRoot: string;
|
|
1307
|
+
/** Absolute path to the package's pnpm-lock.yaml. */
|
|
1308
|
+
lockfile: string;
|
|
1309
|
+
/** Absolute path to the package's package.json. */
|
|
1310
|
+
packageJson: string;
|
|
1311
|
+
/** Absolute path to the package's node_modules root. */
|
|
1312
|
+
nodeModules: string;
|
|
1313
|
+
/** Absolute path to `.eval/release-toolkit/`. Reports go here. */
|
|
1314
|
+
reportDir: string;
|
|
1315
|
+
}
|
|
1316
|
+
/**
|
|
1317
|
+
* Resolve filesystem paths relative to a starting cwd. Walks up to find the
|
|
1318
|
+
* first directory containing both `package.json` and `pnpm-lock.yaml`. This
|
|
1319
|
+
* matches how `pnpm` itself locates package roots and lets the CLI be invoked
|
|
1320
|
+
* from a sub-directory.
|
|
1321
|
+
*/
|
|
1322
|
+
declare function resolvePaths(startCwd?: string): ResolvedPaths;
|
|
1323
|
+
|
|
1324
|
+
/**
|
|
1325
|
+
* Rich variants loader — replaces the per-package `_variants.mjs` helper
|
|
1326
|
+
* (43 copies across the workspace).
|
|
1327
|
+
*
|
|
1328
|
+
* Reads `variants.json` at the package root and returns typed variant
|
|
1329
|
+
* objects with derived `packagePath`/`exists`/`subpaths` fields, plus
|
|
1330
|
+
* helper queries (`packageVariants`, `uiVariants`, `dbProviderVariants`,
|
|
1331
|
+
* `storybookApps`, `publishedSubpaths`, …). Honors the
|
|
1332
|
+
* OMEGA_INCLUDE_OUT_OF_SCOPE env flag the legacy scripts depend on.
|
|
1333
|
+
*/
|
|
1334
|
+
interface RichVariantTestsConfig {
|
|
1335
|
+
unit?: boolean;
|
|
1336
|
+
coverage?: Record<string, number>;
|
|
1337
|
+
[key: string]: unknown;
|
|
1338
|
+
}
|
|
1339
|
+
interface RichVariant {
|
|
1340
|
+
name: string;
|
|
1341
|
+
kind: string;
|
|
1342
|
+
framework?: string;
|
|
1343
|
+
packageDir?: string;
|
|
1344
|
+
workspace?: string;
|
|
1345
|
+
driver?: string;
|
|
1346
|
+
subpath?: string;
|
|
1347
|
+
aliases?: string[];
|
|
1348
|
+
published?: boolean;
|
|
1349
|
+
storybook?: string;
|
|
1350
|
+
tests?: RichVariantTestsConfig;
|
|
1351
|
+
inScope?: boolean;
|
|
1352
|
+
/** Derived: absolute path to the variant directory. */
|
|
1353
|
+
packagePath: string | null;
|
|
1354
|
+
/** Derived: whether `packagePath` exists on disk. */
|
|
1355
|
+
exists: boolean;
|
|
1356
|
+
/** Derived: subpath + aliases concatenated. */
|
|
1357
|
+
subpaths: string[];
|
|
1358
|
+
[key: string]: unknown;
|
|
1359
|
+
}
|
|
1360
|
+
interface RichVariantsManifest {
|
|
1361
|
+
package: string;
|
|
1362
|
+
rootDir: string;
|
|
1363
|
+
variants: RichVariant[];
|
|
1364
|
+
coverage?: {
|
|
1365
|
+
reference?: Record<string, number>;
|
|
1366
|
+
library?: Record<string, number>;
|
|
1367
|
+
provider?: Record<string, number>;
|
|
1368
|
+
};
|
|
1369
|
+
[key: string]: unknown;
|
|
1370
|
+
}
|
|
1371
|
+
interface LoadRichVariantsOptions {
|
|
1372
|
+
/** Override the package root (otherwise the caller's cwd is used). */
|
|
1373
|
+
rootDir?: string;
|
|
1374
|
+
/** Force-include out-of-scope variants regardless of env. */
|
|
1375
|
+
includeOutOfScope?: boolean;
|
|
1376
|
+
}
|
|
1377
|
+
declare function loadRichVariants(opts?: LoadRichVariantsOptions): RichVariantsManifest;
|
|
1378
|
+
interface VariantQueryOptions extends LoadRichVariantsOptions {
|
|
1379
|
+
includeMissing?: boolean;
|
|
1380
|
+
publishedOnly?: boolean;
|
|
1381
|
+
kinds?: readonly string[];
|
|
1382
|
+
/** Only include variants flagged `implemented: true`. */
|
|
1383
|
+
implementedOnly?: boolean;
|
|
1384
|
+
}
|
|
1385
|
+
declare function packageVariants(opts?: VariantQueryOptions): RichVariant[];
|
|
1386
|
+
declare function variantsByKind(kind: string, opts?: LoadRichVariantsOptions): RichVariant[];
|
|
1387
|
+
declare function uiVariants(opts?: VariantQueryOptions): RichVariant[];
|
|
1388
|
+
declare function dbProviderVariants(opts?: LoadRichVariantsOptions): RichVariant[];
|
|
1389
|
+
declare function publishedSubpaths(opts?: LoadRichVariantsOptions): {
|
|
1390
|
+
variant: RichVariant;
|
|
1391
|
+
subpath: string;
|
|
1392
|
+
}[];
|
|
1393
|
+
declare function storybookVariants(opts?: LoadRichVariantsOptions): RichVariant[];
|
|
1394
|
+
declare function storybookApps(opts?: LoadRichVariantsOptions): {
|
|
1395
|
+
variant: RichVariant;
|
|
1396
|
+
app: string;
|
|
1397
|
+
appDir: string;
|
|
1398
|
+
}[];
|
|
1399
|
+
declare function missingRequiredVariants(opts?: LoadRichVariantsOptions): RichVariant[];
|
|
1400
|
+
|
|
1401
|
+
export { type BudgetRow, type BundleBudgetsResult, type CommandReport, type CommandStatus, type Config, ConfigSchema, type ConvexBuildResult, type ConvexCodegenResult, type CoverageResult, type DbMigrationsResult, type DtsRewriteRule, type E2EResult, type EnvSnapshot, ExitCode, type LintResult, type PackContractResult, type PatchDtsResult, type PnpmFiltersResult, ReleaseToolkitError, type ResolvedPaths, type RewriteRule, type RichVariant, type RichVariantsManifest, type RunA11yReportOptions, type RunAttwOptions, type RunBundleBudgetsOptions, type RunConvexBuildOptions, type RunConvexCodegenOptions, type RunCoverageOptions, type RunCoverageReportOptions, type RunDbMigrationsOptions, type RunDiffCoverageOptions, type RunE2EOptions, type RunGauntletOptions, type RunLicenseOptions, type RunLintOptions, type RunManifestContractOptions, type RunMutationReportOptions, type RunPackContractOptions, type RunPatchDtsOptions, type RunPerfSmokeOptions, type RunPnpmFiltersOptions, type RunPublintOptions, type RunRewriteImportsOptions, type RunSanitizeDistOptions, type RunSbomOptions, type RunScriptsOptions, type RunScriptsResult, type RunSizeCheckOptions, type RunSizeLimitConfigOptions, type RunSmokePackedOptions, type RunStorybookOptions, type RunSupplyChainOptions, type RunTypeCheckOptions, type RunVariantsOptions, type RunVitestBrowserPrepareOptions, type SanitizeDistResult, type ScannerState, type SizeLimitEntry, type StepReport, type StepStatus, type TypeCheckResult, type VitestBrowserPreparePlugin, dbProviderVariants, loadConfig, loadRichVariants, missingRequiredVariants, packageVariants, publishedSubpaths, readEnv, resolvePaths, runA11yReport, runAttw, runBundleBudgets, runConvexBuild, runConvexCodegen, runCoverage, runCoverageReport, runDbMigrations, runDiffCoverage, runE2E, runGauntlet, runLicense, runLint, runManifestContract, runMutationReport, runPackContract, runPatchDts, runPerfSmoke, runPnpmFilters, runPublint, runRewriteImports, runSanitizeDist, runSbom, runScripts, runSizeCheck, runSizeLimitConfig, runSmokePacked, runStorybook, runSupplyChain, runTypeCheck, runVariants, runVitestBrowserPrepare, storybookApps, storybookVariants, uiVariants, variantsByKind, vitestBrowserPrepareRetry };
|