@stll/oxlint-config 1.8.0 → 2.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (63) hide show
  1. package/README.md +99 -67
  2. package/dist/cloud-setup-cli.cjs +5 -1
  3. package/dist/cloud-setup-cli.cjs.map +1 -1
  4. package/dist/cloud-setup-cli.mjs +6 -2
  5. package/dist/cloud-setup-cli.mjs.map +1 -1
  6. package/dist/dependabot.d.cts +0 -19
  7. package/dist/dependabot.d.mts +0 -19
  8. package/dist/git-tracked-output.cjs +1 -1
  9. package/dist/git-tracked-output.mjs +1 -1
  10. package/dist/publish-artifact-syntax.cjs +1 -1
  11. package/dist/publish-artifact-syntax.mjs +1 -1
  12. package/dist/publish-contract-cli.cjs +2 -2
  13. package/dist/publish-contract-cli.mjs +2 -2
  14. package/dist/quarantine-cli.cjs +3 -2
  15. package/dist/quarantine-cli.cjs.map +1 -1
  16. package/dist/quarantine-cli.mjs +3 -2
  17. package/dist/quarantine-cli.mjs.map +1 -1
  18. package/dist/quarantine-policy.d.cts +25 -2
  19. package/dist/quarantine-policy.d.mts +25 -2
  20. package/dist/quarantine-policy2.cjs +177 -5
  21. package/dist/quarantine-policy2.cjs.map +1 -1
  22. package/dist/quarantine-policy2.mjs +166 -6
  23. package/dist/quarantine-policy2.mjs.map +1 -1
  24. package/dist/toolchain-changed-cli.cjs +1477 -2
  25. package/dist/toolchain-changed-cli.cjs.map +1 -1
  26. package/dist/toolchain-changed-cli.mjs +1474 -1
  27. package/dist/toolchain-changed-cli.mjs.map +1 -1
  28. package/dist/toolchain-check-cli.cjs +2 -0
  29. package/dist/toolchain-check-cli.cjs.map +1 -1
  30. package/dist/toolchain-check-cli.mjs +2 -0
  31. package/dist/toolchain-check-cli.mjs.map +1 -1
  32. package/dist/toolchain-guard.cjs +355 -241
  33. package/dist/toolchain-guard.cjs.map +1 -1
  34. package/dist/toolchain-guard.mjs +352 -244
  35. package/dist/toolchain-guard.mjs.map +1 -1
  36. package/dist/toolchain-inputs.cjs +13 -40
  37. package/dist/toolchain-inputs.cjs.map +1 -1
  38. package/dist/toolchain-inputs.mjs +13 -40
  39. package/dist/toolchain-inputs.mjs.map +1 -1
  40. package/dist/toolchain-schema.cjs +69 -46
  41. package/dist/toolchain-schema.cjs.map +1 -1
  42. package/dist/toolchain-schema.mjs +69 -47
  43. package/dist/toolchain-schema.mjs.map +1 -1
  44. package/dist/typecheck-probe-cli.cjs +40 -2
  45. package/dist/typecheck-probe-cli.cjs.map +1 -1
  46. package/dist/typecheck-probe-cli.mjs +39 -1
  47. package/dist/typecheck-probe-cli.mjs.map +1 -1
  48. package/package.json +3 -4
  49. package/toolchain.json +2 -28
  50. package/dist/toolchain-changed.cjs +0 -1484
  51. package/dist/toolchain-changed.cjs.map +0 -1
  52. package/dist/toolchain-changed.mjs +0 -1477
  53. package/dist/toolchain-changed.mjs.map +0 -1
  54. package/dist/typecheck-parity-cli.cjs +0 -71
  55. package/dist/typecheck-parity-cli.cjs.map +0 -1
  56. package/dist/typecheck-parity-cli.d.cts +0 -1
  57. package/dist/typecheck-parity-cli.d.mts +0 -1
  58. package/dist/typecheck-parity-cli.mjs +0 -71
  59. package/dist/typecheck-parity-cli.mjs.map +0 -1
  60. package/dist/typecheck-parity.cjs +0 -907
  61. package/dist/typecheck-parity.cjs.map +0 -1
  62. package/dist/typecheck-parity.mjs +0 -896
  63. package/dist/typecheck-parity.mjs.map +0 -1
package/README.md CHANGED
@@ -75,10 +75,12 @@ Shared-pin Dependabot ignores must contain only `dependency-name` and
75
75
  `version-update:semver-minor`, and `version-update:semver-patch`. This ignores
76
76
  version updates while preserving security update pull requests.
77
77
 
78
- Set `packageManager` to `bun@` followed by the policy's `bun` value, and pin
79
- `bun-types` to that same value. Dependency pins can live in default or named
80
- catalogs, including Bun's `workspaces` catalogs. Bun image tags, version
81
- files, and mise/asdf entries also inherit the policy pin.
78
+ The policy's `bun` value is the minimum Bun. Set `packageManager` to `bun@`
79
+ followed by one exact release at or above it, and pin `bun-types` to that same
80
+ release. Dependency pins can live in default or named catalogs, including
81
+ Bun's `workspaces` catalogs. Bun image tags, version files, and mise/asdf
82
+ entries also inherit the repository's pin, so a repository can take a newer
83
+ Bun without a policy release.
82
84
 
83
85
  Configure `oven-sh/setup-bun` with a tracked manifest as its version source:
84
86
 
@@ -234,11 +236,41 @@ The CLI checks tracked files, prints `path:line: [rule] message` diagnostics,
234
236
  and exits with status 1 on a mismatch. Updating the package updates the
235
237
  policy; update consumer pins and run the checker together.
236
238
 
237
- `typescriptInstallLayouts` declares the compiler package, exact specifier,
238
- and typecheck command for each supported layout. Prefer the direct layout.
239
- Use the split compatibility layout for the compiler-API consumers and peer
240
- blockers listed in `typescript6Compatibility`; it retains the current
241
- compiler for typechecking while providing the compatibility package.
239
+ The `typescript-layout` rule keeps TypeScript out of manifests: type checking
240
+ runs `bun check`, programs and checkers use tsrs, and syntax reads use
241
+ oxc-parser. No manifest, catalog, override or resolution declares `typescript`,
242
+ `@typescript/native` or an `npm:typescript@…` alias unless the repository
243
+ allows it. A `typecheck` script that runs a compiler must run `bun check`.
244
+
245
+ Each repository lists the TypeScript installs its own tools need in
246
+ `typescriptAllowlist` in tracked root `stll-toolchain.json`; there is no shared
247
+ list. An entry names the workspace directory (`.` for the root), the declared
248
+ name, the exact spec the manifest resolves to, the dependency in that same
249
+ workspace that needs it, and a reason:
250
+
251
+ ```json
252
+ {
253
+ "typescriptAllowlist": [
254
+ {
255
+ "workspace": "apps/docs",
256
+ "name": "typescript",
257
+ "spec": "6.0.3",
258
+ "dependency": "@astrojs/check",
259
+ "reason": "astro check loads the TypeScript 6 language service."
260
+ }
261
+ ]
262
+ }
263
+ ```
264
+
265
+ The workspace's `dependencies`, `devDependencies` or `optionalDependencies`
266
+ may declare the entry directly or through a catalog (`catalog:`,
267
+ `catalog:ts6`); it must resolve to `spec`. A catalog holds a TypeScript entry
268
+ only at the spec of an allowed install that references it. An undeclared
269
+ install fails with the entry to add; an entry fails when its spec differs,
270
+ when the workspace no longer declares the name, or when it no longer depends on
271
+ `dependency`. Overrides and resolutions never declare TypeScript. To keep
272
+ Dependabot from moving an allowed alias, declare it in `dependabotIgnores`;
273
+ `typescript` and `@typescript/native` are already shared ignores.
242
274
 
243
275
  An exception requires a tracked root `stll-toolchain.json` with the named
244
276
  rule and a nonempty reason:
@@ -249,13 +281,8 @@ rule and a nonempty reason:
249
281
  }
250
282
  ```
251
283
 
252
- Workspace TypeScript toolchains combine the root and declared members' devDependencies.
253
- An included member may declare the exact TypeScript 6 compatibility API across
254
- dependencies, devDependencies, and peerDependencies when that shared install uses
255
- the complete split layout. Ambiguous or partial layouts do not grant this allowance.
256
- Peer ranges declare support: they must include the policy compiler release and the
257
- compatibility release when the selected layout uses it. Ranges do not contribute
258
- to the installed compiler inventory.
284
+ Peer ranges, exact versions included, declare support: a `typescript` range
285
+ must include the policy release. Ranges do not count as installs.
259
286
 
260
287
  JavaScript update roots include the repository root, declared workspace membership,
261
288
  and directories with their own `bun.lock`, `package-lock.json`, `yarn.lock`, or
@@ -274,23 +301,6 @@ rules, empty reasons, and malformed configuration fail validation. See the
274
301
  for the schema, rule list, runtime support ranges, and generated Dependabot
275
302
  template.
276
303
 
277
- ## Typecheck parity project selection
278
-
279
- Run `stll-typecheck-parity` from the repository root. Without flags, it checks
280
- the root `tsconfig.json` and recursively discovers project references in build
281
- mode. Repeat `--project` to check exactly the selected configs:
282
-
283
- ```sh
284
- stll-typecheck-parity --project packages/api/tsconfig.json --project packages/web/tsconfig.json
285
- ```
286
-
287
- Selected configs run independently using the repository-root compiler
288
- installation; child packages need no compiler declaration and a root tsconfig
289
- is unnecessary. Their original reference metadata is preserved without
290
- discovering or building referenced projects. Missing, unreadable, and zero-input
291
- selected configs fail the check. `--help` prints usage and exits successfully;
292
- unknown arguments fail.
293
-
294
304
  ## Generate dependency update configuration
295
305
 
296
306
  Run `bunx --no-install stll-dependabot` from the repository root. It reads tracked
@@ -394,6 +404,7 @@ Add an explicit declaration to tracked root `stll-toolchain.json`:
394
404
  "cloud": {
395
405
  "services": ["postgres", "valkey"],
396
406
  "install": "bun install --frozen-lockfile",
407
+ "submodules": true,
397
408
  "envFile": ".env.cloud",
398
409
  "rust": {
399
410
  "components": ["clippy", "rustfmt"],
@@ -415,7 +426,13 @@ only. No `cloud` declaration means no cloud setup script. `envFile` is required
415
426
  with services and rejected without services; runtime-only scripts emit no
416
427
  environment file code. With services, `envFile` must be a canonical
417
428
  repository-relative path; its existing parent must be safe at runtime. Track an exact stable Node patch in root
418
- `.node-version` within the shared Node series. Generate and commit the script:
429
+ `.node-version` within the shared Node series.
430
+
431
+ Set `cloud.submodules` to `true` when workspace inputs are held in Git
432
+ submodules. The networked install phase synchronizes and shallow-initializes
433
+ submodules recursively before dependency installation; startup remains offline.
434
+
435
+ Generate and commit the script:
419
436
 
420
437
  ```sh
421
438
  bunx --no-install stll-cloud-setup
@@ -952,25 +969,25 @@ aliases), oxlint, oxlint-tsgolint, and shared tooling pins. Lockfile
952
969
  resolutions determine installed package versions; manifest ranges alone do not.
