NK-WP-0058-T04 done: bx, four founder commands plus the approval
All checks were successful
CI Smoke / host-smoke (push) Successful in 0s
CI Smoke / container-smoke (push) Successful in 2s

bx ready / request / run / status (close for emergencies): inputs in a state file, receipts numbered
by the tool, every command safe to repeat and one value-free line. OpenBao steps run as silent
children of the warden platform-admin lane (executor-lanes.py --quiet); run closes the window in the
same child, also on error. Runbook sections 5-6 replaced; pilot-run.sh deleted. 134 tests.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>

Assistant: claude-code
Assistant-Model: opus
Assistant-Process: 943911@bnt-lap001
Assistant-Session: fc322940-1c8e-4bed-ab39-86cec99f23a0
This commit is contained in:
tegwick 2026-11-05 23:45:02 +01:00
parent a29d92ecda
commit 646ced3f9e
10 changed files with 577 additions and 120 deletions

View file

@ -0,0 +1,308 @@
#!/usr/bin/env python3
"""Founder commands for one bounded-execution run (NK-WP-0058-T04). Each prints one value-free line.
BX="python3 tools/bounded-execution-run/bx.py"
$BX ready admissions/BEA-YYYY-NNNN.yaml # readiness; one platform-admin login (OpenBao status)
$BX request # file the approval; the id goes into the state file
(approve the memo in informed-decision: browser profile of admin, aal2 with OTP)
$BX run # preflight, then window open, run, close; one platform-admin login
$BX status # the run's state and receipts, no login
$BX close # emergency: delete the write role; safe to repeat
Inputs live in a state file (~/.local/state/net-kingdom/bounded-execution/<id>.json), not in shell variables.
The admission named last is the current one; --admission selects another. Receipts are numbered by the tool in
docs/evidence/<date>-<id>/. Each command is safe to repeat: `run` never starts a second run for an admission.
The OpenBao steps run as silent children of `warden access openbao-platform-admin-login --exec`; the window
is closed in the same child, also when the run fails or is interrupted.
--attest names the trust states you attest for the run (default: runtime_secret_trust,runtime_identity_trust).
They are recorded in the state file and the run config, never edited in by hand.
"""
import argparse
import datetime as dt
import hashlib
import json
import os
import re
import subprocess
import sys
import time
from pathlib import Path
import yaml
REPO = Path(__file__).resolve().parents[2]
HOME = Path.home()
STATE_DIR = Path(os.environ.get('BX_STATE_DIR', HOME / '.local/state/net-kingdom/bounded-execution'))
RAPP = Path(os.environ.get('BX_RAPP', REPO.parent / 'rapp-bounded-executor'))
PLATFORM = Path(os.environ.get('BX_PLATFORM', REPO.parent / 'railiance-platform'))
KUBECONFIG = Path(os.environ.get('BX_KUBECONFIG', HOME / '.kube/config-railiance01'))
BAO_ADDR = os.environ.get('BAO_ADDR', 'http://127.0.0.1:18200')
LANE = ['warden', 'access', 'openbao-platform-admin-login', '--exec', '--']
LANES_TOOL = REPO / 'tools/service-binds/executor-lanes.py'
READY_TOOL = REPO / 'tools/bounded-execution-readiness/ready.py'
CCRS = {'write': 'CCR-2026-0058-*.yaml', 'journey': 'CCR-2026-0059-*.yaml'}
DELIVERIES = ('keycape-nk-bind-executor-approval-client', 'bounded-executor-tokens')
ATTEST = 'runtime_secret_trust,runtime_identity_trust'
WARDEN_EXIT = {10: 'login_failed', 11: 'child_failed', 12: 'child_output', 13: 'revoke_unconfirmed',
14: 'cleanup_failed'}
class Runner:
"""Every outside command goes through here; tests replace it."""
def run(self, argv, env=None, timeout=900):
full = {**os.environ, **(env or {})}
done = subprocess.run([str(a) for a in argv], capture_output=True, env=full, timeout=timeout)
return done.returncode, done.stdout.decode(errors='replace')
def sleep(self, seconds):
time.sleep(seconds)
def kubectl():
return f'kubectl --kubeconfig {KUBECONFIG}'
def json_blocks(text):
"""The value-free JSON results in a log: one-line objects and the executor's indented result blocks."""
out = []
for block in re.findall(r'^\{\n.*?\n\}$', text, re.M | re.S) + re.findall(r'^\{.*\}$', text, re.M):
try:
out.append(json.loads(block))
except ValueError:
pass
return out
class Bx:
def __init__(self, runner=None, now=None):
self.r = runner or Runner()
self.now = now or (lambda: dt.datetime.now(dt.timezone.utc))
# ------------------------------------------------------------------ state and receipts
def state_path(self, admission_id):
return STATE_DIR / f'{admission_id}.json'
def load(self, admission=None):
if admission:
doc = yaml.safe_load(Path(admission).read_text())
sid = doc['spec']['id']
path = self.state_path(sid)
if path.exists():
return json.loads(path.read_text())
evidence = REPO / 'docs/evidence' / f"{self.now():%Y-%m-%d}-{sid.lower()}"
return {'admission_id': sid, 'admission': str(Path(admission).resolve()), 'evidence': str(evidence),
'approval_id': None, 'attest': None, 'run': None}
current = STATE_DIR / 'current'
if not current.exists():
raise SystemExit(self.line({'status': 'refused', 'reason': 'no_admission', 'next': 'bx ready ADMISSION'}))
return json.loads(self.state_path(current.read_text().strip()).read_text())
def save(self, state):
STATE_DIR.mkdir(parents=True, exist_ok=True)
path = self.state_path(state['admission_id'])
path.write_text(json.dumps(state, indent=2, sort_keys=True) + '\n')
(STATE_DIR / 'current').write_text(state['admission_id'] + '\n')
def receipt(self, state, name):
folder = Path(state['evidence'])
folder.mkdir(parents=True, exist_ok=True)
numbers = [int(p.name[:2]) for p in folder.glob('[0-9][0-9]-*')]
return folder / f'{max(numbers, default=0) + 1:02d}-{name}.json'
def write(self, path, data):
path.write_text(json.dumps(data, indent=2, sort_keys=True) + '\n')
return path
def config(self, state):
"""The run config: the rapp's pilot config with the attested trust states. Non-secret."""
cfg = json.loads((RAPP / 'examples/config.pilot.json').read_text())
cfg['trust_satisfied'] = list(state['attest'])
path = STATE_DIR / f"{state['admission_id']}.config.json"
path.write_text(json.dumps(cfg, indent=2) + '\n')
return path
@staticmethod
def line(data):
return json.dumps(data, separators=(', ', ': '))
def lane(self, child):
"""Run a silent child under one platform-admin login. The child gets an isolated HOME from warden, so every
path it needs is passed as an absolute path here."""
env = {'BAO_ADDR': BAO_ADDR, 'VAULT_ADDR': BAO_ADDR, 'PYTHONWARNINGS': 'ignore', 'BX_STATE_DIR': STATE_DIR,
'BX_RAPP': RAPP, 'BX_PLATFORM': PLATFORM, 'BX_KUBECONFIG': KUBECONFIG, 'NK_PLATFORM_ROOT': PLATFORM}
code, _ = self.r.run(LANE + child, env={k: str(v) for k, v in env.items()})
return code
# ------------------------------------------------------------------ commands
def ready(self, admission, attest):
state = self.load(admission)
state['attest'] = state['attest'] or attest.split(',')
self.save(state)
rec = self.receipt(state, 'readiness')
self.r.run(['python3', READY_TOOL, '--admission', state['admission'],
'--approval-id', state['approval_id'] or 'none', '--receipt', rec])
agent = (json.loads(rec.read_text()) if rec.exists()
else {'agent_checks_pass': False, 'failures': ['no_receipt']})
custody = {}
for name in DELIVERIES:
code, out = self.r.run(kubectl().split() + ['-n', 'sso', 'get', 'externalsecret', name, '-o',
'jsonpath={.status.conditions[?(@.type=="Ready")].status}'])
custody[name] = code == 0 and out.strip() == 'True'
self.write(self.receipt(state, 'custody'), {'action': 'custody-delivery', 'ready': custody,
'values_recorded': False})
status = self.receipt(state, 'lanes-status')
warden = self.lane(['python3', LANES_TOOL, 'status', '--receipt', status, '--quiet'])
lanes = json.loads(status.read_text()) if status.exists() else {}
failures = list(agent.get('failures', [])) + [f'custody:{n}' for n, ok in custody.items() if not ok]
if not lanes.get('ready_for_window'):
failures.append('openbao:' + (lanes.get('reason') or WARDEN_EXIT.get(warden, 'not_ready_for_window')))
state['ready'] = {'at': f'{self.now():%Y-%m-%dT%H:%M:%SZ}', 'failures': failures}
self.save(state)
nxt = 'bx run' if state['approval_id'] else 'bx request'
return self.line({'ready': not failures, 'admission': state['admission_id'], 'failures': failures,
'next': nxt if not failures else 'fix the failures, then bx ready again'})
def request(self):
state = self.load()
if state['approval_id']:
return self.line({'approval_id': state['approval_id'], 'status': 'already_requested',
'next': 'approve as admin (aal2), then bx run'})
code, out = self.r.run(['make', '-C', RAPP, 'request', f"ADMISSION={state['admission']}",
f'CONFIG={self.config(state)}', f'KUBECTL={kubectl()}'])
result = next((b for b in reversed(json_blocks(out)) if 'outcome' in b), {})
self.write(self.receipt(state, 'request'), {**result, 'exit': code})
if result.get('approval_id'):
state['approval_id'] = result['approval_id']
self.save(state)
return self.line({'approval_id': result.get('approval_id'), 'outcome': result.get('outcome'),
'next': 'open the memo as admin (aal2, fresh OTP), approve, then bx run'
if result.get('outcome') == 'presented' else 'bx request again (idempotent)'})
def run(self):
state = self.load()
if state.get('run') and state['run'].get('started'):
return self.line({**self.summary(state), 'status': 'already_run'})
if not state['approval_id']:
return self.line({'status': 'refused', 'reason': 'no_approval', 'next': 'bx request'})
self.config(state)
code = self.lane(['python3', Path(__file__).resolve(), '_run-inner', '--state',
self.state_path(state['admission_id'])])
state = json.loads(self.state_path(state['admission_id']).read_text())
if code and not (state.get('run') or {}).get('finished'):
state['run'] = {**(state.get('run') or {}), 'warden': WARDEN_EXIT.get(code, f'exit_{code}')}
self.save(state)
return self.line(self.summary(state))
def run_inner(self, state_file):
"""The silent lane child: preflight, then window open, run, poll, and close in `finally`. Prints nothing."""
state = json.loads(Path(state_file).read_text())
cfg = STATE_DIR / f"{state['admission_id']}.config.json"
k = kubectl()
run = state['run'] = {'started': False, 'receipts': []}
def note(path):
run['receipts'].append(Path(path).name)
self.save(state)
_, out = self.r.run(['make', '-C', RAPP, 'preflight', f"ADMISSION={state['admission']}",
f"APPROVAL_ID={state['approval_id']}", f'CONFIG={cfg}', f'KUBECTL={k}'])
report = next((b for b in reversed(json_blocks(out)) if b.get('mode') == 'preflight-only'),
{'ready': False, 'failures': ['preflight_no_report']})
note(self.write(self.receipt(state, 'preflight'), report))
if not report.get('ready'):
run.update(outcome='not_started', reason='preflight_not_ready', failures=report.get('failures'))
return self.save(state)
digests = {}
for lane, pattern in CCRS.items():
files = sorted((PLATFORM / 'credential-change-requests').glob(pattern))
digests[lane] = hashlib.sha256(files[0].read_bytes()).hexdigest()
opened = self.receipt(state, 'window-open')
try:
self.r.run(['python3', LANES_TOOL, 'window-open', '--admission', state['admission'],
'--write-ccr-sha256', digests['write'], '--journey-ccr-sha256', digests['journey'],
'--receipt', opened, '--quiet'])
note(opened)
if json.loads(opened.read_text()).get('status') != 'window_opened':
run.update(outcome='not_started', reason='window_not_opened')
return
run['started'] = True
self.save(state)
code, _ = self.r.run(['make', '-C', RAPP, 'run', f"ADMISSION={state['admission']}",
f"APPROVAL_ID={state['approval_id']}", f'CONFIG={cfg}', f'KUBECTL={k}'])
if code:
run.update(outcome='not_started', reason='job_not_created')
return
job = 'bounded-executor-' + state['admission_id'].lower()
budget = yaml.safe_load(Path(state['admission']).read_text())['spec']['budget']['wall_time_seconds']
for _ in range(int(budget / 5) + 60):
_, st = self.r.run(k.split() + ['-n', 'sso', 'get', f'job/{job}', '-o',
'jsonpath={.status.succeeded}{.status.failed}'])
if st.strip():
break
self.r.sleep(5)
_, logs = self.r.run(k.split() + ['-n', 'sso', 'logs', f'job/{job}'])
result = next((b for b in reversed(json_blocks(logs)) if 'outcome' in b),
{'outcome': 'unknown', 'reason': 'no_result_in_log'})
note(self.write(self.receipt(state, 'result'), result))
run.update(outcome=result.get('outcome'), reason=result.get('reason'), run_id=result.get('run_id'))
finally:
closed = self.receipt(state, 'window-close')
self.r.run(['python3', LANES_TOOL, 'window-close', '--admission', state['admission'],
'--receipt', closed, '--quiet'])
if closed.exists():
note(closed)
run['window_closed'] = json.loads(closed.read_text()).get('status') == 'window_closed'
run['finished'] = True
self.save(state)
def summary(self, state):
run = state.get('run') or {}
return {'admission': state['admission_id'], 'approval_id': state['approval_id'],
'outcome': run.get('outcome'), 'reason': run.get('reason'), 'window_closed': run.get('window_closed'),
'warden': run.get('warden'), 'error': run.get('error'), 'receipts': len(run.get('receipts', [])),
'evidence': os.path.relpath(state['evidence'], REPO)}
def status(self):
return self.line(self.summary(self.load()))
def close(self):
state = self.load()
rec = self.receipt(state, 'window-close')
code = self.lane(['python3', LANES_TOOL, 'window-close', '--admission', state['admission'], '--receipt', rec,
'--quiet'])
closed = json.loads(rec.read_text()) if rec.exists() else {}
return self.line({'status': closed.get('status', 'failed'), 'reason': closed.get('reason'),
'warden': WARDEN_EXIT.get(code) if code else None})
def main(argv=None, bx=None):
p = argparse.ArgumentParser(description=__doc__, formatter_class=argparse.RawDescriptionHelpFormatter)
p.add_argument('command', choices=['ready', 'request', 'run', 'status', 'close', '_run-inner'])
p.add_argument('admission', nargs='?')
p.add_argument('--attest', default=ATTEST)
p.add_argument('--state', help=argparse.SUPPRESS)
a = p.parse_args(argv)
bx = bx or Bx()
if a.command == '_run-inner': # a silent lane child: any output would fail the lane, so record, never print
try:
bx.run_inner(a.state)
except Exception as error:
state = json.loads(Path(a.state).read_text())
state['run'] = {**(state.get('run') or {}), 'error': type(error).__name__, 'finished': True}
Path(a.state).write_text(json.dumps(state, indent=2, sort_keys=True) + '\n')
return 0
if a.command == 'ready':
if not a.admission:
p.error('ready takes the admission file')
print(bx.ready(a.admission, a.attest))
return 0
if a.admission:
bx.save(bx.load(a.admission))
print({'request': bx.request, 'run': bx.run, 'status': bx.status, 'close': bx.close}[a.command]())
return 0
if __name__ == '__main__':
sys.exit(main())

