Glidepath · Spec · Production roadmap

Glidepath, from the lab to production

The SDLC review told me where Glidepath falls short. Reading it back, I realized some of those gaps were my lab, not the design. So this sorts every weakness the review found by cause, then orders the work in three lanes, so a production install is never blocked on a feature it doesn't need.

Spec October 12, 2026Companion Glidepath SDLC reviewEffort single-engineer estimates: S is days, M is one to three weeks, L is one to two months
Nine items · three lanes · now, next, later

Some gaps are the lab, not the design. Finish the architecture first, then build what it lacks.

Correction to the review

Approvals and change management: Partial, not Not enforced.

The review rated approvals and change management as not enforced. That was the lab, not the architecture. Glidepath's install requires a GitHub ruleset on every gitops repo, generated from releaseGuardrails, with two approvals and every gate as a required check. In an organization, one ruleset covers gitops-*. The lab runs on GitHub Free, where private-repo rulesets exist but are not applied.

Revised rating: Partial. The ruleset would block, but three of its required checks always pass, and the September 27, 2026 audit found that non-release PRs and bot commits would be stuck the day it is switched on. Item T1 fixes that.

Three kinds of gap

Each weakness from the review falls into one of three groups, and each group needs different work.

5 weaknesses

Lab-bound

Specified in the architecture; the lab substitutes something weaker. The work is to write it down and verify it.

4 weaknesses

Fix before enforcing

In the architecture, but would break the day the ruleset is enforced.

18 weaknesses

Design gap

Missing whatever the environment. Needs new design.

Weakness from the reviewKindRoadmap item
Approvals and required checks don't block a mergeLab-boundP1 · T1
NetworkPolicy is a no-op on the dev CNILab-boundP1
Prod reads secrets from a dev-hosted store over a NodePortLab-boundP1 · P2
Webhook arrives through a tunnel and port-forwardLab-boundP1
No Prometheus on the upper clusterLab-boundP1 · T3
Required checks never report on non-release PRsFix before enforcingT1
Bot bootstrap commits would be refused by the rulesetFix before enforcingT1
/retest <gate> re-runs nothingFix before enforcingT1
Bypass alert not yet proven against a real bypassFix before enforcingT1
ITSM, QA and policy gates always passDesign gapT2
A scan that never ran counts as a passDesign gapT2
No signature check at admissionDesign gapT2
No secret, dependency or license scanningDesign gapT2
Test secrets copied into the shared Testkube namespaceDesign gapT2
Extra .tekton files run uncheckedDesign gapT2
Inert canary; analysis passes on no dataDesign gapT3
Next environment starts when the PR opensDesign gapT3
DORA has no environment, skips Ground and cloudDesign gapT3
Chained stages never report to the PR; no test reportsDesign gapD1
Missing test file reports successDesign gapD1
Push branch globs never match; no cron or manual runsDesign gapD2
No build secrets or build args; cache misses Python and GoDesign gapD2
Closed stage graph, fixed agents, no monorepoDesign gapD3
Control plane shares a cluster with GroundDesign gapP2
Kaniko archived; amd64 Go builds crash under QEMUDesign gapP3
Hardcoded to GHCR and GitHub; cloud targets unverifiedDesign gapP3
No migration or feature-flag storyDesign gapP3

The roadmap at a glance

Three lanes that can move independently, each with three horizons. Within a lane, order matters: T2 adds required checks, so T1 must first make sure every check reports. Across lanes, P1 writes down the profile that T1 and P2 verify against.

The roadmap at a glanceRoadmap in three lanes and three horizons. Trust lane: T1 ready the ruleset to enforce now, T2 make every gate real next, T3 release on health later. Developer lane: D1 feedback on the PR now, D2 triggers and build inputs next, D3 an extensible pipeline later. Platform lane: P1 write the production profile now, P2 separate the control plane next, P3 portable builds and targets later. T1 blocks a production install; T1, P1 and P2 complete the existing architecture; the rest is new design.NOWNEXTLATERTRUST · GOVERNANCE THAT BLOCKSReady the ruleset to enforceT1 · effort SMake every gate realT2 · effort M–LRelease on healthT3 · effort LDEVELOPER · THE INNER LOOPFeedback on the PRD1 · effort MTriggers and build inputsD2 · effort MAn extensible pipelineD3 · effort LPLATFORM · THE PRODUCTION PROFILEWrite the production profileP1 · effort SSeparate the control planeP2 · effort LPortable builds and targetsP3 · effort LFinish the architecture first, then build what it lacks. Each lane can move on its own.LEGENDBlocks a production installCompletes the architectureNew design
Figure 1Nine items in three lanes. Effort is a rough single-engineer estimate: S is days, M is one to three weeks, L is one to two months.

