After this chapter you can operate APM across a whole organization — not one repo, but a
fleet. You will wire apm audit --ci into branch protection as a
required, protected pull-request check (the integrity gate from
Chapter 7 and policy gate from
Chapter 9, re-run in CI as defence in depth), stand it up
with microsoft/apm-action, route dependency traffic through an approved
registry proxy where supported (or prepare an offline bundle handoff), publish and own an
org apm-policy.yml baseline, and roll it all out with a measured adoption playbook. This is
the capstone: it introduces no new property. Instead it asks whether the four you already know —
Portability,
Reproducibility,
Provenance / security, and above all
Governance — hold for every repo,
enforced and operated at scale. Governance is the star of the chapter: the org’s
policy must reach a protected enforcement point, not merely exist in a repository.
This chapter targets apm v0.31.0, compared with the book’s
v0.23.1 baseline. Policy enforcement remains early preview and dedicated registries
remain experimental. Pin the CLI and integration independently, and distinguish install-time
governance from the harness’s runtime controls
(0.31.0 policy reference).
Objective
Concept/Theory
From “can this repo install?” to “can every repo install?”
A single team starts with a manifest, a lockfile, and a restore habit:
apm.yml, apm.lock.yaml, and apm install. Everything in
Chapters 5–9
answered a repo-sized question: does my project install, reproduce, stay current, stay safe, and
stay within policy? An enterprise asks a different, larger question — the shift this whole
chapter turns on: not “can this repo install?” but “can
every repo install safely and predictably, without the platform team in the loop?”
That reframing surfaces five things the single-team story never forces you to build (Making the case):
- Repeatable rollout — a runbook any team follows, not a hero who hand-holds each repo.
- Policy ownership — a named, protected owner of the org’s
apm-policy.yml. - Audit gates — a required CI check on every pull request, authoritative regardless of what a developer does locally.
- Registry strategy — controlled, mirrored, and (when needed) offline dependency traffic.
- Exception handling — a visible, reviewable way to grant a waiver.
The docs’ worked figure is a mid-to-large org: 50 repositories, 200 developers, five AI coding tools. Without central management a predictable failure set emerges — manual config drifting per repo, no audit trail (“what agent configuration was active at release 4.2.1?” has no answer), version drift between developers and CI, onboarding friction, and ungoverned dependencies: “the same problem regulated industries spent a decade solving for application code, now back in a new form” (Making the case). These are the Chapter 1 pains, multiplied by the repo count.
Two boundaries keep the rest of the chapter honest. First, consuming policy is not owning
policy: a fleet team (including the original pilot) consumes the org policy discovered
from its git remote — authorship lives in <org>/.github behind CODEOWNERS and
branch protection, exactly the org-remote model from
Chapter 1 and
Chapter 9. Second, nothing here is a new
property: fleet scale is Chapters 6–10 made repeatable, owned, gated, and
measured. The common trap is to think “fleet scale is just the single-repo setup, copied
N times” — but N copies without central ownership simply reproduce the drift problem at
higher cost. The missing pieces are ownership, gates, a registry strategy, and exceptions, none of which
a single repo ever needs.
In APM
The fleet gate: apm audit --ci
Run apm audit --ci on every pull request as defence in depth.
It checks the manifest/lock relationship, recorded deployment ownership
(deployment-ledger-owners), deployed content and consent, plus
install-replay drift by default. A resolved policy adds the org’s
Governance checks. Do not program against an
“eight plus one” total: configuration, policy and early failures affect enumeration.
Exit 1 means a blocking failure; exit 0 does not prove that policy was
found, that every warning was absent, or that every runtime file was checked
(baseline checks).
A cold runner is no longer a reason to suppress drift. With a reviewed manifest, lock and deployed
files but no apm_modules or warm cache, 0.31.0 can hydrate lock-pinned sources
in scratch without rewriting the checkout. The public-source probe succeeded; making that
source unreachable failed closed with exit 1, not a green skip. Cold is therefore
not synonymous with offline. Allow the necessary acquisition traffic rather than adding
--no-drift to make the job green
(recorded cold-run evidence;
audit contract).
Authority comes from protecting the enforcement point, not from the letters
--ci. Protect the workflow, reviewed manifest/lock and deployed files, selected policy
source, credentials, environment, and ruleset bypass permissions. The CLI really accepts
--no-policy; an explicit --policy beats that flag, but
APM_POLICY_DISABLE=1 still suppresses even explicit policy in the
observed 0.31.0 run, including with consumer fail-closed settings. A required
GitHub Ruleset check
only earns its guarantee when contributors cannot change or bypass those inputs. This is how you
operationalize the Chapter 9 authority boundary.
| Flag | Job | Fleet note |
|---|---|---|
--policy <src> |
Explicit policy ref: org | owner/repo | https://… | local path |
[experimental]. Select a reviewed authority; omission uses org discovery. Explicit selection is not protection from every environment bypass. |
--no-cache |
Force a fresh policy fetch | Refreshes policy, not the package cache. Requires reachable policy infrastructure; see the consumer fail-closed setting below. |
--no-policy |
Skip automatic policy discovery | A real bypass of that layer, including in CI; baseline checks remain. Do not put it in the protected org gate. |
--no-fail-fast |
Run every check even after one fails | Use for fuller diagnostics; it does not expand the tool’s runtime coverage. |
-f sarif|json, -o <path> |
Structured output; write to a file (format inferred from extension) | SARIF feeds Code Scanning. Markdown is not supported in --ci mode. |
Baseline integrity failures are independent of the policy’s warn/block
dial, tying this gate back to Chapter 6.
Make exceptions visible through a reviewed policy amendment at the authority that imposed the rule,
not an environment switch hidden in one job. A child cannot lower an inherited
block to warn. A deliberate --no-drift run reduces coverage;
it is neither a repair nor the standard cold-runner setup.
microsoft/apm-action: the turnkey CI path
microsoft/apm-action supplies the CLI and optional project operations; it is not the
authority itself. Pin the Action to its reviewed commit and set
apm-version: '0.31.0'. The inspected v1.10.0 wrapper otherwise defaults to an older
CLI. Its audit-report input runs bare, informational audit, not
apm audit --ci; it is not the required gate
(pinned Action dispatch).
Choose the job by what you are reviewing. Default mode runs ordinary apm install,
which can repair deployed bytes before audit sees them. When committed deployed files are the
review contract, setup-only: 'true' installs only the CLI, then an explicit audit
examines those files. Cold scratch hydration means this pattern needs no mandatory
--no-drift. Frozen installation is a separate, limited structural check
(Chapter 5’s boundary),
not an equivalent content audit.
backend/examples/updates/1.2/producer/ci/apm-audit.yml.
SKIPPED-needs-network: no GitHub runner, authorized private-source access,
or required-check/ruleset enforcement was exercised. This does not configure org policy.
needs GitHub infrastructure
target apm v0.31.0; Action v1.10.0
name: APM integrity audit
on:
pull_request:
jobs:
audit:
runs-on: ubuntu-latest
permissions:
contents: read
steps:
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
- uses: microsoft/apm-action@d723bb64ed70c135bbaf87d126b721dd2dae0439 # v1.10.0
with:
setup-only: 'true'
apm-version: '0.31.0'
- name: Audit checked-out content
run: apm audit --ci
env:
GITHUB_TOKEN: ${{ github.token }}
The repository token is not authorization to read every private repository in the organization. Configure access to the actual locked sources and policy authority separately. The same CLI gate can run in Azure Pipelines, GitLab CI or Jenkins; the wrapper is GitHub-specific, not the integrity concept (CI/CD integration).
Historical workflow sketches — APM 0.23.1, not refreshed runner evidence
These earlier install-then-audit and SARIF sketches retain their historical pins. The three files
under backend/examples/ch11/workflows/ are unchanged documentation artifacts,
including the old setup-only recipe. Do not copy their major-tag pinning or cold-cache
drift-suppression advice as the current pattern. None was executed on a GitHub runner.
backend/examples/ch11/workflows/apm-audit.yml, with explanatory comments
corrected; no new execution. SKIPPED-needs-network: runner and ruleset access.
needs networkapm v0.23.1 — historical
# .github/workflows/apm-audit.yml -- SKIPPED-needs-network (the `apm audit --ci` it runs IS verified)
name: APM audit
on:
pull_request:
paths: ['apm.yml', 'apm.lock.yaml', '.apm/**', '.github/**', '.claude/**', '.cursor/**']
jobs:
audit:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: microsoft/apm-action@v1 # historical major tag, not an immutable Action pin
with:
apm-version: '0.23.1' # pin the CLI for reproducible CI
- run: apm audit --ci --no-cache # verified gate: exit 0 clean / 1 on violation
env:
GITHUB_APM_PAT: ${{ secrets.APM_PAT }} # must authorize the intended source
For findings to appear inline on the PR diff and in the repo’s Security tab, emit SARIF and upload
it. The if: always() step is load-bearing — SARIF must upload even when the audit
exits 1, or the failing run produces no Code Scanning entry:
backend/examples/ch11/workflows/apm-audit-sarif.yml.
SKIPPED-needs-network: GitHub runner, Code Scanning permissions and SARIF upload.
needs networkapm v0.23.1 — historical
# .github/workflows/apm-audit-sarif.yml -- SKIPPED-needs-network (documented)
jobs:
audit:
runs-on: ubuntu-latest
permissions:
contents: read
security-events: write # required to upload SARIF to Code Scanning
steps:
- uses: actions/checkout@v4
- uses: microsoft/apm-action@v1
with: { apm-version: '0.23.1' }
- name: Audit
run: apm audit --ci --no-cache -o apm-audit.sarif # format inferred from the .sarif extension
env: { GITHUB_APM_PAT: '${{ secrets.APM_PAT }}' }
- name: Upload SARIF
if: always() # upload even on exit 1, or a failing run has no alert
uses: github/codeql-action/upload-sarif@v3
with: { sarif_file: apm-audit.sarif, category: apm-audit }
Current local evidence also includes a real SARIF report written with -o
(ci-cold-sarif). Writing that report is not an upload test. Keep the upload eligible
after a failing audit, as the historical if: always() example illustrates, and test
Code Scanning permissions on your actual runner.
Registry strategy: proxy and air-gapped
A controlled acquisition path makes the lockfile
contract operable behind an enterprise firewall. APM’s proxy controls are
environment variables, not apm config keys: standardize them in CI
secrets and dev containers. Do not infer that APM has only three accepted configuration keys
from the defaults its config display happens to list; saved targets and gated registry settings
also exist. These transport controls do not cover every APM network request
(0.31.0 registry-proxy coverage).
| Need | Knob | Note |
|---|---|---|
| Allow outbound traffic at the firewall | HTTPS_PROXY / HTTP_PROXY / NO_PROXY |
Standard forward-proxy variables; validate both Git and HTTP acquisition paths in your environment. |
| Mirror covered Git-hosted archives | PROXY_REGISTRY_URL |
Routes supported archive downloads through a mirror, such as an Artifactory GitHub remote; not policy or MCP traffic. |
| Authenticate to the mirror | PROXY_REGISTRY_TOKEN |
Bearer token on proxy requests; independent of GITHUB_APM_PAT. |
| Refuse direct-VCS fallback (mandatory + auditable) | PROXY_REGISTRY_ONLY=1 |
Refuses supported direct-VCS fallback. The lock records registry_prefix; directly pinned entries need reviewed re-resolution through the proxy. |
Silence the plaintext-token warning on http:// |
PROXY_REGISTRY_ALLOW_HTTP=1 |
Use only inside an isolated network. (Deprecated ARTIFACTORY_* aliases still work with a warning.) |
| Offline artifact handoff | Prepare a real bundle and its required tooling before disconnecting | Chapter 10’s producer/consumer loop, with the one-shot limitations below. |
The proxy is a route, not a trust anchor. Review the lockfile and its recorded content hashes, then verify the materialized result. Hashes detect changed bytes relative to trusted metadata; neither a mirror nor a hash authenticates the publisher. The GitHub archive proxy covers supported dependency and marketplace fetches, but not Azure DevOps dependency acquisition, MCP-registry traffic, or policy fetching. Those paths need their own connectivity and authorization.
A dedicated registry is a different package source, not this proxy.
APM 0.31.0 ships experimental REST consumption/publication and an implementable
HTTP API /v1. That does not establish a Microsoft-operated public
searchable hub. OpenAPM’s deferred normative registry work is a standards boundary, not
evidence that the client is absent. Meridian can continue using Git and curated marketplaces
without adopting a registry server
(experimental registries;
implemented API).
Org policy at fleet scale
Scale the Chapter 9 ownership model, not copies of
unowned policy. Meridian keeps meridian-finance/.github/apm-policy.yml behind
CODEOWNERS and branch protection. In 0.31.0, GitHub discovery prefers
<org>/.github-private/apm-policy.yml, then the
.github, .apm and _apm repositories.
GitLab uses the top-level group’s apm-policy project; Azure DevOps uses project
apm, repository apm-policy, with legacy _apm/_apm fallback
after a 404. Live private-host discovery remains SKIPPED-needs-network: no org
repository or authorization was supplied
(host-specific discovery).
Select an explicit, reviewed source when the gate must not depend on ambiguous
discovery: --policy for CI audit, --policy-source for policy status.
Record the canonical host/repository/path and, if pinning policy bytes, the consumer’s
policy.hash SHA-256 from the reviewed raw file — not its display
name/version or a package’s content_hash.
GitHub/registry owner-repository policy matching uses canonical casing; refs, subpaths and MCP
identities are not generally case-insensitive. Crucially, an unread remote
fetch_failure: block cannot protect its own first fetch: set consumer
policy.fetch_failure_default: block.
Even a policy-byte hash mismatch only warned and exited 0 in the default-posture
audit probe; the consumer block setting made it exit 1
(operations reference OP09.3;
policy source and hash configuration).
Local inheritance now works. The tested extends: ./apm-policy.parent.yml
retained parent restrictions: allow lists intersect, deny/require lists accumulate, and enforcement
and fetch-failure posture tighten. Empty child lists do not erase inherited restrictions.
Cold and warm HTTPS-loopback probes retained the same strict fields and TTL; the warm read made
no further requests. This is local/loopback evidence, not a live org deployment
(tighten-only implementation).
If policy freshness itself must gate CI, inspect policy status --check too:
the stale-cache probe failed that preflight while audit still evaluated cached rules successfully.
Resolution status and rule compliance answer different questions.
When to use / pitfalls
Roll out in phases, measure by leading indicators
Rolling APM out to a fleet is a staged program, not a switch. The official adoption playbook is five phases, each with a single owner, a deliverable, and a gate to clear before advancing (Adoption playbook). The outline’s four-word mnemonic — pilot → measure → standardize → gate — maps directly onto them:
| Phase | Owner | Gate to advance |
|---|---|---|
| Discover | Platform team | Shadow apm install --dry-run + apm audit on representative repos; answer “what breaks if we turn this on tomorrow, and for whom?” |
| Pilot | One product team + platform | Manifest, lockfile, CI audit, and policy in warn; two consecutive weeks of clean pilot CI with every warning triaged. |
| Harden | Security + platform | Flip warn → block, add the registry proxy, stand up marketplaces; a fresh repo installs against org policy + proxy with no manual help. |
| Scale | Product teams (self-service) | Platform is no longer in the critical path; new repos onboard from a checklist. |
| Sustain | A named on-call | Steady state: weekly drift triage, monthly lockfile review, quarterly marketplace refresh. |
Success is measured by leading indicators, not package counts. The docs are explicit
that “measuring apm.yml count and nothing else” is a vanity
metric — a repo with a manifest but a failing audit or rising drift is not adopted, it is
at risk. Watch audit pass rate, the drift trend (findings closed vs. opened),
and marketplace uptake instead
(Adoption
playbook).
Pin the fleet’s targets, not an expanding default. Meridian keeps
targets: [copilot, claude, cursor]. The 0.31.0 default-stable catalog now has nine
targets, including grok-build; stable hermes, like
agent-skills and antigravity, is explicit-only.
grok-cloud remains experimental and outside that default set.
Catalog support does not mean every primitive or native plugin works on every target
(Chapter 3;
0.31.0 target matrix).
Worked example
Meridian’s four moves, in order. Rehearse the CLI locally, then validate the infrastructure
separately. Current evidence comes from the existing fixtures and the
content/research/updates/1.2/ reports named in the captions; these are not new
Action or agent-runtime executions. Use short disposable copies with isolated user/config/cache
state, not the book root. Here $Apm is the absolute prepared 0.31.0
executable, and APM_POLICY_DISABLE is absent.
Move 1 — rehearse the gate, including its cold-cache boundary
Reuse the already materialized
backend/examples/updates/1.2/core/local-instruction fixture from
Chapter 5, including its authored
instruction, manifest and genuine lock. It has no remote dependencies, so this
particular rehearsal is offline. It tests recorded local content, not org discovery.
ch05-verification.md,
local-local-instruction-frozen and local-local-instruction-audit,
both exit 0; no new execution claimed here.
apm v0.31.0 — verified 2026-09-16
& $Apm install --frozen
& $Apm audit --ci
A public dependency tests a different boundary. The producer probes used the immutable
microsoft/apm-sample-package style-checker slice at
fb2851683be0e0e7711421d518bd8dba23b0b1f6, with the genuine lock and deployed files.
Removing modules and starting with an independent empty cache tested acquisition, not just replay
from a warmed developer machine:
| Probe | Boundary tested | Result |
|---|---|---|
ci-cold-audit |
No modules or warm cache; locked public source reachable | Exit 0; scratch hydrated, checkout bytes and timestamps unchanged. |
ci-unreachable-source |
Separate cold run; deliberately unreachable loopback proxy | Exit 1 on hydration/replay failure; no green skip or checkout repair. |
ci-tamper-audit |
Harmless ASCII edit to recorded deployed content | Exit 1; changed bytes rejected. |
ci-cold-sarif |
Clean audit with a SARIF output file | Exit 0; real report written, no Code Scanning upload tested. |
Historical comparison — the original 0.23.1 clean, direct and transitive runs
These July 2 recordings retain their original version, counts and cache-only wording.
Setup fetched a public package over the network; the displayed audits then used warmed local
state. They are not fresh-clone offline recipes or 0.31.0 results. The
Could not determine org… warning explains why the clean scratch run did
not enforce org policy, rather than demonstrating a production fail-closed gate.
$ apm audit --ci
[!] Could not determine org from git remote; enforcement skipped (set policy.fetch_failure_default=block in apm.yml to fail closed)
[>] Replaying install (cache-only)... [+] Replayed 2 package(s) [+] No drift detected
[>] APM Policy Compliance
│ [+] │ lockfile-exists │ Lockfile present │
│ [+] │ ref-consistency │ All dependency refs match lockfile │
│ [+] │ deployed-files-present │ All deployed files present on disk │
│ [+] │ no-orphaned-packages │ No orphaned packages in lockfile │
│ [+] │ skill-subset-consistency │ Skill subset selections match lockfile │
│ [+] │ config-consistency │ No MCP configs to check │
│ [+] │ content-integrity │ No critical hidden Unicode or hash drift detected │
│ [+] │ includes-consent │ No local content deployed -- includes … skipped │
│ [+] │ drift │ no drift detected against lockfile │
[*] All 9 check(s) passed # exit 0 -- 8 baseline checks + drift
The historical negative case used a block policy
(enforcement: block, require_pinned_constraint: true) against an
unpinned direct dependency on a bare #main branch. The
dependency-pinned-constraint check fails and the gate exits 1 — a
correctly protected required check would reject that result:
$ apm audit --ci --policy ./pol-block.yml # enforcement: block, require_pinned_constraint: true
[>] Replaying install (cache-only)... [+] No drift detected
... # baseline + policy checks run
│ │ dependency-pinned-constraint │ 1 dependency(ies) use unbounded constraints
│ │ │ (hint: pin to a semver range, literal tag, or SHA) │
│ │ │ - microsoft/apm-sample-package: bare branch 'main' tracks a moving tip │
[x] 1 of 18 check(s) failed # exit 1 -- the required check blocks the PR
The same historical policy passed with a pinned direct dependency and an unpinned transitive declaration. Its higher count reflects enumeration without the earlier fail-fast stop, not a fixed current schema. The separate 0.31.0 coverage limits still apply.
$ apm audit --ci --policy ./pol-block.yml # DIRECT dep pinned to #v1.0.0; a transitive dep is unpinned
│ [+] │ dependency-pinned-constraint │ All dependencies use pinned constraints │
...
[*] All 29 check(s) passed # exit 0 -- direct-only rule; count higher because nothing fails
# (fail-fast never trips; use --no-fail-fast for a full report)
Move 2 — make it required in CI (SKIPPED-needs-network)
Meridian starts with the current pinned integrity sketch, then configures its reviewed policy source and makes the job a required status check across all three product groups. Workflow ownership, runner environment and ruleset bypass permissions are part of that change. A local audit proves CLI behavior, not required-check enforcement or SARIF delivery; those need an authorized GitHub runner and repository settings.
Move 3 — route traffic through the approved proxy (SKIPPED-needs-network)
Meridian’s security org already mandates Artifactory for npm and PyPI, so APM joins the same
operating model. The platform team pins these environment variables in CI secrets and the shared dev
container — not in apm config — for consistent covered acquisition paths:
# SKIPPED-needs-network: pin in CI secrets / dev-container env, not `apm config`.
export HTTPS_PROXY="http://proxy.meridian.example:8080"
export PROXY_REGISTRY_URL="https://artifactory.meridian.example/artifactory/github-remote"
export PROXY_REGISTRY_TOKEN="$ARTIFACTORY_TOKEN" # bearer token; independent of GITHUB_APM_PAT
export PROXY_REGISTRY_ONLY=1 # refuse direct github.com fallback (mandatory + auditable)
apm install # covered archive path only;
# separately review the lock and audit deployed content
For an offline handoff, use a real bundle, not the historical
Chapter 10 manifest-only output.
The current producer/local-bundle fixture adds dependencies: {};
its default-format ZIP actually installed and audited with exit 0 using explicit
--target copilot,claude,cursor. Omitting that install flag selected only Copilot
in the probe despite the consumer’s three-target manifest. This is a
one-shot deployment: the lock records local deployed ownership, not a replayable
archive dependency in apm.yml. Retain the artifact for reinstall
(producer reference §3;
bundle contract).
Provision the bundle, CLI and required policy inputs before disconnecting. The Action’s
offline input only forwards to pack’s marketplace resolution; it does not make
earlier CLI acquisition or installation air-gapped. Nor does an offline handoff make cold audit
hydration or remote policy fetching unnecessary in every project.
Move 4 — publish and own the org baseline (SKIPPED-needs-network)
Finally the platform team lands the org apm-policy.yml in meridian-finance/.github,
behind branch protection. This keeps the Chapter 9
ownership beat: product-group repos consume a reviewed authority. Local inheritance can be
rehearsed without infrastructure; publishing that authority and verifying private-host discovery
remain SKIPPED-needs-network.
# meridian-finance/.github/apm-policy.yml -- SKIPPED-needs-network (publication/discovery)
name: meridian-org-baseline
version: "1.0.0"
enforcement: block # past the pilot: fail closed on violations
fetch_failure: block # remote posture; does NOT secure an unread first fetch
dependencies:
require_pinned_constraint: true # bounded DIRECT declarations, not all transitive constraints
allow: # only these sources (deny still wins)
- meridian-finance/**
- microsoft/**
- github/awesome-copilot/**
deny:
- sketchy-org/**
compilation:
target:
allow: [copilot, claude, cursor] # target rules live HERE, not a top-level `targets:` (Ch9)
Keep compilation.target.allow, not a top-level targets policy key:
unknown top-level keys now warn; malformed known types are rejected by the parser.
Do not use target rules alone to demonstrate blocking: the 0.31.0 plural-only target audit
control passed where the singular-target control failed
(policy-target-plural-audit/policy-target-singular-audit,
operations reference OP09.1).
apm.yml, separately from the
remote policy. Observed missing-org install/audit exits 1/1:
policy-no-remote-failclosed-install/policy-no-remote-failclosed-audit;
hash-mismatch audit exit 1: policy-pin-nonempty-mismatch-failclosed.
Operations reference OP09.3; local/loopback evidence, not live org discovery.
apm v0.31.0 — observed configuration
# apm.yml (consumer excerpt)
policy:
fetch_failure_default: block
Rehearse effective policy in a materialized disposable copy of
backend/examples/updates/1.2/operations/policy. Its child tries
enforcement: warn and empty deny/require lists; its parent requires a deliberately
absent package. Resolving that local chain succeeds, but auditing it must still block:
local-parent-merged (exit 0) and
child-cannot-clear-parent (expected exit 1); primary evidence:
policy-local-inheritance-status/policy-local-inheritance-audit.
These are recorded CLI observations, not an organization deployment.
apm v0.31.0
& $Apm policy status --policy-source ./apm-policy.child.yml --json --check
& $Apm audit --ci --policy ./apm-policy.child.yml -f json
With the baseline in warn first, Meridian watches Code Scanning across the three groups for
two sprints, remediates the top offenders, then flips to block — the same
measured rollout as Chapter 9, now fleet-wide, with the
pilot repo as the canary. Their status report to leadership is audit pass rate and drift
trend, not “repos with a manifest.”
Recap & next
Recap
- The question changes at scale. From “can this repo install?” to “can every repo install safely and predictably?” A fleet needs five things one team never forces: repeatable rollout, policy ownership, audit gates, a registry strategy, and exception handling. This is the capstone for Governance — enforced and operated across the org.
-
The fleet gate is
apm audit --ci. The same integrity gate (Chapter 7) and policy gate (Chapter 9), operated as defence in depth. Protect the command, policy authority, environment and ruleset permissions;--cidoes not neutralize bypasses. Cold scratch replay can fetch locked content and fails when that hydration cannot complete. Pin the Action and CLI independently. -
Proxy routing is environment-variable driven.
HTTPS_PROXY+PROXY_REGISTRY_URL+PROXY_REGISTRY_ONLY=1route and mirror traffic; reviewed bundles support offline handoffs with one-shot deployment limits. Recorded hashes and ownership support Reproducibility; the proxy is neither a publisher signature nor a dedicated registry. Experimental registry implementation exists; a public hosted hub is not established by this evidence. - Adoption is change management. Discover → Pilot → Harden → Scale → Sustain, each with an owner, a deliverable, and a gate. Measure by leading indicators — audit pass rate, drift trend, marketplace uptake, setup time — not by manifest count, which is a vanity metric. Carrot before stick; a named on-call, never “the platform team.”
- Mind the measured limits at apm v0.31.0. Pin constraints are direct-scoped; consumer fail-closed posture protects first policy resolution, not an environment-disabled gate. A green audit is not complete native MCP/runtime coverage. gh-aw imports isolated context, and the legacy Copilot pack’s shared-skill omission remains a real bug — the successful instruction control is not blanket compatibility.
Next
You have now consumed, locked, maintained, secured, governed, produced, and operated agent context across a fleet — the full arc from one repo to an organization. Chapter 12 — The Landscape & What’s Next steps back to place APM among the standards it builds on (AGENTS.md, Agent Skills, MCP, OpenAPM v0.1) and the roadmap ahead — distinguishing shipped experimental registry support from draft normative commitments — so you can decide what to adopt, watch, or build around.