Skip to content

feat(nl): add Netherlands public sector overlay - #739

Open
umag wants to merge 6 commits into
tractorjuice:mainfrom
umag:feat/arckit-nl-overlay
Open

feat(nl): add Netherlands public sector overlay#739
umag wants to merge 6 commits into
tractorjuice:mainfrom
umag:feat/arckit-nl-overlay

Conversation

@umag

@umag umag commented Aug 7, 2026

Copy link
Copy Markdown
Contributor

Adds a Netherlands public sector overlay — plugins/arckit-nl/, four commands, community-contributed.

Why

There is no NL overlay, and Dutch central-government cloud rules changed substantially in 2025–2026 in ways that make generic EU guidance insufficient:

Instrument Status
Herziening rijksbreed cloudbeleid 2026 Ministerie van Economische Zaken en Klimaat, 3 July 2026 — replaces the 2022 policy
VIRBI 2025 (BWBR0051482) In force 9 September 2025 — repealed VIRBI 2013 the same day
Cyberbeveiligingswet + Wet weerbaarheid kritieke entiteiten In force 15 August 2026 — the Dutch NIS2 and CER transpositions
BIO2 Established by the OBDO 23 September 2025, on NEN-EN-ISO/IEC 27001:2023 / 27002:2022

The repeal date matters in particular: material still citing VIRBI 2013 is stale, and the commands say so.

Commands

Command Code Produces
/arckit:nl-cloud RBCLOUD Rijksbreed cloudbeleid compliance assessment
/arckit:nl-tbb TBB Te Beschermen Belangen / VIRBI 2025 rubricering
/arckit:nl-bio BIO2 BIO2 conformance assessment
/arckit:nl-exit NLEXIT Cloud exit plan (clause 3.2)

/arckit:nl-cloud walks the policy clause by clause: the determination of materieel publiek cloudgebruik (4.1), the mandatory risk analysis (3.1), notification to CISO Rijk (3.3), and the eligibility rules that prohibit public cloud for staatsgeheim-classified information and Te Beschermen Belangen levels 1–3 (5.2), and permit email and workplace services only where three cumulative conditions are met (4.5).

/arckit:nl-tbb scores Beschikbaarheid, Integriteit and Vertrouwelijkheid against the five kernbelangen, with the highest of the three setting the TBB category. It carries a prominent warning that the inference runs one way only — information at Stg. GEHEIM implies TBB 2, but a TBB 2 process does not imply it holds Stg. GEHEIM data. Getting that backwards silently over-classifies.

Two deliberate omissions

Both are places where inventing content would have been worse than leaving a gap, so I would rather flag them than have a reviewer discover them:

  • No provider list. Unlike France's SecNumCloud there is no published Dutch cloud qualification scheme, so no commercial provider is named as compliant or qualified — and /arckit:nl-cloud and the README both say so explicitly, because a reader coming from fr-secnumcloud will expect one.
  • No invented clause content. Where I did not have the source text to hand — the remaining aspects of the clause 3.1 risk analysis, and the individual BIO2 overheidsmaatregelen — the commands instruct the assessor to consult the current text and use a [PENDING — cite from current text] placeholder, rather than shipping a plausible-looking list.

No vendor-analyst market reports are cited anywhere.

Registry changes (the two-part PR from CONTRIBUTING.md)

NL is the first of its regime, so beyond the four codes in plugins/arckit-claude/config/doc-types.mjs this also registers NL in REGIMES and REGIME_LABELS (placed after FR, keeping community regimes alphabetical).

Two further integration points that CONTRIBUTING.md does not currently mention, both found by running your own tooling rather than by reading the docs — worth a line in the contributing guide if you agree:

  • scripts/check-doc-type-registry.py requires a row per code in the /arckit:pages known-artifact-types table. Added, in new NL groups under Compliance and Governance.
  • scripts/converter.py carries a hardcoded plugin-source list, and .claude-plugin/marketplace.json a plugin list. Without entries in both, a new overlay silently produces zero generated files for the non-Claude targets — the converter reports success and nothing is wrong-looking. Both updated; the converter now emits 30 NL files across the eight target formats.

Verification

Full Python suite                  1305 passed, 225 skipped
check_doctype_collisions.py        PASS
check-doc-type-registry.py         PASS
check_references.py                PASS
check_recipes.py                   PASS
check-guide-parity.py              PASS
check-contributor-credits.py       PASS
check-guide-site-links.py          PASS
check-quality-checklist-refs.py    PASS   (arckit-nl: 4 per-type references)
sync-shared-assets --check         clean
sync-claude-plugin-layout --check  clean
test-regime-registration.mjs       10 regimes, all registered and labelled
converter.py                       zero drift
markdownlint-cli2                  0 errors, repo-wide

plugin.json parses; every command's frontmatter carries the same key set as fr-secnumcloud.md; UK English throughout. Generated extensions/ output is gitignored and therefore not committed, matching how the existing overlays sit in the tree.

Notes for review

Structure mirrors arckit-fr closely — it was the model for this, fr-secnumcloud in particular, as the nearest analogue in subject matter. references/citation-instructions.md and the _partials are byte-identical copies of the FR ones. quality-checklist.md is a synced shared asset — the RBCLOUD / TBB / BIO2 / NLEXIT per-type sections were added to the canonical plugins/arckit-claude/references/quality-checklist.md and propagated by sync-shared-assets.py, so they reach every overlay rather than only this one. (An earlier revision of this body said the NL copy was "the FR file plus four appended sections". That was wrong: the sections had been written into the synced copy and a later sync reverted them.)

Happy to split this, rename codes, or move anything if you would rather the Dutch cloud command live somewhere else. The separate PR adding the EU Cloud Sovereignty Framework to arckit-eu is #740 — it is an EU Commission instrument that applies across member states, so it seemed wrong to bury it in a national overlay, though the Dutch government has adopted it as its own sovereignty yardstick.

🤖 Generated with Claude Code

@umag
umag requested a review from tractorjuice as a code owner August 7, 2026 12:18
@umag
umag force-pushed the feat/arckit-nl-overlay branch 2 times, most recently from bbb5bf1 to a934867 Compare August 7, 2026 12:42
@tractorjuice

Copy link
Copy Markdown
Owner

Code Review

