You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@magpie.apache.org by po...@apache.org on 2026/09/08 01:21:10 UTC

(magpie) branch main updated: fix(docs): reconcile documentation with the state of the tree (#1159)

This is an automated email from the ASF dual-hosted git repository.

potiuk pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/magpie.git


The following commit(s) were added to refs/heads/main by this push:
     new 3d9b2c98 fix(docs): reconcile documentation with the state of the tree (#1159)
3d9b2c98 is described below

commit 3d9b2c987da48eb6a1dad098a0d0c9c482ca7375
Author: Jarek Potiuk <ja...@potiuk.com>
AuthorDate: Tue Sep 8 03:21:03 2026 +0200

    fix(docs): reconcile documentation with the state of the tree (#1159)
    
    * fix(docs): reconcile documentation with the state of the tree
    
    Closes a batch of doc-vs-reality inconsistencies, most of them filed as
    issues after an earlier audit pass.
    
    Reported (#882-#888, #935):
    - labels-and-capabilities: the family:* section documented 4 of the 10
      canonical families and conflated them with three repo-area labels that
      are rejected in frontmatter; "multi-capability tools are rare, gmail is
      the only one" sat above a table of ten. A stray blank line was also
      splitting the tool-capability table in two.
    - adapters/registry: the mail-source and mail-archive rows omitted
      adapters that declare those contracts. Fossil is NOT misclassified —
      it is deliberately both a forge bridge and a VCS backend; the real bug
      was the opposite, tools/vcs omitting Fossil from its backend table.
    - adapters/add-a-harness: detection table missing Kiro; stale harness
      values for agent-guard, permission-audit, sandbox-lint, spec-loop.
    - setup/personal-use-unadopted-repo and AGENTS.md: the per-skill override
      chain listed an organization layer that does not exist. Organizations
      supply config-key defaults, not skill overrides.
    - setup/mixed-adoption-teams: the symlink recipe linked through the relay
      dir, producing four hops instead of two.
    - RFC-AI-0002 and RFC-AI-0004: status said Draft while the body described
      shipped, enforced behaviour. RFC-AI-0004 also said "four shifts" above a
      four-item list in a document that says six everywhere else; the two
      missing gap bullets are added rather than the numeral flipped.
    - spec-loop/organization-adapters: #935's bullet was already fixed by
      #994; the rest of the Known gaps section was stale the same way.
    
    Found while verifying, not separately reported:
    - Skill counts: security 12->15 and the modes glance table (Triage 34->35,
      Drafting 9->11) went stale in #1156. repo-health 6->7, the CONTRIBUTING
      tree's four prefix counts, and one of three skill counts in
      contributor-growth were already drifting.
    - spec-loop/adapters: Bitbucket write coverage gained PR-comment creation.
    - spec-loop/project-agnosticism: the non-ASF smoke suite is 15 cases over
      6 steps across 5 skills, not 6 cases over 2; and the catalogue produces
      3 asf-coupling warnings, not 0.
    
    Generated-by: Claude Code (Opus 5)
    
    * fix(skill-and-tool-validator): skip dot-directories under skills/
    
    The eval-coverage check globbed skills/.mypy_cache, .pytest_cache,
    .ruff_cache and .claude as if each were a skill, so a dirty working tree
    produced four phantom "no eval suite" warnings. Those directories are
    gitignored, so they exist only locally — exactly when a bogus warning is
    hardest to act on, because it names a path the reader cannot find in the
    repo.
    
    One enumeration already had the guard; the other four did not. Adds it to
    all of them, with a regression test.
    
    Generated-by: Claude Code (Opus 5)
---
 AGENTS.md                                          |  6 ++-
 CONTRIBUTING.md                                    |  8 +--
 README.md                                          |  4 +-
 docs/adapters/add-a-harness.md                     |  9 ++--
 docs/adapters/registry.md                          |  4 +-
 docs/contributor-growth/README.md                  |  2 +-
 docs/labels-and-capabilities.md                    | 57 +++++++++++++++++-----
 docs/modes.md                                      |  4 +-
 docs/rfcs/RFC-AI-0002.md                           | 15 ++++--
 docs/rfcs/RFC-AI-0004.md                           | 12 +++--
 docs/setup/mixed-adoption-teams.md                 | 14 ++++--
 docs/setup/personal-use-unadopted-repo.md          |  4 +-
 .../src/skill_and_tool_validator/__init__.py       | 15 ++++--
 .../tests/test_validator.py                        | 18 +++++++
 tools/spec-loop/specs/adapters.md                  |  3 +-
 tools/spec-loop/specs/organization-adapters.md     | 41 +++++++++++-----
 tools/spec-loop/specs/project-agnosticism.md       | 17 ++++---
 tools/vcs/README.md                                |  3 +-
 18 files changed, 169 insertions(+), 67 deletions(-)

diff --git a/AGENTS.md b/AGENTS.md
index 955cbc10..23e05e79 100644
--- a/AGENTS.md
+++ b/AGENTS.md
@@ -324,10 +324,12 @@ chain used when an adopter tailors a framework workflow:
 ```text
 .apache-magpie-local/<skill>.md
   →  .apache-magpie-overrides/<skill>.md
-    →  organization defaults
-      →  framework default
+    →  framework default
 ```
 
+There is no organization layer in the per-skill chain: an organization
+supplies config-key defaults to the chain above, not skill overrides.
+
 `.apache-magpie-local/` is the personal, gitignored layer and takes
 precedence over the committed `.apache-magpie-overrides/` layer when both
 provide the same setting. Both override surfaces are additive only: they
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index 695b215b..5296b1e0 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -209,10 +209,10 @@ every piece of context it needs from some combination of the four
 │
 ├── .claude/
 │   └── skills/           # Agent workflows (invoked via the Skill tool)
-│       ├── security-*/   # Security-issue lifecycle (10 skills)
-│       ├── pr-management-*/  # PR triage, review, mentor, stats (4 skills)
-│       ├── issue-*/      # Issue triage, fix, reassess, reproducer, stats (5 skills)
-│       ├── setup-*/      # Adoption, sandbox install/verify/update (7 skills)
+│       ├── security-*/   # Security-issue lifecycle + security model (15 skills)
+│       ├── pr-management-*/  # PR triage, review, mentor, stats (5 skills)
+│       ├── issue-*/      # Issue triage, fix, reassess, reproducer, stats (8 skills)
+│       ├── setup-*/      # Adoption, sandbox install/verify/update (8 skills)
 │       ├── contributor-nomination/
 │       ├── write-skill/
 │       └── list-skills/
diff --git a/README.md b/README.md
index 06b2a759..684e50db 100644
--- a/README.md
+++ b/README.md
@@ -105,11 +105,11 @@ means and which modes are still proposed vs. shipping today.
 |---|---|---|---|---|
 | [**setup**](docs/setup/README.md) | always-on | (infra) | Isolated agent setup, framework install + maintenance, shared-config sync. The prerequisite — at minimum the `setup` skill itself runs out of this family. | 9 skills, [`docs/setup/`](docs/setup/) |
 | **utilities** | always-on | (meta) | Framework meta-skills: author skills (`write-skill`), restructure them (`optimize-skill`), reconcile skill state (`skill-reconciler`), report framework issues (`report-framework-issue`), and print a live index (`list-skills`). | 5 skills |
-| [**security**](docs/security/README.md) | opt-in | Triage, Drafting | 16-step security-issue handling lifecycle — from `security@` import through CVE publication, including state sync. Maintainer-only. | 12 skills, [`docs/security/`](docs/security/) |
+| [**security**](docs/security/README.md) | opt-in | Triage, Drafting | 16-step security-issue handling lifecycle — from `security@` import through CVE publication, including state sync — plus producing, verifying, and maintaining the project's own security model. Maintainer-only. | 15 skills, [`docs/security/`](docs/security/) |
 | [**pr-management**](docs/pr-management/README.md) | opt-in | Triage | Maintainer-facing PR-queue management — triage, stats, deep code review, express-lane merge, stale-sweep, reviewer routing, and pre-first-PR checks. | 8 skills, [`docs/pr-management/`](docs/pr-management/README.md) |
 | [**issue**](docs/issue-management/README.md) | opt-in | Triage, Drafting | General-issue lifecycle: triage, reproduction, fix drafting, reassess, stale-sweep, deduplication, and backlog reporting. | 8 skills, [`docs/issue-management/`](docs/issue-management/README.md) |
 | [**release-management**](docs/release-management/README.md) | opt-in | Triage, Drafting | 14-step ASF release lifecycle, planning issue, RC cut + sign, `[VOTE]` thread, tally, promote, `[ANNOUNCE]`, archive, audit log. Agent never holds the RM's signing key and never publishes the release. **Experimental**, all 10 skills shipped. | 10 skills, [`docs/release-management/`](docs/release-management/) |
-| [**repo-health**](docs/repo-health/README.md) | opt-in | Triage | Read-only repository-health audits: obsolete runner labels, Actions workflow security, dependency vulnerabilities, license/NOTICE compliance, flaky-test patterns, plus audit-finding fixes. | 6 skills, [`docs/repo-health/`](docs/repo-health/) |
+| [**repo-health**](docs/repo-health/README.md) | opt-in | Triage | Read-only repository-health audits: obsolete runner labels, Actions workflow security, dependency vulnerabilities, dependency licence review, license/NOTICE compliance, flaky-test patterns, plus audit-finding fixes. | 7 skills, [`docs/repo-health/`](docs/repo-health/) |
 | [**pairing**](docs/pairing/README.md) | opt-in | Pairing | Pair a change with a structured self-review or a multi-agent adversarial review before it lands. | 2 skills, [`docs/pairing/`](docs/pairing/README.md) |
 | [**mentoring**](docs/mentoring/README.md) | opt-in | Mentoring | Newcomer-facing mentoring — first-contact welcome, newcomer-issue explanations, and good-first-issue authoring + backlog curation. **Experimental**. | 4 skills, [`docs/mentoring/`](docs/mentoring/README.md) |
 | [**contributor-growth**](docs/contributor-growth/README.md) | opt-in | Triage, Mentoring | The path-to-committer track: activity sweeps, nomination briefs, contributor-sentiment signals, readiness tracking, and committer / post-vote onboarding. | 6 skills, [`docs/contributor-growth/`](docs/contributor-growth/README.md) |
diff --git a/docs/adapters/add-a-harness.md b/docs/adapters/add-a-harness.md
index 2c8cc20c..f56a03a1 100644
--- a/docs/adapters/add-a-harness.md
+++ b/docs/adapters/add-a-harness.md
@@ -156,6 +156,7 @@ case "${SPEC_LOOP_HARNESS:-$(basename "$AGENT")}" in
     *cursor*)     HARNESS=cursor ;;
     *gemini*)     HARNESS=gemini ;;
     *opencode*)   HARNESS=opencode ;;
+    *kiro*)       HARNESS=kiro ;;
     *<runtime>*)  HARNESS=<runtime> ;;    # add your case here
     *)            HARNESS=claude ;;
 esac
