Skip to content

Migrate per-skill .claude config files to userConfig, one conventions doc, or the cascade (ADR 0018) #5906

Open
15 of 17 issues completed

Description

@kyle-sexton

Problem

Many skills keep their customization in a one-off file under .claude/. This repository alone has seven: ai-slop.json, attribution.json, bugs.md, code-metrics.yaml, docs-naming.json, source-control.md and audit-pass.md. About 38 skill bodies name such a file. Each consumer has to discover them one skill at a time, and agents without the skill installed cannot read the intent.

The maintainer's target: "Customizations should be userConfig when they are per-project or per-repo settings, otherwise concise markdown lines in one well-known docs/conventions file that CLAUDE.md or AGENTS.md points to ('if you use these skills, look here')." It keeps them out of every context, easy to find, and readable by agents that don't have the skills.

What already decides part of this

docs/adr/0018-express-team-shared-conventions-as-consumer-convention-docs.md (decision 1, L30-35): team-shared prose configuration with no per-operator axis becomes a convention doc bound by one pointer line in the root instruction file, while "Per-operator-keyed surfaces, structured data, policy-floor surfaces, and all state stay dedicated files under the config-cascade layers." Two ADRs are numbered 0018, so cite the full filename. The nearby conventions are docs/conventions/config-cascade, consumer-config-layering and plugin-reconfiguration.

Interim rule (decided in the poteto-talk interview, Q53)

New settings added before this migration go in one of three homes:

  • per-consumer scalar keys in the owning plugin's userConfig
  • team prose conventions in the one conventions doc
  • structured or per-operator data in the cascade file (ADR 0018)

Scope

  1. Inventory every per-skill .claude/<topic>.* file and every skill body that names one.
  2. Classify each setting: userConfig scalar, convention prose, or cascade data (structured, per-operator, policy floor or state), against ADR 0018.
  3. Migrate each file to its home, with a compatibility read of the old file for one release, and update the skill bodies and setup skills.
  4. Update the three conventions docs and ADR 0018 if the classification changes anything.

Acceptance criteria

  • No skill reads a one-off .claude/<topic>.* file except cascade-data files ADR 0018 keeps.
  • The root instruction file holds one pointer line to the conventions doc.
  • Each migrated setting is listed with its new home in the PR.