The work, item by item

Each item names the review findings it closes and a test that says when it is done.

Trust · governance that blocks

T1 · Now · effort S

Ready the ruleset to enforce

Fix before enforcing

  • Run every gate on every PR to main, passing at once when the head is not a release-* branch.
  • Make the Crossplane GitHub App a bypass actor, scoped to the bootstrap files it writes.
  • Match the retest comment event in each gate's CEL.
  • Prove detect-bypass-merge against a real bypass merge in the lab.
  • Already built: hack/apply-guardrail-ruleset.sh generates the ruleset from releaseGuardrails.

Done whenOn an org with rulesets enforced, a release PR merges green, a resync PR and a Tower Config PR merge with no bypass, a bot bootstrap commit lands, and a failing gate blocks.

github-ruleset.md audit 1 to 3 · gaps 15, 16, 20

T2 · Next · effort M–L

Make every gate real

Design gap

  • ITSM: open a change from change.created and pass on approval. QA: read the test stage's recorded outcome for the digest. Policy: Conforma or Kyverno CLI over the rendered manifests.
  • For any production: true environment, a missing scan fails instead of passing.
  • Verify signatures at admission on upper clusters against the cluster's own Fulcio root.
  • Add secret, dependency and license scanning to the build.
  • Stop copying app secrets into the shared Testkube namespace; run tests where the secret already lives.
  • Reject .tekton files the platform did not generate.

Done whenNo entry in releaseGuardrails is a stub, and an unsigned image is refused by the upper cluster.

governance-gate-stub.yaml · verify-sast-attestation.yaml · run-testworkflow.yaml

T3 · Later · effort L

Release on health

Design gap

  • Scrape ingress metrics wherever canaries run, and make an analysis with no data fail.
  • Ship a default multi-step canary with an error-rate analysis.
  • Start the next environment from the release record's Healthy fact instead of change.created.
  • On a failed analysis, abort and open the rollback PR automatically. It stays gated.
  • Label DORA by environment, count Ground and cloud deploys, and start lead time at the first commit.

Done whenA bad image in staging aborts itself and the prod release PR never opens.

airframe/analysis · rollout.yaml · dora-exporter

Developer · the inner loop

D1 · Now · effort M

Feedback on the PR

Design gap

  • Post every chained stage as a check run on the app commit, using the broker's per-repo token.
  • Parse JUnit and coverage from unit tests and Testkube into the check summary.
  • A test step with no test file fails, or reports neutral, instead of passing.
  • Run PR pipelines on opened when the label is already there, and give each preview an ingress URL.

Done whenA PR shows build, test and preview checks with test counts and a link to the running preview.

gap 7 · run-tests.yaml · ephemeral-envs.yaml

D2 · Next · effort M

Triggers and build inputs

Design gap

  • Glob matching for push branches, reusing the regex builder branch.created already has.
  • Cron and manual runs: a PaC incoming webhook, and a Run button in Tower.
  • Path filters on PR and tag events.
  • Build secrets and build args from the app's own secrets.
  • Dependency cache for Python and Go; pin agent images by digest.

