Watch
0
0
Fork
You've already forked hyperhive
0

read grafana's datasource key from the store into /run, seeding an empty store from the old file

This commit is contained in:
atlas 2026-10-30 16:08:35 +01:00
commit 204abb1d0e
2 changed files with 236 additions and 69 deletions

View file

@ -0,0 +1,68 @@
# `checks.script-test-grafana-secret-key` — runs
# ../host-modules/lib/grafana-secret-key.nix's `grafana_secret_key` against a
# stub `bao` that keeps its leaves in files. The cases are in
# ./grafana-secret-key.sh.
#
# What runs is the rendered helper, sourced as the unit's script includes it.
{
pkgs,
...
}:
let
# `login` answers from `FAKE_BAO_LOGIN_RC`. `kv get` and `kv put -cas=0` act
# on a file per leaf under `FAKE_BAO_KV`, and answer as bao does: a missing
# leaf is "No value found at <path>" on stderr, status 2. `FAKE_BAO_DENY_READ`
# and `FAKE_BAO_DENY_WRITE` answer 403 as a policy that grants neither does.
# `FAKE_BAO_RACE` has another run create the leaf with that value between
# this one's read and its write. Every call is logged without the value
# `put` reads from stdin.
fakeBao = pkgs.writeShellScriptBin "bao" ''
echo "$*" >> "$FAKE_BAO_LOG"
case "$1 $2" in
"login -method=cert")
[ "$FAKE_BAO_LOGIN_RC" = 0 ] || { echo "fake bao: certificate refused" >&2; exit 2; }
printf 's.fake'
;;
"kv get")
[ "''${BAO_TOKEN-}" = s.fake ] || { echo "fake bao: kv without the login's token" >&2; exit 97; }
[ "$3" = -field=value ] || { echo "fake bao: get without -field=value" >&2; exit 95; }
leaf="$FAKE_BAO_KV/$(printf '%s' "$4" | tr / _)"
[ -z "''${FAKE_BAO_DENY_READ-}" ] || { echo "fake bao: permission denied" >&2; exit 2; }
if [ -n "''${FAKE_BAO_RACE-}" ] && [ ! -e "$FAKE_BAO_KV/.raced" ]; then
touch "$FAKE_BAO_KV/.raced"
printf '%s' "$FAKE_BAO_RACE" > "$leaf"
echo "No value found at secret/data/x" >&2
exit 2
fi
[ -e "$leaf" ] || { echo "No value found at secret/data/x" >&2; exit 2; }
cat "$leaf"
echo
;;
"kv put")
[ "''${BAO_TOKEN-}" = s.fake ] || { echo "fake bao: kv without the login's token" >&2; exit 97; }
[ "$3" = -cas=0 ] || { echo "fake bao: put without -cas=0" >&2; exit 96; }
[ "$5" = value=- ] || { echo "fake bao: put with the value as an argument" >&2; exit 94; }
leaf="$FAKE_BAO_KV/$(printf '%s' "$4" | tr / _)"
[ -z "''${FAKE_BAO_DENY_WRITE-}" ] || { echo "fake bao: permission denied" >&2; exit 2; }
[ ! -e "$leaf" ] || { echo "fake bao: check-and-set parameter did not match" >&2; exit 2; }
cat > "$leaf"
;;
*)
echo "fake bao: unexpected call: $*" >&2
exit 98
;;
esac
'';
in
pkgs.runCommand "hyperhive-script-test-grafana-secret-key"
{
HELPER = pkgs.writeText "grafana-secret-key.sh" (
import ../host-modules/lib/grafana-secret-key.nix { }
);
FAKE_BAO_BIN = "${fakeBao}/bin";
nativeBuildInputs = [ pkgs.coreutils ];
}
''
${pkgs.bash}/bin/bash ${./grafana-secret-key.sh}
touch "$out"
''

View file

@ -0,0 +1,89 @@
# Cases for ./grafana-secret-key.nix. Each case sets up the store's leaf, the
# seed file and the stub's behaviour, runs `grafana_secret_key` the way the
# unit's script does, and compares its status, the key it hands over and what
# the store holds afterwards.
set -uo pipefail
failures=0
leaf=secret/swarm/services/t/secret-key
# setup <description>
setup() {
case=$1
dir=$(mktemp -d)
mkdir "$dir/kv"
export FAKE_BAO_KV=$dir/kv FAKE_BAO_LOG=$dir/bao.log FAKE_BAO_LOGIN_RC=0
unset FAKE_BAO_DENY_READ FAKE_BAO_DENY_WRITE FAKE_BAO_RACE
: >"$FAKE_BAO_LOG"
seed=$dir/secret_key
stored=$FAKE_BAO_KV/$(printf '%s' "$leaf" | tr / _)
}
mint() {
printf 'minted-key\n'
}
# expect <status> <key> <what the store holds, "" for nothing>
expect() {
(
PATH="$FAKE_BAO_BIN:$PATH"
unset BAO_TOKEN
# shellcheck source=/dev/null
. "$HELPER"
rc=0
grafana_secret_key "$leaf" "$seed" mint >/dev/null 2>"$dir/err" || rc=$?
printf '%s' "$rc" >"$dir/rc"
printf '%s' "$GRAFANA_KEY" >"$dir/key"
)
held=$(cat "$stored" 2>/dev/null)
if [ "$(cat "$dir/rc")" != "$1" ]; then fail "exited $(cat "$dir/rc"), wanted $1: $(cat "$dir/err")"; fi
if [ "$(cat "$dir/key")" != "$2" ]; then fail "handed over '$(cat "$dir/key")', wanted '$2'"; fi
if [ "$held" != "$3" ]; then fail "the store holds '$held', wanted '$3'"; fi
}
fail() {
echo "FAILED: $case: $*" >&2
failures=$((failures + 1))
}
setup "an empty store takes the seed's key"
printf 'seed-key\n' >"$seed"
expect 0 seed-key seed-key
grep -q '^kv put -cas=0 ' "$FAKE_BAO_LOG" || fail "no create-only write"
[ -e "$seed" ] || fail "the seed file was removed"
setup "a store that holds a key wins over the seed, and is not written"
printf 'seed-key\n' >"$seed"
printf 'store-key' >"$stored"
expect 0 store-key store-key
! grep -q '^kv put' "$FAKE_BAO_LOG" || fail "wrote to the store"
setup "with no seed and an empty store, a key is minted and stored"
expect 0 minted-key minted-key
setup "a store that refuses the login mints nothing, with or without a seed"
export FAKE_BAO_LOGIN_RC=1
expect 1 "" ""
printf 'seed-key\n' >"$seed"
expect 1 "" ""
setup "a store that refuses the read stores and hands over nothing"
printf 'seed-key\n' >"$seed"
export FAKE_BAO_DENY_READ=1
expect 1 "" seed-key
setup "a store that refuses the write hands over nothing"
export FAKE_BAO_DENY_WRITE=1
expect 1 "" ""
setup "a store that holds an empty value hands over nothing"
: >"$stored"
expect 1 "" ""
setup "a lost race takes the winner's key"
printf 'seed-key\n' >"$seed"
export FAKE_BAO_RACE=other-key
expect 0 other-key other-key
echo "$failures failures"
[ "$failures" = 0 ]