Verdict: Strong contribution — the registry work is more complete than most overlay PRs (it clears B5, the class that shipped broken in #432), and the two deliberate omissions are the right calls. Four things block merge: the Document Control marker is never resolved, the Dutch classification ladder has nowhere to render, and the overlay is absent from the four user-facing registration points CLAUDE.md requires.

Verified on pr-739 in a clean worktree: 1,125 plugin tests pass (0 new failures), all 7 check scripts pass, converter.py runs clean with zero drift, sync-claude-plugin-layout.py --check and sync-shared-assets.py --check both pass.


BLOCKERS (must fix before merge)

1. No command resolves <!-- DOC-CONTROL-HEADER --> — every NL artefact ships a raw HTML comment where Document Control should be.

All four templates carry the marker (plugins/arckit-nl/templates/nl-cloud-template.md:9, and the same in nl-tbb/nl-bio/nl-exit). Per templates/_partials/RENDERING.md:3, "the command that reads the template MUST resolve the marker … before writing the artefact to disk". None of the four commands mention it:

$ grep -l "DOC-CONTROL-HEADER" plugins/arckit-nl/commands/nl-*.md
(no matches)

Nothing else resolves it at runtime — scripts/python/apply_doc_control_marker.py is a one-off maintainer migration tool that inserts the marker into templates, not a runtime resolver. So the generated artefact gets the literal comment instead of a Document Control table.

Fix — add to each command's write step, per plugins/arckit-ca/commands/ca-pia.md:34,40:

- `${CLAUDE_PLUGIN_ROOT}/templates/_partials/RENDERING.md`
...
Resolve the `<!-- DOC-CONTROL-HEADER -->` marker per `RENDERING.md`.

arckit-fr, arckit-eu and arckit-at have the identical gap (0/12, 0/7, 0/3). That's a reason to fix FR separately, not to add a fourth instance — particularly given blocker 2. For contrast: ca 12/12, au 10/10, uae 12/12, au-energy 2/2.

2. The Dutch classification ladder has nowhere to render — nl-tbb would contradict itself.

RENDERING.md:6-8 routes to a non-UK partial only for UAE Federal/UAE Smart Data and AT Gov/AT InfoSiG. Everything else falls through to document-control-uk.md, whose Classification row is:

| **Classification** | [PUBLIC / OFFICIAL / OFFICIAL-SENSITIVE / SECRET] |

nl-tbb determines Stg. ZEER GEHEIM / Stg. GEHEIM / Stg. CONFIDENTIEEL / Departementaal VERTROUWELIJK (nl-tbb.md:100-105, nl-tbb-template.md:88-95). Once blocker 1 is fixed, the one document whose entire purpose is a VIRBI 2025 rubricering determination carries the UK ladder in its own header while stating a Stg. level in section 4.

Minimum fix (this PR) — a per-command override line, CA precedent at plugins/arckit-ca/commands/ca-pia.md:40:

Use the VIRBI 2025 rubricering ladder (Ongerubriceerd / Departementaal VERTROUWELIJK / Stg. CONFIDENTIEEL / Stg. GEHEIM / Stg. ZEER GEHEIM) — replace the standard UK line in the header.

Proper fix (fine as a follow-up PR) — ship _partials/document-control-nl.md, extend the RENDERING.md routing table, and add the NL Gov / NL VIRBI values to plugin.json userConfig. Note _partials/ is a synced shared asset, so the canonical copy is plugins/arckit-claude/templates/_partials/ followed by sync-shared-assets.py.

3. The overlay is absent from all four user-facing registration points.

CLAUDE.md step 7 requires README.md, docs/index.html, docs/DEPENDENCY-MATRIX.md and CHANGELOG.md. Only CHANGELOG.md was updated. Compared against fr-secnumcloud:

File FR NL
README.md :381, :399, :1223 absent
docs/DEPENDENCY-MATRIX.md :735, :745-746, :756 absent
docs/index.html :415, :450, :653 (jurisdiction card) absent
.github/CODEOWNERS :25-26 (@thomas-jardinet) absent

Net effect: arckit-nl is installable from the marketplace but appears in no user-facing listing, and no reviewer is routed for NL changes. CODEOWNERS in particular — arckit-at routes to @gtonic at :33-34; NL needs an equivalent pair for plugins/arckit-nl/commands/nl-*.md and plugins/arckit-nl/templates/nl-*-template.md.


IMPORTANT (should fix)

4. All four commands verify per-type checks that do not exist.

Each command ends with "verify all Common Checks plus the RBCLOUD / TBB / BIO2 / NLEXIT per-type checks pass" (nl-cloud.md:147, nl-tbb.md:131, nl-bio.md:116, nl-exit.md:118). There are no such sections:

$ grep -c "RBCLOUD\|^### TBB\|BIO2\|NLEXIT" plugins/arckit-nl/references/quality-checklist.md
0
$ diff plugins/arckit-fr/references/quality-checklist.md plugins/arckit-nl/references/quality-checklist.md
(identical, 671 lines both)

The PR body says the file is "the FR file plus four appended per-type sections" — it is byte-identical to FR, with zero appended. Instead it ships 14 French and Austrian per-type sections irrelevant to a Dutch assessment.

To be fair, this is a pre-existing systemic gap, not one you introduced: the canonical file covers the FR/AT/EU codes but none of CA's PIA, AU's, US's FEDRAMP, NHS's NHSDTAC or finance's FSSAFE either. So NL is the sixth instance, not the first.

references/ is a synced shared directory (sync-shared-assets.py:27), so appending to the NL copy would be reverted on the next sync. The fix belongs in plugins/arckit-claude/references/quality-checklist.md, then re-run sync-shared-assets.py. Either do that, or drop the claim from the PR body and leave the four commands pointing at Common Checks only.

5. No citation traceability, despite Step 0b reading external documents.

Every NL command reads external/ and 000-global/policies/ but none references ${CLAUDE_PLUGIN_ROOT}/references/citation-instructions.md, so no [DOC_ID-CN] markers or External References section. Precedent: ca 12/12, au 10/10, uae 12/12, uk-gcloud 10/11. See plugins/arckit-ca/commands/ca-pia.md:52 for the shape. Given the overlay's whole value is fidelity to specific clause numbers, this one matters more here than usual.

6. No generate-document-id.mjs; project creation is hand-rolled.

nl-cloud.md:60-66 reimplements project creation with Glob + manual zero-padding, and each command hand-rolls version detection. ca/au/uae/us all call node scripts/generate-document-id.mjs <PROJECT_ID> RBCLOUD --filename. Since #723 that helper also rejects unregistered doc-type codes, which is free validation you're currently not getting. Consistent with FR, but below where CA/AU sit.

7. The governing instrument has no citable URL anywhere in the overlay.

Every Key References row for the Rijksbreed cloudbeleid 2026, Cbw/Wwke, BIO2, the OBDO begrippenlijst, the Digitaliseringsstrategie and the Visie Digitale Autonomie reads "(not linked — verify current text …)". Only VIRBI 2025 has a real link (wetten.overheid.nl/BWBR0051482). The commands assert specific clause numbers throughout — 3.1, 3.2, 3.3, 3.4, 4.1, 4.2, 4.3, 4.4, 4.5, 4.6, 5.2, 5.4 — with nothing a reviewer or user can check them against. At minimum please add a rijksoverheid.nl landing URL for the policy.

8. Please double-check the ministry attribution.

"Herziening rijksbreed cloudbeleid 2026 (Ministerie van Economische Zaken en Klimaat, 3 July 2026)" appears in the CHANGELOG and in nl-cloud.md. Two things prompt the question rather than settle it: EZK was reorganised in 2024 (Klimaat moving to KGG), and rijksbreed cloud policy has historically sat with BZK — the 2022 policy it replaces was BZK's, and the policy text you cite refers to the bewindspersoon voor digitalisering. If it is EZ/EZK, a URL (item 7) resolves it immediately.

9. No overlay guide in docs/guides/.

fr-secnumcloud.md, au-federal-overlay.md, us-federal-overlay.md, uae-overlay.md, uk-fs-payments-overlay.md and uk-nhs-clinical-safety-overlay.md all exist. Add docs/guides/nl-overlay.md, then python3 scripts/check-guide-parity.py --sync (root is canonical — never edit the plugin copy).


MINOR (nits)

10. PR body says "the converter now emits 30 NL files across the eight target formats". Actual is 64 (find extensions -path '*nl-*' -type f | wc -l).

11. No build recipe — correct, and worth stating explicitly: only uk-* recipes exist today, so FR/CA/AU/US/EU/AT all ship without one. plugins/arckit-nl/README.md:11 already says so. No action needed.


POSITIVE (worth calling out)

  • B5 cleared properly. NL registered in REGIMES and REGIME_LABELS, placed after FR per the officially-maintained-first-then-community-alphabetical convention (config/doc-types.mjs:255,266). This is exactly the class that shipped broken in feat: Canada Federal Overlay (community) — 12 ca-* commands #432 (12 CA doc-types with an unregistered CA regime) and had to be corrected retroactively in au-federal recipe + 8 community commands (Australian Federal Government / DISP-supplier compliance overlay) #441. First overlay PR I've reviewed that got it right unprompted.
  • Integration surface is unusually complete. Beyond the two points you flagged (converter.py PLUGIN_SOURCES, both marketplace manifests) you also caught push-extensions.sh, sync-claude-plugin-layout.py, and five separate test fixture lists. The tracked mirror at plugins/arckit-claude/plugins/nl/ is present and correctly namespaced to /arckit-nl:* while the source tree keeps the portable /arckit:* form — that publish-time distinction trips up most people, including a v6.7.1 regression. Yes, please do add those two points to CONTRIBUTING.md.
  • All four templates carry ## Document Control above the marker — B1 clean, unlike PR au-federal recipe + 8 community commands (Australian Federal Government / DISP-supplier compliance overlay) #441.
  • Zero UK leakage. No NCSC/ICO/GDS/Cyber Essentials/G-Cloud/Orange Book anywhere in the commands or templates.
  • Clean mechanics throughout: all 11 handoffs resolve (7 intra-overlay, 4 to core risk); frontmatter keys identical across all four and free of invalid fields; $ARGUMENTS present in all four, so these pass test_arguments_placeholder_present where 32 existing ca-*/uae-* commands fail it; .arckit/templates/ parity exact.
  • The one-way inference warning is genuinely good governance design. Enforced in three places — nl-tbb.md:111 (command), nl-tbb-template.md:20-22 (template banner), and the success criteria — with explicit "do not omit or soften this" framing. Over-classification from a reversed inference is a real and expensive failure mode, and this is the right way to prevent an LLM committing it.
  • Both deliberate omissions are the right call, and stated where a reader would otherwise assume the opposite. "No published Dutch qualification list, unlike SecNumCloud" appears in nl-cloud.md Step 6.4, Important Notes, the reviewer note, the plugin README and the CHANGELOG. Someone arriving from fr-secnumcloud cannot miss it. Shipping [PENDING — cite from current text] over an invented clause list is likewise correct.

Recommended pre-merge sequence

  1. Add the RENDERING.md read + <!-- DOC-CONTROL-HEADER --> resolution line to all four commands (blocker 1).
  2. Add the VIRBI 2025 classification override to the same four (blocker 2, minimum fix). Open a follow-up issue for document-control-nl.md + routing + userConfig.
  3. Register the overlay in README.md, docs/DEPENDENCY-MATRIX.md, docs/index.html and .github/CODEOWNERS (blocker 3).
  4. Either add the four per-type sections to plugins/arckit-claude/references/quality-checklist.md + sync-shared-assets.py, or drop the claim from the PR body (important 4).
  5. Add the citation-instructions.md reference and switch to generate-document-id.mjs (important 5, 6).
  6. Add a URL for the Rijksbreed cloudbeleid 2026 and confirm the ministry attribution (important 7, 8).
  7. Add docs/guides/nl-overlay.md, then python3 scripts/check-guide-parity.py --sync (important 9).
  8. Re-run: python scripts/converter.py && python scripts/sync-shared-assets.py && python scripts/sync-claude-plugin-layout.py && npx markdownlint-cli2 "**/*.md" && python -m pytest tests/plugin/ -q.

Items 5–7 are fine to defer to a follow-up if you would rather land the overlay now — 1 through 4 are the ones that produce broken artefacts or an invisible plugin.

tractorjuice added a commit that referenced this pull request Aug 7, 2026
…l silently (#741)

A new plugins/arckit-<name>/ directory is not discovered automatically, and
two of the hardcoded plugin lists report success while producing nothing:
converter.py's PLUGIN_SOURCES (which cost arckit-uk-finance four releases of
missing extension output) and the two marketplace manifests.

Raised by @umag on #739, who found both by running the tooling rather than by
reading this file.


Claude-Session: https://claude.ai/code/session_01VKbHCujejpxkgvh47BndDE

Co-authored-by: Claude Opus 5 <noreply@anthropic.com>
tractorjuice added a commit that referenced this pull request Aug 7, 2026
…742)