953
970
  Resolution locations and importer bindings are retained: swapping compiler
954
971
  versions between workspaces cannot look unchanged. Compiler specifier changes
955
- run parity even when the resolved release version is unchanged. Unknown lock
956
- shapes and ambiguous resolutions report an unreadable snapshot. Supported text
957
- locks include Bun JSONC (schema 0/1), pnpm YAML (5.4/6/9), npm package-lock/
972
+ report `typescript` even when the resolved release version is unchanged. Unknown
973
+ lock shapes and ambiguous resolutions report an unreadable snapshot. Supported
974
+ text locks include Bun JSONC (schema 0/1), pnpm YAML (5.4/6/9), npm package-lock/
958
975
  shrinkwrap (1/2/3), and bounded Yarn Classic/Berry shapes; a binary-only Bun lock
959
976
  cannot be compared without executing Bun.
960
977
  Workflow/action and Docker definition edits conservatively force full CI.
961
- Unrelated application dependency changes do not force compiler parity.
978
+ Unrelated application dependency changes do not report a compiler change.
962
979
  Setup-action runtime selectors and their tracked version-file contents must
963
980
  identify an exact stable release. Floating selectors,
964
981
  ranges, expressions, empty
965
- values, or omitted runtime versions report an unreadable snapshot and run parity
966
- even when their committed text is unchanged.
982
+ values, or omitted runtime versions report an unreadable snapshot even when
983
+ their committed text is unchanged.
967
984
 
968
- On pull requests, run the repository's ordinary Bun typecheck and the probe,
969
- then select parity using the same detector:
985
+ On pull requests, run the repository's ordinary Bun typecheck and the probe. The
986
+ shared `rust-napi-ci.yml` workflow runs both when called with `typecheck: true`;
987
+ elsewhere, run:
970
988
 
971
989
  ```sh
972
990
  stll-typecheck-probe --project packages/api/tsconfig.json --seed-dir packages/api/src -- bun run typecheck
973
- stll-typecheck-parity --changed-since origin/main --project packages/api/tsconfig.json
974
991
  ```
975
992
 
976
993
  The probe writes an exclusive temporary TypeScript file in the declared
@@ -981,35 +998,31 @@ excluded seeds fail instead of producing a vacuous pass. Commands are argv,
981
998
  not shell expressions. Cleanup also runs on failure and handled termination.
982
999
  Repeat the probe for independently checked projects as needed.
983
1000
 
984
- Conditional parity runs when Bun, TypeScript, or shared declarations change;
985
- otherwise it prints `parity skipped: toolchain unchanged since ...`. An unreadable
986
- reference runs full parity. Nightly jobs omit `--changed-since` to run full parity.
987
- Node and lint-tool changes still force full CI through the shared detector.
988
-
989
1001
  Workflow, composite-action, Docker, mise, and tool-version declarations are
990
- conservatively fingerprinted for compiler parity, including referenced tracked
1002
+ conservatively fingerprinted as `shared` changes, including referenced tracked
991
1003
  setup-action version files (Node, Bun, Python, Go, Java and other runtimes).
992
1004
  Rust toolchain-file selectors and conventional runtime files are included;
993
1005
  cache-dependency-path is not a runtime selector. Compose and Kubernetes image
994
- definitions are conservatively fingerprinted alongside Dockerfiles. Catalog and unresolved declaration changes also force parity;
995
- an unclassifiable reference runs full parity. This may run parity for unrelated
996
- edits to these declaration files. Active installed compiler comparisons still
997
- use the owning lockfile resolutions.
1006
+ definitions are conservatively fingerprinted alongside Dockerfiles. Catalog and
1007
+ unresolved declaration changes also report a change; an unclassifiable reference
1008
+ reports an unreadable snapshot. This may report a change for unrelated edits to
1009
+ these declaration files. Installed compiler comparisons use the owning lockfile
1010
+ resolutions.
998
1011
 
999
1012
  Compiler patch declarations, lockfile patch hashes, and their tracked patch files
1000
1013
  are included even when the compiler version is unchanged. Compiler patch-package
1001
1014
  files are included too. Missing referenced compiler patches fail closed; unrelated
1002
- package patches do not trigger compiler parity.
1015
+ package patches do not report a compiler change.
1003
1016
 
1004
1017
  Compiler manifest specifiers and complete compiler lock entries form part of the
1005
1018
  change identity, including resolved URLs, integrity, commits, checksums and patch
1006
- hashes. Changing a source at the same release version runs parity. Local compiler
1007
- sources without an immutable byte identity fail closed; a version alone does not
1008
- identify a local directory. Git compiler sources require a full commit identity.
1009
- Supported text locks include Bun, npm, pnpm and bounded
1010
- Yarn Classic/Berry shapes; unrecognized lock shapes run parity. Yarn compiler
1011
- `patch:` protocols are unsupported and run parity because their patch bytes are
1012
- not represented by the lock checksum alone.
1019
+ hashes. Changing a source at the same release version reports `typescript`. Local
1020
+ compiler sources without an immutable byte identity fail closed; a version alone
1021
+ does not identify a local directory. Git compiler sources require a full commit
1022
+ identity. Supported text locks include Bun, npm, pnpm and bounded
1023
+ Yarn Classic/Berry shapes; unrecognized lock shapes report an unreadable snapshot.
1024
+ Yarn compiler `patch:` protocols are unsupported and report an unreadable
1025
+ snapshot because their patch bytes are not represented by the lock checksum alone.
1013
1026
 
1014
1027
  ## Rust selectors
1015
1028
 
@@ -1021,8 +1034,10 @@ Cargo manifest `rust-version` remains an MSRV floor at or below the shared pin.
1021
1034
 
1022
1035
  Only `rustExceptions` in the consumer's root `stll-toolchain.json` can authorize
1023
1036
  another exact stable release. Each record contains exactly `pin`, `reason`,