Done whenA release/* branch flow, a nightly job and a build against a private package registry all work from cicd.yaml.

deliver-onboarding-files.yaml:498 · build-source.yaml

D3 · Later · effort L

An extensible pipeline

Design gap

  • Named extension points (pre-build, post-test, pre-release) that run a team's container under a fixed contract and the stage's identity.
  • Bring-your-own agent image from an allow-listed, signed registry.
  • Monorepo support: app path, build context and image per app.
  • Matrix test runs and a retry budget.

Done whenA team adds a custom step with no platform change, and two apps build from one repo.

ADR-0017 · stage-preflight.yaml

Platform · the production profile

P1 · Now · effort S

Write the production profile

Lab-bound

  • An ADR naming each lab substitution and what production requires: an enforced org ruleset with two approvals, an enforcing CNI, a routable secret store per zone, TLS ingress for the relay and webhooks, Prometheus on upper clusters.
  • An alert when no PaC event has arrived in N hours.
  • A conformance check, as a script or a Tower page, that reports which profile a cluster meets.

Done whenAn installer can tell a lab install from a production one by running one check.

security.md "Known, accepted gaps" · infisical-nodeport.yaml · gap 8

P2 · Next · effort L

Separate the control plane

Lab-bound

  • Ground environments on a lower workloads cluster, so the control-plane cluster runs no apps.
  • Upper clusters read secrets from a store in their own zone, never from dev.
  • Back up release records, or move them off 14-day ConfigMaps.

Done whenLosing the dev workloads cluster leaves pipelines, release records and prod secrets untouched.

ADR-0024 "Future" · gap 39

P3 · Later · effort L

Portable builds and targets

Design gap

  • Replace kaniko with rootless BuildKit or Buildah, and cross-compile natively instead of under QEMU.
  • Take the registry and git host from config, not from ghcr.io and api.github.com in Task scripts.
  • Verify ECS, Lambda and Container Apps live, with OIDC federation instead of static keys, and give them release records.
  • Document expand/contract migrations as a gated Job, and add an OpenFeature integration.

Done whenThe same app builds to a non-GHCR registry and releases to ECS with a release record.

gaps 33, 36 to 38 · build-image.yaml

Where it lands

The production profile keeps what the review found sound, Argo CD on each upper cluster pulling merged commits, and replaces each lab shortcut with a real endpoint.

Where it lands: the target production topologyA GitHub organization holds app repos, gitops repos and an org ruleset that requires two approvals and the gate checks before a gitops merge; in the lab the free plan does not enforce it. A control-plane cluster runs Tekton and Pipelines-as-Code, the broker and relay, and backed-up release records and DORA, and no apps. A separate lower workloads cluster, not built yet (gap 39), runs Argo CD for dev and the Ground environments. The upper cluster runs its own Argo CD pulling merged commits, an admission policy that verifies signatures, staging and prod with canary analysis, and External Secrets reading a secret store in its own zone. GitHub webhooks and rollout facts travel over TLS ingress instead of the lab tunnel and node ports.GITHUB ORGANIZATIONApp reposGround configGitops reposone per appOrg ruleset2 approvals · required checksLAB: FREE PLAN, NOT ENFORCEDCONTROL PLANE · LOWERLOWER WORKLOADS · GAP 39UPPER ZONETekton + PaCpipelines only, no appsBroker + relayCDEvents, rollout factsRecords + DORAbacked up, env-labeledArgo CD · devmoves off the control planeGround environmentsdev, previewsArgo CD · prodown instanceAdmissionverifies signaturesStaging + prodcanary + analysisZone storesecretsESOsecret syncWEBHOOK · INGRESSRELEASE PRPULLS MERGED COMMITFACTS · TLS INGRESSLAB: SHARES A CLUSTER WITH GROUNDLAB: NOT BUILT YETLAB: STORE OVER NODEPORT, NO PROMETHEUSThe production profile keeps the pull-only boundary and gives every other link a real endpoint.LEGENDIn the architectureOrg rulesetProposed hereExternalProposed link
Figure 2The target topology. Blue outlines are proposed by this roadmap; solid outlines exist in the architecture today. Grey notes under each zone say what the lab uses instead.

What to defer

Hangar's own cost essay warns that operating 47 tools is the platform's real limit. For one engineer, these can wait until a second team asks:

Sources: the Glidepath SDLC review, glidepath/docs/admin/github-ruleset.md (the September 27, 2026 audit), the security.md known gaps, known-gaps.md, ADR-0024, and Apron's Infisical NodePort notes. Effort estimates are judgement, not measurement. The lab-bound items come from what the architecture already specifies; nothing here was verified on an enforcing GitHub plan.