The card credited "fixed stakeholder analysis generation" and "improved
template formatting consistency". Neither matches their merged PRs.

What they actually did, per #3 (2025-10-23) and #5 (2025-10-27): fixed
markdown packaging into the built wheel, added Gemini CLI support across 21
commands, and created converter.py (33d3363, 48 lines) — the ancestor of the
engine that now generates all seven non-Claude distribution formats.

"First external code contributor" was the one accurate claim and is kept: the
next external merged PR is #333, six months later.

Open PRs #739 and #740 are deliberately not credited yet.


Claude-Session: https://claude.ai/code/session_01VKbHCujejpxkgvh47BndDE

Co-authored-by: Claude Opus 5 <noreply@anthropic.com>
@tractorjuice

Copy link
Copy Markdown
Owner

Correction to my review above — blocker 3 was unfair

Reviewing #740 I checked what CONTRIBUTING.md actually asks of a contributor, and found I had held this PR to a standard that is not written down anywhere you would have seen.

Blocker 3 above cited CLAUDE.md step 7 to require README.md, docs/index.html, docs/DEPENDENCY-MATRIX.md and CODEOWNERS. But CLAUDE.md is maintainer-facing. CONTRIBUTING.md — the file a contributor reads — said only:

  1. Update documentation:
    • Update CHANGELOG.md
    • Add to README.md if major feature

docs/index.html and docs/DEPENDENCY-MATRIX.md appeared in neither, and CODEOWNERS in nothing at all. You updated the CHANGELOG, which is what the guide asked for.

Revised standing of blocker 3:

Item Now Why
docs/index.html not a blocker undocumented for contributors — maintainer will handle
docs/DEPENDENCY-MATRIX.md not a blocker same
.github/CODEOWNERS not a blocker never documented anywhere; and it is a question for the maintainer, since it is about who reviews NL changes, not about your code
README.md still worth fixing not because the guide demands it, but because the overlay is otherwise invisible in the canonical listing while being installable from the marketplace

That leaves two real blockers on this PR, both of which produce broken artefacts rather than missing documentation:

  1. No command resolves <!-- DOC-CONTROL-HEADER --> — every NL artefact ships a raw HTML comment where the Document Control table belongs.
  2. The VIRBI 2025 ladder has nowhere to rendernl-tbb would state Stg. GEHEIM in section 4 while its own header offers the UK [PUBLIC / OFFICIAL / OFFICIAL-SENSITIVE / SECRET].