Activity

  1. added
    needs-triageNot yet classified. Floor until a type and one priority tier are set.
    on Oct 2, 2026
  2. kyle-sexton commented on Oct 4, 2026

    @kyle-sexton
    MemberAuthor

    This was generated by AI during triage.

    Triage

    Routing: human-gated, status: needs-decision, priority medium, work class structural. This is a cross-plugin configuration migration with a compatibility window, which is C4 by class: it needs plan approval before execution and human review and merge.

    Decision needed: approve the per-file classification (userConfig scalar, convention prose, or cascade data) before any migration starts. ADR 0018 and the interim rule settle the categories, but not which file or setting lands where; that table is the plan to approve.

    Inventory notes for whoever plans it:

    • The repository's .claude/ holds the seven files the issue names plus cloud-bootstrap.sh and cutover-pathdet-ack.txt; the plan should say whether either is a skill configuration file.
    • The "about 38 skill bodies" count needs redoing: a rough grep for .claude/<topic>.(json|md|yaml) across plugin SKILL.md files matches 60 files, though that pattern also catches settings.json and similar, so it overcounts.
    • Two ADRs are numbered 0018 (the issue already says to cite the full filename).
      Basis: verified, git ls-tree --name-only origin/main .claude/, git grep -lE '\.claude/[a-z-]+\.(json|md|ya?ml)' origin/main -- 'plugins/*/skills/*/SKILL.md' | wc -l (60), git ls-tree origin/main docs/adr/ | grep 0018 at e3bef1210.

    Agent Brief

    Type: Task
    Summary: Move each per-skill one-off .claude/<topic>.* setting to its ADR 0018 home: owning plugin userConfig, one conventions doc, or the config cascade.

    Current behavior:
    Many skills read customization from their own file under the consumer's .claude/. Consumers discover them one skill at a time, and agents without the skill installed cannot read the intent.

    Desired behavior:
    Per-consumer scalar keys live in the owning plugin's userConfig; team prose conventions live in one conventions doc that the root instruction file points to with one line; structured, per-operator, policy-floor or state data stays in the cascade per ADR 0018. Each migrated skill reads its new home and, for one release, still reads the old file.

    Key interfaces:

    • Each plugin's userConfig schema and its setup skill.
    • The consumer conventions doc and its single pointer line.
    • The config-cascade, consumer-config-layering and plugin-reconfiguration conventions, and ADR 0018 (express team-shared conventions as consumer convention docs).

    Acceptance criteria:

    • An approved classification table lists every file and setting with its home.
    • No skill reads a one-off .claude/<topic>.* file except cascade-data files ADR 0018 keeps.
    • The root instruction file holds one pointer line to the conventions doc.
    • Each migrated setting is listed with its new home in the PR, with the one-release compatibility read in place.

    Out of scope:

    • .claude/settings.json, hooks and rules.
    • Changing ADR 0018's categories unless the approved classification requires it.
  3. added
    priority: mediumReal value, no hard deadline; normal backlog flow.
    needs-humanHuman-in-the-loop required; autonomous sessions must not resolve items carrying this.
    status: needs-decisionAwaiting a human or maintainer judgment call.
    work-class: structuralRefactors, migrations, contract changes; cross-cutting and hard to reverse.
    and removed
    needs-triageNot yet classified. Floor until a type and one priority tier are set.
    on Oct 4, 2026
  4. kyle-sexton commented on Oct 4, 2026

    @kyle-sexton
    MemberAuthor

    The target home has changed. Standards components/github-actions-conventions/README.md:131-136 (merged
    2026-10-04) puts structured configuration in docs/conventions/<concern>.yaml, validated by a JSON Schema,
    with its prose in docs/conventions/<concern>.md, and it supersedes ADR 0044 for structured
    configuration. The 2,000-PRs effort records this in a new ADR, "home plugin customization in
    docs/conventions/.yaml", numbered at write time. Per-user values stay in plugin userConfig.
    pluginConfigs is read only from user and managed settings, so it never carries a per-repository value.

    This issue now owns migrating these surfaces to that form:

    • .claude/source-control.md, which is read by about 41 files, including guardrails' commit-msg hook. It
      moves to docs/conventions/source-control.yaml, which by then will already exist holding only
      pr_open_state. Keep the old file with identical keys until a release carrying the new reader has
      shipped and the git hooks have been reinstalled.
    • The other .claude/* files: ai-slop.json, attribution.json, bugs.md, docs-naming.json and
      audit-pass.md. The effort moves code-metrics.yaml itself.
    • The ADR 0044 fenced config blocks in the multi-agent plugin and in docs/conventions/review-digest.md.
      The effort migrates testing's block itself.
    • Guardrails' folder-form docs/conventions/source-control/commit-convention.yml.

    Script readers use the shared reader lib/parse-concern-value.sh. After the effort's change it reads
    dotted keys, lists, stdin and a validated --ref.

    Done when (replaces the body's acceptance criteria for structured settings): no skill reads a team
    setting from a .claude/<topic>.* file or a fenced config block, and the PR lists each migrated setting
    with its new docs/conventions/<concern>.yaml home and schema.

  5. added theissue type on Oct 15, 2026
  6. 35 remaining items

  7. kyle-sexton commented on Oct 27, 2026

    @kyle-sexton
    MemberAuthor

    Decision recorded. The owner answered in the Refinement and Issue Triage sessions (2026-10-25), deciding the open items below on the facts:

    go with whatever the facts/data/metrics + /discovery:research says and ensure we're aligned with SOLID, DRY/SSOT principles

    I should only ever be in the loop ONLY when necessary (intent/vision changed, something came up during implementation that impacts trajectory/alignment, OR a high security risk) - I've covered this all before

    No owner ledger (.work/*/interview-checklist.md, .work/gh-monitor-owner-decisions/) names this issue.

    The 2026-10-04 comment moved the target home to docs/conventions/<concern>.yaml (#5906 (comment)), and the 2026-10-24 split filed 12 slices, #9725 to #9737 (#5906 (comment)).

    1. Should this issue stay open only as a tracker that closes when the slices are done, instead of being picked up as one change?
      Decided: Yes. The lane works the slices, not this issue. Six are closed; refactor(source-control): read the babysit loop keys from docs/conventions/source-control.yaml #9726, refactor(guardrails): resolve the commit convention from docs/conventions/source-control.yaml #9727, refactor(attribution): move the .claude/attribution.json settings to docs/conventions/attribution.yaml #9729, refactor(docs-naming): move the .claude/docs-naming.json settings to docs/conventions/docs-naming.yaml #9731, chore(guardrails): reinstall the commit-msg git hooks on operator machines after the convention move #9735 and chore: drop the one-release .claude config reads and this repository's old config files #9737 are open. chore: drop the one-release .claude config reads and this repository's old config files #9737 drops the one-release reads and waits on the others, so the lane closes this issue when chore: drop the one-release .claude config reads and this repository's old config files #9737 closes and no slice is open. Basis: the split comment above.
    2. Should the body's acceptance criteria be replaced with the 2026-10-04 comment's done-when?
      Decided: Yes. That comment says its done-when "replaces the body's acceptance criteria for structured settings", and the body's criteria still name the old targets. The done-when is checked by the slices, chiefly chore: drop the one-release .claude config reads and this repository's old config files #9737; this issue adds no criteria of its own. Basis: Migrate per-skill .claude config files to userConfig, one conventions doc, or the cascade (ADR 0018) #5906 (comment).

    Tracker only. Done when, for the record (from the 2026-10-04 comment, wording unchanged): no skill reads a team setting from a .claude/<topic>.* file or a fenced config block, and the PR lists each migrated setting with its new docs/conventions/<concern>.yaml home and schema. This record changes no slice.

  8. added
    status: confirmedA maintainer confirmed the item is real and in scope; ready to be worked.
    and removed
    status: needs-decisionAwaiting a human or maintainer judgment call.
    on Oct 27, 2026
  9. added
    needs-triageNot yet classified. Floor until a type and one priority tier are set.
    and removed
    status: confirmedA maintainer confirmed the item is real and in scope; ready to be worked.
    needs-triageNot yet classified. Floor until a type and one priority tier are set.
    on Oct 27, 2026
  10. kyle-sexton commented on Oct 31, 2026

    @kyle-sexton
    MemberAuthor

    Host run. The #5906 chain was checked against its done-when, and the #9727 deletion ran with its done-when checks on the host; #5906 cannot finish this session.

    What ran: repository reads at c7e50d15a0; on the #9727 branch, the four scripts/run-test-file.sh suites, check-convention-yaml.sh --check, sync-shared-copies.sh --check, check-changelog-fragments.sh --check-required origin/main, and check-affected.sh --tests on the committed head (4 min 19 s). Claude Code 2.1.316. No eval ran.

    PR: #11625 (ready; head 04550f17, verified again after merging main). Not armed or merged. Merging needs the verify:repeated-fail hold lifted, as below.

    Issue claims. #5906 is the last open sub-issue of #7571: confirmed (six others closed). 20 issues behind #7571: confirmed from ready-edges.json. #5906 has open sub-issues: confirmed, and #7571 cannot close by #5906 this session.

    What remains on #5906. Done when (2026-10-04 comment): no skill reads a team setting from a .claude/<topic>.* file or a fenced config block, with each setting's new home listed. Nine of 12 slices are closed. Three are open, in this order:

    1. refactor(guardrails): resolve the commit convention from docs/conventions/source-control.yaml #9727: one file left to delete. The PR does it, and all four of its done-when items pass.
    2. chore(guardrails): reinstall the commit-msg git hooks on operator machines after the convention move #9735, the next step on the chain: reinstall the commit-msg hooks on each operator machine. It needs a guardrails release containing refactor(guardrails): resolve the commit convention from docs/conventions/source-control.yaml #9727's merge, so it cannot start until that merges and releases. A laptop lane holds it, so this run did not touch it.
    3. chore: drop the one-release .claude config reads and this repository's old config files #9737: drop the compatibility reads. Not ready: it waits on chore(guardrails): reinstall the commit-msg git hooks on operator machines after the convention move #9735. On main, 419 non-CHANGELOG, non-retirement lines still name the old files in plugins, lib and scripts (77 of them in one test file, parse-branch-issue.test.sh), and six .claude/ files remain. It also has a code gap: its grep for yaml config still prints lines in plugins/multi-agent/scripts, so that block reader is not gone.

    New blocker on #9737: six repositories. #9737 removes the legacy read: its grep must print no live .claude/source-control.md line, and lib/resolve-convention-pattern.sh:23-25 is that read. Checked by contents reads this session: architecture, azure-iac, knowledge-corpus, songwriting, pr-pipeline-sandbox (all melodic-software) and kyle-sexton/autonomy-demo-scratch each hold subject_pattern in .claude/source-control.md, with no docs/conventions/source-control.yaml and no folder-form file. When the read goes, each loses commit-convention enforcement. So each repository needs its pattern in the YAML first, and #9737 needs those six as its blocker. The #9727 PR removes no read, only this repository's own file, so it does not affect them. Those PRs are outside this worker's brief, so none was opened. Only these six were checked, not every consumer in the repo map. A standards target entry cannot cover them all: the sync manifest's comments mark architecture, knowledge-corpus and songwriting as not sync targets and azure-iac as a trust root the sync App must not write to. pr-pipeline-sandbox is listed under targets, though its comment calls it a test bed. autonomy-demo-scratch does not appear.

    Two files sit outside #9737's list: .claude/code-metrics.yaml and .claude/mutation-testing.md. plugins/code-metrics/reference/config.md:20 documents the first as an older team file. Nothing tracks whether either still counts against #5906's done-when; this needs a line on #9737.

    Why #9727 keeps failing. The lane's PRs #11402 and #11422 were closed on verify:repeated-fail with "No FAIL findings were counted". All three counted heads (09f699f1, 5a4fde34, f70b8c1e) are on branches of #10134, which merged with Refs: #9727. Its FAILs count against the issue, and the cap excuses only PRs a capped-close record names (docs/conventions/pr-pipeline/CHANGELOG.md, the cross-pull-request FAIL cap entry). So every new PR for #9727 starts at the cap. Re-queueing it would repeat this, and it is parked with its one fresh attempt spent. The merge path for a PR not authored by the lanes App is UNVERIFIED. .github/scripts/pr-merge/merge-holds.test.mjs:980-982 shows an owner-person approval on the head lifting a pr-verify FAIL hold, while docs/conventions/pr-pipeline/README.md:2476 says verify:repeated-fail never clears for the pull request. They may be different gates; this run did not establish which governs #11625.

    Pipeline finding for the coordinator: a merged Refs: PR's old FAILs permanently cap its follow-up issue. The code path is not fixed here.

    Stale links, for the coordinator to edit

    1. corrections: new plugin with /corrections:codify #7573's dependency on config-cascade: settings resolution and convention home #7571 is stale: recommended removal.
    2. Migrate per-skill .claude config files to userConfig, one conventions doc, or the cascade (ADR 0018) #5906's sub-issue link under config-cascade: settings resolution and convention home #7571 is the larger lever, and it is contested: the owner should see both sides.

    Not done: a partial #9737. It would free nothing, because #5906 still needs the source-control half.

    Eval remaining on this chain: none.

    Target labels: add none; remove none.

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

Metadata

Metadata

Assignees

No one assigned

    Labels

    priority: mediumReal value, no hard deadline; normal backlog flow.status: readyTriaged, unblocked, and fully specified; eligible to pick up.work-class: structuralRefactors, migrations, contract changes; cross-cutting and hard to reverse.

    Type

    Fields

    No fields configured for Task.

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions