Remove internal notification caller tokens

This commit is contained in:
Stephan D committed 2026-09-12 23:59:30 +02:00
1 parent 1fe173397f
commit caad7a3d5b
27 files changed
+112 -165

No files matched your search

-1
View File
@@ -38,5 +38,4 @@ api:
min_length: 12
notifications:
address: notifications:8083
token_env: SXCHNGE_NOTIFICATIONS_TOKEN
activation_url: https://localhost:5126/verify-email
-2
View File
@@ -17,8 +17,6 @@ messaging:
max_reconnects: -1
reconnect_wait: 2
templates: "/etc/sxchnge/templates.json"
callers:
product: "SXCHNGE_NOTIFICATIONS_PRODUCT_TOKEN"
email:
driver: resend
settings:
+3 -3
View File
@@ -58,8 +58,8 @@ provision_agents() {
directory="$STATE/agents/$service"
mkdir -p "$directory"; chmod 755 "$directory"
case "$service" in
bff) paths='services/bff/jwt services/notifications/callers/bff';;
notifications) paths='services/notifications/callers/bff infrastructure/nats/auth services/notifications/email/resend';;
bff) paths='services/bff/jwt';;
notifications) paths='infrastructure/nats/auth services/notifications/email/resend';;
nats) paths=infrastructure/nats/auth;;
esac
: > "$WORK/policy"
@@ -92,7 +92,7 @@ up() {
initialize
mounts
migrate_secrets
for path in infrastructure/nats/auth services/notifications/callers/bff services/bff/jwt; do
for path in infrastructure/nats/auth services/bff/jwt; do
if [ "$(kv "$path")" = null ]; then
field=token; [ "$path" != services/bff/jwt ] || field=jwt
random | jq -Rs --arg field "$field" '{($field):rtrimstr("\n")}' | put "$path"
+2 -3
View File
@@ -1,8 +1,7 @@
# Canonical paths follow ownership. Shared callers live under the receiving service.
# Canonical paths follow ownership.
secret_moves() {
cat <<'PATHS'
bff services/bff/jwt
caller services/notifications/callers/bff
email services/notifications/email/resend
nats infrastructure/nats/auth
bootstrap/mongo infrastructure/mongo/bootstrap
@@ -47,7 +46,7 @@ retire_secrets() (
archive_secret "$old"
printf '{}' | vault "kv/metadata/$old" DELETE >/dev/null
done < "$WORK/moves"
for old in tls frontend-tls notifications-tls; do
for old in caller services/notifications/callers/bff tls frontend-tls notifications-tls; do
archive_secret "$old"
if [ "$(vault "kv/metadata/$old" GET yes)" != null ]; then printf '{}' | vault "kv/metadata/$old" DELETE >/dev/null; fi
done
+19
View File
@@ -74,3 +74,22 @@ printf '{"data":{"metadata":{"version":43},"data":{"api_key":"preserved-fixture-
if (normalize_email_secret) >/dev/null 2>&1; then fail 'Unknown secret field was silently dropped'; fi
if grep -q EMAIL_CONFIG infra/local/vault/notifications.hcl infra/local/scripts/start-service.sh; then fail 'Email configuration is still rendered from Vault'; fi
echo 'PASS: email migration preserves API key, removes configuration fields and rejects unknown fields'
# Caller retirement is repeatable and must not remove NATS authentication.
secret_moves() { :; }
printf '{"caller":true,"services/notifications/callers/bff":true,"infrastructure/nats/auth":true}' > "$WORK/retirement"
vault() {
path=${1#kv/metadata/}
case "${2:-GET}" in
GET) jq -c --arg path "$path" '.[$path] // null' "$WORK/retirement";;
DELETE)
case "$path" in caller|services/notifications/callers/bff) ;; *) fail 'Unexpected secret retirement';; esac
jq --arg path "$path" 'del(.[$path])' "$WORK/retirement" > "$WORK/retirement-next"
mv "$WORK/retirement-next" "$WORK/retirement"
;;
*) fail 'Unexpected retirement method';;
esac
}
retire_secrets
retire_secrets
jq -e '.=={"infrastructure/nats/auth":true}' "$WORK/retirement" >/dev/null
echo 'PASS: obsolete caller secrets retired idempotently; NATS authentication preserved'
+3 -3
View File
@@ -6,7 +6,7 @@ policies() (
directory="$STATE/agents/$service"
login=$(jq -n --rawfile role "$directory/role-id" --rawfile secret "$directory/secret-id" '{role_id:($role|rtrimstr("\n")),secret_id:($secret|rtrimstr("\n"))}' | vault auth/approle/login POST)
identity=$(printf '%s' "$login" | jq -er '.auth.client_token')
printf '%s' "$login" | jq '{token:.auth.client_token,paths:["kv/data/bootstrap/mongo","kv/data/infrastructure/mongo/bootstrap","sys/init","kv/data/bff","kv/data/caller","kv/data/email","kv/data/nats","kv/data/tls"]}' | vault sys/capabilities POST | jq -e '.data | all(.[]; .==["deny"])' >/dev/null || fail 'Service can access bootstrap credentials'
printf '%s' "$login" | jq '{token:.auth.client_token,paths:["kv/data/bootstrap/mongo","kv/data/infrastructure/mongo/bootstrap","sys/init","kv/data/bff","kv/data/caller","kv/data/services/notifications/callers/bff","kv/data/email","kv/data/nats","kv/data/tls"]}' | vault sys/capabilities POST | jq -e '.data | all(.[]; .==["deny"])' >/dev/null || fail 'Service can access bootstrap credentials'
VAULT_TOKEN=$(printf '%s' "$login" | jq -er '.auth.client_token')
printf '{}' | vault auth/token/revoke-self POST >/dev/null
VAULT_TOKEN=$root_token
@@ -51,10 +51,10 @@ product() {
}
layout() {
kv services/notifications/email/resend | jq -e 'keys==["api_key"]' >/dev/null || fail 'Non-secret email configuration remains in Vault'
for old in bootstrap/mongo bff caller email nats tls frontend-tls notifications-tls; do
for old in bootstrap/mongo bff caller services/notifications/callers/bff email nats tls frontend-tls notifications-tls; do
[ "$(vault "kv/metadata/$old" GET yes)" = null ] || fail "Obsolete KV entry remains: $old"
done
for path in services/bff/jwt services/notifications/callers/bff services/notifications/email/resend infrastructure/nats/auth infrastructure/mongo/bootstrap; do
for path in services/bff/jwt services/notifications/email/resend infrastructure/nats/auth infrastructure/mongo/bootstrap; do
vault "kv/metadata/$path" | jq -e '.data.current_version>0' >/dev/null || fail "Missing canonical KV entry: $path"
done
echo 'PASS: canonical Vault hierarchy present; obsolete flat and TLS entries absent'
-4
View File
@@ -19,10 +19,6 @@ env_template "SXCHNGE_JWT_SECRET" {
error_on_missing_key = true
}
env_template "SXCHNGE_NOTIFICATIONS_TOKEN" {
contents = "{{ with secret \"kv/data/services/notifications/callers/bff\" }}{{ .Data.data.token }}{{ end }}"
error_on_missing_key = true
}
exec {
command = ["/usr/local/bin/start-service"]
-4
View File
@@ -14,10 +14,6 @@ template_config {
}
env_template "SXCHNGE_NOTIFICATIONS_PRODUCT_TOKEN" {
contents = "{{ with secret \"kv/data/services/notifications/callers/bff\" }}{{ .Data.data.token }}{{ end }}"
error_on_missing_key = true
}
env_template "SXCHNGE_NATS_URL" {
contents = "{{ with secret \"kv/data/infrastructure/nats/auth\" }}nats://{{ .Data.data.token }}@nats:4222{{ end }}"