The IMPORTANT items are unchanged, and item 4 in particular (the quality-checklist.md per-type sections) I have since confirmed is a pre-existing gap affecting six overlays, not something this PR introduced.

The contributing guide has been fixed so the next person is not caught the same way: #741 documents the overlay registration points that fail silently — including the two you found by running the tooling — and #743 names all four documentation files, drops the "if major feature" hedge, and adds the five places a command count goes stale.

Apologies for the noise. The two remaining blockers stand.

umag added a commit to umag/arc-kit that referenced this pull request Aug 7, 2026
Blockers 1-3 and important 4-9 from the review on tractorjuice#739.

BLOCKER 1 — resolve the Document Control marker. All four commands now read
${CLAUDE_PLUGIN_ROOT}/templates/_partials/RENDERING.md and resolve the
<!-- DOC-CONTROL-HEADER --> marker in their write step, per the ca-pia.md
precedent. Without this every NL artefact shipped a raw HTML comment where
Document Control belongs.

BLOCKER 2 — the Dutch classification ladder had nowhere to render. Applied the
minimum per-command override: all four commands instruct the writer to use the
VIRBI 2025 rubricering ladder (Ongerubriceerd / Departementaal VERTROUWELIJK /
Stg. CONFIDENTIEEL / Stg. GEHEIM / Stg. ZEER GEHEIM) in the Classification row,
replacing the UK line. The proper fix — document-control-nl.md plus RENDERING.md
routing and userConfig values — is left for a follow-up as suggested.

BLOCKER 3 — user-facing registration. Added to README.md (heading, overlay
list, a Dutch command block, and the closing integration sentence),
docs/DEPENDENCY-MATRIX.md (command list, inter-dependencies, typical compliance
path), docs/index.html (jurisdiction card, keywords meta, structured-data
feature list) and .github/CODEOWNERS (@umag @tractorjuice, mirroring the FR and
AT pairs).

IMPORTANT 4 — per-type quality checks. Added RBCLOUD, TBB, BIO2 and NLEXIT
sections to the CANONICAL plugins/arckit-claude/references/quality-checklist.md,
then re-ran sync-shared-assets.py. The PR body's claim that the NL copy already
carried them was wrong: the sections were written into the synced copy and a
later sync reverted them, which is exactly the trap you describe. PR body
corrected.

IMPORTANT 5 — citation traceability. All four commands now reference
references/citation-instructions.md and name the instruments that must appear in
the Document Register.

IMPORTANT 6 — all four commands now call
node scripts/generate-document-id.mjs <PROJECT_ID> <CODE> --filename instead of
hand-rolling version detection, picking up the unregistered-code validation from
 tractorjuice#723 for free.

IMPORTANT 7 and 8 — the governing instrument now has citable URLs, and the
ministry attribution is confirmed rather than asserted. Both the policy PDF
letterhead and the Kamerbrief metadata name Ministerie van Economische Zaken en
Klimaat, Staatssecretaris W.J.M. Aerdts, 3 juli 2026:
  https://www.tweedekamer.nl/kamerstukken/brieven_regering/detail?id=2026Z15738&did=2026D35294
  https://www.tweedekamer.nl/downloads/document?id=2026D35295
  Kamerstuk 26643, nr. 1541
Good catch prompting the check — the missing URL was the reason it could not be
verified from the PR.

IMPORTANT 9 — added docs/guides/nl-overlay.md and a guides.html site link, then
ran check-guide-parity.py --sync.

Also adds the "Adding a new jurisdiction overlay" section to CONTRIBUTING.md, as
requested, covering all nine registration points and flagging the two that fail
silently (converter.py and sync-claude-plugin-layout.py), the shared-asset rule
for references/ and _partials/, and the gitignored-extensions branch-switch trap.

Full Python suite: 1249 passed, 225 skipped. All seven check scripts pass,
sync-shared-assets --check and sync-claude-plugin-layout --check clean,
markdownlint-cli2 clean repo-wide.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@umag

umag commented Aug 7, 2026

Copy link
Copy Markdown
Contributor Author

Thank you — that's a genuinely useful review, and two of the findings are corrections to claims I made rather than gaps I left. Pushed as 55a47b4. Blockers 1–3 and important 4–9 are all addressed; nothing deferred.

Blockers

1 — Document Control marker. All four commands now read ${CLAUDE_PLUGIN_ROOT}/templates/_partials/RENDERING.md and resolve <!-- DOC-CONTROL-HEADER --> in their write step, following ca-pia.md. You're right that this shipped broken artefacts: a raw HTML comment where Document Control belongs, in every NL document. I copied the marker from the FR templates without checking that FR resolves it — which it doesn't, hence the 0/12.

2 — the classification ladder. Applied the minimum per-command override: all four instruct the writer to use the VIRBI 2025 ladder in the Classification row, replacing the UK line. This was the sharpest catch in the review — nl-tbb would have determined a Stg. level in section 4 while its own header offered PUBLIC / OFFICIAL / OFFICIAL-SENSITIVE / SECRET. A document contradicting itself about the classification it exists to determine is worse than no document. Happy to follow up with document-control-nl.md + RENDERING.md routing + userConfig as a separate PR.

3 — user-facing registration. Added to README.md (heading, overlay list, Dutch command block, closing integration sentence), docs/DEPENDENCY-MATRIX.md (commands, inter-dependencies, typical compliance path), docs/index.html (jurisdiction card, keywords, structured-data feature list) and .github/CODEOWNERS (@umag @tractorjuice, mirroring the FR/AT pairs).

Two corrections to my own PR body

The quality-checklist claim was false. The body said the NL copy was "the FR file plus four appended per-type sections". The sections were written — into the synced copy — and a later sync-shared-assets.py run reverted them. I then re-read the diff, saw it byte-identical to FR, and didn't reconcile that against what the body claimed. Now added to the canonical plugins/arckit-claude/references/quality-checklist.md and synced, so all four codes have real per-type checks. Body corrected.

The file count was wrong. I said 30 generated NL files; it's 64. I'd counted a glob covering only two of the four command names and reported it as the total.

Important 5–9

Citation instructions referenced in all four commands with the instruments named for the Document Register; generate-document-id.mjs replaces the hand-rolled version detection everywhere, which also picks up the #723 unregistered-code validation; docs/guides/nl-overlay.md added with a guides.html link, then check-guide-parity.py --sync.

On the ministry attribution (8)

Good question to ask — and the missing URL (7) is precisely why it couldn't be settled from the PR. It is EZK, confirmed twice:

  • the policy PDF letterhead reads Ministerie van Economische Zaken en Klimaat
  • the Kamerbrief metadata gives EZK, Staatssecretaris W.J.M. Aerdts, 3 juli 2026

Now cited in the commands:

Your instinct about the 2024 reorganisation was reasonable; it just happens that this one did come from EZ/EZK rather than BZK, notwithstanding that the 2022 policy it replaces was BZK's.

CONTRIBUTING.md

Added the section you asked for — "Adding a new jurisdiction overlay" — covering all nine registration points, and flagging the two that fail silently: without a converter.py entry the converter reports success and generates zero files for all eight non-Claude targets, and without a sync-claude-plugin-layout.py entry the mirror that actually publishes is never produced. It also documents the shared-asset rule for references/ and _partials/ (the trap I fell into) and the gitignored-extensions/ branch-switch problem, which cost me a round of phantom parity failures when working this branch and #740 in one clone.

