# whynot-design npm publish token Date: 2026-06-29 Catalog: `whynot-design-npm-publish` (status `active`, `resolvable: true`) Owner: `railiance-platform` (OpenBao) · provisioning CCR-2026-0001 (commit 8f617fc) The `NPM_AUTH_TOKEN` that publishes `@whynot/design` to the coulomb Gitea npm registry (`https://gitea.coulomb.social/api/packages/coulomb/npm/`). ops-warden **does not hold this token** — it is the access front door: `warden access` proxies the read from OpenBao **as the caller** and never persists, caches, or logs the value. --- ## Owner-confirmed lane (no placeholders) | Field | Value | | --- | --- | | OpenBao path | `platform/workloads/coulomb/whynot-design/npm-publish` | | Field | `NPM_AUTH_TOKEN` | | KV mount | `platform` | | Read policy | `workload-kv-read-whynot-design-npm-publish` | | OIDC login | `bao login -method=oidc -path=netkingdom role=whynot-design-workload-kv-read` | | Bound group | `whynot-design` | | flex-auth ref | `secret.read:whynot-design` (if tenant policy requires pre-approval) | | Runbook (owner) | `railiance-platform/docs/workload-kv-access-lanes.md` | > The `platform/workloads/whynot-design/whynot-design/npm-publish` path from early in the > provisioning thread is **superseded** — the live path is under the `coulomb` tenant. --- ## Worker checklist 1. **Authenticate as yourself** (you need your own identity; ops-warden adds none): ```bash bao login -method=oidc -path=netkingdom role=whynot-design-workload-kv-read ``` Your token must carry the `whynot-design` group bound claim; a non-whynot identity is denied by policy (verified negative case). 2. **Run via the owner-native front door (primary).** secrets-engine owns the secret-exec for this lane (SECRETS-WP-0003, decision e6381a56); ops-warden routes to it: ```bash secrets-engine route whynot-design-npm-publish --json # pointer / readiness secrets-engine exec --catalog whynot-design-npm-publish -- npm publish ``` **ops-warden transparent fallback** — same lane via the `warden access` proxy (fetches as you, holds nothing). Field-verified flags (whynot-design, @whynot/design@0.4.0): ```bash # --exec needs the env-var name; --no-policy is required while the gate is advisory # (policy.enabled=false), else the call exits 4. warden access whynot-design-npm-publish --no-policy --field NPM_AUTH_TOKEN \ --exec -- npm publish warden access whynot-design-npm-publish --no-policy --field NPM_AUTH_TOKEN --fetch ``` On either path the value transits to you (or the child env) and never enters ops-warden's memory, disk, or audit log. 3. **Readiness gate (for automated callers).** Before attempting `--fetch`, check the flag: ```bash warden route show whynot-design-npm-publish --json | jq .resolvable # true ``` `resolvable: true` means the lane is concrete and `--fetch` will run; a template lane reports `false`. 4. **Publish is outward-facing and immutable.** `npm publish` is irreversible and public. Even once the token resolves, hold for an explicit operator "yes, publish" — do not auto-run it from an agent. --- ## Scopes This lane is the **publish** token only. A separate **read/install** token (for consumers of `@whynot/design`) is a distinct need and would be its own catalog id (`whynot-design-npm-read`) once railiance-platform provisions it — do not conflate them. --- ## See also - `wiki/OperatorAccessAssist.md` — the `warden access` front door + guardrails - `wiki/CredentialRouting.md` — routing model - `railiance-platform/docs/workload-kv-access-lanes.md`, `workplans/RAILIANCE-WP-0006-workload-kv-access-lanes.md`