@@ -212,11 +213,11 @@ README. When your new runtime uses one of these tools, update its line:
 
 | Tool | Current harness declaration |
 |---|---|
-| `tools/agent-guard` | `**Harness:** Claude Code, OpenCode` |
+| `tools/agent-guard` | `**Harness:** Claude Code, OpenCode, Kiro` |
 | `tools/agent-isolation` | `**Harness:** agnostic` |
-| `tools/permission-audit` | `**Harness:** Claude Code, OpenCode` |
-| `tools/sandbox-lint` | `**Harness:** Claude Code, OpenCode` |
-| `tools/spec-loop` | `**Harness:** Claude Code, Codex, Cursor, Gemini CLI, OpenCode` |
+| `tools/permission-audit` | `**Harness:** agnostic` |
+| `tools/sandbox-lint` | `**Harness:** Claude Code, Codex, Cursor, Gemini CLI, OpenCode, Kiro` |
+| `tools/spec-loop` | `**Harness:** Claude Code, Codex, Cursor, Gemini CLI, OpenCode, Kiro` |
 
 `tools/agent-isolation` already exposes a harness-agnostic `agent-iso <cli>` entry
 point — no update needed for new runtimes (see
diff --git a/docs/adapters/registry.md b/docs/adapters/registry.md
index f4159009..b4121a7e 100644
--- a/docs/adapters/registry.md
+++ b/docs/adapters/registry.md
@@ -49,8 +49,8 @@ extension point = a documented, labelled slot with a tracking issue.
 | Capability contract | Shipping adapter(s) | Extension points (tracked) |
 |---|---|---|
 | [`tools/cve-tool`](../../tools/cve-tool/) | [`cve-tool-vulnogram`](../../tools/cve-tool-vulnogram/) (ASF) | MITRE form, CVE.org direct, GHSA |
-| [`tools/mail-archive`](../../tools/mail-archive/) | [`ponymail`](../../tools/ponymail/) (ASF) | Hyperkitty, Discourse, Google Groups, GitHub Discussions |
-| [`tools/mail-source`](../../tools/mail-source/) | mbox, IMAP | Mailman 3 ([#306](https://github.com/apache/magpie/issues/306)) |
+| [`tools/mail-archive`](../../tools/mail-archive/) | [`ponymail`](../../tools/ponymail/) (ASF), [`gmail`](../../tools/gmail/), [`sourcehut`](../../tools/sourcehut/) | Hyperkitty, Discourse, Google Groups, GitHub Discussions |
+| [`tools/mail-source`](../../tools/mail-source/) | mbox, IMAP, [`gmail`](../../tools/gmail/), [`maildir`](../../tools/maildir/), [`ponymail`](../../tools/ponymail/) (ASF) | Mailman 3 ([#306](https://github.com/apache/magpie/issues/306)) |
 | [`tools/forwarder-relay`](../../tools/forwarder-relay/) | ASF-security ([`tools/gmail/asf-relay.md`](../../tools/gmail/asf-relay.md)) | huntr.com, HackerOne, GHSA relay |
 | [`tools/scan-format`](../../tools/scan-format/) | ASVS | other scanner formats |
 | [`tools/vcs`](../../tools/vcs/) | Git, Mercurial, Fossil | Subversion [\#602](https://github.com/apache/magpie/issues/602), Jujutsu [\#603](https://github.com/apache/magpie/issues/603), Perforce [\#605](https://github.com/apache/magpie/issues/605) |
diff --git a/docs/contributor-growth/README.md b/docs/contributor-growth/README.md
index 19315389..d17d7018 100644
--- a/docs/contributor-growth/README.md
+++ b/docs/contributor-growth/README.md
@@ -113,7 +113,7 @@ adopter's `<project-config>/` directory:
 
 ## Status
 
-**Experimental.** All seven skills are on main with eval suites; no
+**Experimental.** All nine skills are on main with eval suites; no
 adopter has run the full contributor-to-committer path end-to-end under
 evaluation conditions.
 
diff --git a/docs/labels-and-capabilities.md b/docs/labels-and-capabilities.md
index da1c4907..95b7046a 100644
--- a/docs/labels-and-capabilities.md
+++ b/docs/labels-and-capabilities.md
@@ -60,16 +60,44 @@ or PR typically carries one label from each dimension that applies.
 
 What part of the framework does this touch?
 
+Ten of these labels mirror the **canonical skill-family vocabulary** —
+the closed set every skill declares in its `family:` frontmatter key,
+enforced as `ALLOWED_FAMILIES` by
+[`skill-and-tool-validator`](../tools/skill-and-tool-validator/) and
+summarised in [`README.md` → Skill families](../README.md#skill-families).
+Two of them (`setup`, `utilities`) are the always-on families wired on
+every install; the other eight are opt-in (see
+[`skills/setup/SKILL.md`](../skills/setup/SKILL.md) Golden rule 8).
+
+| Label | Type | Covers |
+|---|---|---|
+| `family:setup` | always-on | `setup` plus the `setup-*` skills — framework adoption / upgrade / verify, isolated-agent sandbox setup, shared-config sync ([`docs/setup/`](setup/README.md)) |
+| `family:utilities` | always-on | Framework meta-skills: `write-skill`, `optimize-skill`, `skill-reconciler`, `report-framework-issue`, `list-skills` ([`docs/utilities/`](utilities/README.md)) |
+| `family:security` | opt-in | `security-issue-*`, `security-cve-allocate`, `security-model-*`, `security-tracker-stats-dashboard` ([`docs/security/`](security/README.md)) |
+| `family:issue` | opt-in | `issue-*` skills (`issue-triage`, `issue-reproducer`, `issue-fix-workflow`, `issue-reassess`, `issue-reassess-stats`, `issue-stale-sweep`, `issue-deduplicate`, `issue-backlog-stats`) ([`docs/issue-management/`](issue-management/README.md)) |
+| `family:pr-management` | opt-in | `pr-management-*` skills plus `pr-stale-sweep`, `pre-first-pr-check`, `reviewer-routing` ([`docs/pr-management/`](pr-management/README.md)) |
+| `family:release-management` | opt-in | `release-*` skills — planning, RC cut, `[VOTE]` draft + tally, promote, `[ANNOUNCE]`, archive sweep, audit report, keys sync ([`docs/release-management/`](release-management/README.md)) |
+| `family:repo-health` | opt-in | Read-only repository audits and their follow-up fixes: `ci-runner-audit`, `workflow-security-audit`, `dependency-audit`, `dependency-license-audit`, `license-compliance-audit`, `flaky-test-triage`, `audit-finding-fix` ([`docs/repo-health/`](repo-health/README.md)) |
+| `family:pairing` | opt-in | `pairing-self-review`, `pairing-multi-agent-review` ([`docs/pairing/`](pairing/README.md)) |
+| `family:mentoring` | opt-in | `mentoring-welcome`, `newcomer-issue-explainer`, `good-first-issue-author`, `good-first-issue-sweep` ([`docs/mentoring/`](mentoring/README.md)) |
+| `family:contributor-growth` | opt-in | The path-to-committer track: `contributor-activity-sweep`, `contributor-sentiment`, `contributor-to-committer`, `contributor-nomination`, `committer-onboarding`, `onboarding-concierge` ([`docs/contributor-growth/`](contributor-growth/README.md)) |
+
+Three further `family:*` labels cover parts of the repository that are
+**not** a skill family. They exist only as issue / PR labels and never
+appear in a `family:` frontmatter key — the validator would reject them:
+
 | Label | Covers |
 |---|---|
-| `family:pr-management` | `pr-management-*` skills |
-| `family:security` | `security-*` skills, `security-tracker-stats-dashboard` |
-| `family:setup` | `setup-*` skills, framework adoption, agent-sandbox setup |
-| `family:issue` | `issue-*` skills (`issue-triage`, `issue-fix-workflow`, `issue-reassess`, `issue-reassess-stats`, `issue-reproducer`, `issue-stale-sweep`, `issue-deduplicate`, `issue-backlog-stats`) |
-| `family:tools` | Substrate tools under `tools/*` (CLI bridges, agent-runtime adapters, mail-source backends) |
-| `family:ci` | `.github/` workflows, prek, validators |
+| `family:tools` | Substrate tools and capability adapters under `tools/*` (CLI bridges, agent-runtime adapters, mail-source backends) |
+| `family:ci` | `.github/` workflows, prek hooks, validators |
 | `family:docs` | `docs/`, `MISSION.md`, READMEs |
 
+A change that spans both dimensions carries both labels — a new
+mentoring skill and its guide is `family:mentoring` + `family:docs`.
+The two tables above are the reference for the repository's label set:
+if the label you need is not on the repository yet, a committer creates
+it from here rather than reaching for an approximate existing one.
+
 ### 2. capability — two axes (skills vs tools)
 
 Per [RFC-AI-0005](rfcs/RFC-AI-0005.md), "capability" is **two orthogonal
@@ -104,7 +132,6 @@ framework substrate:
 | `contract:tracker` | contract | Issue / board / label backend. |
 | `contract:source-control` | contract | Branch / commit / diff / push (VCS). |
 | `contract:change-request` | contract | Proposed-change review + merge gate (pull request / merge request / Gerrit change). |
-
 | `contract:mail-archive` | contract | Mailing-list / forum archive reads. |
 | `contract:mail-source` | contract | Inbound-mail ingestion (mbox / IMAP / …). |
 | `contract:mail-create` | contract | Outbound mail composition. Always produces an editable draft; sending is a separate human-approved step on that draft (draft mode = default and the only mode implemented today; send mode declared but unimplemented — no autonomous send). |
@@ -260,8 +287,10 @@ Capabilities for every skill currently in
 
 Tools under [`tools/`](../tools/). A tool's capability is the interface
 it provides; a tool may carry more than one value (separated by `+`) when
-it implements multiple contracts (e.g. `tools/gmail` provides both
-`mail-source` and `mail-create`).
+it provides more than one interface — either several contracts (e.g.
+`tools/gmail` provides `mail-source`, `mail-archive`, and `mail-create`)
+or a contract-free mix of substrates (e.g. `tools/spec-inventory` is
+`substrate:framework-dev` + `substrate:analytics`).
 
 | Tool | Capability / capabilities | Role |
 |---|---|---|
@@ -308,7 +337,7 @@ it implements multiple contracts (e.g. `tools/gmail` provides both
 | [`tools/symlink-lint`](../tools/symlink-lint/) | `substrate:framework-dev` | Self-adoption symlink hygiene — rejects cyclic symlinks, misdirected skill relays (canonical/relay target-correctness), and incomplete self-adoption symlink sets |
 | [`tools/pilot-report-validator`](../tools/pilot-report-validator/) | `substrate:framework-dev` | Adopter pilot-report validator — required frontmatter keys, no unfilled placeholders, valid profile, and required body sections; counterpart to `spec-validator` for `docs/pilot-report-template.md` |
 | [`tools/skill-reconciler-diff`](../tools/skill-reconciler-diff/) | `substrate:framework-dev` | Deterministic structural diff between two skill trees — parses frontmatter, section headings, step inventory, placeholders, support files, and safety-baseline clauses into a JSON diff object for the `skill-reconciler` skill |
-| [`tools/vcs`](../tools/vcs/) | `contract:source-control` | Backend-dispatching implementation of the source-control (VCS) capability ([`tools/github/source-control.md`](../tools/github/source-control.md)); complete Git and Mercurial (Hg) backends, plus detected extension point for SVN (#602) |
+| [`tools/vcs`](../tools/vcs/) | `contract:source-control` | Backend-dispatching implementation of the source-control (VCS) capability ([`tools/github/source-control.md`](../tools/github/source-control.md)); complete Git, Mercurial (Hg), and Fossil backends, plus detected extension point for SVN (#602) |
 | [`tools/sourcehut`](../tools/sourcehut/) | `contract:tracker` + `contract:source-control` + `contract:mail-archive` | SourceHut (sr.ht) forge bridge: todo.sr.ht, lists.sr.ht, builds.sr.ht, and git/hg repository reads |
 
 A tool's capability is the **interface it provides**, not which skills
@@ -317,8 +346,12 @@ happen to consume it (RFC-AI-0005). `tools/github` provides the
 `contract:cve-authority`; `tools/privacy-llm` is `substrate:privacy`.
 Use a `contract:<name>` value when the tool implements a capability
 contract under `tools/<contract>/`, and a `substrate:<name>` value for
-framework substrate. A tool may carry more than one (rare —
-`tools/gmail` is the only one today).
+framework substrate. A tool may carry more than one value whenever it
+genuinely exposes several interfaces — the multi-value rows in the table
+above are the authoritative list, and they are a normal case rather than
+an exception (forge bridges such as `tools/github`, `tools/fossil`, and
+`tools/sourcehut`; the mail backends `tools/gmail`, `tools/maildir`, and
+`tools/ponymail`; and the framework-dev tools that double as analytics).
 
 ## MCP servers, classified by capability
 
diff --git a/docs/modes.md b/docs/modes.md
index 406a5e11..2a2e4adb 100644
--- a/docs/modes.md
+++ b/docs/modes.md
@@ -59,9 +59,9 @@ Autonomous* (the renamed former *Auto-merge*).
 
 | Mode | Purpose | Status | Skill count |
 |---|---|---|---|
-| **Triage** | *(Agentic Triage)* Issues, security reports, PRs: spot, classify, route, surface duplicates. Every output is a suggestion the human signs off on. | stable (security) / experimental (pr-management, issue-management, contributor-nomination, repo-health, release-management) | 34 |
+| **Triage** | *(Agentic Triage)* Issues, security reports, PRs: spot, classify, route, surface duplicates. Every output is a suggestion the human signs off on. | stable (security) / experimental (pr-management, issue-management, contributor-nomination, repo-health, release-management) | 35 |
 | **Mentoring** | *(Agentic Mentoring)* Joins issue and PR threads in a teaching register: clarifying questions, pointers to project conventions, paired examples from prior PRs, hand-off to a human when scope exceeds the agent. Also authors net-new good first issues, curates the existing backlog, and explains filed issues to newcomers to lower onboarding latency. | experimental | 7 |
-| **Drafting** | *(Agentic Drafting)* Agent drafts a fix for a well-scoped problem and opens a PR; every PR is reviewed and merged by a human committer. | stable (security-only); experimental (issue-management, audit-findings, release-management family) | 9 |
+| **Drafting** | *(Agentic Drafting)* Agent drafts a fix for a well-scoped problem and opens a PR; every PR is reviewed and merged by a human committer. | stable (security-only); experimental (issue-management, audit-findings, release-management family) | 11 |
 | **Pairing** | *(Agentic Pairing)* Developer-side dev-cycle skills with mentorship intrinsic — multi-agent review pipelines, self-review and pre-flight patterns, scoped fix drafting under the developer's driver's seat. | experimental | 3 |
 | **Meta** | *(framework infrastructure & authoring)* Adoption, isolation, upgrade, status, and skill-authoring flows plus read-only stats dashboards' framework plumbing. These skills are framework machinery rather than a maintainership mode; they do not act on issues, PRs, or contributor threads on their own. | stable | 18 |
 | **Agentic Autonomous** | Auto-merge restricted to objectively boring change classes only (lint, dependency bumps inside an allow-list, license-header insertion, formatting, broken-link repair). | off | 0 |
diff --git a/docs/rfcs/RFC-AI-0002.md b/docs/rfcs/RFC-AI-0002.md
index 5ba66150..b9326807 100644
--- a/docs/rfcs/RFC-AI-0002.md
+++ b/docs/rfcs/RFC-AI-0002.md
@@ -7,6 +7,7 @@
 
 - [RFC-AI-0002: Secure Agents setup](#rfc-ai-0002-secure-agents-setup)
   - [Abstract](#abstract)
+  - [Status of this document](#status-of-this-document)
   - [Motivation](#motivation)
   - [Proposal](#proposal)
     - [Three-layer defence (overview)](#three-layer-defence-overview)
@@ -42,11 +43,11 @@
 
 # RFC-AI-0002: Secure Agents setup
 
-| **Status** | Draft |
+| **Status** | Implemented |
 |---|---|
 | **Author** | Jarek Potiuk ([@potiuk](https://github.com/potiuk)) |
 | **Created** | 2026-05-02 |
-| **Last updated** | 2026-05-02 |
+| **Last updated** | 2026-09-08 |
 | **Discussion** | *TBD — link to mailing list thread once posted* |
 | **Reference implementation** | [`apache/magpie`](https://github.com/apache/magpie) |
 | **Related documents** | [`secure-agent-setup.md`](https://github.com/apache/magpie/blob/main/docs/setup/secure-agent-setup.md), [`secure-agent-internals.md`](https://github.com/apache/magpie/blob/main/docs/setup/secure-agent-internals.md) |
@@ -55,12 +56,20 @@
 
 ## Abstract
 
-This RFC proposes a layered, opt-in secure setup that an ASF project handling **pre-disclosure or otherwise sensitive material** (security CVE trackers, embargoed reports, internal credentials) can adopt to safely run an AI coding agent (Claude Code today, the shape generalises) against that material on a developer workstation.
+This RFC proposes a layered, opt-in secure setup that an ASF project handling **pre-disclosure or otherwise sensitive material** (security CVE trackers, embargoed reports, internal credentials) can adopt to safely run an AI coding agent (Claude Code, OpenCode, Kiro, or any other agent CLI — the shape is agent-neutral) against that material on a developer workstation.
 
 The setup is built around four layers — a **clean-env shell wrapper**, a **filesystem sandbox** (bubblewrap on Linux, Seatbelt on macOS), a set of **tool-permission rules** in the agent's own configuration, and a **forced-confirmation** policy for write-side actions visible to others — plus two **visibility mechanisms** (a status-line indicator and a per-call bypass-warn hook) that make sandbox state continuously legible to the operator.
 
 A reference implementation ships in the [`apache/magpie`](https://github.com/apache/magpie) Top-Level Project (agent-assisted repository maintainership tooling for a tracker repo). This RFC abstracts the lessons of that implementation into a pattern other ASF projects can adopt with or without depending on `magpie` itself.
 
+## Status of this document
+
+**Implemented.** Every layer and visibility mechanism this RFC proposes ships in the reference implementation and is covered by tests: the clean-env wrapper ([`tools/agent-isolation/agent-iso.sh`](https://github.com/apache/magpie/blob/main/tools/agent-isolation/agent-iso.sh)), the filesystem sandbox and the tool-permission rules ([`.claude/settings.json`](https://github.com/apache/magpie/blob/main/.claude/settings.json)), the forced-confirmation policy, the bypass-warn hook, and the sand [...]
+
+The setup is no longer Claude-Code-only. The wrapper ships named entry points for Claude Code, OpenCode and Kiro plus a generic `agent-iso <cli>` form for any other agent CLI, each with its own test suite; [`sandbox-lint`](https://github.com/apache/magpie/tree/main/tools/sandbox-lint) and [`permission-audit`](https://github.com/apache/magpie/tree/main/tools/permission-audit) carry per-agent adapters over the same posture model.
+
+`Implemented` describes the layers proposed above; it does not close the gaps this RFC already records. The macOS network-egress gap (see *Drawbacks*) and the items under *Open questions* remain open, and neither is a prerequisite for adopting the layers described here.
+
 ## Motivation
 
 Default AI-coding-agent installations grant the agent — and any Bash subprocess it spawns — full access to the developer's home directory, full access to the parent shell's environment variables, and a network egress shaped only by host-level DNS. For projects whose working tree contains nothing more sensitive than ordinary source code, that default is fine. For projects whose tracker repo or working set contains pre-disclosure CVE material, security-list email content, embargoed advisor [...]
diff --git a/docs/rfcs/RFC-AI-0004.md b/docs/rfcs/RFC-AI-0004.md
index fe0e99bd..e641fe32 100644
--- a/docs/rfcs/RFC-AI-0004.md
+++ b/docs/rfcs/RFC-AI-0004.md
@@ -71,7 +71,7 @@
 |---|---|
 | **RFC** | AI-0004 |
 | **Title** | Principles of agentic interaction for open-source maintainers |
-| **Status** | Draft |
+| **Status** | Implemented |
 | **Authors** | The Apache Magpie project (see [`MISSION.md`](https://github.com/apache/magpie/blob/main/MISSION.md) for roster) |
 | **Initial draft** | 2026-05-07 |
 | **Supersedes** | None |
@@ -93,10 +93,12 @@ It is **not** a specification of any particular implementation detail (LLM cho
 
 ## Status of this document
 
-This is a **Draft**. The Apache Magpie project's reference implementation operationalises every principle in this RFC, but the RFC itself is the project's first attempt to extract the principles from the implementation and frame them as a portable contract. The next two milestones are:
+**Implemented.** The Apache Magpie project's reference implementation operationalises every principle in this RFC; the framework's own governance document, [`PRINCIPLES.md`](https://github.com/apache/magpie/blob/main/PRINCIPLES.md), binds the project to them and its skills, tools and pre-commit gates enforce them.
+
+`Implemented` describes the reference implementation, not this RFC's standing as a portable contract for projects beyond Apache Magpie. Two milestones remain before promotion from `Implemented` to `Stable`:
 
 1. **Public review** — comments solicited from ASF Members, non-ASF maintainers running similar agentic frameworks, and the ASF Responsible AI Initiative working group.
-2. **Pilot validation** — the six principles tested against the Apache Magpie pilot cohort (one ASF PMC running the full security-issue flow, one ASF PMC running just triage + mentoring, at least one non-ASF project) before promotion from `Draft` to `Stable`.
+2. **Pilot validation** — the six principles tested against the Apache Magpie pilot cohort (one ASF PMC running the full security-issue flow, one ASF PMC running just triage + mentoring, at least one non-ASF project).
 
 ---
 
@@ -108,8 +110,10 @@ Maintainers of open-source projects increasingly find themselves at the receivin
 - Sandbox posture varies wildly. Some agents read everything in `~`; some read nothing. Some can `gh pr create`; some can silently push to the default branch. The maintainer is on the hook for figuring this out.
 - Vendor lock-in is largely silent. A skill that "uses Claude" is a skill that *requires* Claude — not a skill that happens to use Claude today and would work on a local model tomorrow. The lock-in is rarely surfaced as a choice.
 - "How do I correct this?" has become an afterthought. The maintainer who notices the agent is doing the wrong thing often has no path to fix it short of opening an upstream PR to the tool author.
+- Outbound messages carry the maintainer's voice, but the agent writes them. A tool that mails a contributor, a reporter, or a list on the maintainer's behalf without a human reading the text first has borrowed an identity it does not own.
+- Privacy is treated as a deployment detail rather than a design constraint. A security reporter's name, a contributor's mail address, an embargoed advisory — which of these reach a third-party model, and under what retention terms, is usually invisible to the maintainer who triggered the call.
 
-This RFC names the four shifts that, taken together, make agentic tooling acceptable on a maintainer-governed project. Each shift is independently necessary; the combination is sufficient.
+This RFC names the six shifts that, taken together, make agentic tooling acceptable on a maintainer-governed project. Each shift is independently necessary; the combination is sufficient.
 
 ---
 
diff --git a/docs/setup/mixed-adoption-teams.md b/docs/setup/mixed-adoption-teams.md
index feb6a4fb..6b2387c8 100644
--- a/docs/setup/mixed-adoption-teams.md
+++ b/docs/setup/mixed-adoption-teams.md
@@ -71,12 +71,15 @@ git clone --depth=1 --branch main \
 ```
 
 **Create user-scope skill symlinks** so Claude Code finds the skills in
-any project:
+any project. Link through the clone's **canonical** `.agents/skills/`
+entries — the one home every agent-specific dir relays into (see
+[`agents.md`](../../skills/setup/agents.md)) — not through a relay dir
+such as `.claude/skills/`, which would add a pointless third hop:
 
 ```bash
 mkdir -p ~/.claude/skills
-for skill_dir in ~/.magpie/.claude/skills/*/; do
-    skill_name=$(basename "$skill_dir")
+for skill_dir in ~/.magpie/.agents/skills/*/; do
+    skill_name=$(basename "$skill_dir")   # already magpie-<skill>
     ln -sfn "$skill_dir" ~/.claude/skills/"$skill_name"
 done
 ```
@@ -231,8 +234,9 @@ is straightforward:
 
 1. Run `/magpie-setup install` in the shared repo (see
    [`install-recipes.md`](install-recipes.md)) — this commits the bootstrap
-   skill and lock, wires the skill symlinks under `.agents/skills/` and
-   `.claude/skills/`, and adds the sandbox block to the shared
+   skill and lock, wires the canonical skill symlinks under
+   `.agents/skills/` plus a relay into them from `.claude/skills/`, and
+   adds the sandbox block to the shared
    `.claude/settings.json`.
 2. Move any project context from `.apache-magpie-local/project.md` into
    the committed `projects/<project>/project.md`.
diff --git a/docs/setup/personal-use-unadopted-repo.md b/docs/setup/personal-use-unadopted-repo.md
index 175f39f5..a39f1018 100644
--- a/docs/setup/personal-use-unadopted-repo.md
+++ b/docs/setup/personal-use-unadopted-repo.md
@@ -240,8 +240,8 @@ install will shadow your `~/.claude/skills/magpie-*` links for that repo.
 Your `.apache-magpie-local/` files continue to work: the project adoption
 adds the `.gitignore` entry automatically (idempotent — the line is
 already there if you added it in Step 2), and the override lookup chain
-(`personal-local → committed → organization → framework default`) honours
-them as the highest-precedence layer.
+(`.apache-magpie-local/` → `.apache-magpie-overrides/` → framework
+default) honours them as the highest-precedence layer.
 
 You can delete the personal directory once the project is adopted and any
 overrides you care about have been upstreamed into
diff --git a/tools/skill-and-tool-validator/src/skill_and_tool_validator/__init__.py b/tools/skill-and-tool-validator/src/skill_and_tool_validator/__init__.py
index acae007c..4ac9a304 100644
--- a/tools/skill-and-tool-validator/src/skill_and_tool_validator/__init__.py
+++ b/tools/skill-and-tool-validator/src/skill_and_tool_validator/__init__.py
@@ -162,6 +162,11 @@ from pathlib import Path
 # ---------------------------------------------------------------------------
 
 SKILLS_DIR = Path("skills")
+# Dot-directories under ``skills/`` are never skills: they are local build
+# junk (``.mypy_cache``, ``.pytest_cache``, ``.ruff_cache``) or an agent dir
+# (``.claude``) that a tool dropped there. They are gitignored, so they exist
+# only in a dirty working tree — which is exactly when a phantom warning is
+# most confusing. Every enumeration of skill directories skips them.
 TOOLS_DIR = Path("tools")
 DOCS_DIR = Path("docs")
 SKILL_EVALS_DIR = Path("tools/skill-evals/evals")
@@ -2537,7 +2542,7 @@ def collect_skill_dirs(root: Path | None = None) -> set[Path]:
     base = (root or find_repo_root()) / SKILLS_DIR
     if not base.exists():
         return set()
-    return {p.resolve() for p in base.iterdir() if p.is_dir()}
+    return {p.resolve() for p in base.iterdir() if p.is_dir() and not p.name.startswith(".")}
 
 
 # ---------------------------------------------------------------------------
@@ -2919,7 +2924,7 @@ def validate_modes_doc_consistency(root: Path | None = None) -> Iterable[Violati
     if not skills_base.exists():
         return
     for skill_dir in sorted(skills_base.iterdir()):
-        if not skill_dir.is_dir():
+        if not skill_dir.is_dir() or skill_dir.name.startswith("."):
             continue
         skill_md = skill_dir / "SKILL.md"
         if not skill_md.exists():
@@ -3101,7 +3106,9 @@ def collect_skill_source_pointers(root: Path | None = None) -> list[Path]:
     base = (root or find_repo_root()) / SKILLS_DIR
     if not base.exists():
         return []
-    return sorted(d for d in base.iterdir() if d.is_dir() and is_skill_source_pointer(d))
+    return sorted(
+        d for d in base.iterdir() if d.is_dir() and not d.name.startswith(".") and is_skill_source_pointer(d)
+    )
 
 
 def _skill_source_descriptor_files(root: Path) -> list[Path]:
@@ -3310,7 +3317,7 @@ def validate_eval_coverage(root: Path | None = None) -> Iterable[Violation]:
             # (same posture as collect_tool_python_files on OSError).
             return
     try:
-        skill_dirs = sorted(skills_base.iterdir())
+        skill_dirs = sorted(d for d in skills_base.iterdir() if not d.name.startswith("."))
     except OSError:
         # Same posture as collect_tool_python_files: unreadable → skip.
         return
diff --git a/tools/skill-and-tool-validator/tests/test_validator.py b/tools/skill-and-tool-validator/tests/test_validator.py
index b729a4cb..79193e4d 100644
--- a/tools/skill-and-tool-validator/tests/test_validator.py
+++ b/tools/skill-and-tool-validator/tests/test_validator.py
@@ -4786,6 +4786,24 @@ class TestSkillSourcePointer:
         vs = list(validate_eval_coverage(tmp_path))
         assert not any("acme-thing" in v.message for v in vs)
 
+    def test_dot_dirs_under_skills_draw_no_eval_coverage_advisory(self, tmp_path: Path) -> None:
+        """Build junk under ``skills/`` is not a skill.
+
+        ``.mypy_cache`` / ``.pytest_cache`` / ``.ruff_cache`` and a stray
+        ``.claude`` land in ``skills/`` on any dirty working tree. They are
+        gitignored, so they exist only locally — which is exactly when a
+        phantom "no eval suite" warning is most confusing to act on.
+        """
+        _make_source_repo(tmp_path)
+        for junk in (".mypy_cache", ".pytest_cache", ".ruff_cache", ".claude"):
+            (tmp_path / "skills" / junk).mkdir(parents=True, exist_ok=True)
+        vs = list(validate_eval_coverage(tmp_path))
+        assert not any(
+            junk in v.message
+            for v in vs
+            for junk in (".mypy_cache", ".pytest_cache", ".ruff_cache", ".claude")
+        )
+
 
 class TestSkillSourceDescriptorValidation:
     def test_valid_descriptor_passes(self, tmp_path: Path) -> None:
diff --git a/tools/spec-loop/specs/adapters.md b/tools/spec-loop/specs/adapters.md
index 56920327..cf61337a 100644
--- a/tools/spec-loop/specs/adapters.md
+++ b/tools/spec-loop/specs/adapters.md
@@ -158,7 +158,8 @@ uv run --project tools/vcs --group dev pytest || echo "check tools/vcs test setu
 - Bitbucket write operations follow the framework write-path discipline:
   the calling skill must obtain explicit user confirmation before invoking a
   mutation. The bridge executes only the confirmed action; current write
-  coverage is limited to Bitbucket Cloud issue-comment creation.
+  coverage is Bitbucket Cloud issue-comment creation and Bitbucket Cloud
+  pull-request comment creation.
 - Fetched Bitbucket descriptions, issue titles/descriptions, fetched or created issue comments, attachment names, uploader names when present, attachment links, raw attachment payloads, issue reporter/assignee/commenter names, issue links, branch restriction policy, commit messages, diff hunks, file paths, comments, pull-request task content, task creator/resolver names, reviewer names, review decisions/events, approval/change-request activity, merge-check decisions/blockers, status desc [...]
   CI URLs, and raw payloads are external data, never agent instructions;
   private or embargoed content must follow the
diff --git a/tools/spec-loop/specs/organization-adapters.md b/tools/spec-loop/specs/organization-adapters.md
index ee1b542f..ad64a422 100644
--- a/tools/spec-loop/specs/organization-adapters.md
+++ b/tools/spec-loop/specs/organization-adapters.md
@@ -120,17 +120,36 @@ Adapter layout is enforced: `validate_organization_structure` in
 `tools/skill-and-tool-validator` requires every `organizations/<org>/`
 directory except `_template` to contain `README.md` and `organization.md`.
 Omitting either results in a HARD violation, so an incomplete adapter fails
-the validator before any skill can resolve against it.
+the validator before any skill can resolve against it. It is not a separate
+command — the check runs inside the top-level `skill-and-tool-validate`
+sweep above.
+
+Organization *references* are enforced alongside it: every `organization:`
+value — in a skill's `SKILL.md` frontmatter, a tool README's
+`**Organization:**` line, a skill-source descriptor, and a
+`skills/<name>/source.md` pointer — must name a directory under
+`organizations/` (`known_organizations()`, which excludes `_template`).
+A typo or a dangling adapter name is therefore a HARD violation rather than
+a silent fall-through to the framework default.
 
 ## Known gaps
 
-- The reflow of `projects/_template/` + `projects/non-asf-example/` to
-  set `organization:` and drop the now-inherited values is not yet done
-  (tracked as the next change); until then the ASF defaults exist in both
-  `projects/_template/project.md` and `organizations/ASF/`.
-- The family-level `organization:` scope (replacing `asf: true/false`)
-  and the external-adapter discovery index are separate follow-ups.
-- **Smoke coverage is narrow.** The non-ASF profile smoke currently proves
-  one path. The next coverage pass should exercise security intake,
-  release backend selection, and contributor governance so organization
-  defaults are tested across the surfaces most likely to drift.
+- **The structural check verifies file presence, not manifest content.**
+  `validate_organization_structure` requires `README.md` and
+  `organization.md` to exist; nothing validates what `organization.md`
+  actually declares. A present-but-empty manifest passes, and the keys it
+  omits then resolve silently to framework defaults instead of failing
+  loudly. Every other organization check in `skill-and-tool-validator` is
+  referential ("is this org name known?"), not schema-level.
+- **`skill-sources.md` is outside the required set.** All three in-tree
+  adapters carry one, `organizations/_template/skill-sources.md` tells
+  authors to keep the file with an empty list when the organization curates
+  nothing, and the validator globs `organizations/*/skill-sources.md` when
+  collecting source descriptors — but the filename is absent from
+  `_ORG_REQUIRED_FILES`, so an adapter that drops it is still structurally
+  valid.
+- **The `_template` authoring path is not covered by an eval.** `ASF` and
+  `independent` are the only adapters in the tree, and no eval exercises
+  authoring a fresh organization from `organizations/_template/`, so the
+  "new organization with no skill edits" criterion rests on the two in-tree
+  examples rather than on a test.
diff --git a/tools/spec-loop/specs/project-agnosticism.md b/tools/spec-loop/specs/project-agnosticism.md
index b2d80781..6e902afd 100644
--- a/tools/spec-loop/specs/project-agnosticism.md
+++ b/tools/spec-loop/specs/project-agnosticism.md
@@ -156,9 +156,11 @@ uv run --project tools/skill-and-tool-validator --group dev skill-and-tool-valid
   coupled tokens automatically on every validator run.  As of the
   `low-confidence-asf-coupling-pass` work (mechanical cleanup + suppression
   of low-confidence hits for `organization:`-scoped families), the live
-  catalogue produces **0 asf-coupling warnings**; remaining bare `PMC` /
-  `ICLA` / `announce@apache.org` references are inside org-scoped skills
-  where ASF-specific text is appropriate.  No remaining tooling gap — the
+  catalogue produces **3 asf-coupling warnings** — `release-audit-report` and
+  `release-promote` (`svn` invocations, remedy:adapter, pending the #602
+  Subversion backend) and `dependency-license-audit` (a bare `PMC`
+  reference). Other bare `PMC` / `ICLA` / `announce@apache.org` references
+  are inside org-scoped skills where ASF-specific text is appropriate.  No remaining tooling gap — the
   lint exists and a human judges any new hits.  In the same pass:
   `skills/pr-management-triage/comment-templates.md` was generalised —
   `security@apache.org` replaced with the `<security-list>` placeholder and
@@ -169,10 +171,11 @@ uv run --project tools/skill-and-tool-validator --group dev skill-and-tool-valid
 - **Non-ASF adopter profile fixture shipped** — `projects/non-asf-example/`
   contains a worked non-ASF profile (Velox Stream: GitHub-hosted, DCO,
   GHSA intake, MITRE CNA, GitHub Releases). The
-  `tools/skill-evals/evals/non-asf-profile-smoke/` eval suite (6 cases
-  across 2 steps) drives `issue-stale-sweep` through it and asserts the
-  skill proceeds without any Apache-specific fields, turning acceptance #3
-  into a measurable gate.
+  `tools/skill-evals/evals/non-asf-profile-smoke/` eval suite (15 cases
+  across 6 steps) drives `issue-stale-sweep`, security intake, release-backend
+  selection, contributor governance, and reviewer routing through it, and
+  asserts each proceeds without any Apache-specific fields, turning
+  acceptance #3 into a measurable gate.
 - **The capability-flag vocabulary for security intake and CVE allocation
   is now documented** in
   `projects/_template/security-intake-config.md` (intake channel,
diff --git a/tools/vcs/README.md b/tools/vcs/README.md
index 22f4747f..56f81536 100644
--- a/tools/vcs/README.md
+++ b/tools/vcs/README.md
@@ -103,10 +103,11 @@ not add its own prompt.
 |---|---|---|
 | `git` | **complete** | GitHub's native VCS; the default binding |
 | `hg` (Mercurial) | **complete** | Mercurial VCS support |
+| `fossil` | **complete** | Fossil SCM; pairs with the [`tools/fossil`](../fossil/) forge bridge |
 | `svn` (Subversion) | extension point | detected; centralized model (`distributed = False`) → [#602](https://github.com/apache/magpie/issues/602) |
 
 Detection is real for every backend (so `magpie-vcs detect` reports the
-working copy's VCS correctly); the non-Git/non-Hg backends raise an actionable
+working copy's VCS correctly); the remaining extension-point backends raise an actionable
 `VCSError` naming their tracking issue until the full binding lands.
 
 ### Adding a backend