Fail the image build when the Nexus token is missing
`docker compose build` without NEXUS_TOKEN produced a Nexus 401 forty seconds in, worded as a credentials problem when it was really an unset variable. The mount's `required=true` asserts the secret was *declared*, not that it holds anything, so an empty one sailed past it and npm sent an empty `_authToken`. The install moves to tools/docker-install-deps.sh, which checks the secret before touching the network and fails in under a second with the three ways to supply it. It is a file rather than inline shell because BuildKit echoes an inline command twice on failure and buries the message. Also ignore .env. It carries NEXUS_TOKEN, compose reads it at build time, and it was not gitignored — .env.example stays tracked. Nothing had been committed: the only prior commit predates all of this. Verified: empty token fails in 0.2s with the message; .env and the environment variable both build; the image carries no trace of the token and serves the full page. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
52
tools/docker-install-deps.sh
Executable file
52
tools/docker-install-deps.sh
Executable file
@@ -0,0 +1,52 @@
|
||||
#!/bin/sh
|
||||
# Installs the workspace's dependencies inside the image.
|
||||
#
|
||||
# Split out of the Dockerfile so a failure prints this file's own message
|
||||
# instead of BuildKit echoing a twenty-line inline shell twice.
|
||||
set -eu
|
||||
|
||||
TOKEN_FILE=/run/secrets/nexus_token
|
||||
NEXUS_PATH=//nexus.pireon.dev/repository/npm-releases/
|
||||
|
||||
# `required=true` on the mount only asserts the secret was declared, not that it
|
||||
# holds anything. An empty one sails past it and surfaces four hundred packages
|
||||
# later as a Nexus 401 that reads like a credentials problem.
|
||||
if [ ! -s "$TOKEN_FILE" ]; then
|
||||
cat >&2 <<'MSG'
|
||||
|
||||
ERROR: the nexus_token build secret is empty.
|
||||
|
||||
@pi/ui is published to the private Nexus, so the install needs a token.
|
||||
|
||||
compose: NEXUS_TOKEN=... docker compose build
|
||||
or put NEXUS_TOKEN in .env, which compose reads on its own
|
||||
docker: docker build --secret id=nexus_token,env=NEXUS_TOKEN .
|
||||
|
||||
Locally the value is the one already in ~/.npmrc:
|
||||
|
||||
grep nexus.pireon.dev ~/.npmrc
|
||||
|
||||
MSG
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# Written and removed inside a single layer, so it leaves no trace even in this
|
||||
# stage — which is discarded anyway.
|
||||
NPMRC=/tmp/npmrc
|
||||
printf '%s:_authToken=%s\n' "$NEXUS_PATH" "$(cat "$TOKEN_FILE")" > "$NPMRC"
|
||||
|
||||
if NPM_CONFIG_USERCONFIG="$NPMRC" npm ci --no-audit --no-fund; then
|
||||
rm -f "$NPMRC"
|
||||
else
|
||||
status=$?
|
||||
rm -f "$NPMRC"
|
||||
|
||||
if [ "$status" -ne 0 ]; then
|
||||
echo "" >&2
|
||||
echo "npm ci failed. If the error above is a 401 from nexus.pireon.dev," >&2
|
||||
echo "the token was present but is not valid for npm-releases." >&2
|
||||
echo "" >&2
|
||||
fi
|
||||
|
||||
exit "$status"
|
||||
fi
|
||||
Reference in New Issue
Block a user