From ec523f50663827b38a4345f1265ace6b45aee70d Mon Sep 17 00:00:00 2001 From: laurenhitchon Date: Mon, 27 Jul 2026 18:09:57 +1000 Subject: [PATCH] ops(sync): add .npmrc to the file-sync map MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Phase 2 was half-done. `.nvmrc` has been mapped in every group since the original rollout — all 22 repos report 24.16.0, which also resolves the old caveat about dtl-sandbox and nswds-tokens running Node 22. `.npmrc` was never mapped: 8 repos carried engine-strict by hand, 12 had no .npmrc at all, and 2 had bespoke variants. Map it now, with two carve-outs rather than a blind whole-file sync. nswds-ui takes a variant source. Its .npmrc is `provenance=false`, not engine-strict: npm only supports provenance for public source repos, and this one is private. Overwriting it with the canonical would reintroduce the E422 publish failure that silently stranded v1.8.0-v2.1.0 as git tags that never reached npm. The variant preserves that directive verbatim and deliberately does not add engine-strict — that is a Turborepo monorepo whose workspace packages each declare their own engines, and turning it on there should be a considered pass, not a side effect of this change. The canonical .npmrc absorbs the rationale that ictds-portal-flows had written into its own copy, so the sync spreads that reasoning to every repo instead of stripping it from the one repo that had it. Adding engine-strict to the 12 repos without it is safe today: every repo's .nvmrc (24.16.0) satisfies its own declared engines.node, so nothing that installed before stops installing. It is load-bearing going forward — it turns a warning nobody reads into a failure in the `install / install` job that rulesets already require. Merging fans out `chore(ci):` PRs to 22 repos. --- .github/sync.yml | 10 ++++++++++ docs/config-single-source-of-truth.md | 18 +++++++++++++----- repo-files/.npmrc | 13 +++++++++++++ repo-files/.npmrc-nswds-ui | 14 ++++++++++++++ 4 files changed, 50 insertions(+), 5 deletions(-) create mode 100644 repo-files/.npmrc-nswds-ui diff --git a/.github/sync.yml b/.github/sync.yml index 6d3e405..2e80ca3 100644 --- a/.github/sync.yml +++ b/.github/sync.yml @@ -45,6 +45,8 @@ group: dest: renovate.json - source: repo-files/.nvmrc dest: .nvmrc + - source: repo-files/.npmrc + dest: .npmrc - source: workflow-stubs/ dest: .github/workflows/ @@ -78,6 +80,8 @@ group: dest: renovate.json - source: repo-files/.nvmrc dest: .nvmrc + - source: repo-files/.npmrc-nswds-ui + dest: .npmrc # ── Group 2b: nswds-tokens ─────────────────────────────────────────────── # Like nswds-ui it keeps its own release.yml + release config, but its @@ -112,6 +116,8 @@ group: dest: renovate.json - source: repo-files/.nvmrc dest: .nvmrc + - source: repo-files/.npmrc + dest: .npmrc # ── Group 3: nswds-app ─────────────────────────────────────────────────── # Publishes @nswds/app via @semantic-release/npm, so it keeps its own @@ -131,6 +137,8 @@ group: dest: renovate.json - source: repo-files/.nvmrc dest: .nvmrc + - source: repo-files/.npmrc + dest: .npmrc - source: workflow-stubs/ dest: .github/workflows/ @@ -169,3 +177,5 @@ group: dest: renovate.json - source: repo-files/.nvmrc dest: .nvmrc + - source: repo-files/.npmrc + dest: .npmrc diff --git a/docs/config-single-source-of-truth.md b/docs/config-single-source-of-truth.md index f5d548c..116acab 100644 --- a/docs/config-single-source-of-truth.md +++ b/docs/config-single-source-of-truth.md @@ -16,8 +16,8 @@ For files that are (or should be) byte-identical everywhere. | File | Canonical | Notes | |------|-----------|-------| -| `.nvmrc` | `24.16.0` | Full pin. **dtl-sandbox** and **nswds-tokens** currently run Node 22 — verify their build/CI on 24 before adding them to the sync group. | -| `.npmrc` | `engine-strict=true` | **nswds-ui** additionally needs `provenance=false` (private-publish workaround). Its sync group gets a variant source, or it keeps that line as a repo-specific override. | +| `.nvmrc` | `24.16.0` | Full pin. **Synced — all groups.** The earlier caveat about dtl-sandbox and nswds-tokens running Node 22 is resolved: every repo in the map is on `24.16.0`. | +| `.npmrc` | `engine-strict=true` | **Synced — all groups.** **nswds-ui takes a variant source** (`repo-files/.npmrc-nswds-ui`), because it needs `provenance=false`: npm only supports provenance for public source repos, and a whole-file sync of the canonical would strand its releases as git tags that never reach npm (as v1.8.0–v2.1.0 were). | `.gitignore` and `.prettierignore` **also** live in `repo-files/` as a canonical **base**, but they are NOT clean whole-file syncs — see Mechanism C. @@ -81,9 +81,17 @@ several repos already carry, and includes `*.err`. 1. **Phase 1 (this PR):** establish the canonical files + packages + this plan in nswds-devops. No `sync.yml` change — merging does not touch other repos. -2. **Phase 2 — `.nvmrc` / `.npmrc`:** verify the two Node-22 repos, then add - `repo-files/.nvmrc` and `repo-files/.npmrc` to the sync map (handling the - nswds-ui `.npmrc` variant). Merging fans out `chore(ci):` PRs. +2. **Phase 2 — `.nvmrc` / `.npmrc`: done.** `.nvmrc` was mapped in every group + during the original rollout, and every repo now reports `24.16.0`, which + resolved the Node-22 caveat. `.npmrc` is mapped as of this change: 21 repos + take `repo-files/.npmrc`, and nswds-ui takes `repo-files/.npmrc-nswds-ui` + so its `provenance=false` survives. + + Adding `engine-strict=true` to the 12 repos that lacked it is safe today — + every repo's `.nvmrc` (`24.16.0`) satisfies its own declared `engines.node`, + so nothing that installed before stops installing. It is load-bearing going + forward: it converts a silently-ignored `engines` warning into a failure in + the `install / install` job that rulesets already require. 3. **Phase 3 — packages:** both packages are extracted to their own repos with publishing wired up. Each still needs a **one-time manual first publish** (`npm publish --access public`) before OIDC trusted publishing can take over — diff --git a/repo-files/.npmrc b/repo-files/.npmrc index b6f27f1..b146b27 100644 --- a/repo-files/.npmrc +++ b/repo-files/.npmrc @@ -1 +1,14 @@ +# Synced from digitalnsw/nswds-devops — DO NOT EDIT in this repo. +# +# engine-strict makes the `engines` floor in package.json a hard install error +# instead of a warning npm prints and nobody reads. +# +# Nothing else enforces it: CI takes its Node version solely from .nvmrc, so +# without this an innocuous-looking .nvmrc edit — pinning back to a Node 22 LTS +# below the floor, or to an early 24 minor — would install and pass CI silently, +# then run unsupported code on main at the moment semantic-release is committing +# and tagging. With this, it fails in the `install / install` job that rulesets +# already require. +# +# Keep the engines range in package.json in step with .nvmrc. engine-strict=true diff --git a/repo-files/.npmrc-nswds-ui b/repo-files/.npmrc-nswds-ui new file mode 100644 index 0000000..dd9a76f --- /dev/null +++ b/repo-files/.npmrc-nswds-ui @@ -0,0 +1,14 @@ +# Synced from digitalnsw/nswds-devops — DO NOT EDIT in this repo. +# nswds-ui variant: the canonical repo-files/.npmrc does NOT apply here. +# +# provenance attestation is intentionally OFF: npm only supports provenance +# for PUBLIC source repositories, and this repo is private — with it enabled, +# every publish fails with E422 ("Unsupported GitHub Actions source repository +# visibility: private"), which silently stranded v1.8.0–v2.1.0 as git tags +# that never reached npm. Re-enable if the repo is ever made public. +provenance=false + +# NOTE: engine-strict=true is deliberately NOT set here yet, unlike the rest of +# the fleet. This is a Turborepo monorepo whose workspace packages each carry +# their own engines; turning it on should be a deliberate pass that checks every +# package, not a side effect of adopting the shared .npmrc.