From a4c1f31557198ae1923d35dc2be6f43186d01c1e Mon Sep 17 00:00:00 2001 From: hermes-bot Date: Tue, 27 Oct 2026 23:25:12 +0000 Subject: [PATCH] fix(review-bot): mint the review-bot PAT with read:issue Since 9ec31f07 (PR #1503) review-bot's sweep lists the PRs that request its review via GET /repos/issues/search?review_requested=true. Gitea requires read:issue for that endpoint, and the rotator mints the review-bot PAT with write:repository only, so every 5-minute sweep fails with HTTP 403 and requested reviews are picked up only by the webhook. - review-bot-secret-rotate: GITEA_SCOPES = write:repository,read:issue. - One-shot Job review-bot-rotate-read-issue runs the CronJob's rotate-mint and sync-woodpecker steps once, so the new token is minted on merge instead of at the next quarterly run (2027-01-01). ESO (refresh 1h) picks it up and Reloader restarts review-bot. Remove the Job in a follow-up once it ran. Closes #1505 --- .../openbao/rotation/kustomization.yaml | 2 + .../rotation/review-bot-rotate-once-job.yaml | 99 +++++++++++++++++++ .../openbao/rotation/review-bot.yaml | 3 +- 3 files changed, 103 insertions(+), 1 deletion(-) create mode 100644 kubernetes/infrastructure/openbao/rotation/review-bot-rotate-once-job.yaml diff --git a/kubernetes/infrastructure/openbao/rotation/kustomization.yaml b/kubernetes/infrastructure/openbao/rotation/kustomization.yaml index eace3520..c7ab4791 100644 --- a/kubernetes/infrastructure/openbao/rotation/kustomization.yaml +++ b/kubernetes/infrastructure/openbao/rotation/kustomization.yaml @@ -51,6 +51,8 @@ resources: - ha-config-sync.yaml - registry-bot.yaml - review-bot.yaml + # ONE-SHOT (#1505): mint review-bot's PAT with read:issue. Remove after it ran. + - review-bot-rotate-once-job.yaml - claude-oauth.yaml # NOT ROTATED, deliberately — recorded here because the whole point of this # directory is that unrotated credentials should be a visible choice: diff --git a/kubernetes/infrastructure/openbao/rotation/review-bot-rotate-once-job.yaml b/kubernetes/infrastructure/openbao/rotation/review-bot-rotate-once-job.yaml new file mode 100644 index 00000000..0b2e16e3 --- /dev/null +++ b/kubernetes/infrastructure/openbao/rotation/review-bot-rotate-once-job.yaml @@ -0,0 +1,99 @@ +--- +# ONE-SHOT, REMOVE AFTER IT RAN (#1505): the rotate-mint + sync-woodpecker steps +# of review-bot-secret-rotate, so the read:issue PAT is minted now, not next quarter. +# No ttlSecondsAfterFinished: a TTL delete would let Flux re-create it and mint again. +apiVersion: batch/v1 +kind: Job +metadata: + name: review-bot-rotate-read-issue + namespace: openbao + labels: + app.kubernetes.io/name: review-bot + app.kubernetes.io/component: secret-rotator +spec: + backoffLimit: 1 + activeDeadlineSeconds: 300 + template: + metadata: + labels: + app.kubernetes.io/name: review-bot + app.kubernetes.io/component: secret-rotator + spec: + serviceAccountName: review-bot-secret-rotator + restartPolicy: Never + securityContext: + runAsNonRoot: true + runAsUser: 65534 + runAsGroup: 65534 + seccompProfile: + type: RuntimeDefault + initContainers: + - name: rotate-mint + image: gitea.renner.uno/gitea_admin/secret-rotator:2026-07-30 + args: ["gitea-token"] + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: + drop: ["ALL"] + env: + - name: BAO_ADDR + value: http://openbao.openbao.svc.cluster.local:8200 + - name: BAO_ROLE + value: rotator-review-bot + - name: BOOTSTRAP_PATH + value: homelab/infrastructure/secret-rotators-bootstrap/review-bot + - name: BAO_PATH + value: homelab/infrastructure/review-bot + - name: GITEA_URL + value: http://gitea.gitea.svc.cluster.local:3000 + # Private repo: the pull check is the real access verification. + - name: GITEA_VERIFY_REPO + value: konairius/shelly-manager + # read:issue: the sweep lists requested reviews via /repos/issues/search. + - name: GITEA_SCOPES + value: write:repository,read:issue + - name: GITEA_REQUIRE_PUSH + value: "false" + - name: GITEA_TOKEN_NAME_PREFIX + value: review-bot-rotated + resources: + requests: + cpu: 25m + memory: 16Mi + limits: + memory: 48Mi + containers: + - name: sync-woodpecker + image: gitea.renner.uno/gitea_admin/secret-rotator:2026-07-30 + args: ["woodpecker-secret"] + securityContext: + allowPrivilegeEscalation: false + readOnlyRootFilesystem: true + capabilities: + drop: ["ALL"] + env: + - name: BAO_ADDR + value: http://openbao.openbao.svc.cluster.local:8200 + - name: BAO_ROLE + value: rotator-review-bot + - name: BOOTSTRAP_PATH + value: homelab/infrastructure/secret-rotators-bootstrap/woodpecker-bot + - name: BAO_PATH + value: homelab/infrastructure/review-bot + - name: BAO_FIELD + value: token + - name: WOODPECKER_URL + value: http://woodpecker.woodpecker.svc.cluster.local:8000 + - name: WOODPECKER_ORG + value: konairius + - name: WOODPECKER_SECRET_NAME + value: review_bot_token + - name: WOODPECKER_EVENTS + value: cron,manual,pull_request + resources: + requests: + cpu: 25m + memory: 16Mi + limits: + memory: 48Mi diff --git a/kubernetes/infrastructure/openbao/rotation/review-bot.yaml b/kubernetes/infrastructure/openbao/rotation/review-bot.yaml index 2b57aef6..69ebcf59 100644 --- a/kubernetes/infrastructure/openbao/rotation/review-bot.yaml +++ b/kubernetes/infrastructure/openbao/rotation/review-bot.yaml @@ -111,8 +111,9 @@ spec: # push, or repoint this at another private repo it collaborates on. - name: GITEA_VERIFY_REPO value: konairius/shelly-manager + # read:issue: the sweep lists requested reviews via /repos/issues/search. - name: GITEA_SCOPES - value: write:repository + value: write:repository,read:issue # review-bot posts reviews via the API (write:repository scope) # but never git-pushes, and is only a read collaborator, so push # verification would fail. The private-repo pull check above is -- 2.54.0