Verification

Full Python suite               1249 passed, 225 skipped
7 check scripts                 all pass
sync-shared-assets --check      clean
sync-claude-plugin-layout --check  clean
markdownlint-cli2               0 errors, repo-wide

Follow-ups I'd suggest, not in this PR

  • document-control-nl.md + RENDERING.md routing + userConfig (the proper fix for blocker 2)
  • The same DOC-CONTROL-HEADER gap in arckit-fr (0/12), arckit-eu (0/7) and arckit-at (0/3) — as you note, better fixed on their own terms than by adding a fourth instance
  • Per-type checklist sections for CA, AU, US, NHS and finance, which have the same gap

Also worth flagging: plugins/arckit-eu/README.md and the marketplace descriptions say "7 commands", which #740 takes to 8 — no conflict between the branches, they touch different files, but the counts want landing in the same order they merge.

Happy to split any of this differently, or to rename RBCLOUD / NLEXIT if you'd prefer codes closer to the bare-noun style.

umag added a commit to umag/arc-kit that referenced this pull request Aug 7, 2026
Blockers 1-3 and important 4-9 from the review on tractorjuice#739.

BLOCKER 1 — resolve the Document Control marker. All four commands now read
${CLAUDE_PLUGIN_ROOT}/templates/_partials/RENDERING.md and resolve the
<!-- DOC-CONTROL-HEADER --> marker in their write step, per the ca-pia.md
precedent. Without this every NL artefact shipped a raw HTML comment where
Document Control belongs.

BLOCKER 2 — the Dutch classification ladder had nowhere to render. Applied the
minimum per-command override: all four commands instruct the writer to use the
VIRBI 2025 rubricering ladder (Ongerubriceerd / Departementaal VERTROUWELIJK /
Stg. CONFIDENTIEEL / Stg. GEHEIM / Stg. ZEER GEHEIM) in the Classification row,
replacing the UK line. The proper fix — document-control-nl.md plus RENDERING.md
routing and userConfig values — is left for a follow-up as suggested.

BLOCKER 3 — user-facing registration. Added to README.md (heading, overlay
list, a Dutch command block, and the closing integration sentence),
docs/DEPENDENCY-MATRIX.md (command list, inter-dependencies, typical compliance
path), docs/index.html (jurisdiction card, keywords meta, structured-data
feature list) and .github/CODEOWNERS (@umag @tractorjuice, mirroring the FR and
AT pairs).

IMPORTANT 4 — per-type quality checks. Added RBCLOUD, TBB, BIO2 and NLEXIT
sections to the CANONICAL plugins/arckit-claude/references/quality-checklist.md,
then re-ran sync-shared-assets.py. The PR body's claim that the NL copy already
carried them was wrong: the sections were written into the synced copy and a
later sync reverted them, which is exactly the trap you describe. PR body
corrected.

IMPORTANT 5 — citation traceability. All four commands now reference
references/citation-instructions.md and name the instruments that must appear in
the Document Register.

IMPORTANT 6 — all four commands now call
node scripts/generate-document-id.mjs <PROJECT_ID> <CODE> --filename instead of
hand-rolling version detection, picking up the unregistered-code validation from
 tractorjuice#723 for free.

IMPORTANT 7 and 8 — the governing instrument now has citable URLs, and the
ministry attribution is confirmed rather than asserted. Both the policy PDF
letterhead and the Kamerbrief metadata name Ministerie van Economische Zaken en
Klimaat, Staatssecretaris W.J.M. Aerdts, 3 juli 2026:
  https://www.tweedekamer.nl/kamerstukken/brieven_regering/detail?id=2026Z15738&did=2026D35294
  https://www.tweedekamer.nl/downloads/document?id=2026D35295
  Kamerstuk 26643, nr. 1541
Good catch prompting the check — the missing URL was the reason it could not be
verified from the PR.

IMPORTANT 9 — added docs/guides/nl-overlay.md and a guides.html site link, then
ran check-guide-parity.py --sync.

Also adds the "Adding a new jurisdiction overlay" section to CONTRIBUTING.md, as
requested, covering all nine registration points and flagging the two that fail
silently (converter.py and sync-claude-plugin-layout.py), the shared-asset rule
for references/ and _partials/, and the gitignored-extensions branch-switch trap.

Full Python suite: 1249 passed, 225 skipped. All seven check scripts pass,
sync-shared-assets --check and sync-claude-plugin-layout --check clean,
markdownlint-cli2 clean repo-wide.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@umag
umag force-pushed the feat/arckit-nl-overlay branch from 55a47b4 to 3f8c653 Compare August 7, 2026 14:50
@tractorjuice tractorjuice self-assigned this Aug 7, 2026
tractorjuice added a commit that referenced this pull request Aug 7, 2026
…#743)

Step 5 said "update CHANGELOG.md" and "add to README.md if major feature".
docs/index.html and docs/DEPENDENCY-MATRIX.md appeared only in CLAUDE.md,
which contributors do not read, so PRs kept arriving without them — #739 and
#740 both did. Reviewing against a requirement we never wrote down is our
omission, so the guide now carries the same list as CLAUDE.md step 7.

Adds a step 6 for the count claims, which go stale in five places on a new
overlay command and are checked by nothing.


Claude-Session: https://claude.ai/code/session_01VKbHCujejpxkgvh47BndDE

