feat: verify live KeyCape custody and preserve versions on resume
All checks were successful
CI Smoke / host-smoke (push) Successful in 0s
CI Smoke / container-smoke (push) Successful in 2s

Assistant: codex
Assistant-Model: gpt-5.6-luna
Assistant-Session: 01a07ff8-19d0-7820-b4d0-1353833cb7fc
This commit is contained in:
codex 2026-09-09 02:18:12 +02:00
parent b7861de20e
commit c6dc4286e2
8 changed files with 382 additions and 57 deletions

View file

@ -62,6 +62,36 @@ def contracts():
return result
def resume_provision(lanes, receipt, prior_path):
prior = json.loads(Path(prior_path).read_text())
require(prior.get('status') == 'failed' and prior.get('verifier_delivery_disabled_custody_versions_retained')
and prior.get('keycape', {}).get('compatible_pair_restored'), 'verified_partial_activation_receipt_required')
old_rows = prior['lanes']
require(len(old_rows) == len(lanes), 'partial_receipt_lane_mismatch')
for lane, old in zip(lanes, old_rows):
require(old['ccr'] == lane['ccr'] and (old.get('custody_seeded') or old.get('existing_version_reused')) and old.get('kv_version') == 1,
'initial_version_provenance_required')
metadata = read_optional(lane['metadata'])
require(metadata is not None and metadata['current_version'] == 1
and not metadata['versions']['1'].get('destroyed') and not metadata['versions']['1'].get('deletion_time'),
'initial_custody_version_changed')
role = read_optional('auth/kubernetes/role/' + lane['role'])
require(role is not None and role.get('token_policies') == []
and role_matches(dict(role, token_policies=[lane['policy']]), lane), 'disabled_role_drift')
require(read_optional('sys/policies/acl/' + lane['policy'])['policy'] == lane['hcl'], 'resume_policy_drift')
require(all(re.search(r'path\s+"' + re.escape(path) + r'"\s*\{\s*capabilities\s*=\s*\["deny"\]\s*\}', read_optional(BOUNDARY)['policy'])
for path in (lane['kv'], lane['metadata'])), 'resume_boundary_drift')
# Only reattach the same reviewed reader roles. No KV write, import or rotation.
for lane, old in zip(lanes, old_rows):
bao(['write', 'auth/kubernetes/role/' + lane['role'], '-'], payload=lane['role_payload'])
require(role_matches(read_optional('auth/kubernetes/role/' + lane['role']), lane), 'resumed_role_readback_failed')
receipt['lanes'].append({'ccr': lane['ccr'], 'source_sha256': lane['source_sha256'],
'custody_seeded': False, 'existing_version_reused': True, 'kv_version': 1,
'initial_request_id': old.get('initial_request_id', old.get('request_id')), 'policy_applied': False, 'role_applied': True})
receipt['custody_versions_unchanged'] = True
def read_optional(path):
result = bao(['read', '-format=json', path], allow_failure=True)
if result.returncode == 0:
@ -264,8 +294,9 @@ def run(args, receipt):
check = data(command(['python3', '-B', '/home/worsch/net-kingdom/sso-mfa/k8s/keycape/openbao-client-config.py', 'issuer-check-live'], env=env))
require(check['issuer_matches'] and check['verified_issuer'] == 'https://auth.coulomb.social', 'verified_issuer_pin_required')
receipt['issuer_pin_revision'] = check['before']['resource_version']
rollout = load_rollout() if args.action == 'activate' else None
rollout = load_rollout() if args.action in {'activate', 'resume-activate'} else None
if rollout:
rollout.verify_artifact()
# Exercise config construction and API admission before any custody write.
secret = rollout.get(kube, 'secret', 'keycape-config')
dep = rollout.get(kube, 'deployment', 'keycape')
@ -282,6 +313,9 @@ def run(args, receipt):
receipt['phase'] = 'provision'
if args.action in {'provision', 'activate'}:
provision(lanes, receipt)
elif args.action == 'resume-activate':
require(args.prior_receipt, 'prior_receipt_required')
resume_provision(lanes, receipt, args.prior_receipt)
else:
receipt['lanes'] = [{'ccr': lane['ccr']} for lane in lanes]
receipt['phase'] = 'native_verification'
@ -307,10 +341,11 @@ def run(args, receipt):
def main():
parser = argparse.ArgumentParser(description=__doc__)
parser.add_argument('action', choices=['provision', 'verify', 'activate'])
parser.add_argument('action', choices=['provision', 'verify', 'activate', 'resume-activate'])
parser.add_argument('--kubeconfig', required=True)
parser.add_argument('--receipt', required=True)
parser.add_argument('--recovery')
parser.add_argument('--prior-receipt')
args = parser.parse_args()
receipt = {'schema': 'platform.keycape-approval-custody.v1', 'status': 'failed', 'lanes': [],
'started_at': datetime.now(timezone.utc).isoformat(), 'credential_values_emitted': False,