View file

@ -0,0 +1,183 @@
"""bx.py on stubs (NK-WP-0058-T04): every outside command is faked; no cluster, no OpenBao, no warden."""
import contextlib
import importlib.util
import io
import json
from pathlib import Path
import pytest
REPO = Path(__file__).resolve().parents[3]
spec = importlib.util.spec_from_file_location('bx', REPO / 'tools/bounded-execution-run/bx.py')
bx = importlib.util.module_from_spec(spec)
spec.loader.exec_module(bx)
ADMISSION = REPO / 'admissions/BEA-2026-0003.yaml'
def arg(argv, name):
return argv[argv.index(name) + 1]
class Fake:
def __init__(self, tool, preflight_ready=True, window_opens=True, result='completed', logs_raise=False):
self.tool, self.calls, self.child_output = tool, [], ''
self.preflight_ready, self.window_opens, self.result, self.logs_raise = (
preflight_ready, window_opens, result, logs_raise)
def write(self, argv, data):
Path(arg(argv, '--receipt')).write_text(json.dumps(data))
def run(self, argv, env=None, timeout=900):
argv = [str(a) for a in argv]
joined = ' '.join(argv)
if argv[:3] == ['warden', 'access', 'openbao-platform-admin-login']:
self.calls.append('lane')
assert env['BX_STATE_DIR'] and env['BX_KUBECONFIG'] # absolute paths: the child's HOME is isolated
child = argv[argv.index('--') + 1:]
if '_run-inner' in child:
with contextlib.redirect_stdout(io.StringIO()) as out, contextlib.redirect_stderr(out):
self.tool.main(['_run-inner', '--state', arg(child, '--state')], bx=self.tool_bx)
self.child_output += out.getvalue()
return 0, ''
return self.run(child)
if 'ready.py' in joined:
self.calls.append('readiness')
self.write(argv, {'agent_checks_pass': True, 'failures': []})
return 0, ''
if 'externalsecret' in joined:
self.calls.append('custody')
return 0, 'True'
if 'executor-lanes.py' in joined:
action = argv[2]
self.calls.append(action)
assert '--quiet' in argv
if action == 'status':
self.write(argv, {'status': 'status_read', 'ready_for_window': True})
elif action == 'window-open':
self.write(argv, {'status': 'window_opened' if self.window_opens else 'failed'})
elif action == 'window-close':
self.write(argv, {'status': 'window_closed'})
return 0, ''
if argv[:1] == ['make']:
target = argv[3]
self.calls.append('make ' + target)
if target == 'request':
return 0, 'kubectl ...\n{\n "approval_id": "apr-9",\n "outcome": "presented"\n}\n'
if target == 'preflight':
report = {'mode': 'preflight-only', 'ready': self.preflight_ready, 'failures':
[] if self.preflight_ready else ['preflight:approval']}
return (0 if self.preflight_ready else 2), json.dumps(report, indent=2) + '\n'
if target == 'run':
return 0, 'kubectl create -f - < .rendered/run.yaml\n'
if 'get' in argv and any(a.startswith('job/') for a in argv):
self.calls.append('poll')
return 0, '1'
if 'logs' in argv:
self.calls.append('logs')
if self.logs_raise:
raise TimeoutError
return 0, json.dumps({'outcome': self.result, 'run_id': 'r-1', 'effects': True}, indent=2) + '\n'
raise AssertionError(argv)
def sleep(self, seconds):
pass
@pytest.fixture
def env(tmp_path, monkeypatch):
monkeypatch.setattr(bx, 'STATE_DIR', tmp_path / 'state')
monkeypatch.setattr(bx, 'REPO', tmp_path / 'repo')
rapp = tmp_path / 'rapp'
(rapp / 'examples').mkdir(parents=True)
(rapp / 'examples/config.pilot.json').write_text(json.dumps({'executor_identity': 'service:nk-bind-executor'}))
monkeypatch.setattr(bx, 'RAPP', rapp)
ccrs = tmp_path / 'platform/credential-change-requests'
ccrs.mkdir(parents=True)
for name in ('CCR-2026-0058-w.yaml', 'CCR-2026-0059-j.yaml'):
(ccrs / name).write_text('id: x\n')
monkeypatch.setattr(bx, 'PLATFORM', tmp_path / 'platform')
return tmp_path
def tool(**kw):
fake = Fake(bx, **kw)
fake.tool_bx = bx.Bx(fake)
return fake, fake.tool_bx
def cli(b, *argv):
with contextlib.redirect_stdout(io.StringIO()) as out:
assert bx.main(list(argv), bx=b) == 0
lines = out.getvalue().splitlines()
assert len(lines) == 1 # one value-free line per command
return json.loads(lines[0])
def test_full_run_is_four_commands_plus_the_approval(env):
fake, b = tool()
assert cli(b, 'ready', str(ADMISSION))['next'] == 'bx request'
assert cli(b, 'request')['approval_id'] == 'apr-9'
done = cli(b, 'run')
assert (done['outcome'], done['window_closed'], done['receipts']) == ('completed', True, 4)
assert cli(b, 'status')['outcome'] == 'completed'
assert fake.calls == ['readiness', 'custody', 'custody', 'lane', 'status', 'make request', 'lane',
'make preflight', 'window-open', 'make run', 'poll', 'logs', 'window-close']
assert fake.child_output == '' # the lane child is silent
evidence = sorted(p.name for p in (env / 'repo/docs/evidence').glob('*/*'))
assert [n[:2] for n in evidence] == [f'{i:02d}' for i in range(1, 9)]
assert evidence[4:] == ['05-preflight.json', '06-window-open.json', '07-result.json', '08-window-close.json']
state = json.loads((env / 'state/BEA-2026-0003.json').read_text())
assert state['attest'] == ['runtime_secret_trust', 'runtime_identity_trust']
cfg = json.loads((env / 'state/BEA-2026-0003.config.json').read_text())
assert cfg['trust_satisfied'] == state['attest']
def test_commands_are_safe_to_repeat(env):
fake, b = tool()
cli(b, 'ready', str(ADMISSION))
cli(b, 'request')
assert cli(b, 'request')['status'] == 'already_requested'
cli(b, 'run')
calls = len(fake.calls)
assert cli(b, 'run')['status'] == 'already_run'
assert len(fake.calls) == calls # no second run, no second login
def test_preflight_not_ready_never_opens_the_window(env):
fake, b = tool(preflight_ready=False)
cli(b, 'ready', str(ADMISSION))
cli(b, 'request')
done = cli(b, 'run')
assert (done['outcome'], done['reason']) == ('not_started', 'preflight_not_ready')
assert 'window-open' not in fake.calls and 'make run' not in fake.calls
fake.preflight_ready = True
assert cli(b, 'run')['outcome'] == 'completed' # a run that never started may be retried
@pytest.mark.parametrize('kw, outcome', [({'window_opens': False}, 'not_started'), ({'result': 'reverted'}, 'reverted')])
def test_the_window_is_always_closed(env, kw, outcome):
fake, b = tool(**kw)
cli(b, 'ready', str(ADMISSION))
cli(b, 'request')
done = cli(b, 'run')
assert done['outcome'] == outcome and fake.calls[-1] == 'window-close' and done['window_closed']
def test_an_error_in_the_child_still_closes_and_stays_silent(env):
fake, b = tool(logs_raise=True)
cli(b, 'ready', str(ADMISSION))
cli(b, 'request')
done = cli(b, 'run')
assert done['error'] == 'TimeoutError' and done['window_closed'] is True
assert fake.calls[-1] == 'window-close' and fake.child_output == ''
def test_close_is_one_lane_and_idempotent(env):
fake, b = tool()
cli(b, 'ready', str(ADMISSION))
assert cli(b, 'close')['status'] == 'window_closed'
assert cli(b, 'close')['status'] == 'window_closed'
def test_instructions_fit_120_characters():
assert all(len(line) <= 120 for line in bx.__doc__.splitlines())

View file

@ -331,6 +331,8 @@ def main():
p.add_argument('--kubeconfig', help='admin kubeconfig; required for verify')
p.add_argument('--admission', help='the admitted BEA file; required for window-open and window-close')
p.add_argument('--receipt', required=True)
p.add_argument('--quiet', action='store_true',
help='print nothing; the receipt is the result (a silent child of warden access --exec)')
a = p.parse_args()
if a.action == 'verify' and not a.kubeconfig: p.error('--kubeconfig is required for verify')
if a.action.startswith('window-') and not a.admission: p.error('--admission is required for ' + a.action)
@ -351,8 +353,9 @@ def main():
if r['reason'] in HINTS: r['hint'] = HINTS[r['reason']]
finally:
with os.fdopen(fd, 'w') as out: json.dump(r, out, indent=2, sort_keys=True); out.write('\n')
print(json.dumps({k: r[k] for k in ('status', 'phase', 'reason', 'hint', 'ready_for_window', 'write_role_absent')
if k in r}))
if not a.quiet:
print(json.dumps({k: r[k] for k in ('status', 'phase', 'reason', 'hint', 'ready_for_window',
'write_role_absent') if k in r}))
return int(r['status'] == 'failed')