Co-authored-by: Claude Opus 5 <noreply@anthropic.com>
tractorjuice added a commit that referenced this pull request Aug 7, 2026
…r config (#744)

* feat(doc-control): add REGIME_PARTIALS map and guard it in CI

* fix(doc-control): guard REGIME_PARTIALS for orphan keys not in REGIMES

* feat(doc-control): route CA artefacts to the Canadian classification ladder

* feat(doc-control): route AU artefacts to the PSPF classification ladder

* feat(doc-control): add VIRBI 2025 partial ahead of the NL regime (#739)

* docs(doc-control): document regime-first resolution in RENDERING.md

* fix(templates): mirror _partials to the CLI copy and guard it (AT had drifted)

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01VKbHCujejpxkgvh47BndDE

* test(templates): assert plugin _partials source dir is non-empty before comparing

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01VKbHCujejpxkgvh47BndDE

* chore(doc-control): propagate new partials to community plugins and mirror

Runs sync-shared-assets.py and sync-claude-plugin-layout.py to push the
Task 1-6 REGIME_PARTIALS routing changes (updated RENDERING.md plus the
new document-control-{au,ca,nl}.md partials) out to all 14 community
plugins and the mirrored plugins/arckit-claude/plugins/ tree.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01VKbHCujejpxkgvh47BndDE

* fix(doc-control): assert which partial each regime maps to, and stop hard-routing the UK fallback

The regime guard only asserted that a non-UK partial *differed* from the UK
one, never which partial a regime named. Pointing CA at document-control-au.md
and AU at document-control-uk.md exited 0: Canadian artefacts got the
Australian ladder, Australian artefacts silently fell back to UK — precisely
the bug class regime routing exists to prevent.

REGIME_PARTIALS now has a companion UK_FALLBACK_BY_DESIGN set naming the
regimes that legitimately resolve to the UK partial, and the guard enforces
both halves: a regime in the set must map to document-control-uk.md, and a
regime outside it must map to document-control-<its own code>.md. The US/FR
deferral becomes a registered decision rather than an unguarded hole.

The same set fixes a behaviour change nobody asked for. Hard-routing UK, MOD,
EU, FR and US moved 52 doc-types off the user-config chain, so a UAE- or
Austrian-configured entity running /arckit:dpia lost its own ladder — against
the design's own success criterion that no artefact type changes ladder except
CA, AU and NL. Those regimes now fall through to step 2 exactly as before;
regimes outside the set hard-route as designed.

RENDERING.md is also self-contained now. Step 1 told the model to read
config/doc-types.mjs, which only the core plugin ships — no overlay has a
config/ directory, and every AT, AU, CA and UAE doc-type is overlay-owned, so
the lookup was unresolvable exactly where it mattered. It carries the regime
index and routing table inline instead, and the guard holds both tables to the
registry so the runtime authority cannot drift from the data.

Also: mirror RENDERING.md into .arckit/templates/_partials/, which had sat on
the pre-branch config-only chain and did not know about Austria, and compare
partials by content rather than basename in test_template_consistency.py so
the same staleness cannot recur silently.

* docs(doc-control): record regime routing in the changelog and correct two overlay guides

Both guides now contradicted shipped behaviour. uae-classification.md said the
Document Control header "will not render the UAE ladder" without userConfig,
which stopped being true for the uae-* commands the moment UAE doc-types began
hard-routing; the setting now governs the jurisdiction-agnostic artefacts
produced alongside them. au-federal-overlay.md still described the AU partial
and the routing as a future enhancement, and it shipped two commits ago — but
the part of that note about userConfig driving non-AU artefacts inside an AU
project remains unimplemented, because step 2 recognises the UAE and Austrian
schemes only, so the guide now separates the two.

The changelog entry covers the routing, the three new partials, and the
deliberate US/FR deferral, which is a deferral rather than a decision: neither
has authoritative ladder wording in this repository, and a wrong ladder inside
a Document Control header reads more authoritative than a fallback does.

* fix(at,uae): route classification header via RENDERING.md, not user config

Three overlay command bodies still instructed models to resolve the
Document Control classification ladder from the user's plugin
userConfig (governance_framework / classification_scheme), overriding
the hard-routing this branch introduces for AT/UAE/CA/AU regimes in
RENDERING.md. Fixed uae-classification.md, at-dsgvo.md and
at-bvergg.md to defer to RENDERING.md / state the InfoSiG value
unconditionally, so an Austrian or Emirati artefact can no longer be
given a UK classification ladder.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01VKbHCujejpxkgvh47BndDE

---------

Co-authored-by: Claude Opus 5 <noreply@anthropic.com>
@tractorjuice

Copy link
Copy Markdown
Owner

Re-review — all blockers cleared, one mechanical rebase left

I've re-reviewed against your three commits. Every blocker and every Important item from my original review is fixed, and you went further than I asked on two of them.

Fixed

Original finding Status
Blocker 1 — <!-- DOC-CONTROL-HEADER --> never resolved Fixed, all four commands (nl-tbb.md:131 et al)
Blocker 2 — VIRBI ladder had nowhere to render Fixed via per-command override, the CA/AU pattern
Blocker 3 — README / index.html / DEPENDENCY-MATRIX / CODEOWNERS Retracted by me; see my correction
Important 4 — quality-checklist per-type sections Fixed — and across every overlay, not just NL
Important 5 — citation traceability Fixed (nl-tbb.md:133), with VIRBI 2025 required in the Document Register
Important 6 — generate-document-id.mjs Fixed (nl-tbb.md:123), correct PROJECT_ID DOC_TYPE form

On the quality-checklist: I'd told you that gap was pre-existing and affected six overlays, i.e. not yours to fix. You fixed the canonical copy and propagated it to all of them. That closes a defect that had been shipping unreported since the CA overlay landed — thank you.

What changed underneath you

#744 merged an hour ago and rebuilt the mechanism your blocker 2 was working around. The classification ladder now routes from the doc-type's regime via a REGIME_PARTIALS map, and document-control-nl.md already exists on main using your VIRBI wording, credited to you in the plan. So you don't need to create it.

Your per-command ladder override is now belt-and-braces rather than the primary mechanism — exactly like the CA and AU commands. Keep it; it's harmless and consistent.

The remaining work — mechanical

I test-merged main into your branch. One conflict, and it's trivial: CHANGELOG.md, where both add a ## [Unreleased] heading. Keep both entries.

After resolving it, #744's new CI guard fails with exactly three lines telling you what to add:

[FAIL] regimes in REGIMES but missing a REGIME_PARTIALS entry:
  - NL
[FAIL] RENDERING.md "Regime routing" table has no row for regime NL
[FAIL] RENDERING.md "Regime index" table has no row for regime NL

That's the guard doing its job — I flagged in #744 that your PR would hit it. To clear:

  1. Add NL: 'document-control-nl.md', to REGIME_PARTIALS in plugins/arckit-claude/config/doc-types.mjs. Do not add NL to UK_FALLBACK_BY_DESIGN — the Netherlands has a real ladder, so it hard-routes.
  2. Add an NL row to both tables in plugins/arckit-claude/templates/_partials/RENDERING.md.
  3. Re-run python3 scripts/sync-shared-assets.py and python3 scripts/sync-claude-plugin-layout.py — your branch carries the pre-feat(doc-control): route the classification ladder by regime, not user config #744 RENDERING.md in its _partials copies, and without a re-sync you'd reintroduce the stale config-only routing into the NL plugin.
  4. Re-run python scripts/converter.py, then python -m pytest -q and node scripts/tests/test-regime-registration.mjs.

No further review findings from me. Once the guard is green this is good to merge as far as I'm concerned.

umag added a commit to umag/arc-kit that referenced this pull request Aug 7, 2026
Blockers 1-3 and important 4-9 from the review on tractorjuice#739.

BLOCKER 1 — resolve the Document Control marker. All four commands now read
${CLAUDE_PLUGIN_ROOT}/templates/_partials/RENDERING.md and resolve the
<!-- DOC-CONTROL-HEADER --> marker in their write step, per the ca-pia.md
precedent. Without this every NL artefact shipped a raw HTML comment where
Document Control belongs.

BLOCKER 2 — the Dutch classification ladder had nowhere to render. Applied the
minimum per-command override: all four commands instruct the writer to use the
VIRBI 2025 rubricering ladder (Ongerubriceerd / Departementaal VERTROUWELIJK /
Stg. CONFIDENTIEEL / Stg. GEHEIM / Stg. ZEER GEHEIM) in the Classification row,
replacing the UK line. The proper fix — document-control-nl.md plus RENDERING.md
routing and userConfig values — is left for a follow-up as suggested.

BLOCKER 3 — user-facing registration. Added to README.md (heading, overlay
list, a Dutch command block, and the closing integration sentence),
docs/DEPENDENCY-MATRIX.md (command list, inter-dependencies, typical compliance
path), docs/index.html (jurisdiction card, keywords meta, structured-data
feature list) and .github/CODEOWNERS (@umag @tractorjuice, mirroring the FR and
AT pairs).

IMPORTANT 4 — per-type quality checks. Added RBCLOUD, TBB, BIO2 and NLEXIT
sections to the CANONICAL plugins/arckit-claude/references/quality-checklist.md,
then re-ran sync-shared-assets.py. The PR body's claim that the NL copy already
carried them was wrong: the sections were written into the synced copy and a
later sync reverted them, which is exactly the trap you describe. PR body
corrected.

IMPORTANT 5 — citation traceability. All four commands now reference
references/citation-instructions.md and name the instruments that must appear in
the Document Register.

IMPORTANT 6 — all four commands now call
node scripts/generate-document-id.mjs <PROJECT_ID> <CODE> --filename instead of
hand-rolling version detection, picking up the unregistered-code validation from
 tractorjuice#723 for free.

IMPORTANT 7 and 8 — the governing instrument now has citable URLs, and the
ministry attribution is confirmed rather than asserted. Both the policy PDF
letterhead and the Kamerbrief metadata name Ministerie van Economische Zaken en
Klimaat, Staatssecretaris W.J.M. Aerdts, 3 juli 2026:
  https://www.tweedekamer.nl/kamerstukken/brieven_regering/detail?id=2026Z15738&did=2026D35294
  https://www.tweedekamer.nl/downloads/document?id=2026D35295
  Kamerstuk 26643, nr. 1541
Good catch prompting the check — the missing URL was the reason it could not be
verified from the PR.

IMPORTANT 9 — added docs/guides/nl-overlay.md and a guides.html site link, then
ran check-guide-parity.py --sync.

Also adds the "Adding a new jurisdiction overlay" section to CONTRIBUTING.md, as
requested, covering all nine registration points and flagging the two that fail
silently (converter.py and sync-claude-plugin-layout.py), the shared-asset rule
for references/ and _partials/, and the gitignored-extensions branch-switch trap.

Full Python suite: 1249 passed, 225 skipped. All seven check scripts pass,
sync-shared-assets --check and sync-claude-plugin-layout --check clean,
markdownlint-cli2 clean repo-wide.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@umag
umag force-pushed the feat/arckit-nl-overlay branch from 5786858 to 3d78e35 Compare August 7, 2026 17:23
umag and others added 6 commits August 7, 2026 19:24
The Netherlands had no overlay, and its central-government cloud rules
changed substantially in 2025-2026 in ways that make generic EU guidance
insufficient:

- Herziening rijksbreed cloudbeleid 2026 (EZK, 3 July 2026) replaced the
  2022 policy
- VIRBI 2025 (BWBR0051482) came into force 9 September 2025 and repealed
  VIRBI 2013 the same day
- Cyberbeveiligingswet and Wet weerbaarheid kritieke entiteiten, the Dutch
  NIS2 and CER transpositions, came into force 15 August 2026
- BIO2 was established by the OBDO on 23 September 2025

Four commands:

- /arckit:nl-cloud  (RBCLOUD) Rijksbreed cloudbeleid compliance assessment
- /arckit:nl-tbb    (TBB)     Te Beschermen Belangen / VIRBI 2025 rubricering
- /arckit:nl-bio    (BIO2)    BIO2 conformance assessment
- /arckit:nl-exit   (NLEXIT)  cloud exit plan (clause 3.2)

Two deliberate omissions. Unlike France's SecNumCloud there is no published
Dutch qualification list, so no commercial provider is named as compliant and
the overlay says so where a reader would expect one. Where the source text was
not to hand — the remaining aspects of the clause 3.1 risk analysis, and the
individual BIO2 overheidsmaatregelen — the commands instruct the assessor to
consult the current text rather than shipping a plausible-looking list.

Registers the first NL regime: four codes in config/doc-types.mjs plus NL in
REGIMES and REGIME_LABELS, a row per code in the /arckit:pages
known-artifact-types table, and entries in .claude-plugin/marketplace.json and
the converter.py plugin list so the overlay reaches the non-Claude targets.

Registration points beyond those CONTRIBUTING.md lists, each found by running
the repository's own tooling rather than from the docs:

- a row per code in the /arckit:pages known-artifact-types table
  (scripts/check-doc-type-registry.py)
- .claude-plugin/marketplace.json and plugins/arckit-claude/.claude-plugin/
  marketplace.json, which tests/plugin/test_release_process.py asserts are
  equal (note the standalone one uses ./plugins/<short>, not the full dir name)
- the hardcoded plugin lists in scripts/converter.py,
  scripts/sync-claude-plugin-layout.py and scripts/push-extensions.sh
- the mirrored standalone layout at plugins/arckit-claude/plugins/nl,
  produced by sync-claude-plugin-layout.py
- overlay templates duplicated into .arckit/templates for the CLI
- the plugin command-dir lists in tests/extension_helpers.py,
  tests/paperclip/test_commands_json.py, tests/codex/test_codex_extension.py,
  tests/plugin/test_template_consistency.py and
  EXPECTED_CLAUDE_MARKETPLACE_SOURCES in tests/plugin/test_release_process.py

Without the converter and sync entries a new overlay silently produces zero
generated files for the non-Claude targets, with the converter still reporting
success.

Full Python suite: 1249 passed, 225 skipped. All seven check scripts pass.
markdownlint-cli2 clean repo-wide.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Blockers 1-3 and important 4-9 from the review on tractorjuice#739.

BLOCKER 1 — resolve the Document Control marker. All four commands now read
${CLAUDE_PLUGIN_ROOT}/templates/_partials/RENDERING.md and resolve the
<!-- DOC-CONTROL-HEADER --> marker in their write step, per the ca-pia.md
precedent. Without this every NL artefact shipped a raw HTML comment where
Document Control belongs.

BLOCKER 2 — the Dutch classification ladder had nowhere to render. Applied the
minimum per-command override: all four commands instruct the writer to use the
VIRBI 2025 rubricering ladder (Ongerubriceerd / Departementaal VERTROUWELIJK /
Stg. CONFIDENTIEEL / Stg. GEHEIM / Stg. ZEER GEHEIM) in the Classification row,
replacing the UK line. The proper fix — document-control-nl.md plus RENDERING.md
routing and userConfig values — is left for a follow-up as suggested.

BLOCKER 3 — user-facing registration. Added to README.md (heading, overlay
list, a Dutch command block, and the closing integration sentence),
docs/DEPENDENCY-MATRIX.md (command list, inter-dependencies, typical compliance
path), docs/index.html (jurisdiction card, keywords meta, structured-data
feature list) and .github/CODEOWNERS (@umag @tractorjuice, mirroring the FR and
AT pairs).

IMPORTANT 4 — per-type quality checks. Added RBCLOUD, TBB, BIO2 and NLEXIT
sections to the CANONICAL plugins/arckit-claude/references/quality-checklist.md,
then re-ran sync-shared-assets.py. The PR body's claim that the NL copy already
carried them was wrong: the sections were written into the synced copy and a
later sync reverted them, which is exactly the trap you describe. PR body
corrected.

IMPORTANT 5 — citation traceability. All four commands now reference
references/citation-instructions.md and name the instruments that must appear in
the Document Register.

IMPORTANT 6 — all four commands now call
node scripts/generate-document-id.mjs <PROJECT_ID> <CODE> --filename instead of
hand-rolling version detection, picking up the unregistered-code validation from
 tractorjuice#723 for free.

IMPORTANT 7 and 8 — the governing instrument now has citable URLs, and the
ministry attribution is confirmed rather than asserted. Both the policy PDF
letterhead and the Kamerbrief metadata name Ministerie van Economische Zaken en
Klimaat, Staatssecretaris W.J.M. Aerdts, 3 juli 2026:
  https://www.tweedekamer.nl/kamerstukken/brieven_regering/detail?id=2026Z15738&did=2026D35294
  https://www.tweedekamer.nl/downloads/document?id=2026D35295
  Kamerstuk 26643, nr. 1541
Good catch prompting the check — the missing URL was the reason it could not be
verified from the PR.

IMPORTANT 9 — added docs/guides/nl-overlay.md and a guides.html site link, then
ran check-guide-parity.py --sync.

Also adds the "Adding a new jurisdiction overlay" section to CONTRIBUTING.md, as
requested, covering all nine registration points and flagging the two that fail
silently (converter.py and sync-claude-plugin-layout.py), the shared-asset rule
for references/ and _partials/, and the gitignored-extensions branch-switch trap.

Full Python suite: 1249 passed, 225 skipped. All seven check scripts pass,
sync-shared-assets --check and sync-claude-plugin-layout --check clean,
markdownlint-cli2 clean repo-wide.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
CONTRIBUTING.md: superseded by tractorjuice#741, which documents the overlay
registration points including the two silent failures found here.

CODEOWNERS: per review, assigning a reviewer for NL changes is a
maintainer decision rather than part of this contribution.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
check-guide-parity flagged nl-overlay.md as root-only. Every sibling
overlay guide exists in both trees, so this one should too — the note
is non-fatal, which is why the earlier run looked clean.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
docs/guides/eu-cloud-sovereignty.md and its plugin-tree copy belong to
 tractorjuice#740, not here. They were untracked on the EU branch when I switched
branches — git stash does not stash untracked files and checkout carries
them across — so a git add -A on this branch swept them in.

Also re-adds the Netherlands block to docs/guides.html, which was lost
when guides.html was reverted while removing the leak.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
…of per-command overrides

Rebased onto main and adopted the mechanism tractorjuice#744 introduced, which arrived
after this branch was cut. The CHANGELOG conflict is resolved keeping both
entries, tractorjuice#744's first.

  NL:  'document-control-nl.md',   in REGIME_PARTIALS

NL is deliberately NOT added to UK_FALLBACK_BY_DESIGN — the Netherlands has a
real ladder in VIRBI 2025, so it hard-routes, and an artefact assessed under
Dutch rules should carry the Dutch ladder whoever runs the command. Adds the NL
row to both RENDERING.md tables (Regime routing: hard-routes; Regime index:
RBCLOUD, TBB, BIO2, NLEXIT) and names NL in the step-1 hard-routing list, then
re-runs sync-shared-assets.py, sync-claude-plugin-layout.py and converter.py —
this branch carried the pre-tractorjuice#744 RENDERING.md in its _partials copies, so
without the re-sync the NL plugin would have shipped the stale config-only
chain. document-control-nl.md now reaches arckit-nl through the sync rather
than being authored here; thank you for landing it ahead of this PR.

The per-command VIRBI override stays, as you suggested — belt-and-braces,
consistent with the ca-* and au-* commands, and it now agrees with the routing
rather than substituting for it.

.arckit/templates/_partials/RENDERING.md is copied by hand: sync-shared-assets
covers the 14 community plugins but not the CLI mirror, and
test_plugin_and_cli_partials_are_in_sync compares it by content.

One more registration point, not in CONTRIBUTING.md and not caught by any check
script — plugins/arckit-claude/config/guide-groups.mjs carries an explicit
per-guide list. Without an entry, docs/guides/nl-overlay.md landed in "Other /
Uncategorised" and test_codex_hook_runs_pages_preprocessor failed on
other_guides == []. Added as a "Community overlays - Netherlands" pack, with
the category slotted into GUIDE_CATEGORY_ORDER between France and UAE. Worth a
line in the CONTRIBUTING.md section, if you agree — I hit the identical failure
on tractorjuice#740.

Full Python suite: 1275 passed, 225 skipped. All seven check scripts pass, both
sync --check runs clean, test-regime-registration.mjs reports 10 regimes all
registered and labelled, markdownlint-cli2 clean repo-wide.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@umag
umag force-pushed the feat/arckit-nl-overlay branch from 3d78e35 to 3cad7bb Compare August 7, 2026 17:29
@umag

umag commented Aug 7, 2026

Copy link
Copy Markdown
Contributor Author

All four steps done, plus one more the guard didn't catch. Pushed as 3cad7bb4, rebased onto 703068d5.

The #744 adoption

NL: 'document-control-nl.md' in REGIME_PARTIALS, and not in UK_FALLBACK_BY_DESIGN — agreed, the Netherlands has a real ladder, so it hard-routes. NL rows added to both RENDERING.md tables, and NL named in the step-1 hard-routing list alongside AT/AU/CA/UAE, which the guard doesn't check but a reader of the prose would notice. Re-ran both sync scripts; you were right that the branch carried the pre-#744 _partials copies.

Keeping the per-command VIRBI override, as you suggested.

document-control-nl.md now reaches arckit-nl through the sync rather than being authored in this branch. Thank you for landing it ahead of the PR — it turned blocker 2 into a registration change, which is what you said it would.

A tenth registration point

plugins/arckit-claude/config/guide-groups.mjs carries an explicit per-guide stem list. Without an entry, docs/guides/nl-overlay.md fell to Other / Uncategorised and test_codex_hook_runs_pages_preprocessor failed on other_guides == []:

E       AssertionError: assert ['docs/guides/nl-overlay.md'] == []

Added as a Community overlays - Netherlands pack, with the category slotted into GUIDE_CATEGORY_ORDER between France and UAE. Nothing in CONTRIBUTING.md mentions it and no check script reports it — the failure surfaces from a Codex-extension test, which is not where a contributor looks for a missing overlay registration. I hit the identical failure on #740, so it is not NL-specific. Worth adding to the section you wrote in #741, if you agree.

The rebase

Two rounds — #744 first, then #750/#751 while I was verifying. CHANGELOG.md resolved keeping both entries, yours first. references/quality-checklist.md also conflicted: #750 added the 15 togaf-adm and agent-architecture sections in the same region as my four NL ones. Resolved in the canonical copy and re-synced, rather than in the 29 generated ones — the trap from the first round.

#751's guard is green and counts the NL sections:

Quality-checklist reference check OK: 85 per-type reference(s) across 5 plugin(s),
all resolve (arckit-agent-architecture: 6, arckit-claude: 52, arckit-fr: 7,
arckit-nl: 4, arckit-togaf-adm: 9).

Verification

Full Python suite                  1305 passed, 225 skipped
8 check scripts                    all pass
sync-shared-assets --check         clean
sync-claude-plugin-layout --check  clean
test-regime-registration.mjs       10 regimes, all registered and labelled
converter.py                       zero drift
markdownlint-cli2                  0 errors, repo-wide

One note on merge order: #740 is also rebased onto 703068d5 now, so whichever lands first will leave the other with only the ## [Unreleased] conflict you predicted.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants