Prepare empty OpenBao slots for the two backup publisher pairs.
All checks were successful
CI Smoke / host-smoke (push) Successful in 1s
CI Smoke / container-smoke (push) Successful in 2s

Version 1 names both AWS fields and holds a placeholder. The founder enters the real keys as the next version.

Assistant: grok
Assistant-Session: 01a11cdb-f9fe-7011-947c-936e72007e54
This commit is contained in:
codex 2026-10-08 23:13:17 +02:00
parent 9b658e3f19
commit 31c679f212
2 changed files with 106 additions and 2 deletions

View file

@ -0,0 +1,102 @@
#!/usr/bin/env python3
"""Create the two empty backup-primary KV slots.
One CAS=0 write per path stores both field names with the placeholder
PENDING. The founder replaces that version in the OpenBao UI. No provider
key is read or written.
"""
from __future__ import annotations
import json
import os
import subprocess
from pathlib import Path
STAGE = Path("/home/worsch/.local/state/railiance/receipts/backup-pair-slots.stage")
RECEIPT = Path("/home/worsch/.local/state/railiance/receipts/backup-pair-slots.json")
PATHS = (
"platform/workloads/coulomb-social/backup-primary",
"platform/workloads/email-connect/backup-primary",
)
def stage(text):
STAGE.parent.mkdir(mode=0o700, exist_ok=True)
STAGE.write_text(text + "\n")
STAGE.chmod(0o600)
def run(args, token=None):
env = os.environ.copy()
if token is None:
env.pop("BAO_TOKEN", None)
env.pop("VAULT_TOKEN", None)
else:
env["BAO_TOKEN"] = token
env["VAULT_TOKEN"] = token
return subprocess.run(args, capture_output=True, env=env)
def main():
created = run(
[
"bao", "token", "create",
"-policy=backup-pair-writer",
"-ttl=5m",
"-use-limit=3",
"-orphan",
"-format=json",
]
)
if created.returncode:
stage(f"token_create_failed {created.returncode}")
raise SystemExit(51)
token = json.loads(created.stdout)["auth"]["client_token"]
body = Path(os.environ["HOME"]) / "backup-pair-slot.json"
body.write_text(json.dumps({
"AWS_ACCESS_KEY_ID": "PENDING",
"AWS_SECRET_ACCESS_KEY": "PENDING",
}))
body.chmod(0o600)
puts = []
try:
for path in PATHS:
meta = run(["bao", "kv", "metadata", "get", "-format=json", path])
if meta.returncode == 0:
stage(f"already_present {path}")
raise SystemExit(52)
put = run(["bao", "kv", "put", "-cas=0", path, f"@{body}"], token=token)
puts.append({"path": path, "put_returncode": put.returncode})
if put.returncode:
stage(f"put_failed {path} {put.returncode}")
raise SystemExit(53)
finally:
body.unlink(missing_ok=True)
run(["bao", "token", "revoke", "-self"], token=token)
slots = []
for path in PATHS:
meta = run(["bao", "kv", "metadata", "get", "-format=json", path])
if meta.returncode:
slots.append({"path": path, "metadata_returncode": meta.returncode})
continue
data = json.loads(meta.stdout)["data"]
slots.append({
"path": path,
"current_version": data.get("current_version"),
"version_count": len(data.get("versions") or {}),
})
RECEIPT.parent.mkdir(mode=0o700, exist_ok=True)
RECEIPT.write_text(json.dumps({"slots": slots, "puts": puts}, indent=2) + "\n")
RECEIPT.chmod(0o600)
stage("ok")
if __name__ == "__main__":
try:
main()
except SystemExit:
raise
except Exception as exc:
stage("failed " + type(exc).__name__)
raise SystemExit(54) from None