1024
- `tracking` (a GitHub issue URL) and `expires` (a future `YYYY-MM-DD` date).
1025
- Channels, expired records and `rust-version` rule opt-outs fail validation.
1037
+ `tracking` (a GitHub issue URL) and `expires` (a `YYYY-MM-DD` date).
1038
+ Channels and `rust-version` rule opt-outs fail validation. A record expires on
1039
+ its date and then follows the same expiry scope as quarantine excludes (see
1040
+ [Quarantine preset and expiry checks](#quarantine-preset-and-expiry-checks)).
1026
1041
  See the [root policy guide](../../README.md) for a complete declaration.
1027
1042
 
1028
1043
  `stll-toolchain-check` requires tracked JavaScript and TypeScript files selected by type-aware lint to belong to declared TypeScript projects. See the [Node scripts project recipe](https://github.com/stella/tooling/blob/main/README.md) for scripts outside the library project. The check inventories Oxlint-selected files and expands compiler configurations; it does not run lint or type checking.
@@ -1046,16 +1061,33 @@ creation timestamps remain stable across runs; they are not expiries.
1046
1061
 
1047
1062
  Third-party entries require `# quarantine-expires: YYYY-MM-DDTHH:mm:ss.sssZ`.
1048
1063
  `stll-toolchain-check` warns 48 hours before expiry; warnings continue through
1049
- the existing 24-hour removal grace, after which expired entries fail. The
1050
- quarantine rule cannot be opted out. `stll-quarantine --check` is read-only;
1064
+ the existing 24-hour removal grace, after which expired entries fail where the
1065
+ run can act on them. The same scope applies to expired `rustExceptions`. The
1066
+ clock alone never fails a change that leaves an entry untouched:
1067
+
1068
+ - `push`, `schedule`, `workflow_dispatch` and other GitHub Actions events, and
1069
+ non-GitHub CI (`CI` set), fail every overdue entry, which prompts the removal
1070
+ PR.
1071
+ - `pull_request`, `pull_request_target` and `merge_group` fail an overdue entry
1072
+ only when the change adds it or edits its expiry, compared with the event's
1073
+ base commit; inherited overdue entries warn. A shallow checkout that lacks the
1074
+ base fetches exactly that commit from its remote
1075
+ (`git fetch --no-tags --depth=1 origin <base>`, using the checkout's
1076
+ credentials). Only if that also fails does an overdue entry fail, with the
1077
+ reason. Entries that have not expired never need the base.
1078
+ - Local runs outside CI warn.
1079
+
1080
+ The quarantine rule cannot be opted out. `stll-quarantine --check` is read-only;
1051
1081
  `--prune` removes expired third-party entries without removing first-party ones.
1052
1082
  `--help` lists modes. Linked output files are rejected.
1053
1083
 
1054
1084
  `@stll/oxlint-config/quarantine` exports the Node-compatible repository helpers
1055
1085
  `checkRepositoryQuarantine`, `synchronizeRepositoryQuarantine`, and
1056
1086
  `pruneRepositoryQuarantine`, accepting a tracked `files` snapshot and optional
1057
- `now`. The toolchain API reports advisory expiry messages through `onWarning`;
1058
- its returned diagnostics remain failures. Snapshot readers keep lockfiles
1087
+ `now`, plus an optional `expiry` scope (`{ kind: "enforce" }` by default). The
1088
+ toolchain API takes the same scope as `expiryScope`, reports advisory
1089
+ expiry messages through `onWarning`, and its returned diagnostics remain
1090
+ failures. Snapshot readers keep lockfiles
1059
1091
  opaque by default; `{ bunLock: "content" }` explicitly requests the root graph
1060
1092
  when quarantine identity checks need it.
1061
1093
 
@@ -56,7 +56,11 @@ const main = async () => {
56
56
  if (cloud === void 0) throw new Error("requires an explicit cloud declaration");
57
57
  const nodeVersion = files[".node-version"];
58
58
  if (nodeVersion === void 0) throw new Error("requires tracked root .node-version");
59
- const policy = require_toolchain_schema.parseToolchainPolicy(JSON.parse(await (0, node_fs_promises.readFile)(new URL("../toolchain.json", require("url").pathToFileURL(__filename).href), "utf8")));
59
+ const sharedPolicy = require_toolchain_schema.parseToolchainPolicy(JSON.parse(await (0, node_fs_promises.readFile)(new URL("../toolchain.json", require("url").pathToFileURL(__filename).href), "utf8")));
60
+ const policy = {
61
+ ...sharedPolicy,
62
+ bun: require_toolchain_guard.repositoryBun(sharedPolicy.bun, files["package.json"])
63
+ };
60
64
  const script = require_toolchain_inputs.generateCloudSetup({
61
65
  policy,
62
66
  cloud,
@@ -1 +1 @@
1
- {"version":3,"file":"cloud-setup-cli.cjs","names":["checkGeneratedOutput","open","constants","cloudClaudeSettingsPath","cloudSessionStartFix","realpath","readToolchainInputs","join","cloudSetupPath","generationDiagnostics","parseToolchainConfiguration","parseToolchainPolicy","readFile","generateCloudSetup","mergeCloudClaudeSettings","writeGeneratedFile"],"sources":["../src/cloud-setup-cli.ts"],"sourcesContent":["#!/usr/bin/env node\nimport { constants } from \"node:fs\";\nimport { open, readFile, realpath } from \"node:fs/promises\";\nimport { join } from \"node:path\";\n\nimport { cloudSetupPath, generateCloudSetup } from \"./cloud-setup\";\nimport {\n cloudClaudeSettingsPath,\n cloudSessionStartFix,\n mergeCloudClaudeSettings,\n} from \"./cloud-setup-claude\";\nimport {\n checkGeneratedOutput,\n generationDiagnostics,\n writeGeneratedFile,\n} from \"./generated-file\";\nimport {\n parseToolchainConfiguration,\n readToolchainInputs,\n} from \"./toolchain-guard\";\nimport { parseToolchainPolicy } from \"./toolchain-schema\";\n\nconst usage =\n \"Usage: stll-cloud-setup (run from repository root)\\n stll-cloud-setup --help\";\nconst readClaudeSettings = async (destination: string) => {\n try {\n if ((await checkGeneratedOutput(destination)) === undefined)\n return undefined;\n const input = await open(\n destination,\n constants.O_RDONLY | constants.O_NOFOLLOW,\n );\n try {\n const opened = await input.stat();\n if (!opened.isFile() || opened.nlink !== 1)\n throw new Error(\n \"settings must be a single-link regular repository file\",\n );\n return { text: await input.readFile(\"utf8\"), mode: opened.mode & 0o777 };\n } finally {\n await input.close();\n }\n } catch (error) {\n throw new Error(\n `cannot safely merge ${cloudClaudeSettingsPath}: ${error instanceof Error ? error.message : String(error)}; ${cloudSessionStartFix}`,\n );\n }\n};\n\nconst main = async () => {\n const args = process.argv.slice(2);\n if (args.length === 1 && args.at(0) === \"--help\") {\n process.stdout.write(`${usage}\\n`);\n return;\n }\n if (args.length !== 0) throw new Error(usage);\n const root = await realpath(process.cwd());\n const { files, diagnostics } = readToolchainInputs(root);\n const destination = join(root, cloudSetupPath);\n const settingsDestination = join(root, cloudClaudeSettingsPath);\n // Validate settings separately to retain actionable merge diagnostics.\n const settings = await readClaudeSettings(settingsDestination);\n const remainingDiagnostics = await generationDiagnostics({\n diagnostics,\n outputs: [\n { relative: cloudSetupPath, destination },\n { relative: cloudClaudeSettingsPath, destination: settingsDestination },\n ],\n });\n if (remainingDiagnostics.length > 0)\n throw new Error(\n remainingDiagnostics\n .map(\n ({ path, message }) =>\n `${path}: ${message}${path === cloudClaudeSettingsPath ? `; ${cloudSessionStartFix}` : \"\"}`,\n )\n .join(\"\\n\"),\n );\n const text = files[\"stll-toolchain.json\"];\n if (text === undefined)\n throw new Error(\"requires tracked stll-toolchain.json\");\n const { cloud, rustExceptions } = parseToolchainConfiguration(\n JSON.parse(text),\n );\n if (cloud === undefined)\n throw new Error(\"requires an explicit cloud declaration\");\n const nodeVersion = files[\".node-version\"];\n if (nodeVersion === undefined)\n throw new Error(\"requires tracked root .node-version\");\n const policy = parseToolchainPolicy(\n JSON.parse(\n await readFile(new URL(\"../toolchain.json\", import.meta.url), \"utf8\"),\n ),\n );\n const script = generateCloudSetup({\n policy,\n cloud,\n nodeVersion: nodeVersion.trim(),\n files,\n rustExceptions,\n });\n const mergedSettings = mergeCloudClaudeSettings(settings?.text);\n await writeGeneratedFile({ destination, text: script, mode: 0o755 });\n if (mergedSettings !== settings?.text)\n await writeGeneratedFile({\n destination: settingsDestination,\n text: mergedSettings,\n mode: settings?.mode ?? 0o644,\n });\n process.stdout.write(\n `Generated ${cloudSetupPath} and ${cloudClaudeSettingsPath}\\n`,\n );\n};\n\nmain().catch((error: unknown) => {\n process.stderr.write(\n `cloud-setup: ${error instanceof Error ? error.message : String(error)}\\n`,\n );\n process.exitCode = 1;\n});\n"],"mappings":"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"}
1
+ {"version":3,"file":"cloud-setup-cli.cjs","names":["checkGeneratedOutput","open","constants","cloudClaudeSettingsPath","cloudSessionStartFix","realpath","readToolchainInputs","join","cloudSetupPath","generationDiagnostics","parseToolchainConfiguration","parseToolchainPolicy","readFile","repositoryBun","generateCloudSetup","mergeCloudClaudeSettings","writeGeneratedFile"],"sources":["../src/cloud-setup-cli.ts"],"sourcesContent":["#!/usr/bin/env node\nimport { constants } from \"node:fs\";\nimport { open, readFile, realpath } from \"node:fs/promises\";\nimport { join } from \"node:path\";\n\nimport { cloudSetupPath, generateCloudSetup } from \"./cloud-setup\";\nimport {\n cloudClaudeSettingsPath,\n cloudSessionStartFix,\n mergeCloudClaudeSettings,\n} from \"./cloud-setup-claude\";\nimport {\n checkGeneratedOutput,\n generationDiagnostics,\n writeGeneratedFile,\n} from \"./generated-file\";\nimport { repositoryBun } from \"./toolchain-bun\";\nimport {\n parseToolchainConfiguration,\n readToolchainInputs,\n} from \"./toolchain-guard\";\nimport { parseToolchainPolicy } from \"./toolchain-schema\";\n\nconst usage =\n \"Usage: stll-cloud-setup (run from repository root)\\n stll-cloud-setup --help\";\nconst readClaudeSettings = async (destination: string) => {\n try {\n if ((await checkGeneratedOutput(destination)) === undefined)\n return undefined;\n const input = await open(\n destination,\n constants.O_RDONLY | constants.O_NOFOLLOW,\n );\n try {\n const opened = await input.stat();\n if (!opened.isFile() || opened.nlink !== 1)\n throw new Error(\n \"settings must be a single-link regular repository file\",\n );\n return { text: await input.readFile(\"utf8\"), mode: opened.mode & 0o777 };\n } finally {\n await input.close();\n }\n } catch (error) {\n throw new Error(\n `cannot safely merge ${cloudClaudeSettingsPath}: ${error instanceof Error ? error.message : String(error)}; ${cloudSessionStartFix}`,\n );\n }\n};\n\nconst main = async () => {\n const args = process.argv.slice(2);\n if (args.length === 1 && args.at(0) === \"--help\") {\n process.stdout.write(`${usage}\\n`);\n return;\n }\n if (args.length !== 0) throw new Error(usage);\n const root = await realpath(process.cwd());\n const { files, diagnostics } = readToolchainInputs(root);\n const destination = join(root, cloudSetupPath);\n const settingsDestination = join(root, cloudClaudeSettingsPath);\n // Validate settings separately to retain actionable merge diagnostics.\n const settings = await readClaudeSettings(settingsDestination);\n const remainingDiagnostics = await generationDiagnostics({\n diagnostics,\n outputs: [\n { relative: cloudSetupPath, destination },\n { relative: cloudClaudeSettingsPath, destination: settingsDestination },\n ],\n });\n if (remainingDiagnostics.length > 0)\n throw new Error(\n remainingDiagnostics\n .map(\n ({ path, message }) =>\n `${path}: ${message}${path === cloudClaudeSettingsPath ? `; ${cloudSessionStartFix}` : \"\"}`,\n )\n .join(\"\\n\"),\n );\n const text = files[\"stll-toolchain.json\"];\n if (text === undefined)\n throw new Error(\"requires tracked stll-toolchain.json\");\n const { cloud, rustExceptions } = parseToolchainConfiguration(\n JSON.parse(text),\n );\n if (cloud === undefined)\n throw new Error(\"requires an explicit cloud declaration\");\n const nodeVersion = files[\".node-version\"];\n if (nodeVersion === undefined)\n throw new Error(\"requires tracked root .node-version\");\n const sharedPolicy = parseToolchainPolicy(\n JSON.parse(\n await readFile(new URL(\"../toolchain.json\", import.meta.url), \"utf8\"),\n ),\n );\n const policy = {\n ...sharedPolicy,\n bun: repositoryBun(sharedPolicy.bun, files[\"package.json\"]),\n };\n const script = generateCloudSetup({\n policy,\n cloud,\n nodeVersion: nodeVersion.trim(),\n files,\n rustExceptions,\n });\n const mergedSettings = mergeCloudClaudeSettings(settings?.text);\n await writeGeneratedFile({ destination, text: script, mode: 0o755 });\n if (mergedSettings !== settings?.text)\n await writeGeneratedFile({\n destination: settingsDestination,\n text: mergedSettings,\n mode: settings?.mode ?? 0o644,\n });\n process.stdout.write(\n `Generated ${cloudSetupPath} and ${cloudClaudeSettingsPath}\\n`,\n );\n};\n\nmain().catch((error: unknown) => {\n process.stderr.write(\n `cloud-setup: ${error instanceof Error ? error.message : String(error)}\\n`,\n );\n process.exitCode = 1;\n});\n"],"mappings":"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"}
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env node
2
2
  import { n as generationDiagnostics, r as writeGeneratedFile, t as checkGeneratedOutput } from "./generated-file.mjs";
3
3
  import { C as cloudSetupPath, S as mergeCloudClaudeSettings, v as cloudClaudeSettingsPath, w as generateCloudSetup, y as cloudSessionStartFix } from "./toolchain-inputs.mjs";
4
- import { n as parseToolchainConfiguration, r as readToolchainInputs } from "./toolchain-guard.mjs";
4
+ import { i as repositoryBun, n as parseToolchainConfiguration, r as readToolchainInputs } from "./toolchain-guard.mjs";
5
5
  import { t as parseToolchainPolicy } from "./toolchain-schema.mjs";
6
6
  import { open, readFile, realpath } from "node:fs/promises";
7
7
  import { join } from "node:path";
@@ -55,7 +55,11 @@ const main = async () => {
55
55
  if (cloud === void 0) throw new Error("requires an explicit cloud declaration");
56
56
  const nodeVersion = files[".node-version"];
57
57
  if (nodeVersion === void 0) throw new Error("requires tracked root .node-version");
58
- const policy = parseToolchainPolicy(JSON.parse(await readFile(new URL("../toolchain.json", import.meta.url), "utf8")));
58
+ const sharedPolicy = parseToolchainPolicy(JSON.parse(await readFile(new URL("../toolchain.json", import.meta.url), "utf8")));
59
+ const policy = {
60
+ ...sharedPolicy,
61
+ bun: repositoryBun(sharedPolicy.bun, files["package.json"])
62
+ };
59
63
  const script = generateCloudSetup({
60
64
  policy,
61
65
  cloud,
@@ -1 +1 @@
1
- {"version":3,"file":"cloud-setup-cli.mjs","names":[],"sources":["../src/cloud-setup-cli.ts"],"sourcesContent":["#!/usr/bin/env node\nimport { constants } from \"node:fs\";\nimport { open, readFile, realpath } from \"node:fs/promises\";\nimport { join } from \"node:path\";\n\nimport { cloudSetupPath, generateCloudSetup } from \"./cloud-setup\";\nimport {\n cloudClaudeSettingsPath,\n cloudSessionStartFix,\n mergeCloudClaudeSettings,\n} from \"./cloud-setup-claude\";\nimport {\n checkGeneratedOutput,\n generationDiagnostics,\n writeGeneratedFile,\n} from \"./generated-file\";\nimport {\n parseToolchainConfiguration,\n readToolchainInputs,\n} from \"./toolchain-guard\";\nimport { parseToolchainPolicy } from \"./toolchain-schema\";\n\nconst usage =\n \"Usage: stll-cloud-setup (run from repository root)\\n stll-cloud-setup --help\";\nconst readClaudeSettings = async (destination: string) => {\n try {\n if ((await checkGeneratedOutput(destination)) === undefined)\n return undefined;\n const input = await open(\n destination,\n constants.O_RDONLY | constants.O_NOFOLLOW,\n );\n try {\n const opened = await input.stat();\n if (!opened.isFile() || opened.nlink !== 1)\n throw new Error(\n \"settings must be a single-link regular repository file\",\n );\n return { text: await input.readFile(\"utf8\"), mode: opened.mode & 0o777 };\n } finally {\n await input.close();\n }\n } catch (error) {\n throw new Error(\n `cannot safely merge ${cloudClaudeSettingsPath}: ${error instanceof Error ? error.message : String(error)}; ${cloudSessionStartFix}`,\n );\n }\n};\n\nconst main = async () => {\n const args = process.argv.slice(2);\n if (args.length === 1 && args.at(0) === \"--help\") {\n process.stdout.write(`${usage}\\n`);\n return;\n }\n if (args.length !== 0) throw new Error(usage);\n const root = await realpath(process.cwd());\n const { files, diagnostics } = readToolchainInputs(root);\n const destination = join(root, cloudSetupPath);\n const settingsDestination = join(root, cloudClaudeSettingsPath);\n // Validate settings separately to retain actionable merge diagnostics.\n const settings = await readClaudeSettings(settingsDestination);\n const remainingDiagnostics = await generationDiagnostics({\n diagnostics,\n outputs: [\n { relative: cloudSetupPath, destination },\n { relative: cloudClaudeSettingsPath, destination: settingsDestination },\n ],\n });\n if (remainingDiagnostics.length > 0)\n throw new Error(\n remainingDiagnostics\n .map(\n ({ path, message }) =>\n `${path}: ${message}${path === cloudClaudeSettingsPath ? `; ${cloudSessionStartFix}` : \"\"}`,\n )\n .join(\"\\n\"),\n );\n const text = files[\"stll-toolchain.json\"];\n if (text === undefined)\n throw new Error(\"requires tracked stll-toolchain.json\");\n const { cloud, rustExceptions } = parseToolchainConfiguration(\n JSON.parse(text),\n );\n if (cloud === undefined)\n throw new Error(\"requires an explicit cloud declaration\");\n const nodeVersion = files[\".node-version\"];\n if (nodeVersion === undefined)\n throw new Error(\"requires tracked root .node-version\");\n const policy = parseToolchainPolicy(\n JSON.parse(\n await readFile(new URL(\"../toolchain.json\", import.meta.url), \"utf8\"),\n ),\n );\n const script = generateCloudSetup({\n policy,\n cloud,\n nodeVersion: nodeVersion.trim(),\n files,\n rustExceptions,\n });\n const mergedSettings = mergeCloudClaudeSettings(settings?.text);\n await writeGeneratedFile({ destination, text: script, mode: 0o755 });\n if (mergedSettings !== settings?.text)\n await writeGeneratedFile({\n destination: settingsDestination,\n text: mergedSettings,\n mode: settings?.mode ?? 0o644,\n });\n process.stdout.write(\n `Generated ${cloudSetupPath} and ${cloudClaudeSettingsPath}\\n`,\n );\n};\n\nmain().catch((error: unknown) => {\n process.stderr.write(\n `cloud-setup: ${error instanceof Error ? error.message : String(error)}\\n`,\n );\n process.exitCode = 1;\n});\n"],"mappings":";;;;;;;;;AAsBA,MAAM,QACJ;AACF,MAAM,qBAAqB,OAAO,gBAAwB;CACxD,IAAI;EACF,IAAK,MAAM,qBAAqB,WAAW,MAAO,KAAA,GAChD,OAAO,KAAA;EACT,MAAM,QAAQ,MAAM,KAClB,aACA,UAAU,WAAW,UAAU,UACjC;EACA,IAAI;GACF,MAAM,SAAS,MAAM,MAAM,KAAK;GAChC,IAAI,CAAC,OAAO,OAAO,KAAK,OAAO,UAAU,GACvC,MAAM,IAAI,MACR,wDACF;GACF,OAAO;IAAE,MAAM,MAAM,MAAM,SAAS,MAAM;IAAG,MAAM,OAAO,OAAO;GAAM;EACzE,UAAU;GACR,MAAM,MAAM,MAAM;EACpB;CACF,SAAS,OAAO;EACd,MAAM,IAAI,MACR,uBAAuB,wBAAwB,IAAI,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK,EAAE,IAAI,sBAChH;CACF;AACF;AAEA,MAAM,OAAO,YAAY;CACvB,MAAM,OAAO,QAAQ,KAAK,MAAM,CAAC;CACjC,IAAI,KAAK,WAAW,KAAK,KAAK,GAAG,CAAC,MAAM,UAAU;EAChD,QAAQ,OAAO,MAAM,GAAG,MAAM,GAAG;EACjC;CACF;CACA,IAAI,KAAK,WAAW,GAAG,MAAM,IAAI,MAAM,KAAK;CAC5C,MAAM,OAAO,MAAM,SAAS,QAAQ,IAAI,CAAC;CACzC,MAAM,EAAE,OAAO,gBAAgB,oBAAoB,IAAI;CACvD,MAAM,cAAc,KAAK,MAAM,cAAc;CAC7C,MAAM,sBAAsB,KAAK,MAAM,uBAAuB;CAE9D,MAAM,WAAW,MAAM,mBAAmB,mBAAmB;CAC7D,MAAM,uBAAuB,MAAM,sBAAsB;EACvD;EACA,SAAS,CACP;GAAE,UAAU;GAAgB;EAAY,GACxC;GAAE,UAAU;GAAyB,aAAa;EAAoB,CACxE;CACF,CAAC;CACD,IAAI,qBAAqB,SAAS,GAChC,MAAM,IAAI,MACR,qBACG,KACE,EAAE,MAAM,cACP,GAAG,KAAK,IAAI,UAAU,SAAA,0BAAmC,KAAK,yBAAyB,IAC3F,CAAC,CACA,KAAK,IAAI,CACd;CACF,MAAM,OAAO,MAAM;CACnB,IAAI,SAAS,KAAA,GACX,MAAM,IAAI,MAAM,sCAAsC;CACxD,MAAM,EAAE,OAAO,mBAAmB,4BAChC,KAAK,MAAM,IAAI,CACjB;CACA,IAAI,UAAU,KAAA,GACZ,MAAM,IAAI,MAAM,wCAAwC;CAC1D,MAAM,cAAc,MAAM;CAC1B,IAAI,gBAAgB,KAAA,GAClB,MAAM,IAAI,MAAM,qCAAqC;CACvD,MAAM,SAAS,qBACb,KAAK,MACH,MAAM,SAAS,IAAI,IAAI,qBAAqB,YAAY,GAAG,GAAG,MAAM,CACtE,CACF;CACA,MAAM,SAAS,mBAAmB;EAChC;EACA;EACA,aAAa,YAAY,KAAK;EAC9B;EACA;CACF,CAAC;CACD,MAAM,iBAAiB,yBAAyB,UAAU,IAAI;CAC9D,MAAM,mBAAmB;EAAE;EAAa,MAAM;EAAQ,MAAM;CAAM,CAAC;CACnE,IAAI,mBAAmB,UAAU,MAC/B,MAAM,mBAAmB;EACvB,aAAa;EACb,MAAM;EACN,MAAM,UAAU,QAAQ;CAC1B,CAAC;CACH,QAAQ,OAAO,MACb,aAAa,eAAe,OAAO,wBAAwB,GAC7D;AACF;AAEA,KAAK,CAAC,CAAC,OAAO,UAAmB;CAC/B,QAAQ,OAAO,MACb,gBAAgB,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK,EAAE,GACzE;CACA,QAAQ,WAAW;AACrB,CAAC"}
1
+ {"version":3,"file":"cloud-setup-cli.mjs","names":[],"sources":["../src/cloud-setup-cli.ts"],"sourcesContent":["#!/usr/bin/env node\nimport { constants } from \"node:fs\";\nimport { open, readFile, realpath } from \"node:fs/promises\";\nimport { join } from \"node:path\";\n\nimport { cloudSetupPath, generateCloudSetup } from \"./cloud-setup\";\nimport {\n cloudClaudeSettingsPath,\n cloudSessionStartFix,\n mergeCloudClaudeSettings,\n} from \"./cloud-setup-claude\";\nimport {\n checkGeneratedOutput,\n generationDiagnostics,\n writeGeneratedFile,\n} from \"./generated-file\";\nimport { repositoryBun } from \"./toolchain-bun\";\nimport {\n parseToolchainConfiguration,\n readToolchainInputs,\n} from \"./toolchain-guard\";\nimport { parseToolchainPolicy } from \"./toolchain-schema\";\n\nconst usage =\n \"Usage: stll-cloud-setup (run from repository root)\\n stll-cloud-setup --help\";\nconst readClaudeSettings = async (destination: string) => {\n try {\n if ((await checkGeneratedOutput(destination)) === undefined)\n return undefined;\n const input = await open(\n destination,\n constants.O_RDONLY | constants.O_NOFOLLOW,\n );\n try {\n const opened = await input.stat();\n if (!opened.isFile() || opened.nlink !== 1)\n throw new Error(\n \"settings must be a single-link regular repository file\",\n );\n return { text: await input.readFile(\"utf8\"), mode: opened.mode & 0o777 };\n } finally {\n await input.close();\n }\n } catch (error) {\n throw new Error(\n `cannot safely merge ${cloudClaudeSettingsPath}: ${error instanceof Error ? error.message : String(error)}; ${cloudSessionStartFix}`,\n );\n }\n};\n\nconst main = async () => {\n const args = process.argv.slice(2);\n if (args.length === 1 && args.at(0) === \"--help\") {\n process.stdout.write(`${usage}\\n`);\n return;\n }\n if (args.length !== 0) throw new Error(usage);\n const root = await realpath(process.cwd());\n const { files, diagnostics } = readToolchainInputs(root);\n const destination = join(root, cloudSetupPath);\n const settingsDestination = join(root, cloudClaudeSettingsPath);\n // Validate settings separately to retain actionable merge diagnostics.\n const settings = await readClaudeSettings(settingsDestination);\n const remainingDiagnostics = await generationDiagnostics({\n diagnostics,\n outputs: [\n { relative: cloudSetupPath, destination },\n { relative: cloudClaudeSettingsPath, destination: settingsDestination },\n ],\n });\n if (remainingDiagnostics.length > 0)\n throw new Error(\n remainingDiagnostics\n .map(\n ({ path, message }) =>\n `${path}: ${message}${path === cloudClaudeSettingsPath ? `; ${cloudSessionStartFix}` : \"\"}`,\n )\n .join(\"\\n\"),\n );\n const text = files[\"stll-toolchain.json\"];\n if (text === undefined)\n throw new Error(\"requires tracked stll-toolchain.json\");\n const { cloud, rustExceptions } = parseToolchainConfiguration(\n JSON.parse(text),\n );\n if (cloud === undefined)\n throw new Error(\"requires an explicit cloud declaration\");\n const nodeVersion = files[\".node-version\"];\n if (nodeVersion === undefined)\n throw new Error(\"requires tracked root .node-version\");\n const sharedPolicy = parseToolchainPolicy(\n JSON.parse(\n await readFile(new URL(\"../toolchain.json\", import.meta.url), \"utf8\"),\n ),\n );\n const policy = {\n ...sharedPolicy,\n bun: repositoryBun(sharedPolicy.bun, files[\"package.json\"]),\n };\n const script = generateCloudSetup({\n policy,\n cloud,\n nodeVersion: nodeVersion.trim(),\n files,\n rustExceptions,\n });\n const mergedSettings = mergeCloudClaudeSettings(settings?.text);\n await writeGeneratedFile({ destination, text: script, mode: 0o755 });\n if (mergedSettings !== settings?.text)\n await writeGeneratedFile({\n destination: settingsDestination,\n text: mergedSettings,\n mode: settings?.mode ?? 0o644,\n });\n process.stdout.write(\n `Generated ${cloudSetupPath} and ${cloudClaudeSettingsPath}\\n`,\n );\n};\n\nmain().catch((error: unknown) => {\n process.stderr.write(\n `cloud-setup: ${error instanceof Error ? error.message : String(error)}\\n`,\n );\n process.exitCode = 1;\n});\n"],"mappings":";;;;;;;;;AAuBA,MAAM,QACJ;AACF,MAAM,qBAAqB,OAAO,gBAAwB;CACxD,IAAI;EACF,IAAK,MAAM,qBAAqB,WAAW,MAAO,KAAA,GAChD,OAAO,KAAA;EACT,MAAM,QAAQ,MAAM,KAClB,aACA,UAAU,WAAW,UAAU,UACjC;EACA,IAAI;GACF,MAAM,SAAS,MAAM,MAAM,KAAK;GAChC,IAAI,CAAC,OAAO,OAAO,KAAK,OAAO,UAAU,GACvC,MAAM,IAAI,MACR,wDACF;GACF,OAAO;IAAE,MAAM,MAAM,MAAM,SAAS,MAAM;IAAG,MAAM,OAAO,OAAO;GAAM;EACzE,UAAU;GACR,MAAM,MAAM,MAAM;EACpB;CACF,SAAS,OAAO;EACd,MAAM,IAAI,MACR,uBAAuB,wBAAwB,IAAI,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK,EAAE,IAAI,sBAChH;CACF;AACF;AAEA,MAAM,OAAO,YAAY;CACvB,MAAM,OAAO,QAAQ,KAAK,MAAM,CAAC;CACjC,IAAI,KAAK,WAAW,KAAK,KAAK,GAAG,CAAC,MAAM,UAAU;EAChD,QAAQ,OAAO,MAAM,GAAG,MAAM,GAAG;EACjC;CACF;CACA,IAAI,KAAK,WAAW,GAAG,MAAM,IAAI,MAAM,KAAK;CAC5C,MAAM,OAAO,MAAM,SAAS,QAAQ,IAAI,CAAC;CACzC,MAAM,EAAE,OAAO,gBAAgB,oBAAoB,IAAI;CACvD,MAAM,cAAc,KAAK,MAAM,cAAc;CAC7C,MAAM,sBAAsB,KAAK,MAAM,uBAAuB;CAE9D,MAAM,WAAW,MAAM,mBAAmB,mBAAmB;CAC7D,MAAM,uBAAuB,MAAM,sBAAsB;EACvD;EACA,SAAS,CACP;GAAE,UAAU;GAAgB;EAAY,GACxC;GAAE,UAAU;GAAyB,aAAa;EAAoB,CACxE;CACF,CAAC;CACD,IAAI,qBAAqB,SAAS,GAChC,MAAM,IAAI,MACR,qBACG,KACE,EAAE,MAAM,cACP,GAAG,KAAK,IAAI,UAAU,SAAA,0BAAmC,KAAK,yBAAyB,IAC3F,CAAC,CACA,KAAK,IAAI,CACd;CACF,MAAM,OAAO,MAAM;CACnB,IAAI,SAAS,KAAA,GACX,MAAM,IAAI,MAAM,sCAAsC;CACxD,MAAM,EAAE,OAAO,mBAAmB,4BAChC,KAAK,MAAM,IAAI,CACjB;CACA,IAAI,UAAU,KAAA,GACZ,MAAM,IAAI,MAAM,wCAAwC;CAC1D,MAAM,cAAc,MAAM;CAC1B,IAAI,gBAAgB,KAAA,GAClB,MAAM,IAAI,MAAM,qCAAqC;CACvD,MAAM,eAAe,qBACnB,KAAK,MACH,MAAM,SAAS,IAAI,IAAI,qBAAqB,YAAY,GAAG,GAAG,MAAM,CACtE,CACF;CACA,MAAM,SAAS;EACb,GAAG;EACH,KAAK,cAAc,aAAa,KAAK,MAAM,eAAe;CAC5D;CACA,MAAM,SAAS,mBAAmB;EAChC;EACA;EACA,aAAa,YAAY,KAAK;EAC9B;EACA;CACF,CAAC;CACD,MAAM,iBAAiB,yBAAyB,UAAU,IAAI;CAC9D,MAAM,mBAAmB;EAAE;EAAa,MAAM;EAAQ,MAAM;CAAM,CAAC;CACnE,IAAI,mBAAmB,UAAU,MAC/B,MAAM,mBAAmB;EACvB,aAAa;EACb,MAAM;EACN,MAAM,UAAU,QAAQ;CAC1B,CAAC;CACH,QAAQ,OAAO,MACb,aAAa,eAAe,OAAO,wBAAwB,GAC7D;AACF;AAEA,KAAK,CAAC,CAAC,OAAO,UAAmB;CAC/B,QAAQ,OAAO,MACb,gBAAgB,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK,EAAE,GACzE;CACA,QAAQ,WAAW;AACrB,CAAC"}
@@ -103,25 +103,6 @@ export declare const parseToolchainPolicy: (input: unknown) => {
103
103
  sha: string;
104
104
  version: string;
105
105
  }>;
106
- typescriptInstallLayouts: ({
107
- readonly type: "direct";
108
- readonly compilerPackage: "typescript";
109
- readonly compilerSpecifier: string;
110
- readonly typecheckCommand: string;
111
- readonly compatibilityPackage?: never;
112
- readonly compatibilitySpecifier?: never;
113
- } | {
114
- readonly type: "split-compatibility";
115
- readonly compilerPackage: string;
116
- readonly compilerSpecifier: string;
117
- readonly compatibilityPackage: string;
118
- readonly compatibilitySpecifier: string;
119
- readonly typecheckCommand: string;
120
- })[];
121
- typescript6Compatibility: {
122
- version: string;
123
- packageAlias: string;
124
- };
125
106
  dependabot: {
126
107
  schedule: {
127
108
  interval: string;
@@ -103,25 +103,6 @@ export declare const parseToolchainPolicy: (input: unknown) => {
103
103
  sha: string;
104
104
  version: string;
105
105
  }>;
106
- typescriptInstallLayouts: ({
107
- readonly type: "direct";
108
- readonly compilerPackage: "typescript";
109
- readonly compilerSpecifier: string;
110
- readonly typecheckCommand: string;
111
- readonly compatibilityPackage?: never;
112
- readonly compatibilitySpecifier?: never;
113
- } | {
114
- readonly type: "split-compatibility";
115
- readonly compilerPackage: string;
116
- readonly compilerSpecifier: string;
117
- readonly compatibilityPackage: string;
118
- readonly compatibilitySpecifier: string;
119
- readonly typecheckCommand: string;
120
- })[];
121
- typescript6Compatibility: {
122
- version: string;
123
- packageAlias: string;
124
- };
125
106
  dependabot: {
126
107
  schedule: {
127
108
  interval: string;
@@ -1,8 +1,8 @@
1
1
  const require_rolldown_runtime = require("./rolldown-runtime.cjs");
2
2
  let node_path = require("node:path");
3
3
  node_path = require_rolldown_runtime.__toESM(node_path, 1);
4
- let node_fs = require("node:fs");
5
4
  let node_child_process = require("node:child_process");
5
+ let node_fs = require("node:fs");
6
6
  let node_os = require("node:os");
7
7
  //#region src/git-tracked-output.ts
8
8
  /** Stream Git's file list to disk so consumer size cannot exhaust maxBuffer. */
@@ -1,6 +1,6 @@
1
1
  import path from "node:path";
2
- import { closeSync, mkdtempSync, openSync, readFileSync, rmSync } from "node:fs";
3
2
  import { execFileSync } from "node:child_process";
3
+ import { closeSync, mkdtempSync, openSync, readFileSync, rmSync } from "node:fs";
4
4
  import { tmpdir } from "node:os";
5
5
  //#region src/git-tracked-output.ts
6
6
  /** Stream Git's file list to disk so consumer size cannot exhaust maxBuffer. */
@@ -11,8 +11,8 @@ let yaml = require("yaml");
11
11
  let node_os = require("node:os");
12
12
  let node_module = require("node:module");
13
13
  node_module = require_rolldown_runtime.__toESM(node_module, 1);
14
- let acorn = require("acorn");
15
14
  let node_url = require("node:url");
15
+ let acorn = require("acorn");
16
16
  let node_events = require("node:events");
17
17
  let node_readline = require("node:readline");
18
18
  //#region src/consumer-release-pack.ts
@@ -8,8 +8,8 @@ import { lte, parse, satisfies } from "semver";
8
8
  import { isDeepStrictEqual, promisify } from "node:util";
9
9
  import { parseDocument } from "yaml";
10
10
  import { tmpdir } from "node:os";
11
- import { parse as parse$2 } from "acorn";
12
11
  import { fileURLToPath } from "node:url";
12
+ import { parse as parse$2 } from "acorn";
13
13
  import { once } from "node:events";
14
14
  import { createInterface } from "node:readline";
15
15
  //#region src/consumer-release-pack.ts
@@ -9,12 +9,12 @@ const require_publish_artifact_syntax = require("./publish-artifact-syntax.cjs")
9
9
  const require_publish_build_target_vite_dts_helper = require("./publish-build-target-vite-dts-helper2.cjs");
10
10
  let node_path = require("node:path");
11
11
  node_path = require_rolldown_runtime.__toESM(node_path, 1);
12
- let node_fs = require("node:fs");
13
12
  let node_child_process = require("node:child_process");
13
+ let node_fs = require("node:fs");
14
14
  let node_os = require("node:os");
15
15
  let node_module = require("node:module");
16
- let acorn = require("acorn");
17
16
  let node_url = require("node:url");
17
+ let acorn = require("acorn");
18
18
  let esbuild = require("esbuild");
19
19
  //#region src/publish-build-target-nuxt.ts
20
20
  const supportedVersions = {
@@ -7,11 +7,11 @@ import { a as resolveManifestContract, n as readPackedSyntaxFiles, r as checkPub
7
7
  import { n as reviewedViteDtsOptions, t as declarationOnlyDts } from "./publish-build-target-vite-dts-helper2.mjs";
8
8
  import { createRequire } from "node:module";
9
9
  import path from "node:path";
10
- import { existsSync, mkdtempSync, readFileSync, realpathSync, rmSync, writeFileSync } from "node:fs";
11
10
  import { execFileSync, spawnSync } from "node:child_process";
11
+ import { existsSync, mkdtempSync, readFileSync, realpathSync, rmSync, writeFileSync } from "node:fs";
12
12
  import { tmpdir } from "node:os";
13
- import { parse } from "acorn";
14
13
  import { pathToFileURL } from "node:url";
14
+ import { parse } from "acorn";
15
15
  import { transformSync } from "esbuild";
16
16
  //#region src/publish-build-target-nuxt.ts
17
17
  const supportedVersions = {
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env node
2
2
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
3
- const require_generated_file = require("./generated-file.cjs");
4
3
  const require_quarantine_policy = require("./quarantine-policy2.cjs");
4
+ const require_generated_file = require("./generated-file.cjs");
5
5
  const require_toolchain_guard = require("./toolchain-guard.cjs");
6
6
  let node_fs_promises = require("node:fs/promises");
7
7
  let node_path = require("node:path");
@@ -41,7 +41,8 @@ const main = async () => {
41
41
  });
42
42
  const result = require_quarantine_policy.checkRepositoryQuarantine({
43
43
  files,
44
- npmrcPresent: npmrc !== void 0 || trackedFiles.has(".npmrc")
44
+ npmrcPresent: npmrc !== void 0 || trackedFiles.has(".npmrc"),
45
+ expiry: require_quarantine_policy.resolveExpiryScope(root)
45
46
  });
46
47
  for (const warning of result.warnings) process.stderr.write(`warning: ${warning}\n`);
47
48
  if (result.errors.length > 0) throw new Error(result.errors.join("\n"));
@@ -1 +1 @@
1
- {"version":3,"file":"quarantine-cli.cjs","names":["realpath","readToolchainInputs","join","checkGeneratedOutput","readFile","generationDiagnostics","lstat","checkRepositoryQuarantine","synchronizeRepositoryQuarantine","pruneRepositoryQuarantine","writeGeneratedFile"],"sources":["../src/quarantine-cli.ts"],"sourcesContent":["#!/usr/bin/env node\nimport { lstat, readFile, realpath } from \"node:fs/promises\";\nimport { join } from \"node:path\";\n\nimport {\n checkGeneratedOutput,\n generationDiagnostics,\n writeGeneratedFile,\n} from \"./generated-file\";\nimport {\n checkRepositoryQuarantine,\n pruneRepositoryQuarantine,\n synchronizeRepositoryQuarantine,\n} from \"./quarantine-policy\";\nimport { readToolchainInputs } from \"./toolchain-guard\";\n\nconst usage =\n \"Usage: stll-quarantine [--check | --sync | --prune]\\nRun from the repository root; --check is the default.\";\nconst main = async () => {\n const args = process.argv.slice(2);\n if (args.length === 1 && args.at(0) === \"--help\") {\n process.stdout.write(`${usage}\\n`);\n return;\n }\n const mode = args.at(0) ?? \"--check\";\n if (args.length > 1 || ![\"--check\", \"--sync\", \"--prune\"].includes(mode))\n throw new Error(usage);\n const root = await realpath(process.cwd());\n const { files, trackedFiles, diagnostics } = readToolchainInputs(root, {\n bunLock: \"content\",\n });\n const destination = join(root, \"bunfig.toml\");\n // These root inputs may be new outputs not yet staged in Git.\n for (const file of [\"bunfig.toml\", \"bun.lock\"]) {\n const source = join(root, file);\n if ((await checkGeneratedOutput(source)) !== undefined)\n files[file] = await readFile(source, \"utf8\");\n }\n const remaining = await generationDiagnostics({\n diagnostics,\n outputs: [{ relative: \"bunfig.toml\", destination }],\n });\n if (remaining.length > 0)\n throw new Error(\n remaining.map(({ path, message }) => `${path}: ${message}`).join(\"\\n\"),\n );\n if (mode === \"--check\") {\n const npmrc = await lstat(join(root, \".npmrc\")).catch((error: unknown) => {\n if (error instanceof Error && \"code\" in error && error.code === \"ENOENT\")\n return undefined;\n throw error;\n });\n const result = checkRepositoryQuarantine({\n files,\n npmrcPresent: npmrc !== undefined || trackedFiles.has(\".npmrc\"),\n });\n for (const warning of result.warnings)\n process.stderr.write(`warning: ${warning}\\n`);\n if (result.errors.length > 0) throw new Error(result.errors.join(\"\\n\"));\n process.stdout.write(\"Verified bunfig.toml quarantine policy\\n\");\n return;\n }\n const text =\n mode === \"--sync\"\n ? synchronizeRepositoryQuarantine({ files })\n : pruneRepositoryQuarantine({ files }).bunfig;\n const stat = await checkGeneratedOutput(destination);\n if (text !== files[\"bunfig.toml\"])\n await writeGeneratedFile({\n destination,\n text,\n mode: stat === undefined ? 0o644 : stat.mode & 0o777,\n });\n process.stdout.write(\n `${mode === \"--sync\" ? \"Synchronized\" : \"Pruned\"} bunfig.toml quarantine policy\\n`,\n );\n};\nmain().catch((error: unknown) => {\n process.stderr.write(\n `quarantine: ${error instanceof Error ? error.message : String(error)}\\n`,\n );\n process.exitCode = 1;\n});\n"],"mappings":";;;;;;;;AAgBA,MAAM,QACJ;AACF,MAAM,OAAO,YAAY;CACvB,MAAM,OAAO,QAAQ,KAAK,MAAM,CAAC;CACjC,IAAI,KAAK,WAAW,KAAK,KAAK,GAAG,CAAC,MAAM,UAAU;EAChD,QAAQ,OAAO,MAAM,GAAG,MAAM,GAAG;EACjC;CACF;CACA,MAAM,OAAO,KAAK,GAAG,CAAC,KAAK;CAC3B,IAAI,KAAK,SAAS,KAAK,CAAC;EAAC;EAAW;EAAU;CAAS,CAAC,CAAC,SAAS,IAAI,GACpE,MAAM,IAAI,MAAM,KAAK;CACvB,MAAM,OAAO,OAAA,GAAMA,iBAAAA,SAAAA,CAAS,QAAQ,IAAI,CAAC;CACzC,MAAM,EAAE,OAAO,cAAc,gBAAgBC,wBAAAA,oBAAoB,MAAM,EACrE,SAAS,UACX,CAAC;CACD,MAAM,eAAA,GAAcC,UAAAA,KAAAA,CAAK,MAAM,aAAa;CAE5C,KAAK,MAAM,QAAQ,CAAC,eAAe,UAAU,GAAG;EAC9C,MAAM,UAAA,GAASA,UAAAA,KAAAA,CAAK,MAAM,IAAI;EAC9B,IAAK,MAAMC,uBAAAA,qBAAqB,MAAM,MAAO,KAAA,GAC3C,MAAM,QAAQ,OAAA,GAAMC,iBAAAA,SAAAA,CAAS,QAAQ,MAAM;CAC/C;CACA,MAAM,YAAY,MAAMC,uBAAAA,sBAAsB;EAC5C;EACA,SAAS,CAAC;GAAE,UAAU;GAAe;EAAY,CAAC;CACpD,CAAC;CACD,IAAI,UAAU,SAAS,GACrB,MAAM,IAAI,MACR,UAAU,KAAK,EAAE,MAAM,cAAc,GAAG,KAAK,IAAI,SAAS,CAAC,CAAC,KAAK,IAAI,CACvE;CACF,IAAI,SAAS,WAAW;EACtB,MAAM,QAAQ,OAAA,GAAMC,iBAAAA,MAAAA,EAAAA,GAAMJ,UAAAA,KAAAA,CAAK,MAAM,QAAQ,CAAC,CAAC,CAAC,OAAO,UAAmB;GACxE,IAAI,iBAAiB,SAAS,UAAU,SAAS,MAAM,SAAS,UAC9D,OAAO,KAAA;GACT,MAAM;EACR,CAAC;EACD,MAAM,SAASK,0BAAAA,0BAA0B;GACvC;GACA,cAAc,UAAU,KAAA,KAAa,aAAa,IAAI,QAAQ;EAChE,CAAC;EACD,KAAK,MAAM,WAAW,OAAO,UAC3B,QAAQ,OAAO,MAAM,YAAY,QAAQ,GAAG;EAC9C,IAAI,OAAO,OAAO,SAAS,GAAG,MAAM,IAAI,MAAM,OAAO,OAAO,KAAK,IAAI,CAAC;EACtE,QAAQ,OAAO,MAAM,0CAA0C;EAC/D;CACF;CACA,MAAM,OACJ,SAAS,WACLC,0BAAAA,gCAAgC,EAAE,MAAM,CAAC,IACzCC,0BAAAA,0BAA0B,EAAE,MAAM,CAAC,CAAC,CAAC;CAC3C,MAAM,OAAO,MAAMN,uBAAAA,qBAAqB,WAAW;CACnD,IAAI,SAAS,MAAM,gBACjB,MAAMO,uBAAAA,mBAAmB;EACvB;EACA;EACA,MAAM,SAAS,KAAA,IAAY,MAAQ,KAAK,OAAO;CACjD,CAAC;CACH,QAAQ,OAAO,MACb,GAAG,SAAS,WAAW,iBAAiB,SAAS,iCACnD;AACF;AACA,KAAK,CAAC,CAAC,OAAO,UAAmB;CAC/B,QAAQ,OAAO,MACb,eAAe,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK,EAAE,GACxE;CACA,QAAQ,WAAW;AACrB,CAAC"}
1
+ {"version":3,"file":"quarantine-cli.cjs","names":["realpath","readToolchainInputs","join","checkGeneratedOutput","readFile","generationDiagnostics","lstat","checkRepositoryQuarantine","resolveExpiryScope","synchronizeRepositoryQuarantine","pruneRepositoryQuarantine","writeGeneratedFile"],"sources":["../src/quarantine-cli.ts"],"sourcesContent":["#!/usr/bin/env node\nimport { lstat, readFile, realpath } from \"node:fs/promises\";\nimport { join } from \"node:path\";\n\nimport { resolveExpiryScope } from \"./dated-entry-scope\";\nimport {\n checkGeneratedOutput,\n generationDiagnostics,\n writeGeneratedFile,\n} from \"./generated-file\";\nimport {\n checkRepositoryQuarantine,\n pruneRepositoryQuarantine,\n synchronizeRepositoryQuarantine,\n} from \"./quarantine-policy\";\nimport { readToolchainInputs } from \"./toolchain-guard\";\n\nconst usage =\n \"Usage: stll-quarantine [--check | --sync | --prune]\\nRun from the repository root; --check is the default.\";\nconst main = async () => {\n const args = process.argv.slice(2);\n if (args.length === 1 && args.at(0) === \"--help\") {\n process.stdout.write(`${usage}\\n`);\n return;\n }\n const mode = args.at(0) ?? \"--check\";\n if (args.length > 1 || ![\"--check\", \"--sync\", \"--prune\"].includes(mode))\n throw new Error(usage);\n const root = await realpath(process.cwd());\n const { files, trackedFiles, diagnostics } = readToolchainInputs(root, {\n bunLock: \"content\",\n });\n const destination = join(root, \"bunfig.toml\");\n // These root inputs may be new outputs not yet staged in Git.\n for (const file of [\"bunfig.toml\", \"bun.lock\"]) {\n const source = join(root, file);\n if ((await checkGeneratedOutput(source)) !== undefined)\n files[file] = await readFile(source, \"utf8\");\n }\n const remaining = await generationDiagnostics({\n diagnostics,\n outputs: [{ relative: \"bunfig.toml\", destination }],\n });\n if (remaining.length > 0)\n throw new Error(\n remaining.map(({ path, message }) => `${path}: ${message}`).join(\"\\n\"),\n );\n if (mode === \"--check\") {\n const npmrc = await lstat(join(root, \".npmrc\")).catch((error: unknown) => {\n if (error instanceof Error && \"code\" in error && error.code === \"ENOENT\")\n return undefined;\n throw error;\n });\n const result = checkRepositoryQuarantine({\n files,\n npmrcPresent: npmrc !== undefined || trackedFiles.has(\".npmrc\"),\n expiry: resolveExpiryScope(root),\n });\n for (const warning of result.warnings)\n process.stderr.write(`warning: ${warning}\\n`);\n if (result.errors.length > 0) throw new Error(result.errors.join(\"\\n\"));\n process.stdout.write(\"Verified bunfig.toml quarantine policy\\n\");\n return;\n }\n const text =\n mode === \"--sync\"\n ? synchronizeRepositoryQuarantine({ files })\n : pruneRepositoryQuarantine({ files }).bunfig;\n const stat = await checkGeneratedOutput(destination);\n if (text !== files[\"bunfig.toml\"])\n await writeGeneratedFile({\n destination,\n text,\n mode: stat === undefined ? 0o644 : stat.mode & 0o777,\n });\n process.stdout.write(\n `${mode === \"--sync\" ? \"Synchronized\" : \"Pruned\"} bunfig.toml quarantine policy\\n`,\n );\n};\nmain().catch((error: unknown) => {\n process.stderr.write(\n `quarantine: ${error instanceof Error ? error.message : String(error)}\\n`,\n );\n process.exitCode = 1;\n});\n"],"mappings":";;;;;;;;AAiBA,MAAM,QACJ;AACF,MAAM,OAAO,YAAY;CACvB,MAAM,OAAO,QAAQ,KAAK,MAAM,CAAC;CACjC,IAAI,KAAK,WAAW,KAAK,KAAK,GAAG,CAAC,MAAM,UAAU;EAChD,QAAQ,OAAO,MAAM,GAAG,MAAM,GAAG;EACjC;CACF;CACA,MAAM,OAAO,KAAK,GAAG,CAAC,KAAK;CAC3B,IAAI,KAAK,SAAS,KAAK,CAAC;EAAC;EAAW;EAAU;CAAS,CAAC,CAAC,SAAS,IAAI,GACpE,MAAM,IAAI,MAAM,KAAK;CACvB,MAAM,OAAO,OAAA,GAAMA,iBAAAA,SAAAA,CAAS,QAAQ,IAAI,CAAC;CACzC,MAAM,EAAE,OAAO,cAAc,gBAAgBC,wBAAAA,oBAAoB,MAAM,EACrE,SAAS,UACX,CAAC;CACD,MAAM,eAAA,GAAcC,UAAAA,KAAAA,CAAK,MAAM,aAAa;CAE5C,KAAK,MAAM,QAAQ,CAAC,eAAe,UAAU,GAAG;EAC9C,MAAM,UAAA,GAASA,UAAAA,KAAAA,CAAK,MAAM,IAAI;EAC9B,IAAK,MAAMC,uBAAAA,qBAAqB,MAAM,MAAO,KAAA,GAC3C,MAAM,QAAQ,OAAA,GAAMC,iBAAAA,SAAAA,CAAS,QAAQ,MAAM;CAC/C;CACA,MAAM,YAAY,MAAMC,uBAAAA,sBAAsB;EAC5C;EACA,SAAS,CAAC;GAAE,UAAU;GAAe;EAAY,CAAC;CACpD,CAAC;CACD,IAAI,UAAU,SAAS,GACrB,MAAM,IAAI,MACR,UAAU,KAAK,EAAE,MAAM,cAAc,GAAG,KAAK,IAAI,SAAS,CAAC,CAAC,KAAK,IAAI,CACvE;CACF,IAAI,SAAS,WAAW;EACtB,MAAM,QAAQ,OAAA,GAAMC,iBAAAA,MAAAA,EAAAA,GAAMJ,UAAAA,KAAAA,CAAK,MAAM,QAAQ,CAAC,CAAC,CAAC,OAAO,UAAmB;GACxE,IAAI,iBAAiB,SAAS,UAAU,SAAS,MAAM,SAAS,UAC9D,OAAO,KAAA;GACT,MAAM;EACR,CAAC;EACD,MAAM,SAASK,0BAAAA,0BAA0B;GACvC;GACA,cAAc,UAAU,KAAA,KAAa,aAAa,IAAI,QAAQ;GAC9D,QAAQC,0BAAAA,mBAAmB,IAAI;EACjC,CAAC;EACD,KAAK,MAAM,WAAW,OAAO,UAC3B,QAAQ,OAAO,MAAM,YAAY,QAAQ,GAAG;EAC9C,IAAI,OAAO,OAAO,SAAS,GAAG,MAAM,IAAI,MAAM,OAAO,OAAO,KAAK,IAAI,CAAC;EACtE,QAAQ,OAAO,MAAM,0CAA0C;EAC/D;CACF;CACA,MAAM,OACJ,SAAS,WACLC,0BAAAA,gCAAgC,EAAE,MAAM,CAAC,IACzCC,0BAAAA,0BAA0B,EAAE,MAAM,CAAC,CAAC,CAAC;CAC3C,MAAM,OAAO,MAAMP,uBAAAA,qBAAqB,WAAW;CACnD,IAAI,SAAS,MAAM,gBACjB,MAAMQ,uBAAAA,mBAAmB;EACvB;EACA;EACA,MAAM,SAAS,KAAA,IAAY,MAAQ,KAAK,OAAO;CACjD,CAAC;CACH,QAAQ,OAAO,MACb,GAAG,SAAS,WAAW,iBAAiB,SAAS,iCACnD;AACF;AACA,KAAK,CAAC,CAAC,OAAO,UAAmB;CAC/B,QAAQ,OAAO,MACb,eAAe,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK,EAAE,GACxE;CACA,QAAQ,WAAW;AACrB,CAAC"}
@@ -1,6 +1,6 @@
1
1
  #!/usr/bin/env node
2
+ import { i as synchronizeRepositoryQuarantine, r as pruneRepositoryQuarantine, t as checkRepositoryQuarantine, u as resolveExpiryScope } from "./quarantine-policy2.mjs";
2
3
  import { n as generationDiagnostics, r as writeGeneratedFile, t as checkGeneratedOutput } from "./generated-file.mjs";
3
- import { i as synchronizeRepositoryQuarantine, r as pruneRepositoryQuarantine, t as checkRepositoryQuarantine } from "./quarantine-policy2.mjs";
4
4
  import { r as readToolchainInputs } from "./toolchain-guard.mjs";
5
5
  import { lstat, readFile, realpath } from "node:fs/promises";
6
6
  import { join } from "node:path";
@@ -40,7 +40,8 @@ const main = async () => {
40
40
  });
41
41
  const result = checkRepositoryQuarantine({
42
42
  files,
43
- npmrcPresent: npmrc !== void 0 || trackedFiles.has(".npmrc")
43
+ npmrcPresent: npmrc !== void 0 || trackedFiles.has(".npmrc"),
44
+ expiry: resolveExpiryScope(root)
44
45
  });
45
46
  for (const warning of result.warnings) process.stderr.write(`warning: ${warning}\n`);
46
47
  if (result.errors.length > 0) throw new Error(result.errors.join("\n"));
@@ -1 +1 @@
1
- {"version":3,"file":"quarantine-cli.mjs","names":[],"sources":["../src/quarantine-cli.ts"],"sourcesContent":["#!/usr/bin/env node\nimport { lstat, readFile, realpath } from \"node:fs/promises\";\nimport { join } from \"node:path\";\n\nimport {\n checkGeneratedOutput,\n generationDiagnostics,\n writeGeneratedFile,\n} from \"./generated-file\";\nimport {\n checkRepositoryQuarantine,\n pruneRepositoryQuarantine,\n synchronizeRepositoryQuarantine,\n} from \"./quarantine-policy\";\nimport { readToolchainInputs } from \"./toolchain-guard\";\n\nconst usage =\n \"Usage: stll-quarantine [--check | --sync | --prune]\\nRun from the repository root; --check is the default.\";\nconst main = async () => {\n const args = process.argv.slice(2);\n if (args.length === 1 && args.at(0) === \"--help\") {\n process.stdout.write(`${usage}\\n`);\n return;\n }\n const mode = args.at(0) ?? \"--check\";\n if (args.length > 1 || ![\"--check\", \"--sync\", \"--prune\"].includes(mode))\n throw new Error(usage);\n const root = await realpath(process.cwd());\n const { files, trackedFiles, diagnostics } = readToolchainInputs(root, {\n bunLock: \"content\",\n });\n const destination = join(root, \"bunfig.toml\");\n // These root inputs may be new outputs not yet staged in Git.\n for (const file of [\"bunfig.toml\", \"bun.lock\"]) {\n const source = join(root, file);\n if ((await checkGeneratedOutput(source)) !== undefined)\n files[file] = await readFile(source, \"utf8\");\n }\n const remaining = await generationDiagnostics({\n diagnostics,\n outputs: [{ relative: \"bunfig.toml\", destination }],\n });\n if (remaining.length > 0)\n throw new Error(\n remaining.map(({ path, message }) => `${path}: ${message}`).join(\"\\n\"),\n );\n if (mode === \"--check\") {\n const npmrc = await lstat(join(root, \".npmrc\")).catch((error: unknown) => {\n if (error instanceof Error && \"code\" in error && error.code === \"ENOENT\")\n return undefined;\n throw error;\n });\n const result = checkRepositoryQuarantine({\n files,\n npmrcPresent: npmrc !== undefined || trackedFiles.has(\".npmrc\"),\n });\n for (const warning of result.warnings)\n process.stderr.write(`warning: ${warning}\\n`);\n if (result.errors.length > 0) throw new Error(result.errors.join(\"\\n\"));\n process.stdout.write(\"Verified bunfig.toml quarantine policy\\n\");\n return;\n }\n const text =\n mode === \"--sync\"\n ? synchronizeRepositoryQuarantine({ files })\n : pruneRepositoryQuarantine({ files }).bunfig;\n const stat = await checkGeneratedOutput(destination);\n if (text !== files[\"bunfig.toml\"])\n await writeGeneratedFile({\n destination,\n text,\n mode: stat === undefined ? 0o644 : stat.mode & 0o777,\n });\n process.stdout.write(\n `${mode === \"--sync\" ? \"Synchronized\" : \"Pruned\"} bunfig.toml quarantine policy\\n`,\n );\n};\nmain().catch((error: unknown) => {\n process.stderr.write(\n `quarantine: ${error instanceof Error ? error.message : String(error)}\\n`,\n );\n process.exitCode = 1;\n});\n"],"mappings":";;;;;;;AAgBA,MAAM,QACJ;AACF,MAAM,OAAO,YAAY;CACvB,MAAM,OAAO,QAAQ,KAAK,MAAM,CAAC;CACjC,IAAI,KAAK,WAAW,KAAK,KAAK,GAAG,CAAC,MAAM,UAAU;EAChD,QAAQ,OAAO,MAAM,GAAG,MAAM,GAAG;EACjC;CACF;CACA,MAAM,OAAO,KAAK,GAAG,CAAC,KAAK;CAC3B,IAAI,KAAK,SAAS,KAAK,CAAC;EAAC;EAAW;EAAU;CAAS,CAAC,CAAC,SAAS,IAAI,GACpE,MAAM,IAAI,MAAM,KAAK;CACvB,MAAM,OAAO,MAAM,SAAS,QAAQ,IAAI,CAAC;CACzC,MAAM,EAAE,OAAO,cAAc,gBAAgB,oBAAoB,MAAM,EACrE,SAAS,UACX,CAAC;CACD,MAAM,cAAc,KAAK,MAAM,aAAa;CAE5C,KAAK,MAAM,QAAQ,CAAC,eAAe,UAAU,GAAG;EAC9C,MAAM,SAAS,KAAK,MAAM,IAAI;EAC9B,IAAK,MAAM,qBAAqB,MAAM,MAAO,KAAA,GAC3C,MAAM,QAAQ,MAAM,SAAS,QAAQ,MAAM;CAC/C;CACA,MAAM,YAAY,MAAM,sBAAsB;EAC5C;EACA,SAAS,CAAC;GAAE,UAAU;GAAe;EAAY,CAAC;CACpD,CAAC;CACD,IAAI,UAAU,SAAS,GACrB,MAAM,IAAI,MACR,UAAU,KAAK,EAAE,MAAM,cAAc,GAAG,KAAK,IAAI,SAAS,CAAC,CAAC,KAAK,IAAI,CACvE;CACF,IAAI,SAAS,WAAW;EACtB,MAAM,QAAQ,MAAM,MAAM,KAAK,MAAM,QAAQ,CAAC,CAAC,CAAC,OAAO,UAAmB;GACxE,IAAI,iBAAiB,SAAS,UAAU,SAAS,MAAM,SAAS,UAC9D,OAAO,KAAA;GACT,MAAM;EACR,CAAC;EACD,MAAM,SAAS,0BAA0B;GACvC;GACA,cAAc,UAAU,KAAA,KAAa,aAAa,IAAI,QAAQ;EAChE,CAAC;EACD,KAAK,MAAM,WAAW,OAAO,UAC3B,QAAQ,OAAO,MAAM,YAAY,QAAQ,GAAG;EAC9C,IAAI,OAAO,OAAO,SAAS,GAAG,MAAM,IAAI,MAAM,OAAO,OAAO,KAAK,IAAI,CAAC;EACtE,QAAQ,OAAO,MAAM,0CAA0C;EAC/D;CACF;CACA,MAAM,OACJ,SAAS,WACL,gCAAgC,EAAE,MAAM,CAAC,IACzC,0BAA0B,EAAE,MAAM,CAAC,CAAC,CAAC;CAC3C,MAAM,OAAO,MAAM,qBAAqB,WAAW;CACnD,IAAI,SAAS,MAAM,gBACjB,MAAM,mBAAmB;EACvB;EACA;EACA,MAAM,SAAS,KAAA,IAAY,MAAQ,KAAK,OAAO;CACjD,CAAC;CACH,QAAQ,OAAO,MACb,GAAG,SAAS,WAAW,iBAAiB,SAAS,iCACnD;AACF;AACA,KAAK,CAAC,CAAC,OAAO,UAAmB;CAC/B,QAAQ,OAAO,MACb,eAAe,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK,EAAE,GACxE;CACA,QAAQ,WAAW;AACrB,CAAC"}
1
+ {"version":3,"file":"quarantine-cli.mjs","names":[],"sources":["../src/quarantine-cli.ts"],"sourcesContent":["#!/usr/bin/env node\nimport { lstat, readFile, realpath } from \"node:fs/promises\";\nimport { join } from \"node:path\";\n\nimport { resolveExpiryScope } from \"./dated-entry-scope\";\nimport {\n checkGeneratedOutput,\n generationDiagnostics,\n writeGeneratedFile,\n} from \"./generated-file\";\nimport {\n checkRepositoryQuarantine,\n pruneRepositoryQuarantine,\n synchronizeRepositoryQuarantine,\n} from \"./quarantine-policy\";\nimport { readToolchainInputs } from \"./toolchain-guard\";\n\nconst usage =\n \"Usage: stll-quarantine [--check | --sync | --prune]\\nRun from the repository root; --check is the default.\";\nconst main = async () => {\n const args = process.argv.slice(2);\n if (args.length === 1 && args.at(0) === \"--help\") {\n process.stdout.write(`${usage}\\n`);\n return;\n }\n const mode = args.at(0) ?? \"--check\";\n if (args.length > 1 || ![\"--check\", \"--sync\", \"--prune\"].includes(mode))\n throw new Error(usage);\n const root = await realpath(process.cwd());\n const { files, trackedFiles, diagnostics } = readToolchainInputs(root, {\n bunLock: \"content\",\n });\n const destination = join(root, \"bunfig.toml\");\n // These root inputs may be new outputs not yet staged in Git.\n for (const file of [\"bunfig.toml\", \"bun.lock\"]) {\n const source = join(root, file);\n if ((await checkGeneratedOutput(source)) !== undefined)\n files[file] = await readFile(source, \"utf8\");\n }\n const remaining = await generationDiagnostics({\n diagnostics,\n outputs: [{ relative: \"bunfig.toml\", destination }],\n });\n if (remaining.length > 0)\n throw new Error(\n remaining.map(({ path, message }) => `${path}: ${message}`).join(\"\\n\"),\n );\n if (mode === \"--check\") {\n const npmrc = await lstat(join(root, \".npmrc\")).catch((error: unknown) => {\n if (error instanceof Error && \"code\" in error && error.code === \"ENOENT\")\n return undefined;\n throw error;\n });\n const result = checkRepositoryQuarantine({\n files,\n npmrcPresent: npmrc !== undefined || trackedFiles.has(\".npmrc\"),\n expiry: resolveExpiryScope(root),\n });\n for (const warning of result.warnings)\n process.stderr.write(`warning: ${warning}\\n`);\n if (result.errors.length > 0) throw new Error(result.errors.join(\"\\n\"));\n process.stdout.write(\"Verified bunfig.toml quarantine policy\\n\");\n return;\n }\n const text =\n mode === \"--sync\"\n ? synchronizeRepositoryQuarantine({ files })\n : pruneRepositoryQuarantine({ files }).bunfig;\n const stat = await checkGeneratedOutput(destination);\n if (text !== files[\"bunfig.toml\"])\n await writeGeneratedFile({\n destination,\n text,\n mode: stat === undefined ? 0o644 : stat.mode & 0o777,\n });\n process.stdout.write(\n `${mode === \"--sync\" ? \"Synchronized\" : \"Pruned\"} bunfig.toml quarantine policy\\n`,\n );\n};\nmain().catch((error: unknown) => {\n process.stderr.write(\n `quarantine: ${error instanceof Error ? error.message : String(error)}\\n`,\n );\n process.exitCode = 1;\n});\n"],"mappings":";;;;;;;AAiBA,MAAM,QACJ;AACF,MAAM,OAAO,YAAY;CACvB,MAAM,OAAO,QAAQ,KAAK,MAAM,CAAC;CACjC,IAAI,KAAK,WAAW,KAAK,KAAK,GAAG,CAAC,MAAM,UAAU;EAChD,QAAQ,OAAO,MAAM,GAAG,MAAM,GAAG;EACjC;CACF;CACA,MAAM,OAAO,KAAK,GAAG,CAAC,KAAK;CAC3B,IAAI,KAAK,SAAS,KAAK,CAAC;EAAC;EAAW;EAAU;CAAS,CAAC,CAAC,SAAS,IAAI,GACpE,MAAM,IAAI,MAAM,KAAK;CACvB,MAAM,OAAO,MAAM,SAAS,QAAQ,IAAI,CAAC;CACzC,MAAM,EAAE,OAAO,cAAc,gBAAgB,oBAAoB,MAAM,EACrE,SAAS,UACX,CAAC;CACD,MAAM,cAAc,KAAK,MAAM,aAAa;CAE5C,KAAK,MAAM,QAAQ,CAAC,eAAe,UAAU,GAAG;EAC9C,MAAM,SAAS,KAAK,MAAM,IAAI;EAC9B,IAAK,MAAM,qBAAqB,MAAM,MAAO,KAAA,GAC3C,MAAM,QAAQ,MAAM,SAAS,QAAQ,MAAM;CAC/C;CACA,MAAM,YAAY,MAAM,sBAAsB;EAC5C;EACA,SAAS,CAAC;GAAE,UAAU;GAAe;EAAY,CAAC;CACpD,CAAC;CACD,IAAI,UAAU,SAAS,GACrB,MAAM,IAAI,MACR,UAAU,KAAK,EAAE,MAAM,cAAc,GAAG,KAAK,IAAI,SAAS,CAAC,CAAC,KAAK,IAAI,CACvE;CACF,IAAI,SAAS,WAAW;EACtB,MAAM,QAAQ,MAAM,MAAM,KAAK,MAAM,QAAQ,CAAC,CAAC,CAAC,OAAO,UAAmB;GACxE,IAAI,iBAAiB,SAAS,UAAU,SAAS,MAAM,SAAS,UAC9D,OAAO,KAAA;GACT,MAAM;EACR,CAAC;EACD,MAAM,SAAS,0BAA0B;GACvC;GACA,cAAc,UAAU,KAAA,KAAa,aAAa,IAAI,QAAQ;GAC9D,QAAQ,mBAAmB,IAAI;EACjC,CAAC;EACD,KAAK,MAAM,WAAW,OAAO,UAC3B,QAAQ,OAAO,MAAM,YAAY,QAAQ,GAAG;EAC9C,IAAI,OAAO,OAAO,SAAS,GAAG,MAAM,IAAI,MAAM,OAAO,OAAO,KAAK,IAAI,CAAC;EACtE,QAAQ,OAAO,MAAM,0CAA0C;EAC/D;CACF;CACA,MAAM,OACJ,SAAS,WACL,gCAAgC,EAAE,MAAM,CAAC,IACzC,0BAA0B,EAAE,MAAM,CAAC,CAAC,CAAC;CAC3C,MAAM,OAAO,MAAM,qBAAqB,WAAW;CACnD,IAAI,SAAS,MAAM,gBACjB,MAAM,mBAAmB;EACvB;EACA;EACA,MAAM,SAAS,KAAA,IAAY,MAAQ,KAAK,OAAO;CACjD,CAAC;CACH,QAAQ,OAAO,MACb,GAAG,SAAS,WAAW,iBAAiB,SAAS,iCACnD;AACF;AACA,KAAK,CAAC,CAAC,OAAO,UAAmB;CAC/B,QAAQ,OAAO,MACb,eAAe,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK,EAAE,GACxE;CACA,QAAQ,WAAW;AACrB,CAAC"}