Fix git config failures when HOME is unreadable with FF_GIT_URLS_WITHOUT_TOKENS enabled
What does this MR do?
With FF_GIT_URLS_WITHOUT_TOKENS enabled, the GIT_CONFIG_GLOBAL seed file includes
$HOME/.gitconfig and $HOME/.config/git/config unconditionally. git skips an unreadable
global config silently (ACCESS_EACCES_OK, since v1.8.3.1) but dies on an unreadable
include.path target. In a non-root container that keeps HOME=/root (the Kubernetes
default: HOME is not derived from the security context user), access() returns EACCES
even though /root/.gitconfig does not exist, so every git invocation fails with
fatal: unable to access '/root/.gitconfig': Permission denied and the job dies during
Getting source from Git repository.
This MR emits each $HOME include behind a new ShellWriter conditional, IfFileReadable:
[ -r ]in bash[System.IO.File]::OpenReadin PowerShell
A readable config is included as before, and
git config --global writes keep landing in the seed file. A troubleshooting entry keyed
on the error messages points to the existing writable HOME recipe.
Why was this MR needed?
Regression introduced in 19.2.0 by !6729 (merged). The failure hits the seeding sequence itself:
GIT_CONFIG_GLOBAL is exported before the seed is written, so the second of the
git config --file calls that write the seed re-reads the half-written file and exits 128
before get_sources produces any output.
What's the best way to test this MR?
Unit and integration tests:
go test ./shells/ -run 'IfFileReadable|SetupGlobalGitConfigSeed'
go test -tags=integration ./shells/ -run TestIfFileReadableEnd-to-end with the docker executor, where a non-root build container keeps HOME=/root,
a 0700 directory it cannot read:
[[runners]]
executor = "docker"
[runners.docker]
user = "1000"
[runners.feature_flags]
FF_GIT_URLS_WITHOUT_TOKENS = truejob:
image:
name: alpine/git
entrypoint: [""]
variables:
HOME: /root
script:
- git config --global user.name exampleBefore, the script step exits 128 on
fatal: unable to access '/root/.gitconfig': Permission denied. After, it passes. Here the
failure surfaces in the job script rather than during checkout, because get_sources runs in
the helper container, which is root and reads /root fine.
The same before and after was verified on the shell executor, where the failure does land
during Getting source from Git repository, against a 19.2 baseline built from this branch
point. The conditional is exercised on bash, PowerShell, and pwsh, including a
permission-denied case that removes read access from a file (an ACL deny on Windows, a mode
change on Linux) and asserts the guard skips the unreadable file. It was also checked over
SSH to a Windows target.
What are the relevant issue numbers?
Closes #39617 (closed)
Related #37408, #26618
MR !7003, !7019 (closed)
The docs entry is the one planned in #37408.