Files
home-network-k3s-impl/decisions/2026-10-30-renovate-first-run.md
jakman85andClaude Opus 5.5 365e43cdea
gate / gate (pull_request) Successful in 2m52s
gate / conformance (pull_request) Has been skipped
fix(renovate): run Renovate as the job container; the action needs a Docker daemon jobs do not get
renovatebot/github-action is a wrapper around `docker run`. On this runner a job has no Docker
daemon by decision (decisions/2026-10-29-image-pipeline.md), so every run, including dispatch
run 343, died before Renovate started:

  failed to connect to the docker API at unix:///var/run/docker.sock ... no such file or directory

The pinned image ghcr.io/renovatebot/renovate:44.167.0 is now the job container, and a run step
execs renovate-entrypoint.sh. actions/checkout is dropped, since Renovate clones the repo itself.
An optional RENOVATE_GITHUB_COM_TOKEN secret feeds GITHUB_COM_TOKEN.

Local dry run (--platform=local, uid 12021, the step body verbatim): 179 deps extracted, 42
updates, and all 4 own-image digest lookups against the Gitea registry succeed.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
2026-10-30 01:23:36 -05:00

6.9 KiB
Raw Permalink Blame History

date, branch, title
date branch title
2026-10-30 fix/renovate-first-run Renovate never started because its action needs a Docker daemon jobs here do not get; it now runs as the job container

What changed

.gitea/workflows/renovate.yaml: the job no longer uses renovatebot/github-action. The pinned Renovate image (ghcr.io/renovatebot/renovate:44.167.0, the same version the action was pinned to) is now the job's container:. A run: step calls renovate-entrypoint.sh renovate inside it. actions/checkout is gone, because Renovate clones the repo itself. GITHUB_COM_TOKEN is wired from a new optional secret, RENOVATE_GITHUB_COM_TOKEN. The step unsets it, and RENOVATE_DRY_RUN, when they evaluate to the empty string. The preflight also prints renovate --version, which proves the step ran inside the pinned image.

renovate.json5: one comment now names container.image as the version pin, in place of renovate-version. The config itself is unchanged.

Why: the root cause

Every run of the action died before Renovate started. That includes the operator's dispatch, run 343 (task 555, 2026-10-30 06:14 UTC), and the 11 scheduled runs before it (312–322). From run 343's log:

RENOVATE_TOKEN is present (value not printed).
[command]/usr/bin/docker run --env LOG_LEVEL ... --env RENOVATE_TOKEN=*** --env RENOVATE_CONFIG_FILE=/github-action/renovate.json5 ...
failed to connect to the docker API at unix:///var/run/docker.sock; check if the path is correct and if the daemon is running: dial unix /var/run/docker.sock: connect: no such file or directory
Error: The process '/usr/bin/docker' failed with exit code 1

The action is only a wrapper around docker run. On this runner a job deliberately gets no Docker daemon (decisions/2026-10-29-image-pipeline.md): act_runner maps docker_host to - when DOCKER_HOST is tcp://, and the DinD daemon is privileged. So this was a platform-compatibility failure. The run never reached authentication, token scope, config or the network. The re-minted token is not implicated, and nothing in this log can say whether its scopes are right.

A job container: needs no daemon. act creates it through the runner's DinD the same way it creates the default ubuntu-latest image, then execs each step inside it. I checked this against gitea/act v0.261.2:

  • The job container's entrypoint is /bin/sleep (run_context.go). The Renovate image has /usr/bin/sleep.
  • The step command files are written 0o666 (step.go), so the image's uid 12021 can write $GITHUB_STEP_SUMMARY.
  • HOME comes from the image env.

What I verified

  • The root cause. I read all of run 343's job log (162 lines, job 0; job 1 is 404). It has one error, quoted above, and no Renovate output at all. Runs 312–322 are all failure from the schedule event.

  • The config validates against the pinned tag. podman run ... ghcr.io/renovatebot/renovate:44.167.0 renovate-config-validator /tmp/renovate.json5 printed Config validated successfully. It also printed the known migration diff for the top-level docker block.

  • A dry run with the fix extracts and looks up dependencies. This was a local reproduction. I made a clean snapshot of this branch's tracked files. I ran it in a podman container of the pinned image with entrypoint /bin/sleep, as the image's own uid 12021 with HOME=/home/ubuntu. Inside it I execed the workflow step's run: body, extracted verbatim from the YAML, with:

    • RENOVATE_PLATFORM=local, RENOVATE_DRY_RUN=full and GITHUB_COM_TOKEN= (empty, to exercise the unset);
    • a docker host rule for gitea.home.keithjackson.dev using the gitea-admin credential from ~/.git-credentials, passed through env and never printed.

    The run exited 0 and logged Dependency extraction complete:

    • flux 15 deps / 13 files
    • github-actions 24 / 4
    • kubernetes 131 / 67
    • kustomize 2 / 2
    • regex (both custom managers) 7 / 6
    • total 179 deps / 92 files

    It found 42 updates: 29 kubernetes, 6 flux, 2 kustomize, 1 github-actions and 4 regex digest. 7 of them are major.

  • The # renovate-digest: lookups against the Gitea registry succeed. All three /v2/token?scope=repository:home-network/<img>:pull requests succeeded, and so did HEAD /v2/home-network/<img>/manifests/main. They proposed digest updates for conformance/versions.env, infra/agent/versions.env, platform/pm-agent/configmap.yaml and platform/pm-agent/deployment.yaml, all of which carry the zero placeholder digest today. The kubernetes manager's copies of those images report disabled, which is the intended effect of the packageRule.

  • The new pin is still maintained by Renovate. The github-actions manager extracts ghcr.io/renovatebot/renovate:44.167.0 from renovate.yaml as depType container, and proposes 44.198.0.

  • The regex vs custom.regex question from #73/#77 is closed. Both custom managers produced dependencies.

  • Missing GitHub token. The local run logged GitHub token is required for some dependencies. That accounts for 17 deps skipped with github-token-required, which is why RENOVATE_GITHUB_COM_TOKEN is offered as an optional secret.

What I did NOT verify

  • The workflow on the real runner. UNVERIFIED. My reproduction ran with podman, not act_runner + DinD, and used --platform=local. The act behaviour (sleep entrypoint, exec as the image user, 0666 command files) comes from reading the gitea/act v0.261.2 source, not from a run. The first real evidence will be a workflow_dispatch after merge.
  • The Gitea platform path and RENOVATE_TOKEN's scopes. UNVERIFIED. I have no access token, only the gitea-admin password, which Renovate's Gitea platform cannot use. So these were not exercised: platform init (GET /user, which needs read:user), repo clone, and the registry lookups using the token with read:package rather than a password.
  • Behaviour inside the schedule window. A dispatch outside 03:00–06:00 America/New_York (07:00–10:00 UTC during EDT) will extract and look up, but will log "not within schedule" instead of DRY-RUN: Would create ... lines. I did not change this.
  • Renovate as uid 12021 doing artifact updates (for example helm lockfiles) on a real, non-dry run. --dry-run=full does not run the tools.
  • The self-bump. Renovate will propose ghcr.io/renovatebot/renovate 44.167.0 → 44.198.0 as a minor, which the default rule auto-merges. .gitea/** is a sensitive path, so it will in fact wait for an administrator override. Nothing re-runs renovate-config-validator on that bump, and no gate check runs the validator.
  • No alert for "Renovate red every day". That gap is still open. This failure ran for 12 days without anyone noticing.
  • Sensitive path. .gitea/** is in infra/gitea/approval-policy.json, so CI's approval-policy stage will block until the operator posts /approve-override as a PR review.