docs: preserve reviewed NetKingdom session artifacts
Some checks are pending
CI Smoke / host-smoke (push) Waiting to run
CI Smoke / container-smoke (push) Waiting to run
Reject generated-only commits / generated-commit-guard (push) Waiting to run

This commit is contained in:
codex 2026-11-01 23:21:28 +01:00
parent 109a90a424
commit 9e8eea5347
49 changed files with 3673 additions and 0 deletions

View file

@ -0,0 +1,104 @@
{
"adversarial_refusals": {
"detail": {
"controls": [
{
"case": "outside-tmp",
"refused": true,
"returncode": 1
},
{
"case": "existing-workspace",
"refused": true,
"returncode": 1
},
{
"case": "archive-tamper",
"refused": true,
"returncode": 1
},
{
"case": "repeat-verification",
"refused": true,
"returncode": 1
},
{
"case": "dependency-lock-tamper",
"refused": true,
"returncode": 1
},
{
"case": "reviewed-source-tamper",
"refused": true,
"returncode": 1
},
{
"case": "binary-change-before-container",
"refused": true,
"returncode": 1
}
],
"no_build_container_or_network_action_in_controls": true
},
"passed": true
},
"artifact_reproduction_current_bytes": {
"detail": {
"binary_equal": true,
"bindata_sources_each": 4,
"frontend_files_each": 628,
"public_integrity_bound_npm_packages": 1150
},
"passed": true
},
"fresh_bare_binary_asset_extraction": {
"detail": {
"all_public_options_templates_exact": true,
"architecture_approval": false,
"binary_sha256": "4df429454b0289c6df76d7fd95d41394ebc286191809349b2c1e655b6be494e4",
"embedded_file_manifest_sha256": "74a0ec278ab99ac86ee434d7620229dc4a70146efd51876a1e4738d2c9f4ffdb",
"embedded_files": 2234,
"native_admission": false,
"network": "bwrap --unshare-net",
"new_cli_flag_present": true,
"no_dynamic_interpreter": true,
"no_source_assets_libraries_or_host_config_mounted": true,
"source_locks_preserved": true
},
"passed": true
},
"frozen_packet": {
"detail": {
"exact_patch_and_map": true,
"frozen_entries": 71
},
"passed": true
},
"independent_oci_structure_and_content": {
"detail": {
"all_compressed_blobs_and_uncompressed_diffids_checked": true,
"archive_digest": "e0e74653321383e133485191f0ac5af53aafb065fb5809e20ede2808cec91539",
"complete_original_base_manifest_layers_exact": true,
"config_digest": "sha256:e9e81da43c5ea6895a95b6304337a40874e3275833be5f21fc6ffc104f79a2af",
"daemon_or_registry_used": false,
"last_layer_binary_owner_mode_and_epoch_checked": true,
"manifest_digest": "sha256:9d12779f0936b9ccdbde402a9869eaad8bb91ba724d579b6c2983e8e58dabf96",
"rootless_config_exact": true
},
"passed": true
},
"patch_pre_postimages": {
"detail": {
"exact_six_postimages": 6,
"no_other_paths_created": true
},
"passed": true
},
"reviewed_source_binding": {
"detail": {
"both_workspace_outputs_current": true,
"prior_accepted_extension_bound": true
},
"passed": true
}
}

View file

@ -0,0 +1,65 @@
{
"argv": [
"/usr/bin/bwrap",
"--unshare-net",
"--unshare-pid",
"--new-session",
"--die-with-parent",
"--ro-bind",
"/usr",
"/usr",
"--ro-bind",
"/lib",
"/lib",
"--ro-bind",
"/lib64",
"/lib64",
"--symlink",
"usr/bin",
"/bin",
"--proc",
"/proc",
"--dev",
"/dev",
"--tmpfs",
"/tmp",
"--bind",
"/tmp/apps-release-proc-argv-ndafoxcu",
"/tmp/review",
"--ro-bind",
"/home/worsch/the-custodian/docs/changes/netkingdom-target-2026-10-17/apps-forgejo-release-build-r1",
"/proposal",
"--ro-bind",
"/home/worsch/the-custodian/docs/changes/netkingdom-target-2026-10-17/forgejo-required-claim-values-review-r1",
"/prior-review",
"--ro-bind",
"/tmp/apps-forgejo-release-build-r1/source",
"/source1",
"--ro-bind",
"/tmp/apps-forgejo-release-repro-r1/source",
"/source2",
"--ro-bind",
"/tmp/apps-forgejo-release-repro-r1/image.oci.tar",
"/image.oci.tar",
"--ro-bind",
"/home/worsch/the-custodian/docs/changes/netkingdom-target-2026-10-17/apps-release-independent-review-r1/proc-boundary-test.py",
"/review-offline.py",
"--chdir",
"/tmp/review",
"--clearenv",
"--setenv",
"PATH",
"/usr/bin:/bin",
"--setenv",
"HOME",
"/tmp/home",
"--",
"/usr/bin/python3",
"-I",
"/review-offline.py"
],
"returncode": 0,
"workspace": "/tmp/apps-release-proc-argv-ndafoxcu",
"seconds": 0.86,
"owned_pid_terminal": true
}

View file

@ -0,0 +1,65 @@
{
"argv": [
"/usr/bin/bwrap",
"--unshare-net",
"--unshare-pid",
"--new-session",
"--die-with-parent",
"--ro-bind",
"/usr",
"/usr",
"--ro-bind",
"/lib",
"/lib",
"--ro-bind",
"/lib64",
"/lib64",
"--symlink",
"usr/bin",
"/bin",
"--proc",
"/proc",
"--dev",
"/dev",
"--tmpfs",
"/tmp",
"--bind",
"/tmp/apps-release-proc-boundary-50k3c4n3",
"/tmp/review",
"--ro-bind",
"/home/worsch/the-custodian/docs/changes/netkingdom-target-2026-10-17/apps-forgejo-release-build-r1",
"/proposal",
"--ro-bind",
"/home/worsch/the-custodian/docs/changes/netkingdom-target-2026-10-17/forgejo-required-claim-values-review-r1",
"/prior-review",
"--ro-bind",
"/tmp/apps-forgejo-release-build-r1/source",
"/source1",
"--ro-bind",
"/tmp/apps-forgejo-release-repro-r1/source",
"/source2",
"--ro-bind",
"/tmp/apps-forgejo-release-repro-r1/image.oci.tar",
"/image.oci.tar",
"--ro-bind",
"/home/worsch/the-custodian/docs/changes/netkingdom-target-2026-10-17/apps-release-independent-review-r1/proc-boundary-test.py",
"/review-offline.py",
"--chdir",
"/tmp/review",
"--clearenv",
"--setenv",
"PATH",
"/usr/bin:/bin",
"--setenv",
"HOME",
"/tmp/home",
"--",
"/usr/bin/python3",
"-I",
"/review-offline.py"
],
"returncode": 0,
"workspace": "/tmp/apps-release-proc-boundary-50k3c4n3",
"seconds": 0.72,
"owned_pid_terminal": true
}

View file

@ -0,0 +1,16 @@
{
"public_synthetic_fixture_only": true,
"outer_PID_and_network_namespace_prevent_real_host_visibility": true,
"shipped_sandbox": {
"returncode": 1,
"stdout": "",
"stderr": "Traceback (most recent call last):\n File \"<string>\", line 1, in <module>\n File \"/usr/lib/python3.12/pathlib.py\", line 862, in exists\n self.stat(follow_symlinks=follow_symlinks)\n File \"/usr/lib/python3.12/pathlib.py\", line 842, in stat\n return os.stat(self, follow_symlinks=follow_symlinks)\n ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\nPermissionError: [Errno 13] Permission denied: '/proc/2/root/tmp/review/outside-build-workspace-synthetic.txt'\n"
},
"same_command_with_only_unshare_pid_added": {
"returncode": 0,
"stdout": "False\nDENIED\n",
"stderr": ""
},
"shipped_sandbox_proc_parent_root_escape": false,
"unshare_pid_control_denies_fixture": true
}

View file

@ -0,0 +1,20 @@
{
"source_archive_sha256": {
"path": "/tmp/forgejo-independent-r1/forgejo-v11.0.3-clean.tar.gz",
"sha256": "1ddd8c926ca07d40436897971458ace7dcf1d3496a0813ab9e0d869edef2365c",
"matches_lock": true
},
"go_archive_sha256": {
"path": "/tmp/forgejo-independent-r1/go1.24.3.linux-amd64.tar.gz",
"sha256": "3333f6ea53afa971e9078895eaa4ac7204a8c6b5c68c10e6bc9a33e8e391bdd8",
"matches_lock": true
},
"node_archive_sha256": {
"path": "/tmp/apps-forgejo-release-build-r1/node-v22.15.0-linux-x64.tar.xz",
"sha256": "dafe2e8f82cb97de1bd10db9e2ec4c07bbf53389b0799b1e095a918951e78fd4",
"matches_lock": true
},
"official_source_pax_commit": "b81aa4d0807cc1e2d6a2fbafd0b75c46cc0ae237",
"official_node_checksum_file_contains_exact_archive": true,
"upstream_source_go_origin_independent_prior_review": "forgejo-required-claim-values-review-r1/provenance.json (accepted prior review, not re-fetched)"
}

View file

@ -0,0 +1,211 @@
#!/usr/bin/env python3
"""Independent public-only review. Execute only inside the recorded bwrap boundary."""
import hashlib
import importlib.util
import json
import os
from pathlib import Path
import shutil
import subprocess
import tarfile
P = Path('/proposal')
OUT = Path('/tmp/review')
OUT.mkdir(exist_ok=True)
ENV = {'PATH': '/usr/bin:/bin', 'HOME': '/tmp/home', 'GIT_CONFIG_NOSYSTEM': '1',
'GIT_CONFIG_GLOBAL': '/dev/null', 'GIT_TERMINAL_PROMPT': '0'}
Path('/tmp/home').mkdir(exist_ok=True)
results = {}
def digest(p):
h = hashlib.sha256()
with Path(p).open('rb') as f:
for b in iter(lambda: f.read(1024*1024), b''):
h.update(b)
return h.hexdigest()
def save():
(OUT/'results.json').write_text(json.dumps(results, indent=2, sort_keys=True)+'\n')
def checked(name, fn):
try:
value = fn()
results[name] = {'passed': True, 'detail': value}
except Exception as exc:
results[name] = {'passed': False, 'error': repr(exc)}
save()
raise
save()
def frozen():
assert digest(P/'apps-release-build-source.patch') == 'f0bcb2903592874d355e2a403de0c22aeda79b00070f30e7ea02b45106dd67fa'
assert digest(P/'SHA256SUMS.json') == 'ec499038fa9a1e612bb81ed63bd67dad2ca52a178bb7bcb89a33bb64832880bb'
entries = json.loads((P/'SHA256SUMS.json').read_text())
for name, expected in entries.items():
assert digest(P/name) == expected, name
return {'frozen_entries': len(entries), 'exact_patch_and_map': True}
checked('frozen_packet', frozen)
lock = json.loads((P/'owner-source/build/forgejo/inputs.lock.json').read_text())
def patch():
target = OUT/'patch-target'
target.mkdir()
shutil.copyfile(P/'preimages/Makefile', target/'Makefile')
for args in [['apply', '--check'], ['apply']]:
subprocess.run(['/usr/bin/git']+args+[str(P/'apps-release-build-source.patch')],
cwd=target, env=ENV, check=True, capture_output=True)
outputs = json.loads((P/'source-inventory.json').read_text())['owner_postimages']
for n, expected in outputs.items():
assert digest(target/n) == expected == digest(P/'owner-source'/n), n
actual = {str(f.relative_to(target)) for f in target.rglob('*') if f.is_file()}
assert actual == set(outputs)
return {'exact_six_postimages': len(outputs), 'no_other_paths_created': True}
checked('patch_pre_postimages', patch)
def source_outputs():
prior = json.loads(Path('/prior-review/review.json').read_text())
assert lock['patch_sha256'] == prior['candidate_patch_sha256']
assert lock['reviewed_outputs'] == prior['reviewed_outputs']
for source in [Path('/source1'), Path('/source2')]:
for n, expected in lock['lockfiles'].items():
assert digest(source/n) == expected
for record in lock['reviewed_outputs']:
assert digest(source/record['path']) == record['sha256']
return {'prior_accepted_extension_bound': True, 'both_workspace_outputs_current': True}
checked('reviewed_source_binding', source_outputs)
def current_artifacts():
expected = json.loads((P/'evidence/frontend-assets.json').read_text())
binds = json.loads((P/'evidence/binary-reproduction.json').read_text())['generated_bindata_sources_identical']
for source in [Path('/source1'), Path('/source2')]:
actual = {str(f.relative_to(source/'public/assets')): digest(f)
for f in (source/'public/assets').rglob('*') if f.is_file()}
assert actual == expected
for n, h in binds.items():
assert digest(source/n) == h
assert digest(source/'gitea') == '4df429454b0289c6df76d7fd95d41394ebc286191809349b2c1e655b6be494e4'
assert (source/'gitea').stat().st_size == 110936928
packages = json.loads(Path('/source2/package-lock.json').read_text())['packages']
for name, p in packages.items():
if name:
assert p['resolved'].startswith('https://registry.npmjs.org/')
assert p['integrity'].startswith('sha512-')
return {'frontend_files_each': len(expected), 'bindata_sources_each': len(binds),
'binary_equal': True, 'public_integrity_bound_npm_packages': len(packages)-1}
checked('artifact_reproduction_current_bytes', current_artifacts)
spec = importlib.util.spec_from_file_location('reviewed_recipe', P/'owner-source/tools/forgejo-release-build.py')
recipe = importlib.util.module_from_spec(spec)
spec.loader.exec_module(recipe)
work = OUT/'verification'
(work/'source').mkdir(parents=True)
(work/'home').mkdir()
recipe.save(work/'prepared.json', {'lock_sha256': digest(P/'owner-source/build/forgejo/inputs.lock.json'),
'module_cache': '/tmp/review/unused-cache'})
for n in list(lock['lockfiles']) + [r['path'] for r in lock['reviewed_outputs']] + ['gitea']:
f = work/'source'/n
f.parent.mkdir(parents=True, exist_ok=True)
f.symlink_to(Path('/source2')/n)
for folder in ['public', 'options', 'templates']:
(work/'source'/folder).symlink_to(Path('/source2')/folder)
def verify():
recipe.verify(work)
actual = json.loads((work/'verification.json').read_text())
expected = json.loads((P/'evidence/verification.json').read_text())
assert actual == expected
assert json.loads((work/'embedded-files.json').read_text()) == json.loads((P/'evidence/embedded-files.json').read_text())
return actual
checked('fresh_bare_binary_asset_extraction', verify)
def controls():
cases = []
def refused(name, args, expected):
p = subprocess.run(['/usr/bin/python3', '-I', str(P/'owner-source/tools/forgejo-release-build.py')]+args,
env=ENV, text=True, capture_output=True)
(OUT/(name+'.log')).write_text(p.stdout+p.stderr)
assert p.returncode != 0 and expected in p.stdout+p.stderr, name
cases.append({'case': name, 'refused': True, 'returncode': p.returncode})
refused('outside-tmp', ['prepare','--workspace','/var/new'], 'must be under /tmp')
refused('existing-workspace', ['prepare','--workspace',str(work)], 'workspace must be new')
bad = OUT/'bad-archive'; bad.write_bytes(b'public synthetic bad archive')
target = OUT/'never-created'
refused('archive-tamper', ['prepare','--workspace',str(target),'--source-archive',str(bad),
'--go-archive',str(bad),'--node-archive',str(bad)], 'digest differs')
assert not target.exists()
refused('repeat-verification', ['verify','--workspace',str(work)], 'extraction target already exists')
f = work/'source/go.mod'; f.unlink(); f.write_text('synthetic tampered lock\n')
refused('dependency-lock-tamper', ['build','--workspace',str(work)], 'digest differs')
assert not (work/'verify-go-modules-result.json').exists()
f.unlink(); f.symlink_to('/source2/go.mod')
source = work/'source'/lock['reviewed_outputs'][0]['path']
source.unlink(); source.write_text('synthetic tampered reviewed source\n')
refused('reviewed-source-tamper', ['build','--workspace',str(work)], 'digest differs')
assert not (work/'verify-go-modules-result.json').exists()
source.unlink(); source.symlink_to(Path('/source2')/lock['reviewed_outputs'][0]['path'])
f = work/'source/gitea'; f.unlink(); f.write_bytes(b'synthetic changed executable')
refused('binary-change-before-container', ['container','--workspace',str(work)], 'digest differs')
assert not (work/'container-context').exists()
assert not Path('/home/worsch').exists()
assert not Path('/var/run/docker.sock').exists()
assert os.listdir('/tmp/home') == []
return {'controls': cases, 'no_build_container_or_network_action_in_controls': True}
checked('adversarial_refusals', controls)
def oci():
proof = json.loads((P/'evidence/container-result.json').read_text())
assert digest('/image.oci.tar') == proof['archive_sha256']
with tarfile.open('/image.oci.tar') as a:
index = json.load(a.extractfile('index.json'))
assert len(index['manifests']) == 1
d = index['manifests'][0]
assert d['platform'] == {'architecture':'amd64','os':'linux'}
assert d['digest'] == proof['image_manifest_digest']
def blob(descriptor):
name = descriptor['digest']
raw = a.extractfile('blobs/sha256/'+name.split(':')[1]).read()
assert 'sha256:'+hashlib.sha256(raw).hexdigest() == name
assert len(raw) == descriptor['size']
return raw
manifest = json.loads(blob(d))
config = json.loads(blob(manifest['config']))
assert manifest['config']['digest'] == proof['config_digest']
original = json.loads((P/'owner-source/build/forgejo/runtime-base-config.json').read_text())
public_manifest = json.loads((P/'evidence/runtime-public-amd64-manifest.json').read_text())
assert manifest['layers'][:-1] == public_manifest['layers']
import gzip
import io
for i, desc in enumerate(manifest['layers']):
raw = blob(desc)
uncompressed = gzip.decompress(raw) if raw[:2] == b'\x1f\x8b' else raw
assert 'sha256:'+hashlib.sha256(uncompressed).hexdigest() == config['rootfs']['diff_ids'][i]
if i == len(manifest['layers'])-1:
with tarfile.open(fileobj=io.BytesIO(uncompressed)) as layer:
entries = layer.getmembers()
assert {m.name.lstrip('./') for m in entries} == {'app','app/gitea','app/gitea/gitea'}
binary = next(m for m in entries if m.name.lstrip('./') == 'app/gitea/gitea')
assert binary.isfile() and binary.uid == binary.gid == 0 and binary.mode == 0o755
assert hashlib.sha256(layer.extractfile(binary).read()).hexdigest() == '4df429454b0289c6df76d7fd95d41394ebc286191809349b2c1e655b6be494e4'
assert all(m.mtime == proof['container_epoch'] for m in entries)
assert config['rootfs']['diff_ids'][:-1] == original['rootfs']['diff_ids']
for key in ['User','Entrypoint','Cmd','Env','WorkingDir','Volumes']:
assert config['config'].get(key) == original['config'].get(key), key
assert config['config']['User'] == '1000:1000'
labels = dict(original['config'].get('Labels',{}))
labels.update({'org.opencontainers.image.version':lock['release_version'],
'org.opencontainers.image.revision':lock['source_commit'],
'org.railiance.source.patch.sha256':lock['patch_sha256']})
assert config['config']['Labels'] == labels
return {'archive_digest':proof['archive_sha256'],'manifest_digest':proof['image_manifest_digest'],
'config_digest':proof['config_digest'],'all_compressed_blobs_and_uncompressed_diffids_checked':True,
'complete_original_base_manifest_layers_exact':True,'rootless_config_exact':True,
'last_layer_binary_owner_mode_and_epoch_checked':True,'daemon_or_registry_used':False}
checked('independent_oci_structure_and_content', oci)
print(json.dumps(results, indent=2, sort_keys=True))

View file

@ -0,0 +1,214 @@
#!/usr/bin/env python3
"""Independent public-only review. Execute only inside the recorded bwrap boundary."""
import hashlib
import importlib.util
import json
import os
from pathlib import Path
import shutil
import subprocess
import tarfile
P = Path('/proposal')
OUT = Path('/tmp/review')
OUT.mkdir(exist_ok=True)
ENV = {'PATH': '/usr/bin:/bin', 'HOME': '/tmp/home', 'GIT_CONFIG_NOSYSTEM': '1',
'GIT_CONFIG_GLOBAL': '/dev/null', 'GIT_TERMINAL_PROMPT': '0'}
Path('/tmp/home').mkdir(exist_ok=True)
results = {}
def digest(p):
h = hashlib.sha256()
with Path(p).open('rb') as f:
for b in iter(lambda: f.read(1024*1024), b''):
h.update(b)
return h.hexdigest()
def save():
(OUT/'results.json').write_text(json.dumps(results, indent=2, sort_keys=True)+'\n')
def checked(name, fn):
try:
value = fn()
results[name] = {'passed': True, 'detail': value}
except Exception as exc:
results[name] = {'passed': False, 'error': repr(exc)}
save()
raise
save()
def frozen():
assert digest(P/'apps-release-build-source.patch') == 'f0bcb2903592874d355e2a403de0c22aeda79b00070f30e7ea02b45106dd67fa'
assert digest(P/'SHA256SUMS.json') == 'ec499038fa9a1e612bb81ed63bd67dad2ca52a178bb7bcb89a33bb64832880bb'
entries = json.loads((P/'SHA256SUMS.json').read_text())
for name, expected in entries.items():
assert digest(P/name) == expected, name
return {'frozen_entries': len(entries), 'exact_patch_and_map': True}
checked('frozen_packet', frozen)
lock = json.loads((P/'owner-source/build/forgejo/inputs.lock.json').read_text())
def patch():
target = OUT/'patch-target'
target.mkdir()
shutil.copyfile(P/'preimages/Makefile', target/'Makefile')
for args in [['apply', '--check'], ['apply']]:
subprocess.run(['/usr/bin/git']+args+[str(P/'apps-release-build-source.patch')],
cwd=target, env=ENV, check=True, capture_output=True)
outputs = json.loads((P/'source-inventory.json').read_text())['owner_postimages']
for n, expected in outputs.items():
assert digest(target/n) == expected == digest(P/'owner-source'/n), n
actual = {str(f.relative_to(target)) for f in target.rglob('*') if f.is_file()}
assert actual == set(outputs)
return {'exact_six_postimages': len(outputs), 'no_other_paths_created': True}
checked('patch_pre_postimages', patch)
def source_outputs():
prior = json.loads(Path('/prior-review/review.json').read_text())
assert lock['patch_sha256'] == prior['candidate_patch_sha256']
assert lock['reviewed_outputs'] == prior['reviewed_outputs']
for source in [Path('/source1'), Path('/source2')]:
for n, expected in lock['lockfiles'].items():
assert digest(source/n) == expected
for record in lock['reviewed_outputs']:
assert digest(source/record['path']) == record['sha256']
return {'prior_accepted_extension_bound': True, 'both_workspace_outputs_current': True}
checked('reviewed_source_binding', source_outputs)
def current_artifacts():
expected = json.loads((P/'evidence/frontend-assets.json').read_text())
binds = json.loads((P/'evidence/binary-reproduction.json').read_text())['generated_bindata_sources_identical']
for source in [Path('/source1'), Path('/source2')]:
actual = {str(f.relative_to(source/'public/assets')): digest(f)
for f in (source/'public/assets').rglob('*') if f.is_file()}
assert actual == expected
for n, h in binds.items():
assert digest(source/n) == h
assert digest(source/'gitea') == '4df429454b0289c6df76d7fd95d41394ebc286191809349b2c1e655b6be494e4'
assert (source/'gitea').stat().st_size == 110936928
packages = json.loads(Path('/source2/package-lock.json').read_text())['packages']
for name, p in packages.items():
if name:
assert p['resolved'].startswith('https://registry.npmjs.org/')
assert p['integrity'].startswith('sha512-')
return {'frontend_files_each': len(expected), 'bindata_sources_each': len(binds),
'binary_equal': True, 'public_integrity_bound_npm_packages': len(packages)-1}
checked('artifact_reproduction_current_bytes', current_artifacts)
spec = importlib.util.spec_from_file_location('reviewed_recipe', P/'owner-source/tools/forgejo-release-build.py')
recipe = importlib.util.module_from_spec(spec)
spec.loader.exec_module(recipe)
work = OUT/'verification'
(work/'source').mkdir(parents=True)
(work/'home').mkdir()
recipe.save(work/'prepared.json', {'lock_sha256': digest(P/'owner-source/build/forgejo/inputs.lock.json'),
'module_cache': '/tmp/review/unused-cache'})
for n in list(lock['lockfiles']) + [r['path'] for r in lock['reviewed_outputs']] + ['gitea']:
f = work/'source'/n
f.parent.mkdir(parents=True, exist_ok=True)
f.symlink_to(Path('/source2')/n)
for folder in ['public', 'options', 'templates']:
(work/'source'/folder).symlink_to(Path('/source2')/folder)
def verify():
recipe.verify(work)
actual = json.loads((work/'verification.json').read_text())
expected = json.loads((P/'evidence/verification.json').read_text())
assert actual == expected
assert json.loads((work/'embedded-files.json').read_text()) == json.loads((P/'evidence/embedded-files.json').read_text())
return actual
checked('fresh_bare_binary_asset_extraction', verify)
def controls():
cases = []
def refused(name, args, expected):
p = subprocess.run(['/usr/bin/python3', '-I', str(P/'owner-source/tools/forgejo-release-build.py')]+args,
env=ENV, text=True, capture_output=True)
(OUT/(name+'.log')).write_text(p.stdout+p.stderr)
assert p.returncode != 0 and expected in p.stdout+p.stderr, name
cases.append({'case': name, 'refused': True, 'returncode': p.returncode})
refused('outside-tmp', ['prepare','--workspace','/var/new'], 'must be under /tmp')
refused('existing-workspace', ['prepare','--workspace',str(work)], 'workspace must be new')
bad = OUT/'bad-archive'; bad.write_bytes(b'public synthetic bad archive')
target = OUT/'never-created'
refused('archive-tamper', ['prepare','--workspace',str(target),'--source-archive',str(bad),
'--go-archive',str(bad),'--node-archive',str(bad)], 'digest differs')
assert not target.exists()
refused('repeat-verification', ['verify','--workspace',str(work)], 'extraction target already exists')
f = work/'source/go.mod'; f.unlink(); f.write_text('synthetic tampered lock\n')
refused('dependency-lock-tamper', ['build','--workspace',str(work)], 'digest differs')
assert not (work/'verify-go-modules-result.json').exists()
f.unlink(); f.symlink_to('/source2/go.mod')
source = work/'source'/lock['reviewed_outputs'][0]['path']
source.unlink(); source.write_text('synthetic tampered reviewed source\n')
refused('reviewed-source-tamper', ['build','--workspace',str(work)], 'digest differs')
assert not (work/'verify-go-modules-result.json').exists()
source.unlink(); source.symlink_to(Path('/source2')/lock['reviewed_outputs'][0]['path'])
f = work/'source/gitea'; f.unlink(); f.write_bytes(b'synthetic changed executable')
refused('binary-change-before-container', ['container','--workspace',str(work)], 'digest differs')
assert not (work/'container-context').exists()
assert not Path('/home/worsch').exists()
assert not Path('/var/run/docker.sock').exists()
assert os.listdir('/tmp/home') == []
return {'controls': cases, 'no_build_container_or_network_action_in_controls': True}
checked('adversarial_refusals', controls)
def oci():
proof = json.loads((P/'evidence/container-result.json').read_text())
assert digest('/image.oci.tar') == proof['archive_sha256']
with tarfile.open('/image.oci.tar') as a:
index = json.load(a.extractfile('index.json'))
assert len(index['manifests']) == 1
d = index['manifests'][0]
assert d['platform'] == {'architecture':'amd64','os':'linux'}
assert d['digest'] == proof['image_manifest_digest']
def blob(descriptor):
name = descriptor['digest']
raw = a.extractfile('blobs/sha256/'+name.split(':')[1]).read()
assert 'sha256:'+hashlib.sha256(raw).hexdigest() == name
assert len(raw) == descriptor['size']
return raw
manifest = json.loads(blob(d))
config = json.loads(blob(manifest['config']))
assert manifest['config']['digest'] == proof['config_digest']
original = json.loads((P/'owner-source/build/forgejo/runtime-base-config.json').read_text())
public_manifest = json.loads((P/'evidence/runtime-public-amd64-manifest.json').read_text())
assert manifest['layers'][:-1] == public_manifest['layers']
import gzip
import io
for i, desc in enumerate(manifest['layers']):
raw = blob(desc)
uncompressed = gzip.decompress(raw) if raw[:2] == b'\x1f\x8b' else raw
assert 'sha256:'+hashlib.sha256(uncompressed).hexdigest() == config['rootfs']['diff_ids'][i]
if i == len(manifest['layers'])-1:
with tarfile.open(fileobj=io.BytesIO(uncompressed)) as layer:
entries = layer.getmembers()
assert {m.name.lstrip('./') for m in entries} == {'app','app/gitea','app/gitea/gitea'}
binary = next(m for m in entries if m.name.lstrip('./') == 'app/gitea/gitea')
assert binary.isfile() and binary.uid == binary.gid == 0 and binary.mode == 0o755
assert hashlib.sha256(layer.extractfile(binary).read()).hexdigest() == '4df429454b0289c6df76d7fd95d41394ebc286191809349b2c1e655b6be494e4'
# BuildKit rewrites future timestamps down to the epoch;
# older source/base timestamps are correctly preserved.
assert binary.mtime == proof['source_epoch']
assert all(m.mtime <= proof['container_epoch'] for m in entries)
assert config['rootfs']['diff_ids'][:-1] == original['rootfs']['diff_ids']
for key in ['User','Entrypoint','Cmd','Env','WorkingDir','Volumes']:
assert config['config'].get(key) == original['config'].get(key), key
assert config['config']['User'] == '1000:1000'
labels = dict(original['config'].get('Labels',{}))
labels.update({'org.opencontainers.image.version':lock['release_version'],
'org.opencontainers.image.revision':lock['source_commit'],
'org.railiance.source.patch.sha256':lock['patch_sha256']})
assert config['config']['Labels'] == labels
return {'archive_digest':proof['archive_sha256'],'manifest_digest':proof['image_manifest_digest'],
'config_digest':proof['config_digest'],'all_compressed_blobs_and_uncompressed_diffids_checked':True,
'complete_original_base_manifest_layers_exact':True,'rootless_config_exact':True,
'last_layer_binary_owner_mode_and_epoch_checked':True,'daemon_or_registry_used':False}
checked('independent_oci_structure_and_content', oci)
print(json.dumps(results, indent=2, sort_keys=True))

View file

@ -0,0 +1,7 @@
{
"state": "complete",
"verdict": "changes-required",
"all_owned_handles_terminal": true,
"live_handles": [],
"source_integrated": false
}

View file

@ -0,0 +1,37 @@
The exact six-path Apps build-source r2 is accepted for source integration.
Patch SHA256 is
`b7ad8f8fd908532800f4e7eb0f7ad85d77e21a0b729cb5115ade3d5fe3e4acd8`.
All postimages match, and the only source change from the reviewed r1 is adding
`--unshare-pid` to the build sandbox. Locks, application extension, release
version, build commands, runtime base and artifact handling are unchanged.
The exact r2 `sandbox()` closes APPSBUILD-R1-F01. In an outer PID/network-isolated
public-only test, the exact r1 sandbox reads a synthetic unrelated process argv
canary; the exact r2 sandbox returns `DENIED`. Namespace inode checks confirm r2
creates a new PID namespace and r1 shares its parent's. The environment remains
closed, the working directory is correct, host HOME and Docker socket are absent,
and the synthetic helper exits normally. No real host process arguments,
credentials, native endpoint, Docker daemon, registry or network were accessed.
The initial r2 reviewer harness assumed the Python child would be PID1. Bubblewrap
correctly uses a PID1 reaper and the child is PID2. That failure and original
script are retained. The corrected test verifies the namespace inode differs,
which directly checks isolation without assuming an implementation-specific PID.
No candidate correction or additional build success is attributed to this
reviewer-only refinement.
The r1 source packet and independent changes-required review remain frozen and
hash-exact. Their complete frontend, bindata, static executable and OCI artifact
proof remains evidence for the original r1 build profile. No full r2 frontend,
backend or image build was run, and no reproduced r2 binary/image is claimed.
The bounded namespace correction does not change compiler/build/artifact inputs;
no new evidence gap warrants another expensive build for source integration.
Source integration acceptance supplies no formal owner assent, architecture
acceptance, operational image admission or deployment authority. All operational
gaps listed in the frozen r1 review remain: authenticated Access Engine decision,
private runtime secret input, current operation/inverse sessions, authenticated
journal, persisted application-state proof, writer exclusion, exact re-freeze,
browser/group/login probes, capacity and rollout. Canonical owner edits and any
publication remain with the root assignment; this reviewer changed only its own
review packets and public /tmp test workspaces.

View file

@ -0,0 +1,14 @@
{
"README.md": "855805fc29c204052e1c5aa48f5531e547434bffbe72bcc9ba836be7ce278777",
"execution-attempt1.json": "df7fd4535c5c58f3285cf6258f1bf3f0dd5c398a0c973238f9ee1fd04042d09b",
"execution.json": "e0c9d4124107927274076df039d5651faa5a0177df1d9e0e20577fce612d7cc1",
"inputs.json": "9f4fdddccdfe5df01e93ff96895f411b4bfde42b47990de4d9a648abbcd6740f",
"namespace-review-attempt1.log": "eff8c6f66f4958f1fe19ae1a2f7d60ef2cc14fcacb8863fde5e27b0fbd31adbe",
"namespace-review.log": "232827ebb83148b32c67d81b943011f955c0a279604b6c7f764737d22e08c1e5",
"probe-records.json": "8dafa7916a75f57c4c367f02c2626bd4a784c07d73ded1ca72ed6d1174571945",
"results.json": "232827ebb83148b32c67d81b943011f955c0a279604b6c7f764737d22e08c1e5",
"review-namespace-refinement-attempt1.py": "5b3e0afc6e114457371e3914ba1f5ebf3b81e2753eb214e39dba3c21ed164d44",
"review-namespace-refinement.py": "b7526163dcd4bc68bec2f05ae9712134a833a740e6b7696c02e28a95599b07c6",
"review.json": "6f016d53a7ec9ece2f9da9686e76127c52d17066f2b3d371628832ac9537ac5c",
"status.json": "1f0bd85f6283d6da8a212852ce400e5d8a36fe457eced76805356423f56c0c64"
}

View file

@ -0,0 +1,59 @@
{
"argv": [
"/usr/bin/bwrap",
"--unshare-net",
"--unshare-pid",
"--new-session",
"--die-with-parent",
"--ro-bind",
"/usr",
"/usr",
"--ro-bind",
"/lib",
"/lib",
"--ro-bind",
"/lib64",
"/lib64",
"--symlink",
"usr/bin",
"/bin",
"--proc",
"/proc",
"--dev",
"/dev",
"--tmpfs",
"/tmp",
"--bind",
"/tmp/apps-release-r2-independent-ponkb90l",
"/tmp/review",
"--ro-bind",
"/home/worsch/the-custodian/docs/changes/netkingdom-target-2026-10-17/apps-forgejo-release-build-r1",
"/proposal",
"--ro-bind",
"/home/worsch/the-custodian/docs/changes/netkingdom-target-2026-10-17/apps-forgejo-release-build-r2",
"/proposal2",
"--ro-bind",
"/home/worsch/the-custodian/docs/changes/netkingdom-target-2026-10-17/apps-release-independent-review-r1",
"/r1-review",
"--ro-bind",
"/home/worsch/the-custodian/docs/changes/netkingdom-target-2026-10-17/apps-release-independent-review-r2/review-namespace-refinement.py",
"/review.py",
"--chdir",
"/tmp/review",
"--clearenv",
"--setenv",
"PATH",
"/usr/bin:/bin",
"--setenv",
"HOME",
"/tmp/home",
"--",
"/usr/bin/python3",
"-I",
"/review.py"
],
"returncode": 1,
"workspace": "/tmp/apps-release-r2-independent-ponkb90l",
"seconds": 0.29,
"owned_pid_terminal": true
}

View file

@ -0,0 +1,59 @@
{
"argv": [
"/usr/bin/bwrap",
"--unshare-net",
"--unshare-pid",
"--new-session",
"--die-with-parent",
"--ro-bind",
"/usr",
"/usr",
"--ro-bind",
"/lib",
"/lib",
"--ro-bind",
"/lib64",
"/lib64",
"--symlink",
"usr/bin",
"/bin",
"--proc",
"/proc",
"--dev",
"/dev",
"--tmpfs",
"/tmp",
"--bind",
"/tmp/apps-release-r2-independent-attempt2-yd5yg8m8",
"/tmp/review",
"--ro-bind",
"/home/worsch/the-custodian/docs/changes/netkingdom-target-2026-10-17/apps-forgejo-release-build-r1",
"/proposal",
"--ro-bind",
"/home/worsch/the-custodian/docs/changes/netkingdom-target-2026-10-17/apps-forgejo-release-build-r2",
"/proposal2",
"--ro-bind",
"/home/worsch/the-custodian/docs/changes/netkingdom-target-2026-10-17/apps-release-independent-review-r1",
"/r1-review",
"--ro-bind",
"/home/worsch/the-custodian/docs/changes/netkingdom-target-2026-10-17/apps-release-independent-review-r2/review-namespace-refinement.py",
"/review.py",
"--chdir",
"/tmp/review",
"--clearenv",
"--setenv",
"PATH",
"/usr/bin:/bin",
"--setenv",
"HOME",
"/tmp/home",
"--",
"/usr/bin/python3",
"-I",
"/review.py"
],
"returncode": 0,
"workspace": "/tmp/apps-release-r2-independent-attempt2-yd5yg8m8",
"seconds": 0.51,
"owned_pid_terminal": true
}

View file

@ -0,0 +1,11 @@
{
"apps-release-build-source.patch": "b7ad8f8fd908532800f4e7eb0f7ad85d77e21a0b729cb5115ade3d5fe3e4acd8",
"failed-patch-generation-r1.patch": "64c86ac86cf78715535b096cbf47204586a5c26b7e9c993cce2c136cb5ae2cee",
"owner-source/Makefile": "572d36e2dd3dee6321a5f6c4726f83991031672be5eb3480ae6173f8ce50ccdd",
"owner-source/build/forgejo/README.md": "c3d37b8e62a99c351b8630a31f875fb8f4afbf54ec2488460066c88148f76fa8",
"owner-source/build/forgejo/inputs.lock.json": "29f329b204a2a5f72084b50d59e8445486ff4799450097c6f3908c74e87a233a",
"owner-source/build/forgejo/required-claim-values.patch": "f2788b3f2bf84dbc0f94e232b6c9614a864b8123c09f9e44703d50d5e1b53257",
"owner-source/build/forgejo/runtime-base-config.json": "bc5a3df111729582faadebd01d126ba769e2b65d0c62f306f6bc79f4e562452b",
"owner-source/tools/forgejo-release-build.py": "7e28d9bd5adefaece96eb1d31a23e128ec8f448958e45d22467bf7acf476a9ba",
"source-refinement.json": "1e96b866284908299b6363c0ddd1363181bd8513ae63eb178967f636de008972"
}

View file

@ -0,0 +1,119 @@
{
"r1": {
"argv": [
"bwrap",
"--unshare-net",
"--ro-bind",
"/usr",
"/usr",
"--ro-bind",
"/lib",
"/lib",
"--ro-bind",
"/lib64",
"/lib64",
"--symlink",
"usr/bin",
"/bin",
"--proc",
"/proc",
"--dev",
"/dev",
"--tmpfs",
"/tmp",
"--bind",
"/tmp/review/sandbox-work",
"/tmp/review/sandbox-work",
"--ro-bind",
"/tmp/review/sandbox-work/cache",
"/tmp/review/sandbox-work/cache",
"--chdir",
"/tmp/review/sandbox-work/source",
"--",
"env",
"-i",
"PATH=/usr/bin:/bin",
"HOME=/tmp/review/sandbox-work/empty-home",
"GOMODCACHE=/tmp/review/sandbox-work/cache",
"LC_ALL=C",
"/usr/bin/python3",
"-I",
"-c",
"import pathlib,sys,os,json; p=pathlib.Path(sys.argv[1]); print(json.dumps({\"parent_argv\": p.read_text() if p.exists() else \"DENIED\", \"self_pid\":os.getpid(),\"pid_namespace\":os.readlink(\"/proc/self/ns/pid\"),\"cwd\":os.getcwd(),\"host_home_present\":pathlib.Path(\"/home/worsch\").exists(),\"docker_socket_present\":pathlib.Path(\"/var/run/docker.sock\").exists(),\"environment\":dict(os.environ)}))",
"/proc/5/cmdline"
],
"result": {
"parent_argv": "/usr/bin/python3\u0000-I\u0000-c\u0000import sys;sys.stdin.read()\u0000PUBLIC-R2-SYNTHETIC-ARGV-CANARY\u0000",
"self_pid": 7,
"pid_namespace": "pid:[4026532379]",
"cwd": "/tmp/review/sandbox-work/source",
"host_home_present": false,
"docker_socket_present": false,
"environment": {
"PATH": "/usr/bin:/bin",
"HOME": "/tmp/review/sandbox-work/empty-home",
"GOMODCACHE": "/tmp/review/sandbox-work/cache",
"LC_ALL": "C"
}
}
},
"r2": {
"argv": [
"bwrap",
"--unshare-net",
"--unshare-pid",
"--ro-bind",
"/usr",
"/usr",
"--ro-bind",
"/lib",
"/lib",
"--ro-bind",
"/lib64",
"/lib64",
"--symlink",
"usr/bin",
"/bin",
"--proc",
"/proc",
"--dev",
"/dev",
"--tmpfs",
"/tmp",
"--bind",
"/tmp/review/sandbox-work",
"/tmp/review/sandbox-work",
"--ro-bind",
"/tmp/review/sandbox-work/cache",
"/tmp/review/sandbox-work/cache",
"--chdir",
"/tmp/review/sandbox-work/source",
"--",
"env",
"-i",
"PATH=/usr/bin:/bin",
"HOME=/tmp/review/sandbox-work/empty-home",
"GOMODCACHE=/tmp/review/sandbox-work/cache",
"LC_ALL=C",
"/usr/bin/python3",
"-I",
"-c",
"import pathlib,sys,os,json; p=pathlib.Path(sys.argv[1]); print(json.dumps({\"parent_argv\": p.read_text() if p.exists() else \"DENIED\", \"self_pid\":os.getpid(),\"pid_namespace\":os.readlink(\"/proc/self/ns/pid\"),\"cwd\":os.getcwd(),\"host_home_present\":pathlib.Path(\"/home/worsch\").exists(),\"docker_socket_present\":pathlib.Path(\"/var/run/docker.sock\").exists(),\"environment\":dict(os.environ)}))",
"/proc/5/cmdline"
],
"result": {
"parent_argv": "DENIED",
"self_pid": 2,
"pid_namespace": "pid:[4026532441]",
"cwd": "/tmp/review/sandbox-work/source",
"host_home_present": false,
"docker_socket_present": false,
"environment": {
"PATH": "/usr/bin:/bin",
"HOME": "/tmp/review/sandbox-work/empty-home",
"GOMODCACHE": "/tmp/review/sandbox-work/cache",
"LC_ALL": "C"
}
}
}
}

View file

@ -0,0 +1,66 @@
"""Bounded exact r2 review, run only in outer public-only PID/net bwrap."""
from pathlib import Path
import hashlib, importlib.util, json, os, shutil, subprocess
out=Path('/tmp/review');results={}
def sha(p):return hashlib.sha256(Path(p).read_bytes()).hexdigest()
old=Path('/proposal');new=Path('/proposal2')
assert sha(new/'apps-release-build-source.patch')=='b7ad8f8fd908532800f4e7eb0f7ad85d77e21a0b729cb5115ade3d5fe3e4acd8'
assert sha(old/'apps-release-build-source.patch')=='f0bcb2903592874d355e2a403de0c22aeda79b00070f30e7ea02b45106dd67fa'
assert sha('/r1-review/SHA256SUMS.json')=='9a2266ffa638ce771a5cc014e93b53c8e465270d351c502cf42c9c586409f7c9'
for root in [old,Path('/r1-review')]:
for name,h in json.loads((root/'SHA256SUMS.json').read_text()).items():assert sha(root/name)==h
manifest=json.loads((new/'source-refinement.json').read_text())
expected=manifest['owner_postimages'];paths={str(p.relative_to(new/'owner-source')) for p in (new/'owner-source').rglob('*') if p.is_file()}
assert paths==set(expected) and len(paths)==6
changed=[]
for n,h in expected.items():
assert sha(new/'owner-source'/n)=='{}'.format(h.removeprefix('sha256:'))
if (old/'owner-source'/n).read_bytes()!=(new/'owner-source'/n).read_bytes():changed.append(n)
assert changed==['tools/forgejo-release-build.py']
before=(old/'owner-source/tools/forgejo-release-build.py').read_bytes()
after=(new/'owner-source/tools/forgejo-release-build.py').read_bytes()
assert before.count(b"return ['bwrap','--unshare-net','--ro-bind'")==1
assert before.replace(b"return ['bwrap','--unshare-net','--ro-bind'",b"return ['bwrap','--unshare-net','--unshare-pid','--ro-bind'")==after
results['exact_refinement']={'old_review_and_inputs_preserved':True,'six_paths':6,'only_change':'sandbox adds --unshare-pid','unchanged_locks_archives_patch_release_and_runtime_base':True}
env={'PATH':'/usr/bin:/bin','HOME':'/tmp/home','GIT_CONFIG_NOSYSTEM':'1','GIT_CONFIG_GLOBAL':'/dev/null'}
Path('/tmp/home').mkdir()
target=out/'patch';target.mkdir();shutil.copyfile(old/'preimages/Makefile',target/'Makefile')
for args in [['apply','--check'],['apply']]:
p=subprocess.run(['/usr/bin/git']+args+[str(new/'apps-release-build-source.patch')],cwd=target,env=env,capture_output=True,text=True)
assert p.returncode==0,p.stderr
assert {str(p.relative_to(target)) for p in target.rglob('*') if p.is_file()}==paths
for n,h in expected.items():assert sha(target/n)==h.removeprefix('sha256:')
results['patch_exact_six_postimages']=True
def load(name,path):
s=importlib.util.spec_from_file_location(name,path);m=importlib.util.module_from_spec(s);s.loader.exec_module(m);return m
r1=load('r1',old/'owner-source/tools/forgejo-release-build.py')
r2=load('r2',new/'owner-source/tools/forgejo-release-build.py')
work=out/'sandbox-work';(work/'source').mkdir(parents=True);(work/'cache').mkdir()
inner={'PATH':'/usr/bin:/bin','HOME':str(work/'empty-home'),'GOMODCACHE':str(work/'cache')}
helper=subprocess.Popen(['/usr/bin/python3','-I','-c','import sys;sys.stdin.read()','PUBLIC-R2-SYNTHETIC-ARGV-CANARY'],stdin=subprocess.PIPE,env=env)
probe=['/usr/bin/python3','-I','-c',
'import pathlib,sys,os,json; p=pathlib.Path(sys.argv[1]); print(json.dumps({"parent_argv": p.read_text() if p.exists() else "DENIED", "self_pid":os.getpid(),"cwd":os.getcwd(),"host_home_present":pathlib.Path("/home/worsch").exists(),"docker_socket_present":pathlib.Path("/var/run/docker.sock").exists(),"environment":dict(os.environ)}))',
'/proc/'+str(helper.pid)+'/cmdline']
try:
records={}
for name,m in [('r1',r1),('r2',r2)]:
args=m.sandbox(work,inner)+probe
p=subprocess.run(args,env=env,capture_output=True,text=True)
assert p.returncode==0,(name,p.stderr)
records[name]={'argv':args,'result':json.loads(p.stdout)}
assert 'PUBLIC-R2-SYNTHETIC-ARGV-CANARY' in records['r1']['result']['parent_argv']
assert records['r2']['result']['parent_argv']=='DENIED'
assert records['r2']['result']['self_pid']==1
assert not records['r2']['result']['host_home_present']
assert not records['r2']['result']['docker_socket_present']
assert records['r2']['result']['cwd']==str(work/'source')
assert records['r2']['result']['environment']==inner
results['namespace_fix']=records
finally:
helper.stdin.close();helper.wait(timeout=10)
results['synthetic_helper_terminal_returncode']=helper.returncode
results['full_r2_build_or_image_build_performed']=False
results['r1_artifact_evidence_retains_r1_profile']=True
results['APPSBUILD-R1-F01_closed_for_exact_r2']=True
(out/'results.json').write_text(json.dumps(results,indent=2,sort_keys=True)+'\n')
print(json.dumps(results,indent=2,sort_keys=True))

View file

@ -0,0 +1,68 @@
"""Bounded exact r2 review, run only in outer public-only PID/net bwrap."""
from pathlib import Path
import hashlib, importlib.util, json, os, shutil, subprocess
out=Path('/tmp/review');results={}
def sha(p):return hashlib.sha256(Path(p).read_bytes()).hexdigest()
old=Path('/proposal');new=Path('/proposal2')
assert sha(new/'apps-release-build-source.patch')=='b7ad8f8fd908532800f4e7eb0f7ad85d77e21a0b729cb5115ade3d5fe3e4acd8'
assert sha(old/'apps-release-build-source.patch')=='f0bcb2903592874d355e2a403de0c22aeda79b00070f30e7ea02b45106dd67fa'
assert sha('/r1-review/SHA256SUMS.json')=='9a2266ffa638ce771a5cc014e93b53c8e465270d351c502cf42c9c586409f7c9'
for root in [old,Path('/r1-review')]:
for name,h in json.loads((root/'SHA256SUMS.json').read_text()).items():assert sha(root/name)==h
manifest=json.loads((new/'source-refinement.json').read_text())
expected=manifest['owner_postimages'];paths={str(p.relative_to(new/'owner-source')) for p in (new/'owner-source').rglob('*') if p.is_file()}
assert paths==set(expected) and len(paths)==6
changed=[]
for n,h in expected.items():
assert sha(new/'owner-source'/n)=='{}'.format(h.removeprefix('sha256:'))
if (old/'owner-source'/n).read_bytes()!=(new/'owner-source'/n).read_bytes():changed.append(n)
assert changed==['tools/forgejo-release-build.py']
before=(old/'owner-source/tools/forgejo-release-build.py').read_bytes()
after=(new/'owner-source/tools/forgejo-release-build.py').read_bytes()
assert before.count(b"return ['bwrap','--unshare-net','--ro-bind'")==1
assert before.replace(b"return ['bwrap','--unshare-net','--ro-bind'",b"return ['bwrap','--unshare-net','--unshare-pid','--ro-bind'")==after
results['exact_refinement']={'old_review_and_inputs_preserved':True,'six_paths':6,'only_change':'sandbox adds --unshare-pid','unchanged_locks_archives_patch_release_and_runtime_base':True}
env={'PATH':'/usr/bin:/bin','HOME':'/tmp/home','GIT_CONFIG_NOSYSTEM':'1','GIT_CONFIG_GLOBAL':'/dev/null'}
Path('/tmp/home').mkdir()
target=out/'patch';target.mkdir();shutil.copyfile(old/'preimages/Makefile',target/'Makefile')
for args in [['apply','--check'],['apply']]:
p=subprocess.run(['/usr/bin/git']+args+[str(new/'apps-release-build-source.patch')],cwd=target,env=env,capture_output=True,text=True)
assert p.returncode==0,p.stderr
assert {str(p.relative_to(target)) for p in target.rglob('*') if p.is_file()}==paths
for n,h in expected.items():assert sha(target/n)==h.removeprefix('sha256:')
results['patch_exact_six_postimages']=True
def load(name,path):
s=importlib.util.spec_from_file_location(name,path);m=importlib.util.module_from_spec(s);s.loader.exec_module(m);return m
r1=load('r1',old/'owner-source/tools/forgejo-release-build.py')
r2=load('r2',new/'owner-source/tools/forgejo-release-build.py')
work=out/'sandbox-work';(work/'source').mkdir(parents=True);(work/'cache').mkdir()
inner={'PATH':'/usr/bin:/bin','HOME':str(work/'empty-home'),'GOMODCACHE':str(work/'cache'),'LC_ALL':'C'}
helper=subprocess.Popen(['/usr/bin/python3','-I','-c','import sys;sys.stdin.read()','PUBLIC-R2-SYNTHETIC-ARGV-CANARY'],stdin=subprocess.PIPE,env=env)
probe=['/usr/bin/python3','-I','-c',
'import pathlib,sys,os,json; p=pathlib.Path(sys.argv[1]); print(json.dumps({"parent_argv": p.read_text() if p.exists() else "DENIED", "self_pid":os.getpid(),"pid_namespace":os.readlink("/proc/self/ns/pid"),"cwd":os.getcwd(),"host_home_present":pathlib.Path("/home/worsch").exists(),"docker_socket_present":pathlib.Path("/var/run/docker.sock").exists(),"environment":dict(os.environ)}))',
'/proc/'+str(helper.pid)+'/cmdline']
try:
records={}
for name,m in [('r1',r1),('r2',r2)]:
args=m.sandbox(work,inner)+probe
p=subprocess.run(args,env=env,capture_output=True,text=True)
assert p.returncode==0,(name,p.stderr)
records[name]={'argv':args,'result':json.loads(p.stdout)}
(out/'probe-records.json').write_text(json.dumps(records,indent=2)+'\n')
assert 'PUBLIC-R2-SYNTHETIC-ARGV-CANARY' in records['r1']['result']['parent_argv']
assert records['r2']['result']['parent_argv']=='DENIED'
assert records['r1']['result']['pid_namespace']==os.readlink('/proc/self/ns/pid')
assert records['r2']['result']['pid_namespace']!=os.readlink('/proc/self/ns/pid')
assert not records['r2']['result']['host_home_present']
assert not records['r2']['result']['docker_socket_present']
assert records['r2']['result']['cwd']==str(work/'source')
assert records['r2']['result']['environment']==inner
results['namespace_fix']=records
finally:
helper.stdin.close();helper.wait(timeout=10)
results['synthetic_helper_terminal_returncode']=helper.returncode
results['full_r2_build_or_image_build_performed']=False
results['r1_artifact_evidence_retains_r1_profile']=True
results['APPSBUILD-R1-F01_closed_for_exact_r2']=True
(out/'results.json').write_text(json.dumps(results,indent=2,sort_keys=True)+'\n')
print(json.dumps(results,indent=2,sort_keys=True))

View file

@ -0,0 +1,7 @@
{
"state": "complete",
"verdict": "accept",
"source_integration_accepted": true,
"all_owned_handles_terminal": true,
"live_handles": []
}

View file

@ -0,0 +1,426 @@
{
"repo_slug": "railiance-apps",
"repo_path": "/home/worsch/railiance-apps",
"source_revision": "c29408ae6747158a639dc876e6d7492680675658",
"source_revision_reason": null,
"issues": [
{
"severity": "WARN",
"check_id": "C-35",
"message": "Repo Manager warning: .repo-classification.yaml: category is project but slug is not prj-*; not every category:project is a prj- repo",
"file_path": ".repo-classification.yaml",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-35",
"message": "Repo Manager missing: README.md: README.md is required for flavor project",
"file_path": "README.md",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-35",
"message": "Repo Manager warning: workplans/: repository uses more than one workplan prefix: ['RAILIANCE-WP', 'RAPPS-WP']",
"file_path": "workplans/",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-35",
"message": "Repo Manager contradictory: workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-1: task id 'RAILIANCE-WP-0004-I01' is not accepted by the canon kind registry",
"file_path": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-1",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-35",
"message": "Repo Manager contradictory: workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-2: task id 'RAILIANCE-WP-0004-I02' is not accepted by the canon kind registry",
"file_path": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-2",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-35",
"message": "Repo Manager contradictory: workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-3: task id 'RAILIANCE-WP-0004-I03' is not accepted by the canon kind registry",
"file_path": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-3",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-35",
"message": "Repo Manager contradictory: workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-4: task id 'RAILIANCE-WP-0004-I04' is not accepted by the canon kind registry",
"file_path": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-4",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-35",
"message": "Repo Manager contradictory: workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-5: task id 'RAILIANCE-WP-0004-I05' is not accepted by the canon kind registry",
"file_path": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-5",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-35",
"message": "Repo Manager contradictory: workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-6: task id 'RAILIANCE-WP-0004-I06' is not accepted by the canon kind registry",
"file_path": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-6",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-35",
"message": "Repo Manager contradictory: workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-7: task id 'RAILIANCE-WP-0004-I07' is not accepted by the canon kind registry",
"file_path": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-7",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-31",
"message": "[workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md] id 'RAILIANCE-WP-0004-I01' matches no kind in the canon work-record type registry \u2014 unregistered species become sidetracks needing manual reintegration (work-record-types_v0.1)",
"file_path": "",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-31",
"message": "[workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md] id 'RAILIANCE-WP-0004-I02' matches no kind in the canon work-record type registry \u2014 unregistered species become sidetracks needing manual reintegration (work-record-types_v0.1)",
"file_path": "",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-31",
"message": "[workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md] id 'RAILIANCE-WP-0004-I03' matches no kind in the canon work-record type registry \u2014 unregistered species become sidetracks needing manual reintegration (work-record-types_v0.1)",
"file_path": "",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-31",
"message": "[workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md] id 'RAILIANCE-WP-0004-I04' matches no kind in the canon work-record type registry \u2014 unregistered species become sidetracks needing manual reintegration (work-record-types_v0.1)",
"file_path": "",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-31",
"message": "[workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md] id 'RAILIANCE-WP-0004-I05' matches no kind in the canon work-record type registry \u2014 unregistered species become sidetracks needing manual reintegration (work-record-types_v0.1)",
"file_path": "",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-31",
"message": "[workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md] id 'RAILIANCE-WP-0004-I06' matches no kind in the canon work-record type registry \u2014 unregistered species become sidetracks needing manual reintegration (work-record-types_v0.1)",
"file_path": "",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-31",
"message": "[workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md] id 'RAILIANCE-WP-0004-I07' matches no kind in the canon work-record type registry \u2014 unregistered species become sidetracks needing manual reintegration (work-record-types_v0.1)",
"file_path": "",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-33",
"message": "WORK-RECORDS.md is missing or stale \u2014 regenerate via fix-consistency (CUST-WP-0061-T04 generated work-record index)",
"file_path": "WORK-RECORDS.md",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": true
},
{
"severity": "WARN",
"check_id": "C-39",
"message": "Wait task 'RAPPS-WP-0015-T04' in workplan 'RAPPS-WP-0015' has neither depends_on, needs_human: true, blocked_on: message-from:\u2026 nor wait_until \u2014 unqualified wait",
"file_path": "workplans/RAPPS-WP-0015-coulomb-personal-content-release.md#RAPPS-WP-0015-T04",
"db_id": "",
"file_value": "wait",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-20",
"message": "Workplan dependency target 'KEY-WP-0038' is not linked to State Hub",
"file_path": "workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md",
"db_id": "",
"file_value": "KEY-WP-0038",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-39",
"message": "Human wait task 'RAPPS-WP-0016-T04' in workplan 'RAPPS-WP-0016' has needs_human: true without decision_id \u2014 unrouted human gate",
"file_path": "workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md#RAPPS-WP-0016-T04",
"db_id": "",
"file_value": "needs_human: true",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-11",
"message": "Derived task 'RAPPS-WP-0016-T06' is absent from this projection",
"file_path": "workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md#RAPPS-WP-0016-T06",
"db_id": "08ab8921-7801-5309-b84b-bc2a3ceea1e4",
"file_value": "",
"db_value": "",
"fixable": true
},
{
"severity": "WARN",
"check_id": "C-11",
"message": "Derived task 'RAPPS-WP-0016-T07' is absent from this projection",
"file_path": "workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md#RAPPS-WP-0016-T07",
"db_id": "786d6584-6db1-5a10-9324-d7b94db0df94",
"file_value": "",
"db_value": "",
"fixable": true
},
{
"severity": "WARN",
"check_id": "C-11",
"message": "Derived task 'RAPPS-WP-0016-T08' is absent from this projection",
"file_path": "workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md#RAPPS-WP-0016-T08",
"db_id": "4ab8a5e7-ab32-5ee2-aaf2-6da246d1b0c8",
"file_value": "",
"db_value": "",
"fixable": true
},
{
"severity": "WARN",
"check_id": "C-11",
"message": "Derived task 'RAPPS-WP-0016-T09' is absent from this projection",
"file_path": "workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md#RAPPS-WP-0016-T09",
"db_id": "d3804638-c73d-5b9f-a456-4262f62f9e6b",
"file_value": "",
"db_value": "",
"fixable": true
},
{
"severity": "WARN",
"check_id": "C-20",
"message": "Workplan dependency target 'RPF-WP-0058' is not linked to State Hub",
"file_path": "workplans/RAPPS-WP-0017-reuse-private-reader-release.md",
"db_id": "",
"file_value": "RPF-WP-0058",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-20",
"message": "Workplan dependency target 'REUSE-WP-0025' is not linked to State Hub",
"file_path": "workplans/RAPPS-WP-0017-reuse-private-reader-release.md",
"db_id": "",
"file_value": "REUSE-WP-0025",
"db_value": "",
"fixable": false
},
{
"severity": "INFO",
"check_id": "C-08",
"message": "Retired DB workstream 'railiance-wp-0006@retired-20260826' (id=1960b22b\u2026, status=finished) has no backing workplan file \u2014 projection tombstone, not live work",
"file_path": "",
"db_id": "1960b22b-82ae-4b67-9fff-397bd38bdd65",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "INFO",
"check_id": "C-08",
"message": "Retired DB workstream 'railiance-wp-0005@retired-20260826' (id=685f1c18\u2026, status=finished) has no backing workplan file \u2014 projection tombstone, not live work",
"file_path": "",
"db_id": "685f1c18-33c0-400d-a2b1-e1dae0f27c3e",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "INFO",
"check_id": "C-08",
"message": "Retired DB workstream 'railiance-wp-0009@retired-20260826' (id=21c3fcdc\u2026, status=finished) has no backing workplan file \u2014 projection tombstone, not live work",
"file_path": "",
"db_id": "21c3fcdc-f014-4858-8028-0ac3038212b7",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "INFO",
"check_id": "C-08",
"message": "Retired DB workstream 'railiance-wp-0011@retired-20260826' (id=98cf42ae\u2026, status=finished) has no backing workplan file \u2014 projection tombstone, not live work",
"file_path": "",
"db_id": "98cf42ae-9b64-4736-97e1-bae325ded1f9",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "INFO",
"check_id": "C-08",
"message": "Retired DB workstream 'railiance-wp-0008@retired-20260826' (id=41b9deea\u2026, status=finished) has no backing workplan file \u2014 projection tombstone, not live work",
"file_path": "",
"db_id": "41b9deea-a935-4372-8916-b3981336f597",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "INFO",
"check_id": "C-08",
"message": "Retired DB workstream 'railiance-wp-0018@retired-20260826' (id=1b9af4e8\u2026, status=finished) has no backing workplan file \u2014 projection tombstone, not live work",
"file_path": "",
"db_id": "1b9af4e8-7579-5141-837b-c736b85204a0",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "INFO",
"check_id": "C-08",
"message": "Retired DB workstream 'railiance-wp-0007@retired-20260826' (id=7da18dd8\u2026, status=finished) has no backing workplan file \u2014 projection tombstone, not live work",
"file_path": "",
"db_id": "7da18dd8-76b9-4a70-b9d7-de541afc65c0",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "INFO",
"check_id": "C-08",
"message": "Retired DB workstream 'railiance-wp-0010@retired-20260826' (id=a4f301bb\u2026, status=finished) has no backing workplan file \u2014 projection tombstone, not live work",
"file_path": "",
"db_id": "a4f301bb-3f49-450a-8dbd-5cf6a16b8e0f",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-28",
"message": "2 unread inbox message(s) older than 3 day(s): the-custodian:23172cb2, the-custodian:51e9eace",
"file_path": "",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-28",
"message": "2 unread message(s) lack thread_id for supersession tracking: the-custodian:23172cb2, the-custodian:51e9eace",
"file_path": "",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-26",
"message": "Workplan id 'RAIL-AP-WP-0001' uses prefix 'RAIL-AP-WP' but repo canonical prefix is 'RAPPS-WP' \u2014 new plans must conform",
"file_path": "workplans/archived/260605-RAIL-AP-WP-0001-gitea-container-registry.md",
"db_id": "",
"file_value": "RAIL-AP-WP-0001",
"db_value": "RAPPS-WP",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-26",
"message": "Workplan id 'RAILIANCE-WP-0002' uses prefix 'RAILIANCE-WP' but repo canonical prefix is 'RAPPS-WP' \u2014 new plans must conform",
"file_path": "workplans/archived/260702-railiance-apps-WP-0002-vergabe-teilnahme-on-railiance01.md",
"db_id": "",
"file_value": "RAILIANCE-WP-0002",
"db_value": "RAPPS-WP",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-26",
"message": "Workplan id 'RAILIANCE-WP-0004' uses prefix 'RAILIANCE-WP' but repo canonical prefix is 'RAPPS-WP' \u2014 new plans must conform",
"file_path": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md",
"db_id": "",
"file_value": "RAILIANCE-WP-0004",
"db_value": "RAPPS-WP",
"fixable": false
}
],
"fixes_applied": [
"bindings: synced 20/20",
"C-17 cleared: pushed 1 backlogged commit(s)",
"C-33 fixed: regenerated WORK-RECORDS.md",
"C-11 fixed: task 'RAPPS-WP-0016-T06' \u2192 08ab8921\u2026",
"C-11 fixed: task 'RAPPS-WP-0016-T07' \u2192 786d6584\u2026",
"C-11 fixed: task 'RAPPS-WP-0016-T08' \u2192 4ab8a5e7\u2026",
"C-11 fixed: task 'RAPPS-WP-0016-T09' \u2192 d3804638\u2026",
"brief: .custodian-brief.md updated",
"push: pushed"
],
"summary": {
"fail": 0,
"automation_error": 0,
"warn": 32,
"info": 8
},
"result": "warn"
}

View file

@ -0,0 +1 @@
WARN: git commit failed for writeback: Generated-only commits rejected: staged

View file

@ -0,0 +1,74 @@
{
"schema": "repo-manager.identifier-assignment.v1",
"ok": true,
"executed": false,
"repo": "railiance-apps",
"namespace": "helixforge",
"assignments": [
{
"kind": "task",
"record_id": "RAPPS-WP-0016-T06",
"uuid": "08ab8921-7801-5309-b84b-bc2a3ceea1e4",
"path": "workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md"
},
{
"kind": "task",
"record_id": "RAPPS-WP-0016-T07",
"uuid": "786d6584-6db1-5a10-9324-d7b94db0df94",
"path": "workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md"
},
{
"kind": "task",
"record_id": "RAPPS-WP-0016-T08",
"uuid": "4ab8a5e7-ab32-5ee2-aaf2-6da246d1b0c8",
"path": "workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md"
},
{
"kind": "task",
"record_id": "RAPPS-WP-0016-T09",
"uuid": "d3804638-c73d-5b9f-a456-4262f62f9e6b",
"path": "workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md"
}
],
"historical_invalid_identifiers": [
{
"kind": "task",
"id": "RAILIANCE-WP-0004-I01",
"source": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-1"
},
{
"kind": "task",
"id": "RAILIANCE-WP-0004-I02",
"source": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-2"
},
{
"kind": "task",
"id": "RAILIANCE-WP-0004-I03",
"source": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-3"
},
{
"kind": "task",
"id": "RAILIANCE-WP-0004-I04",
"source": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-4"
},
{
"kind": "task",
"id": "RAILIANCE-WP-0004-I05",
"source": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-5"
},
{
"kind": "task",
"id": "RAILIANCE-WP-0004-I06",
"source": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-6"
},
{
"kind": "task",
"id": "RAILIANCE-WP-0004-I07",
"source": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-7"
}
],
"historical_identity_collisions": [],
"files_changed": [
"workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md"
]
}

View file

@ -0,0 +1,170 @@
---
id: RAPPS-WP-0016
type: workplan
title: "Forgejo sign-in through NetKingdom, before the forge closes"
domain: infotech
repo: railiance-apps
status: active
flavor: implementation
owner: claude-code
topic_slug: railiance
created: "2026-10-08"
updated: "2026-10-08"
depends_on:
- KEY-WP-0038
related_repos:
- prj-forgejo-org-refactor
- key-cape
- railiance-platform
state_hub_workstream_id: "f6b1d6f6-0abb-5774-87b9-bf3cfb640a3b"
---
# RAPPS-WP-0016 - Forgejo sign-in through NetKingdom, before the forge closes
## Why
`forgejo.coulomb.social` is closing: private by default, no anonymous access
(prj-forgejo-org-refactor ORGREF-WP-0002, decision
`decisions/forge-visibility-policy.md`). The founder's condition is that sign-in
runs through NetKingdom first. railiance-apps owns the Forgejo Helm release
(`docs/forgejo-on-railiance01.md`: S5 Helm release, ingress, operator Makefile),
so the Forgejo side lands here. This plan is ORGREF-WP-0002-T05. The NetKingdom
side is key-cape `KEY-WP-0038`.
## Boundaries
- **Founder guardrail:** tighten gradually; never lock anyone out; never risk
assets; never reach a state that is hard to repair. Every step keeps the
current sign-in path working until the new one is proven.
- **No visibility change** in this plan. Repositories, packages and
`REQUIRE_SIGNIN_VIEW` are ORGREF-WP-0002-T08.
- **Configuration in git.** The authentication source is declared in
`helm/forgejo-values.yaml` (`gitea.oauth`), with its secret drawn from an
ExternalSecret over OpenBao. No click-ops, and no secret value in git.
- Open registration is already disabled (`service.DISABLE_REGISTRATION: true`).
This plan keeps it that way.
## Tasks
```task
id: RAPPS-WP-0016-T01
status: done
priority: high
state_hub_task_id: "98004ed0-83e6-5f6e-9b18-15b8b2aec2e7"
```
### T01 — Make the local administrator a sealed break-glass
Before anything about sign-in changes: confirm the local administrator account
works, keep its credential only in OpenBao, and document recovery (who, how,
where it is logged) in `docs/forgejo-on-railiance01.md`. Verify one break-glass
sign-in and record it without the credential.
Acceptance: a recorded break-glass sign-in, with the recovery path written down.
This is the "never lock ourselves out" floor for every later step.
Done 2026-10-17: founder sealed `forgejo_admin` into OpenBao
`platform/workloads/forgejo/break-glass-admin` (version 1) and verified a local
sign-in (HTTP 200, site admin): `docs/evidence/2026-10-17-forgejo-breakglass-signin.json`.
Recovery path: `docs/forgejo-on-railiance01.md` § Break-glass administrator.
```task
id: RAPPS-WP-0016-T02
status: wait
depends_on: [RAPPS-WP-0016-T01, KEY-WP-0038-T02]
blocking_reason: "Break-glass done (T01); needs the NetKingdom client registered with its secret in custody (KEY-WP-0038-T02)."
priority: high
state_hub_task_id: "13cd3aec-c87d-5d3f-a421-39d8ff131edd"
```
### T02 — Add the NetKingdom authentication source
- an ExternalSecret delivering the `forgejo` client secret from OpenBao to a
Secret in the `forgejo` namespace. Custody path is
`platform/workloads/keycape/forgejo`, field `CLIENT_SECRET`, read by ESO through
Kubernetes-auth role `external-secrets-keycape-forgejo-forgejo`, which carries
only policy `workload-kv-read-keycape-forgejo-forgejo` (net-kingdom 074b3a0;
replaces the earlier `platform/workloads/forgejo/netkingdom-oidc-client` proposal). The
SA/SecretStore/ExternalSecret shape follows the NK-WP-0048
`deliver-consumer-secret` receipt contract
(`docs/evidence/nk48-t16-owner-review/owner-review-railiance-apps.json`)
- `gitea.oauth`: name `netkingdom` (must match the redirect URI registered in
key-cape), provider `openidConnect`, auto-discovery from
`https://kc.coulomb.social/.well-known/openid-configuration`, scopes
`openid profile email groups`, group-claim name `groups`
- `oauth2_client` settings: no automatic account creation for unknown subjects;
account linking to existing local accounts by username after a successful
local sign-in (so the founder and agent accounts keep their history)
- Helm upgrade with the previous revision noted for rollback
Local password sign-in stays enabled.
Acceptance: the "Sign in with netkingdom" option appears. Local sign-in still
works. Rollback is one `helm rollback` to the noted revision.
```task
id: RAPPS-WP-0016-T03
status: wait
depends_on: [RAPPS-WP-0016-T02]
blocking_reason: "Linking and team mapping follow a working authentication source."
priority: high
state_hub_task_id: "81f072aa-c316-511e-a2cd-21dd1b1d0a00"
```
### T03 — Link accounts and map groups to teams
- The founder links their account through NetKingdom (MFA), then signs in again
through NetKingdom only and sees the same repositories, organisations and
admin rights.
- Map NetKingdom groups (names agreed in KEY-WP-0038-T01) to organisation teams:
owners and readers at least. Create the read-only teams that
ORGREF-WP-0002-T06 consumers will use.
- Apply KEY-WP-0038-T03's decision on agents and services: NetKingdom sign-in, or
scoped tokens bound to service identities.
Acceptance: founder and one agent work through NetKingdom; group-to-team mapping
verified by adding and removing one test membership; break-glass still works.
```task
id: RAPPS-WP-0016-T04
status: wait
depends_on: [RAPPS-WP-0016-T03]
needs_human: true
blocking_reason: "Restricting local password sign-in is a founder decision once NetKingdom sign-in is proven."
priority: medium
state_hub_task_id: "32c54737-c40f-5fde-9b91-163f8dcb0068"
```
### T04 — Decide on local password sign-in
Once NetKingdom sign-in has been used for a while without problems, the founder
decides whether local password sign-in is turned off for everyone except
break-glass. This is not required to close the forge; it is the next tightening
step, taken separately.
```task
id: RAPPS-WP-0016-T05
status: wait
depends_on: [RAPPS-WP-0016-T02]
blocking_reason: "Waits for net-kingdom's answer to the Apps 1.3 needs-change record (the-custodian docs/changes/netkingdom-target-2026-10-17/nk48-1.3-owner-review/owner-review-railiance-apps.json: RAPPS-1.3-C1..C3) and the re-frozen 1.3 candidate."
priority: medium
state_hub_task_id: "728786c9-f1f9-5983-a6a4-dea21faf67f5"
```
### T05 — Apps owner seams for NK-WP-0048 consumer steps
Implement the real Apps capabilities behind the `deliver-consumer-secret` and
`hand-over` adapters, as owner-run paths (option C): `owner_apply` /
`owner_remove` emitting `netkingdom.consumer-secret-delivery.v1` receipts from the
T02 objects; a consumer verifier that observes Forgejo sign-in and the T03
positive/negative group probes; and a committed-evidence hand-over receipt store.
See the owner-review record for the contract.
Acceptance: receipts produced from the live T02/T03 run validate against the
adapters' checks with no value-bearing keys.
## Also in scope: stale node credential
The k3s `registries.yaml` on railiance01 still holds a login for the frozen Gitea
host `92.205.130.254` (ORGREF-WP-0002-T02). Coordinate its removal with the node
owner when ORGREF-WP-0002-T06 adds the forge registry login, in the same change.

View file

@ -0,0 +1,13 @@
{
"owner": "railiance-apps",
"base": "git:944b30ad63ab054cc24617e374e177d34cd572da",
"existing_task_blocks_preserved": 5,
"new_tasks": {
"RAPPS-WP-0016-T06": "done, pending exact independent review acceptance before source apply",
"RAPPS-WP-0016-T07": "progress",
"RAPPS-WP-0016-T08": "progress",
"RAPPS-WP-0016-T09": "todo"
},
"canonical_edits": false,
"native_actions": false
}

View file

@ -0,0 +1,179 @@
{
"ok": true,
"status": "applied",
"repo_slug": "railiance-apps",
"commit": "c29408ae6747158a639dc876e6d7492680675658",
"requests": 2,
"elapsed_ms": 6799.5,
"git": {
"upstream": "origin/main",
"behind": 0,
"ahead": 0
},
"identifiers": {
"schema": "repo-manager.identifier-assignment.v1",
"ok": true,
"executed": true,
"repo": "railiance-apps",
"namespace": "helixforge",
"assignments": [],
"historical_invalid_identifiers": [
{
"kind": "task",
"id": "RAILIANCE-WP-0004-I01",
"source": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-1"
},
{
"kind": "task",
"id": "RAILIANCE-WP-0004-I02",
"source": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-2"
},
{
"kind": "task",
"id": "RAILIANCE-WP-0004-I03",
"source": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-3"
},
{
"kind": "task",
"id": "RAILIANCE-WP-0004-I04",
"source": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-4"
},
{
"kind": "task",
"id": "RAILIANCE-WP-0004-I05",
"source": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-5"
},
{
"kind": "task",
"id": "RAILIANCE-WP-0004-I06",
"source": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-6"
},
{
"kind": "task",
"id": "RAILIANCE-WP-0004-I07",
"source": "workplans/archived/260702-railiance-apps-WP-0004-app-deployment-improvements.md#task-block-7"
}
],
"historical_identity_collisions": [],
"files_changed": []
},
"receipt": {
"schema": "state-hub.repository-projection-reconcile.v1",
"instance_role": "primary",
"instance_label": "railiance01",
"expected_commit": "c29408ae6747158a639dc876e6d7492680675658",
"derived_commit": "c29408ae6747158a639dc876e6d7492680675658",
"outcome": {
"schema": "state-hub.projection-reset.v1",
"repo_slug": "railiance-apps",
"commit": "c29408ae6747158a639dc876e6d7492680675658",
"status": "applied",
"counts": {
"created": 0,
"updated": 20,
"retired": 0,
"refused": 0,
"released": 0,
"created_tasks": 0,
"updated_tasks": 6,
"cancelled_tasks": 0,
"created_edges": 0,
"removed_edges": 0,
"unresolved_edges": 0,
"external_edges": 5
},
"created": [],
"updated": [
"RAIL-AP-WP-0001",
"RAILIANCE-WP-0002",
"RAILIANCE-WP-0004",
"RAPPS-WP-0001",
"RAPPS-WP-0002",
"RAPPS-WP-0003",
"RAPPS-WP-0004",
"RAPPS-WP-0005",
"RAPPS-WP-0006",
"RAPPS-WP-0007",
"RAPPS-WP-0008",
"RAPPS-WP-0009",
"RAPPS-WP-0010",
"RAPPS-WP-0011",
"RAPPS-WP-0012",
"RAPPS-WP-0013",
"RAPPS-WP-0014",
"RAPPS-WP-0015",
"RAPPS-WP-0016",
"RAPPS-WP-0017"
],
"retired": [],
"released": [],
"created_tasks": [],
"updated_tasks": [
"RAPPS-WP-0016-T01",
"RAPPS-WP-0016-T05",
"RAPPS-WP-0016-T06",
"RAPPS-WP-0016-T07",
"RAPPS-WP-0016-T08",
"RAPPS-WP-0016-T09"
],
"cancelled_tasks": [],
"created_edges": [],
"removed_edges": [],
"unresolved_edges": [],
"external_edges": [
{
"workplan": "RAPPS-WP-0016",
"from": "RAPPS-WP-0016-T02",
"target": "RAPPS-WP-0016-T01",
"relationship_type": "starts_after",
"from_workplan_id": "f6b1d6f6-0abb-5774-87b9-bf3cfb640a3b",
"from_task_id": "13cd3aec-c87d-5d3f-a421-39d8ff131edd",
"to_workplan_id": null,
"to_task_id": "98004ed0-83e6-5f6e-9b18-15b8b2aec2e7"
},
{
"workplan": "RAPPS-WP-0016",
"from": "RAPPS-WP-0016-T02",
"target": "KEY-WP-0038-T02",
"relationship_type": "starts_after",
"from_workplan_id": "f6b1d6f6-0abb-5774-87b9-bf3cfb640a3b",
"from_task_id": "13cd3aec-c87d-5d3f-a421-39d8ff131edd",
"to_workplan_id": null,
"to_task_id": "ddcfb482-8f33-5c81-9ce8-84be8fa5dc30"
},
{
"workplan": "RAPPS-WP-0016",
"from": "RAPPS-WP-0016-T04",
"target": "RAPPS-WP-0016-T03",
"relationship_type": "starts_after",
"from_workplan_id": "f6b1d6f6-0abb-5774-87b9-bf3cfb640a3b",
"from_task_id": "32c54737-c40f-5fde-9b91-163f8dcb0068",
"to_workplan_id": null,
"to_task_id": "81f072aa-c316-511e-a2cd-21dd1b1d0a00"
},
{
"workplan": "RAPPS-WP-0016",
"from": "RAPPS-WP-0016-T05",
"target": "RAPPS-WP-0016-T02",
"relationship_type": "starts_after",
"from_workplan_id": "f6b1d6f6-0abb-5774-87b9-bf3cfb640a3b",
"from_task_id": "728786c9-f1f9-5983-a6a4-dea21faf67f5",
"to_workplan_id": null,
"to_task_id": "13cd3aec-c87d-5d3f-a421-39d8ff131edd"
},
{
"workplan": "RAPPS-WP-0016",
"from": "RAPPS-WP-0016-T03",
"target": "RAPPS-WP-0016-T02",
"relationship_type": "starts_after",
"from_workplan_id": "f6b1d6f6-0abb-5774-87b9-bf3cfb640a3b",
"from_task_id": "81f072aa-c316-511e-a2cd-21dd1b1d0a00",
"to_workplan_id": null,
"to_task_id": "13cd3aec-c87d-5d3f-a421-39d8ff131edd"
}
],
"refused": [],
"notes": []
}
}
}

View file

@ -0,0 +1,47 @@
<!-- custodian-brief: generated by fix-consistency — do not edit manually -->
# Custodian Brief — railiance-apps
**Domain:** financials
**Last synced:** 2026-10-17 10:13 UTC
**State Hub:** http://127.0.0.1:8000 *(adjust if running on a remote machine)*
## Active Workstreams
### Forgejo sign-in through NetKingdom, before the forge closes
Progress: 1/5 done | workplan_id: `f6b1d6f6-0abb-5774-87b9-bf3cfb640a3b`
**Open tasks:**
- ! T01 — Make the local administrator a sealed break-glass `13cd3aec`
*(wait: Break-glass done (T01); needs the NetKingdom client registered with its secret in custody (KEY-WP-0038-T02).)*
- ! T02 — Add the NetKingdom authentication source `81f072aa`
*(wait: Linking and team mapping follow a working authentication source.)*
- ! T03 — Link accounts and map groups to teams `32c54737`
*(wait: Restricting local password sign-in is a founder decision once NetKingdom sign-in is proven.)*
- ! T04 — Decide on local password sign-in `728786c9`
*(wait: Waits for net-kingdom's answer to the Apps 1.3 needs-change record (the-custodian docs/changes/netkingdom-target-2026-10-17/nk48-1.3-owner-review/owner-review-railiance-apps.json: RAPPS-1.3-C1..C3) and the re-frozen 1.3 candidate.)*
### Coulomb-social persistent personal workspace release
Progress: 3/4 done | workplan_id: `79abacf8-361e-51ab-829d-40dec8e142d1`
**Open tasks:**
- ! T04 — Personal sign-in and content acceptance `8bc4962a`
### Deploy and recover the first invited Vergabe company pilot
Progress: 2/3 done | workplan_id: `c7fdaa7e-cab8-5d1d-86c2-f1aad7927c57`
**Open tasks:**
- ! Demonstrate restart, isolated restore, rollback and operating ownership `dd069c6d`
*(wait: Await populated two-user/document workflow, coherent PostgreSQL/media/issue-state off-host recovery point, isolated restored workflow, rollback evidence and support ownership. September 25 proves database restore and restart only.)*
## Inbox Hygiene
**Stale unread:** 2 message(s) older than 3 day(s) — triage at session start.
**Missing thread_id:** 2 unread message(s) lack supersession chains.
---
## MCP Orientation (when available)
If the state-hub MCP server is reachable, call:
`get_domain_summary("financials")`
This provides richer cross-domain context.
If the MCP call fails, use this file as your orientation source.

View file

@ -0,0 +1,48 @@
# Work Records — railiance-apps
> Generated by `statehub fix-consistency` (CUST-WP-0061-T04, work-record
> stage 3). Do not edit by hand — edit the source file/block listed for
> each record and re-run fix-consistency to refresh this index. Archived
> workplans are omitted; closed decisions/intakes/engagements stay listed
> so recently-resolved work is still visible. [auto]
| Kind | ID | Status | Lane | Source |
| --- | --- | --- | --- | --- |
| workplan | RAPPS-WP-0001 | finished | — | workplans/RAPPS-WP-0001-cnpg-backup-scheduledbackup-coverage.md |
| workplan | RAPPS-WP-0002 | finished | — | workplans/RAPPS-WP-0002-railiance01-activity-core-backup-automation.md |
| workplan | RAPPS-WP-0003 | finished | — | workplans/RAPPS-WP-0003-policy-nexus-production-binding.md |
| workplan | RAPPS-WP-0014 | blocked | — | workplans/RAPPS-WP-0014-vergabe-invited-pilot.md |
| workplan | RAPPS-WP-0015 | active | — | workplans/RAPPS-WP-0015-coulomb-personal-content-release.md |
| workplan | RAPPS-WP-0016 | active | — | workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md |
| workplan | RAPPS-WP-0017 | finished | — | workplans/RAPPS-WP-0017-reuse-private-reader-release.md |
| task | RAPPS-WP-0001-T01 | done | — | workplans/RAPPS-WP-0001-cnpg-backup-scheduledbackup-coverage.md |
| task | RAPPS-WP-0001-T02 | done | — | workplans/RAPPS-WP-0001-cnpg-backup-scheduledbackup-coverage.md |
| task | RAPPS-WP-0001-T03 | done | — | workplans/RAPPS-WP-0001-cnpg-backup-scheduledbackup-coverage.md |
| task | RAPPS-WP-0001-T04 | done | — | workplans/RAPPS-WP-0001-cnpg-backup-scheduledbackup-coverage.md |
| task | RAPPS-WP-0001-T05 | done | — | workplans/RAPPS-WP-0001-cnpg-backup-scheduledbackup-coverage.md |
| task | RAPPS-WP-0002-T01 | done | — | workplans/RAPPS-WP-0002-railiance01-activity-core-backup-automation.md |
| task | RAPPS-WP-0002-T02 | done | — | workplans/RAPPS-WP-0002-railiance01-activity-core-backup-automation.md |
| task | RAPPS-WP-0002-T03 | done | — | workplans/RAPPS-WP-0002-railiance01-activity-core-backup-automation.md |
| task | RAPPS-WP-0002-T04 | done | — | workplans/RAPPS-WP-0002-railiance01-activity-core-backup-automation.md |
| task | RAPPS-WP-0002-T05 | done | — | workplans/RAPPS-WP-0002-railiance01-activity-core-backup-automation.md |
| task | RAPPS-WP-0002-T06 | done | — | workplans/RAPPS-WP-0002-railiance01-activity-core-backup-automation.md |
| task | RAPPS-WP-0002-T07 | done | — | workplans/RAPPS-WP-0002-railiance01-activity-core-backup-automation.md |
| task | RAPPS-WP-0003-T01 | done | — | workplans/RAPPS-WP-0003-policy-nexus-production-binding.md |
| task | RAPPS-WP-0003-T02 | done | — | workplans/RAPPS-WP-0003-policy-nexus-production-binding.md |
| task | RAPPS-WP-0003-T03 | done | — | workplans/RAPPS-WP-0003-policy-nexus-production-binding.md |
| task | RAPPS-WP-0003-T04 | done | — | workplans/RAPPS-WP-0003-policy-nexus-production-binding.md |
| task | RAPPS-WP-0014-T01 | done | — | workplans/RAPPS-WP-0014-vergabe-invited-pilot.md |
| task | RAPPS-WP-0014-T02 | done | — | workplans/RAPPS-WP-0014-vergabe-invited-pilot.md |
| task | RAPPS-WP-0014-T03 | wait | — | workplans/RAPPS-WP-0014-vergabe-invited-pilot.md |
| task | RAPPS-WP-0015-T01 | done | — | workplans/RAPPS-WP-0015-coulomb-personal-content-release.md |
| task | RAPPS-WP-0015-T02 | done | — | workplans/RAPPS-WP-0015-coulomb-personal-content-release.md |
| task | RAPPS-WP-0015-T03 | done | — | workplans/RAPPS-WP-0015-coulomb-personal-content-release.md |
| task | RAPPS-WP-0015-T04 | wait | — | workplans/RAPPS-WP-0015-coulomb-personal-content-release.md |
| task | RAPPS-WP-0016-T01 | done | — | workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md |
| task | RAPPS-WP-0016-T02 | wait | — | workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md |
| task | RAPPS-WP-0016-T03 | wait | — | workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md |
| task | RAPPS-WP-0016-T04 | wait | — | workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md |
| task | RAPPS-WP-0016-T05 | wait | — | workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md |
| task | RAPPS-WP-0017-T01 | done | — | workplans/RAPPS-WP-0017-reuse-private-reader-release.md |
| task | RAPPS-WP-0017-T02 | done | — | workplans/RAPPS-WP-0017-reuse-private-reader-release.md |
| task | RAPPS-WP-0017-T03 | done | — | workplans/RAPPS-WP-0017-reuse-private-reader-release.md |

View file

@ -0,0 +1,10 @@
[
{
"path": ".custodian-brief.md",
"index": "100644 1f9b6fae4362945f96aa9a2a9647be9c83d8296a 0\t.custodian-brief.md"
},
{
"path": "WORK-RECORDS.md",
"index": "100644 89c6d25cfe29035a2e0ad71113c31b89338b0cc3 0\tWORK-RECORDS.md"
}
]

View file

@ -0,0 +1,37 @@
{
"exit_code": 0,
"commit": "c29408ae6747158a639dc876e6d7492680675658",
"base": "944b30ad63ab054cc24617e374e177d34cd572da",
"files": [
{
"path": "Makefile",
"sha256": "572d36e2dd3dee6321a5f6c4726f83991031672be5eb3480ae6173f8ce50ccdd"
},
{
"path": "build/forgejo/README.md",
"sha256": "c3d37b8e62a99c351b8630a31f875fb8f4afbf54ec2488460066c88148f76fa8"
},
{
"path": "build/forgejo/inputs.lock.json",
"sha256": "29f329b204a2a5f72084b50d59e8445486ff4799450097c6f3908c74e87a233a"
},
{
"path": "build/forgejo/required-claim-values.patch",
"sha256": "f2788b3f2bf84dbc0f94e232b6c9614a864b8123c09f9e44703d50d5e1b53257"
},
{
"path": "build/forgejo/runtime-base-config.json",
"sha256": "bc5a3df111729582faadebd01d126ba769e2b65d0c62f306f6bc79f4e562452b"
},
{
"path": "tools/forgejo-release-build.py",
"sha256": "7e28d9bd5adefaece96eb1d31a23e128ec8f448958e45d22467bf7acf476a9ba"
},
{
"path": "workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md",
"sha256": "0ac8db087247bf980339ef8661a26eeb817af82391e3e85038be773fe3c6fb3a"
}
],
"stdout": "[main c29408a] Add pinned Forgejo release build path and track operational integration\n 7 files changed, 980 insertions(+), 1 deletion(-)\n create mode 100644 build/forgejo/README.md\n create mode 100644 build/forgejo/inputs.lock.json\n create mode 100644 build/forgejo/required-claim-values.patch\n create mode 100644 build/forgejo/runtime-base-config.json\n create mode 100644 tools/forgejo-release-build.py\n",
"stderr": ""
}

View file

@ -0,0 +1,35 @@
{
"owner": "railiance-apps",
"base_revision": "944b30ad63ab054cc24617e374e177d34cd572da",
"message": "Add pinned Forgejo release build path and track operational integration",
"files": [
{
"path": "Makefile",
"sha256": "572d36e2dd3dee6321a5f6c4726f83991031672be5eb3480ae6173f8ce50ccdd"
},
{
"path": "build/forgejo/README.md",
"sha256": "c3d37b8e62a99c351b8630a31f875fb8f4afbf54ec2488460066c88148f76fa8"
},
{
"path": "build/forgejo/inputs.lock.json",
"sha256": "29f329b204a2a5f72084b50d59e8445486ff4799450097c6f3908c74e87a233a"
},
{
"path": "build/forgejo/required-claim-values.patch",
"sha256": "f2788b3f2bf84dbc0f94e232b6c9614a864b8123c09f9e44703d50d5e1b53257"
},
{
"path": "build/forgejo/runtime-base-config.json",
"sha256": "bc5a3df111729582faadebd01d126ba769e2b65d0c62f306f6bc79f4e562452b"
},
{
"path": "tools/forgejo-release-build.py",
"sha256": "7e28d9bd5adefaece96eb1d31a23e128ec8f448958e45d22467bf7acf476a9ba"
},
{
"path": "workplans/RAPPS-WP-0016-forgejo-netkingdom-login.md",
"sha256": "0ac8db087247bf980339ef8661a26eeb817af82391e3e85038be773fe3c6fb3a"
}
]
}

View file

@ -0,0 +1,14 @@
{
"workplan_id": "dfadb19b-445e-59c6-bcd6-48e87b912c52",
"id": "054a23cc-c353-447b-bf78-6b28a2d95bb9",
"topic_id": null,
"task_id": "87637402-02f1-57c1-8fbc-4141598af8e3",
"decision_id": null,
"event_type": "note",
"summary": "CUST-WP-0080 checkpoint: published NetKingdom70f408ca (Pg backend/T21 and real-SOPS/T37), RepoManager9ebde0a9(T05 accepted), Secretsc59bbf56(WP15), StateHub51bc70d1 receiver and086d79a2 policy-compatible preflight/T08. Independent82canonicalprovisioner/65actualSOPS cases; realPg21oracles and migration10SQLshapeoracles passed with exactcleanup. Verified66NK/STATE plus9RMGR/Secrets taskbindings/remotes;4 coordination_receipt events attach ownerwaits withoutmessages/wakes. ClusterWP18 remainsunpublished behind correct historicalguard. PinnedCIimage c802... inspected233files86packagemetadata; exactpackagedreuse-valuesdryrun passes8identities/3imageonlychanges. Stable STATE95T06 proposal revision4/digest63a02e8296d126c0158b7eb2c4ce79c7eeb6f8d6f61298d473c1065c7557ba32 recordedpending/notexecuted; migration/recovery/unpricedriskexplicit. Scanner public-ID falsepositive retained then corrected explicitfieldformat; supervisionenum normalization retained. No liveupgrade, registraractivation, actualcredentialrecovery, rotation or authoritypromotion. All16nativeTSA gatesopen.",
"detail": null,
"author": "codex",
"session_id": null,
"created_at": "2026-10-16T23:48:26.768137Z",
"workstream_id": "dfadb19b-445e-59c6-bcd6-48e87b912c52"
}

View file

@ -0,0 +1,16 @@
{
"published_commit": "f8c7dfa2a9c7919879b62c77eb39582b3e23654e",
"remote_exact": true,
"required_consistency": {
"fail": 0,
"automation_error": 0,
"warn": 8,
"info": 4
},
"authoritative_projection": "applied_primary_railiance01_exact_revision",
"custodian_tasks_verified": 6,
"owner_tasks_verified": 75,
"preexisting_staged_brief_work_records_and_six_assessments_preserved": true,
"rollout_proposal_pending_not_executed": true,
"native_gates_closed": 0
}

View file

@ -0,0 +1,67 @@
<!-- custodian-brief: generated by fix-consistency — do not edit manually -->
# Custodian Brief — secrets-engine
**Domain:** infotech
**Last synced:** 2026-10-16 19:07 UTC
**State Hub:** http://127.0.0.1:8000 *(adjust if running on a remote machine)*
## Active Workstreams
### Design and prove task-scoped protected OpenBao execution
Progress: 1/3 done | workplan_id: `5e38aecc-85ca-5f55-94c6-9fbb08604819`
**Open tasks:**
- ! Define the exact mediated execution contract `b2f0d462`
*(wait: Independent Platform mediated-contract review and identity/approval/PDP owner returns remain required; D3 wrapped primitive source is implemented, no native entitlement is inferred.)*
- ! Implement and prove one native metadata action `5f8f7c41`
### Constrain PDP transport and authenticate decision responses
Progress: 1/3 done | workplan_id: `7252469d-d7a5-5c18-8911-b511b8c6a736`
**Open tasks:**
- ! Verify the admitted native consumer and rotation path `85aa4c78`
*(wait: Requires reviewed verification-key admission, source enforcement and exact native rollout receipt; no production trust change is proposed yet.)*
- ► Implement independently anchored responder authentication `877782e5`
### Activate native Claude credential delivery for Glas
Progress: 2/3 done | workplan_id: `40ccc3b4-d046-5a58-8649-e7935f45c974`
**Open tasks:**
- ! Activate the approved native lane and verify real owner delivery `f8069c8a`
*(wait: Next owner action: reconcile held parent reservation 6efa9436-6a91-47c0-94e5-b31b5a0e7e3a (EUR 10, observed USD still null) from existing provider records. No corrected runtime digest is admitted; do not retry or replay consumed approvals.)*
### Adopt concrete OpenBao credential lanes from ops-warden
Progress: 4/6 done | workplan_id: `31f7f8ea-7f73-516c-8877-f03a13f1db82`
**Open tasks:**
- ! Stage live apply and verification `fb103f1e`
*(wait: Owner work first: publish a reviewed scoped-apply command per lane. Per-lane approvals are no longer needed (D1 standing rule); each lane with a command enters the attended window.)*
- ! Reconcile routing ownership and retire interim proxies `1431edae`
*(wait: Needs owner-agreed routing/proxy retirement for each verified lane and custody disposition of the legacy npm pointer; a single approved OpenRouter key-check does not authorize broader routing cutover.)*
### Evolve the Lifecycle engine to the accepted security layer model
Progress: 5/6 done | workplan_id: `9c9e5164-b2f5-5ea2-a557-5368d65e9fe0`
**Open tasks:**
- ! No standing engine credential `d7bc8bdc`
*(wait: Published JWT contract and positive login/revocation are delivered. Native KEY-WP-0039-T02 claim negatives, CCR-2026-0038 effective-policy/capability/expiry/use checks and MASON-WP-0009-T05 remain. Login-self-only grants no protected-operation authority: agree and implement separately reviewed task-scoped backend execution entitlement, then prove functional steady-state service-identity adoption without bootstrap/env fallback.)*
### Production-safe provisioning, authorization, and lifecycle hardening
Progress: 6/7 done | workplan_id: `68a39be1-bd9c-5133-ad64-e7bca892aaf3`
**Open tasks:**
- ! Resume native production lane adoption `a0a1dd92`
*(wait: Engine approval hardening is complete. Remaining per-lane cutover includes native routing/proxy retirement with ops-warden under SECRETS-WP-0006-T05/T06; the exact OpenRouter key-check receipt does not establish broader recipient readiness.)*
## Inbox Hygiene
**Stale unread:** 3 message(s) older than 3 day(s) — triage at session start.
**Missing thread_id:** 2 unread message(s) lack supersession chains.
---
## MCP Orientation (when available)
If the state-hub MCP server is reachable, call:
`get_domain_summary("infotech")`
This provides richer cross-domain context.
If the MCP call fails, use this file as your orientation source.

View file

@ -0,0 +1,95 @@
# Work Records — secrets-engine
> Generated by `statehub fix-consistency` (CUST-WP-0061-T04, work-record
> stage 3). Do not edit by hand — edit the source file/block listed for
> each record and re-run fix-consistency to refresh this index. Archived
> workplans are omitted; closed decisions/intakes/engagements stay listed
> so recently-resolved work is still visible. [auto]
| Kind | ID | Status | Lane | Source |
| --- | --- | --- | --- | --- |
| workplan | SECRETS-WP-ADHOC-2026-08-21 | finished | — | workplans/ADHOC-2026-08-21.md |
| workplan | SECRETS-WP-ADHOC-2026-08-23 | finished | — | workplans/ADHOC-2026-08-23.md |
| workplan | SECRETS-WP-0001 | finished | — | workplans/SECRETS-WP-0001-statehub-bootstrap.md |
| workplan | SECRETS-WP-0002 | finished | — | workplans/SECRETS-WP-0002-bootstrap.md |
| workplan | SECRETS-WP-0004 | finished | — | workplans/SECRETS-WP-0004-warden-sign-token-lane.md |
| workplan | SECRETS-WP-0005 | finished | — | workplans/SECRETS-WP-0005-scope-intent-value-gaps.md |
| workplan | SECRETS-WP-0006 | blocked | — | workplans/SECRETS-WP-0006-catalog-lane-adoption.md |
| workplan | SECRETS-WP-0007 | blocked | — | workplans/SECRETS-WP-0007-production-lifecycle-hardening.md |
| workplan | SECRETS-WP-0008 | blocked | — | workplans/SECRETS-WP-0008-layer-model-lifecycle-conformance.md |
| workplan | SECRETS-WP-0009 | blocked | — | workplans/SECRETS-WP-0009-glas-claude-native-delivery.md |
| workplan | SECRETS-WP-0010 | finished | — | workplans/SECRETS-WP-0010-openrouter-native-access.md |
| workplan | SECRETS-WP-0011 | finished | — | workplans/SECRETS-WP-0011-multi-lane-exec-owner-delivery.md |
| workplan | SECRETS-WP-0012 | finished | — | workplans/SECRETS-WP-0012-keycape-openbao-consumer-custody.md |
| workplan | SECRETS-WP-0013 | proposed | — | workplans/SECRETS-WP-0013-task-scoped-openbao-execution.md |
| workplan | SECRETS-WP-0014 | active | — | workplans/SECRETS-WP-0014-pdp-transport-and-responder-authentication.md |
| task | SECRETS-WP-ADHOC-2026-08-21-T01 | done | — | workplans/ADHOC-2026-08-21.md |
| task | SECRETS-WP-ADHOC-2026-08-23-T01 | done | — | workplans/ADHOC-2026-08-23.md |
| task | SECRETS-WP-0001-T01 | done | — | workplans/SECRETS-WP-0001-statehub-bootstrap.md |
| task | SECRETS-WP-0001-T02 | done | — | workplans/SECRETS-WP-0001-statehub-bootstrap.md |
| task | SECRETS-WP-0001-T03 | done | — | workplans/SECRETS-WP-0001-statehub-bootstrap.md |
| task | SECRETS-WP-0002-T01 | done | — | workplans/SECRETS-WP-0002-bootstrap.md |
| task | SECRETS-WP-0002-T02 | done | — | workplans/SECRETS-WP-0002-bootstrap.md |
| task | SECRETS-WP-0002-T03 | done | — | workplans/SECRETS-WP-0002-bootstrap.md |
| task | SECRETS-WP-0002-T04 | done | — | workplans/SECRETS-WP-0002-bootstrap.md |
| task | SECRETS-WP-0002-T05 | done | — | workplans/SECRETS-WP-0002-bootstrap.md |
| task | SECRETS-WP-0002-T06 | done | — | workplans/SECRETS-WP-0002-bootstrap.md |
| task | SECRETS-WP-0002-T07 | done | — | workplans/SECRETS-WP-0002-bootstrap.md |
| task | SECRETS-WP-0002-T08 | done | — | workplans/SECRETS-WP-0002-bootstrap.md |
| task | SECRETS-WP-0002-T09 | done | — | workplans/SECRETS-WP-0002-bootstrap.md |
| task | SECRETS-WP-0002-T10 | done | — | workplans/SECRETS-WP-0002-bootstrap.md |
| task | SECRETS-WP-0004-T01 | done | — | workplans/SECRETS-WP-0004-warden-sign-token-lane.md |
| task | SECRETS-WP-0004-T02 | done | — | workplans/SECRETS-WP-0004-warden-sign-token-lane.md |
| task | SECRETS-WP-0004-T03 | done | — | workplans/SECRETS-WP-0004-warden-sign-token-lane.md |
| task | SECRETS-WP-0004-T04 | done | — | workplans/SECRETS-WP-0004-warden-sign-token-lane.md |
| task | SECRETS-WP-0004-T05 | done | — | workplans/SECRETS-WP-0004-warden-sign-token-lane.md |
| task | SECRETS-WP-0005-T01 | done | — | workplans/SECRETS-WP-0005-scope-intent-value-gaps.md |
| task | SECRETS-WP-0005-T02 | done | — | workplans/SECRETS-WP-0005-scope-intent-value-gaps.md |
| task | SECRETS-WP-0005-T03 | done | — | workplans/SECRETS-WP-0005-scope-intent-value-gaps.md |
| task | SECRETS-WP-0005-T04 | done | — | workplans/SECRETS-WP-0005-scope-intent-value-gaps.md |
| task | SECRETS-WP-0005-T05 | done | — | workplans/SECRETS-WP-0005-scope-intent-value-gaps.md |
| task | SECRETS-WP-0005-T06 | done | — | workplans/SECRETS-WP-0005-scope-intent-value-gaps.md |
| task | SECRETS-WP-0005-T07 | done | — | workplans/SECRETS-WP-0005-scope-intent-value-gaps.md |
| task | SECRETS-WP-0006-T01 | done | — | workplans/SECRETS-WP-0006-catalog-lane-adoption.md |
| task | SECRETS-WP-0006-T02 | done | — | workplans/SECRETS-WP-0006-catalog-lane-adoption.md |
| task | SECRETS-WP-0006-T03 | done | — | workplans/SECRETS-WP-0006-catalog-lane-adoption.md |
| task | SECRETS-WP-0006-T04 | done | — | workplans/SECRETS-WP-0006-catalog-lane-adoption.md |
| task | SECRETS-WP-0006-T05 | wait | — | workplans/SECRETS-WP-0006-catalog-lane-adoption.md |
| task | SECRETS-WP-0006-T06 | wait | — | workplans/SECRETS-WP-0006-catalog-lane-adoption.md |
| task | SECRETS-WP-0007-T01 | done | — | workplans/SECRETS-WP-0007-production-lifecycle-hardening.md |
| task | SECRETS-WP-0007-T02 | done | — | workplans/SECRETS-WP-0007-production-lifecycle-hardening.md |
| task | SECRETS-WP-0007-T03 | done | — | workplans/SECRETS-WP-0007-production-lifecycle-hardening.md |
| task | SECRETS-WP-0007-T04 | done | — | workplans/SECRETS-WP-0007-production-lifecycle-hardening.md |
| task | SECRETS-WP-0007-T05 | done | — | workplans/SECRETS-WP-0007-production-lifecycle-hardening.md |
| task | SECRETS-WP-0007-T06 | done | — | workplans/SECRETS-WP-0007-production-lifecycle-hardening.md |
| task | SECRETS-WP-0007-T07 | wait | — | workplans/SECRETS-WP-0007-production-lifecycle-hardening.md |
| task | SECRETS-WP-0008-T01 | done | — | workplans/SECRETS-WP-0008-layer-model-lifecycle-conformance.md |
| task | SECRETS-WP-0008-T02 | done | — | workplans/SECRETS-WP-0008-layer-model-lifecycle-conformance.md |
| task | SECRETS-WP-0008-T03 | done | — | workplans/SECRETS-WP-0008-layer-model-lifecycle-conformance.md |
| task | SECRETS-WP-0008-T04 | done | — | workplans/SECRETS-WP-0008-layer-model-lifecycle-conformance.md |
| task | SECRETS-WP-0008-T05 | done | — | workplans/SECRETS-WP-0008-layer-model-lifecycle-conformance.md |
| task | SECRETS-WP-0008-T06 | wait | — | workplans/SECRETS-WP-0008-layer-model-lifecycle-conformance.md |
| task | SECRETS-WP-0009-T01 | done | — | workplans/SECRETS-WP-0009-glas-claude-native-delivery.md |
| task | SECRETS-WP-0009-T02 | done | — | workplans/SECRETS-WP-0009-glas-claude-native-delivery.md |
| task | SECRETS-WP-0009-T03 | wait | — | workplans/SECRETS-WP-0009-glas-claude-native-delivery.md |
| task | SECRETS-WP-0010-T01 | done | — | workplans/SECRETS-WP-0010-openrouter-native-access.md |
| task | SECRETS-WP-0010-T02 | done | — | workplans/SECRETS-WP-0010-openrouter-native-access.md |
| task | SECRETS-WP-0010-T03 | done | — | workplans/SECRETS-WP-0010-openrouter-native-access.md |
| task | SECRETS-WP-0011-T01 | done | — | workplans/SECRETS-WP-0011-multi-lane-exec-owner-delivery.md |
| task | SECRETS-WP-0011-T02 | done | — | workplans/SECRETS-WP-0011-multi-lane-exec-owner-delivery.md |
| task | SECRETS-WP-0011-T03 | done | — | workplans/SECRETS-WP-0011-multi-lane-exec-owner-delivery.md |
| task | SECRETS-WP-0011-T04 | done | — | workplans/SECRETS-WP-0011-multi-lane-exec-owner-delivery.md |
| task | SECRETS-WP-0011-T05 | done | — | workplans/SECRETS-WP-0011-multi-lane-exec-owner-delivery.md |
| task | SECRETS-WP-0012-T01 | done | — | workplans/SECRETS-WP-0012-keycape-openbao-consumer-custody.md |
| task | SECRETS-WP-0012-T02 | cancel | — | workplans/SECRETS-WP-0012-keycape-openbao-consumer-custody.md |
| task | SECRETS-WP-0012-T03 | done | — | workplans/SECRETS-WP-0012-keycape-openbao-consumer-custody.md |
| task | SECRETS-WP-0012-T04 | done | — | workplans/SECRETS-WP-0012-keycape-openbao-consumer-custody.md |
| task | SECRETS-WP-0013-T01 | wait | — | workplans/SECRETS-WP-0013-task-scoped-openbao-execution.md |
| task | SECRETS-WP-0013-T02 | done | — | workplans/SECRETS-WP-0013-task-scoped-openbao-execution.md |
| task | SECRETS-WP-0013-T03 | wait | — | workplans/SECRETS-WP-0013-task-scoped-openbao-execution.md |
| task | SECRETS-WP-0014-T01 | done | — | workplans/SECRETS-WP-0014-pdp-transport-and-responder-authentication.md |
| task | SECRETS-WP-0014-T02 | progress | — | workplans/SECRETS-WP-0014-pdp-transport-and-responder-authentication.md |
| task | SECRETS-WP-0014-T03 | wait | — | workplans/SECRETS-WP-0014-pdp-transport-and-responder-authentication.md |
| intake | SECRETS-IN-0001 | closed | — | intakes/intakes.md |
| intake | SECRETS-IN-0002 | closed | — | intakes/intakes.md |
| intake | SECRETS-IN-0003 | closed | — | intakes/intakes.md |

View file

@ -0,0 +1 @@
{".custodian-brief.md": "100644 f5952182bbfde84b60c85c4155da8c65f12ba0ab 0\t.custodian-brief.md\n", "WORK-RECORDS.md": "100644 70e5831d75b067c0d05efa3fab37a76a029cf9e9 0\tWORK-RECORDS.md\n"}

View file

@ -0,0 +1 @@
WARN: git commit failed for writeback: Generated-only commits rejected: staged

View file

@ -0,0 +1,142 @@
{
"repo_slug": "the-custodian",
"repo_path": "/home/worsch/the-custodian",
"source_revision": "f8c7dfa2a9c7919879b62c77eb39582b3e23654e",
"source_revision_reason": null,
"issues": [
{
"severity": "WARN",
"check_id": "C-35",
"message": "Repo Manager warning: workplans/: repository uses more than one workplan prefix: ['CUST-WP', 'THE-WP']",
"file_path": "workplans/",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-35",
"message": "Repo Manager contradictory: workplans/ADHOC-2026-08-25-retired.md: workplan id 'CUST-WP-ADHOC-2026-08-25-RETIRED' is not accepted by the canon kind registry",
"file_path": "workplans/ADHOC-2026-08-25-retired.md",
"db_id": "",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-05",
"message": "Title drift in 'cust-wp-0010': file='Domain and Repository Goals' db='Workplan Lifecycle Documentation' (file wins)",
"file_path": "workplans/CUST-WP-0010b-domain-and-repo-goals.md",
"db_id": "def8455a-9de4-4891-a15a-5b09ca98ab1e",
"file_value": "Domain and Repository Goals",
"db_value": "Workplan Lifecycle Documentation",
"fixable": true
},
{
"severity": "WARN",
"check_id": "C-20",
"message": "Workplan dependency target 'STATE-WP-0092' is not linked to State Hub",
"file_path": "workplans/CUST-WP-0072-fleet-flavor-and-depends-on-backfill.md",
"db_id": "",
"file_value": "STATE-WP-0092",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-40",
"message": "blocker satisfied, task still wait: 'CUST-WP-0073-T05' in workplan 'CUST-WP-0073' \u2014 decision 1591daa1-6e85-4dfd-aadd-5a9fe1ef47fa is resolved",
"file_path": "workplans/CUST-WP-0073-agent-credential-separation.md#CUST-WP-0073-T05",
"db_id": "",
"file_value": "1591daa1-6e85-4dfd-aadd-5a9fe1ef47fa",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-39",
"message": "Human wait task 'CUST-WP-0079-T06' in workplan 'CUST-WP-0079' has needs_human: true without decision_id \u2014 unrouted human gate",
"file_path": "workplans/CUST-WP-0079-deterministic-security-flow.md#CUST-WP-0079-T06",
"db_id": "",
"file_value": "needs_human: true",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-22",
"message": "Task description drift 'CUST-WP-0080-T06': file content differs from DB (file wins)",
"file_path": "workplans/CUST-WP-0080-netkingdom-security-blueprint-and-gap-closure.md#CUST-WP-0080-T06",
"db_id": "6aca534c-5c7a-556f-b6b6-406433670c29",
"file_value": "Founder implementation request, 2026-10-16. Document the optimized target and\ncoordinate GPT-6.1-Sol medium agents again",
"db_value": "Founder implementation request, 2026-10-16. Document the optimized target and\ncoordinate GPT-6.1-Sol medium agents again",
"fixable": true
},
{
"severity": "INFO",
"check_id": "C-08",
"message": "Closed DB workstream 'cust-wp-0010b' (id=416ff571\u2026, status=finished) has no backing workplan file",
"file_path": "",
"db_id": "416ff571-18cf-5cb2-9c8b-836f68a301b3",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "INFO",
"check_id": "C-08",
"message": "Retired DB workstream 'interactive-the-custodian@retired-20260828' (id=370c2481\u2026, status=finished) has no backing workplan file \u2014 projection tombstone, not live work",
"file_path": "",
"db_id": "370c2481-6806-41eb-a917-f8874f03184f",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "INFO",
"check_id": "C-08",
"message": "Retired DB workstream 'the-custodian-adhoc-2026-07-02@retired-20260827' (id=5c53733b\u2026, status=finished) has no backing workplan file \u2014 projection tombstone, not live work",
"file_path": "",
"db_id": "5c53733b-c077-4a93-be66-9c3af8f9b6fd",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "INFO",
"check_id": "C-08",
"message": "Retired DB workstream 'adhoc-2026-05-02@retired-20260827' (id=3f54ce9c\u2026, status=finished) has no backing workplan file \u2014 projection tombstone, not live work",
"file_path": "",
"db_id": "3f54ce9c-1f95-42de-894f-0f81a52ba2e8",
"file_value": "",
"db_value": "",
"fixable": false
},
{
"severity": "WARN",
"check_id": "C-26",
"message": "Workplan id 'THE-WP-0001' uses prefix 'THE-WP' but repo canonical prefix is 'CUST-WP' \u2014 new plans must conform",
"file_path": "workplans/THE-WP-0001-federation-interface.md",
"db_id": "",
"file_value": "THE-WP-0001",
"db_value": "CUST-WP",
"fixable": false
}
],
"fixes_applied": [
"bindings: synced 89/89",
"C-17 cleared: pushed 2 backlogged commit(s)",
"C-05 fixed: workstream def8455a\u2026 title \u2192 'Domain and Repository Goals'",
"C-22 fixed: task 6aca534c\u2026 description updated",
"push: pushed"
],
"summary": {
"fail": 0,
"automation_error": 0,
"warn": 8,
"info": 4
},
"result": "warn"
}

View file

@ -0,0 +1 @@
WARN: working-memory commit failed: Generated-only commits rejected: staged

View file

@ -0,0 +1,291 @@
{
"ok": true,
"status": "applied",
"repo_slug": "the-custodian",
"commit": "f8c7dfa2a9c7919879b62c77eb39582b3e23654e",
"requests": 2,
"elapsed_ms": 9278.0,
"git": {
"upstream": "origin/main",
"behind": 0,
"ahead": 0
},
"identifiers": {
"schema": "repo-manager.identifier-assignment.v1",
"ok": true,
"executed": true,
"repo": "the-custodian",
"namespace": "helixforge",
"assignments": [],
"historical_invalid_identifiers": [
{
"kind": "workplan",
"id": "CUST-WP-ADHOC-2026-08-25-RETIRED",
"source": "workplans/ADHOC-2026-08-25-retired.md"
}
],
"files_changed": []
},
"receipt": {
"schema": "state-hub.repository-projection-reconcile.v1",
"instance_role": "primary",
"instance_label": "railiance01",
"expected_commit": "f8c7dfa2a9c7919879b62c77eb39582b3e23654e",
"derived_commit": "f8c7dfa2a9c7919879b62c77eb39582b3e23654e",
"outcome": {
"schema": "state-hub.projection-reset.v1",
"repo_slug": "the-custodian",
"commit": "f8c7dfa2a9c7919879b62c77eb39582b3e23654e",
"status": "applied",
"counts": {
"created": 0,
"updated": 88,
"retired": 0,
"refused": 0,
"released": 0,
"created_tasks": 0,
"updated_tasks": 0,
"cancelled_tasks": 0,
"created_edges": 0,
"removed_edges": 0,
"unresolved_edges": 0,
"external_edges": 13
},
"created": [],
"updated": [
"CUST-WP-0000",
"CUST-WP-0000b",
"CUST-WP-0000c",
"CUST-WP-0001",
"CUST-WP-0002",
"CUST-WP-0004",
"CUST-WP-0005",
"CUST-WP-0006",
"CUST-WP-0007",
"CUST-WP-0008",
"CUST-WP-0009",
"CUST-WP-0010",
"CUST-WP-0010b",
"CUST-WP-0013",
"CUST-WP-0014",
"CUST-WP-0015",
"CUST-WP-0016",
"CUST-WP-0017",
"CUST-WP-0017-LEGACY",
"CUST-WP-0018",
"CUST-WP-0019",
"CUST-WP-0020",
"CUST-WP-0021",
"CUST-WP-0022",
"CUST-WP-0023",
"CUST-WP-0024",
"CUST-WP-0025",
"CUST-WP-0026",
"CUST-WP-0027",
"CUST-WP-0028",
"CUST-WP-0029",
"CUST-WP-0030",
"CUST-WP-0031",
"CUST-WP-0032",
"CUST-WP-0033",
"CUST-WP-0034",
"CUST-WP-0035",
"CUST-WP-0036",
"CUST-WP-0037",
"CUST-WP-0039",
"CUST-WP-0040",
"CUST-WP-0041",
"CUST-WP-0043",
"CUST-WP-0044",
"CUST-WP-0045",
"CUST-WP-0046",
"CUST-WP-0047",
"CUST-WP-0048",
"CUST-WP-0049",
"CUST-WP-0050",
"CUST-WP-0051",
"CUST-WP-0052",
"CUST-WP-0053",
"CUST-WP-0053-LEGACY",
"CUST-WP-0054",
"CUST-WP-0055",
"CUST-WP-0056",
"CUST-WP-0057",
"CUST-WP-0058",
"CUST-WP-0059",
"CUST-WP-0060",
"CUST-WP-0061",
"CUST-WP-0062",
"CUST-WP-0063",
"CUST-WP-0064",
"CUST-WP-0065",
"CUST-WP-0066",
"CUST-WP-0067",
"CUST-WP-0068",
"CUST-WP-0069",
"CUST-WP-0070",
"CUST-WP-0071",
"CUST-WP-0072",
"CUST-WP-0073",
"CUST-WP-0074",
"CUST-WP-0075",
"CUST-WP-0076",
"CUST-WP-0077",
"CUST-WP-0078",
"CUST-WP-0079",
"CUST-WP-0080",
"CUST-WP-0081",
"CUST-WP-ADHOC-2026-03-29",
"CUST-WP-ADHOC-2026-05-02",
"CUST-WP-ADHOC-2026-07-02",
"CUST-WP-ADHOC-2026-08-25",
"CUST-WP-ADHOC-2026-09-06",
"THE-WP-0001"
],
"retired": [],
"released": [],
"created_tasks": [],
"updated_tasks": [],
"cancelled_tasks": [],
"created_edges": [],
"removed_edges": [],
"unresolved_edges": [],
"external_edges": [
{
"workplan": "CUST-WP-0071",
"from": "CUST-WP-0071-T05",
"target": "CUST-WP-0071-T04",
"relationship_type": "starts_after",
"from_workplan_id": "2249bddb-7524-5add-bd5c-c4163a6ca0f3",
"from_task_id": "20ddd4d7-d85d-5b95-bb0a-7b0ca8af76ca",
"to_workplan_id": null,
"to_task_id": "944f98e2-7e42-5894-925b-752423f3a1cc"
},
{
"workplan": "CUST-WP-0071",
"from": "CUST-WP-0071-T03",
"target": "CUST-WP-0071-T01",
"relationship_type": "starts_after",
"from_workplan_id": "2249bddb-7524-5add-bd5c-c4163a6ca0f3",
"from_task_id": "6dc67558-eb1e-5bb6-a667-986f884dd495",
"to_workplan_id": null,
"to_task_id": "4ae8eb8d-f8c5-5256-ae50-c323cfd73d7a"
},
{
"workplan": "CUST-WP-0071",
"from": "CUST-WP-0071-T03",
"target": "CUST-WP-0071-T02",
"relationship_type": "starts_after",
"from_workplan_id": "2249bddb-7524-5add-bd5c-c4163a6ca0f3",
"from_task_id": "6dc67558-eb1e-5bb6-a667-986f884dd495",
"to_workplan_id": null,
"to_task_id": "82192370-2fd7-5363-88d2-3c67889d3d68"
},
{
"workplan": "CUST-WP-0071",
"from": "CUST-WP-0071-T02",
"target": "CUST-WP-0071-T01",
"relationship_type": "starts_after",
"from_workplan_id": "2249bddb-7524-5add-bd5c-c4163a6ca0f3",
"from_task_id": "82192370-2fd7-5363-88d2-3c67889d3d68",
"to_workplan_id": null,
"to_task_id": "4ae8eb8d-f8c5-5256-ae50-c323cfd73d7a"
},
{
"workplan": "CUST-WP-0071",
"from": "CUST-WP-0071-T02",
"target": "RAPPS-WP-0014-T03",
"relationship_type": "starts_after",
"from_workplan_id": "2249bddb-7524-5add-bd5c-c4163a6ca0f3",
"from_task_id": "82192370-2fd7-5363-88d2-3c67889d3d68",
"to_workplan_id": null,
"to_task_id": "dd069c6d-fcc1-5bac-b233-976f2f0d5cd1"
},
{
"workplan": "CUST-WP-0071",
"from": "CUST-WP-0071-T04",
"target": "CUST-WP-0071-T03",
"relationship_type": "starts_after",
"from_workplan_id": "2249bddb-7524-5add-bd5c-c4163a6ca0f3",
"from_task_id": "944f98e2-7e42-5894-925b-752423f3a1cc",
"to_workplan_id": null,
"to_task_id": "6dc67558-eb1e-5bb6-a667-986f884dd495"
},
{
"workplan": "CUST-WP-0073",
"from": "CUST-WP-0073-T02",
"target": "GLAS-WP-0012",
"relationship_type": "blocks",
"from_workplan_id": "a98a9f34-83b4-5c8c-8107-e05f7806d50d",
"from_task_id": "4b88b0b7-dc7e-5612-aa5d-1a08f0530c35",
"to_workplan_id": "170bf1ae-337f-5553-8d1e-03b07100e08f",
"to_task_id": null
},
{
"workplan": "CUST-WP-0073",
"from": "CUST-WP-0073-T04",
"target": "CUST-WP-0073-T02",
"relationship_type": "starts_after",
"from_workplan_id": "a98a9f34-83b4-5c8c-8107-e05f7806d50d",
"from_task_id": "90725511-4e31-549f-b567-47feff1a9ca4",
"to_workplan_id": null,
"to_task_id": "4b88b0b7-dc7e-5612-aa5d-1a08f0530c35"
},
{
"workplan": "CUST-WP-0079",
"from": "CUST-WP-0079-T03",
"target": "ACTIVITY-WP-0047",
"relationship_type": "blocks",
"from_workplan_id": "ab288f92-d364-5c24-9362-aee451f266c3",
"from_task_id": "1be0569c-221d-5925-a0ff-fd2af88e52b1",
"to_workplan_id": "ee97869b-dca2-54c9-aa18-0b479c244fb3",
"to_task_id": null
},
{
"workplan": "CUST-WP-0079",
"from": "CUST-WP-0079-T04",
"target": "PNEX-WP-0006",
"relationship_type": "blocks",
"from_workplan_id": "ab288f92-d364-5c24-9362-aee451f266c3",
"from_task_id": "5dd52156-09a8-5781-b288-99ae822f59a6",
"to_workplan_id": "774c5037-a3d0-5e65-893c-d18970acd66a",
"to_task_id": null
},
{
"workplan": "CUST-WP-0080",
"from": "CUST-WP-0080-T04",
"target": "CUST-WP-0080-T03",
"relationship_type": "starts_after",
"from_workplan_id": "dfadb19b-445e-59c6-bcd6-48e87b912c52",
"from_task_id": "82378b0f-7004-5c2f-9683-b356a1227576",
"to_workplan_id": null,
"to_task_id": "87637402-02f1-57c1-8fbc-4141598af8e3"
},
{
"workplan": "CUST-WP-0080",
"from": "CUST-WP-0080-T05",
"target": "RPF-WP-0056",
"relationship_type": "blocks",
"from_workplan_id": "dfadb19b-445e-59c6-bcd6-48e87b912c52",
"from_task_id": "ed8b909a-23bf-5e5f-b600-e477fbae136b",
"to_workplan_id": "31933d08-c877-5fda-aff9-6220c3705c92",
"to_task_id": null
},
{
"workplan": "CUST-WP-0080",
"from": "CUST-WP-0080-T05",
"target": "RAPP-PLAYWRIGHT-WP-0004",
"relationship_type": "blocks",
"from_workplan_id": "dfadb19b-445e-59c6-bcd6-48e87b912c52",
"from_task_id": "ed8b909a-23bf-5e5f-b600-e477fbae136b",
"to_workplan_id": "f9280c40-201e-59b5-a6f0-1aace8e0e2e2",
"to_task_id": null
}
],
"refused": [],
"notes": [
"Preserved bound historical row and task UUIDs: CUST-WP-ADHOC-2026-08-25-RETIRED"
]
}
}
}

View file

@ -0,0 +1,62 @@
<!-- custodian-brief: generated by fix-consistency — do not edit manually -->
# Custodian Brief — the-custodian
**Domain:** infotech
**Last synced:** 2026-10-15 23:45 UTC
**State Hub:** http://127.0.0.1:8000 *(adjust if running on a remote machine)*
## Active Workstreams
### NetKingdom target security architecture and SEC-DSM implementation
Progress: 2/6 done | workplan_id: `dfadb19b-445e-59c6-bcd6-48e87b912c52`
**Open tasks:**
- ► Close source defects and reconcile uncovered lifecycle gaps `87637402`
- ► Coordinate self-service Playwright identity delivery `ed8b909a`
- ► Establish the target architecture and drive the restructuring `6aca534c`
- · Verify native closure against every requirement `82378b0f`
### Separate agent credentials and establish supervised privileged execution
Progress: 2/5 done | workplan_id: `a98a9f34-83b4-5c8c-8107-e05f7806d50d`
**Open tasks:**
- ! Build and hand out the agent identity `4b88b0b7`
*(wait: Await GLAS-WP-0012 (glas-harness) production acceptance of the local supervised profile; then railiance-platform RBAC, railiance-enablement k3s config, railiance-infra principal mapping and ops-warden certificate issuance.)*
- ! Fleet guidance and harness guards `90725511`
*(wait: Await CUST-WP-0073-T02: the verified agent identity and execution path must exist before it can be documented; Codex/Grok read-denial guard needs glas-harness or harness-owner delivery.)*
- ! Rotate what was exposed `1b41b532`
*(wait: Deferred by founder decision 2026-09-24; reopened only by the founder on one of the three triggers below, in one attended rotation window.)*
### Size Railiance workloads from actual demand and establish a weekly allocation review
Progress: 1/5 done | workplan_id: `2249bddb-7524-5add-bd5c-c4163a6ca0f3`
**Open tasks:**
- ! Measure the Vergabe prototype under representative pilot use `82192370`
*(wait: Await RAPPS-WP-0014-T03 (blocked, needs_human): populated two-user/document workflow run by Bernd and the company contact, giving representative load for p95 <= 2s / zero failures.)*
- ! Review ecosystem allocations and reserve operating room `6dc67558`
*(wait: Await CUST-WP-0071-T02 representative sample; Forgejo/runner demand and zero-request workload review need owner input (railiance-cluster, railiance-forge, resource-control).)*
- ! Apply accepted sizing changes and verify their effects `944f98e2`
*(wait: Await reviewed allocation proposals and applicable workload-owner authority.)*
- ! Establish the regular weekly workload-demand and allocation assessment `20ddd4d7`
*(wait: Await the repeatable observation and accepted sizing/review procedure.)*
### Deterministic security flow: standing authorizations, flow report, and agent re-engagement
Progress: 3/7 done | workplan_id: `ab288f92-d364-5c24-9362-aee451f266c3`
**Open tasks:**
- ! Schedule the flow report and decision sync `1be0569c`
*(wait: Activity Core accepted the schedule in ACTIVITY-WP-0047. Await claiming rein workstation/hub acceptance, owner activation and the first unassisted fire with report/checkpoint evidence.)*
- ! Encode the standing change rule as a policy-nexus guardrail `5dd52156`
*(wait: policy-nexus owns guardrail publication; handoff written as PNEX-WP-0006.)*
- ! Stop agent-authored index and sync commits `8a3dc219`
*(wait: Local guard and repeatable shared-hook installation are implemented. Fleet generator adoption and the required full week of clean history remain unverified; repo-manager owner acceptance is needed.)*
- ! Attended window #1 `e3da807f`
*(wait: Partly done 2026-10-11: list cut from 14 to 3; U05-U07 accepted, U08 waits on KEY-WP-0040-T01. Remaining founder acts: USER-WP-0026-T03 readback, RPF-WP-0044-T08 coulombcore check, the U08 re-run, and Sol's added RPF-WP-0044-T04 issuer login.)*
---
## MCP Orientation (when available)
If the state-hub MCP server is reachable, call:
`get_domain_summary("infotech")`
This provides richer cross-domain context.
If the MCP call fails, use this file as your orientation source.

View file

@ -0,0 +1,536 @@
# Work Records — the-custodian
> Generated by `statehub fix-consistency` (CUST-WP-0061-T04, work-record
> stage 3). Do not edit by hand — edit the source file/block listed for
> each record and re-run fix-consistency to refresh this index. Archived
> workplans are omitted; closed decisions/intakes/engagements stay listed
> so recently-resolved work is still visible. [auto]
| Kind | ID | Status | Lane | Source |
| --- | --- | --- | --- | --- |
| workplan | CUST-WP-ADHOC-2026-05-02 | done | — | workplans/ADHOC-2026-05-02.md |
| workplan | CUST-WP-ADHOC-2026-07-02 | finished | — | workplans/ADHOC-2026-07-02.md |
| workplan | CUST-WP-ADHOC-2026-08-25-RETIRED | finished | — | workplans/ADHOC-2026-08-25-retired.md |
| workplan | CUST-WP-ADHOC-2026-08-25 | finished | — | workplans/ADHOC-2026-08-25.md |
| workplan | CUST-WP-ADHOC-2026-09-06 | finished | — | workplans/ADHOC-2026-09-06.md |
| workplan | CUST-WP-0000 | finished | — | workplans/CUST-WP-0000-state-hub-v0.1-build-deploy.md |
| workplan | CUST-WP-0000b | finished | — | workplans/CUST-WP-0000b-state-hub-v0.2-decisions-dependencies.md |
| workplan | CUST-WP-0001 | done | — | workplans/CUST-WP-0001-custodian-agent-runtime.md |
| workplan | CUST-WP-0002 | finished | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| workplan | CUST-WP-0004 | finished | — | workplans/CUST-WP-0004-ep-td-tracking.md |
| workplan | CUST-WP-0005 | finished | — | workplans/CUST-WP-0005-dynamic-domains.md |
| workplan | CUST-WP-0006 | done | — | workplans/CUST-WP-0006-gems-state-hub.md |
| workplan | CUST-WP-0007 | finished | — | workplans/CUST-WP-0007-gems-migration.md |
| workplan | CUST-WP-0008 | done | — | workplans/CUST-WP-0008-consistency-engine.md |
| workplan | CUST-WP-0009 | finished | — | workplans/CUST-WP-0009-human-interventions.md |
| workplan | CUST-WP-0010 | finished | — | workplans/CUST-WP-0010-workstream-lifecycle-docs.md |
| workplan | CUST-WP-0010b | finished | — | workplans/CUST-WP-0010b-domain-and-repo-goals.md |
| workplan | CUST-WP-0013 | finished | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| workplan | CUST-WP-0015 | done | — | workplans/CUST-WP-0015-agent-inbox.md |
| workplan | CUST-WP-0016 | done | — | workplans/CUST-WP-0016-kaizen-agentic-integration.md |
| workplan | CUST-WP-0017 | done | — | workplans/CUST-WP-0017-scope-md-agent-and-coverage.md |
| workplan | CUST-WP-0018 | done | — | workplans/CUST-WP-0018-api-hardening-code-quality.md |
| workplan | CUST-WP-0019 | done | — | workplans/CUST-WP-0019-dashboard-ux-polish.md |
| workplan | CUST-WP-0020 | done | — | workplans/CUST-WP-0020-test-suite.md |
| workplan | CUST-WP-0021 | done | — | workplans/CUST-WP-0021-multi-host-repo-paths.md |
| workplan | CUST-WP-0022 | done | — | workplans/CUST-WP-0022-capability-requests.md |
| workplan | CUST-WP-0023 | done | — | workplans/CUST-WP-0023-tpsc.md |
| workplan | CUST-WP-0024 | done | — | workplans/CUST-WP-0024-repo-doi-gate.md |
| workplan | CUST-WP-0026 | done | — | workplans/CUST-WP-0026-distributed-consistency.md |
| workplan | CUST-WP-0027 | done | — | workplans/CUST-WP-0027-capability-request-dispute.md |
| workplan | CUST-WP-0029 | done | — | workplans/CUST-WP-0029-token-consumption-tracking.md |
| workplan | CUST-WP-0030 | done | — | workplans/CUST-WP-0030-dashboard-entity-list-ux.md |
| workplan | CUST-WP-0031 | done | — | workplans/CUST-WP-0031-capability-registry.md |
| workplan | CUST-WP-0032 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| workplan | CUST-WP-0033 | done | — | workplans/CUST-WP-0033-interface-change-registry.md |
| workplan | CUST-WP-0039 | done | — | workplans/CUST-WP-0039-dashboard-poll-optimization.md |
| workplan | CUST-WP-0040 | finished | — | workplans/CUST-WP-0040-state-hub-nats-activity-core-integration.md |
| workplan | CUST-WP-0041 | done | — | workplans/CUST-WP-0041-api-performance.md |
| workplan | CUST-WP-0043 | finished | — | workplans/CUST-WP-0043-state-hub-repo-extraction.md |
| workplan | CUST-WP-0044 | finished | — | workplans/CUST-WP-0044-daily-statehub-wsjf-triage.md |
| workplan | CUST-WP-0045 | finished | — | workplans/CUST-WP-0045-activity-core-daily-triage-runner.md |
| workplan | CUST-WP-0069 | finished | — | workplans/CUST-WP-0045-cutover-runbook.md |
| workplan | CUST-WP-0046 | finished | — | workplans/CUST-WP-0046-hourly-recently-on-scope-activity-core.md |
| workplan | CUST-WP-0047 | finished | — | workplans/CUST-WP-0047-ops-hub-service-inventory-now-view.md |
| workplan | CUST-WP-0048 | finished | — | workplans/CUST-WP-0048-hub-core-state-hub-import-refactor.md |
| workplan | CUST-WP-0049 | finished | — | workplans/CUST-WP-0049-interhub-bootstrap-access-lane.md |
| workplan | CUST-WP-0050 | finished | — | workplans/CUST-WP-0050-repo-classification-registration-redesign.md |
| workplan | CUST-WP-0051 | finished | — | workplans/CUST-WP-0051-infrastructure-stabilization-metaplan.md |
| workplan | CUST-WP-0052 | finished | — | workplans/CUST-WP-0052-core-hub-fos-reset.md |
| workplan | CUST-WP-0053 | finished | — | workplans/CUST-WP-0053-coordination-hygiene-improvements.md |
| workplan | CUST-WP-0055 | finished | — | workplans/CUST-WP-0055-workplan-terminology-fleet-refactor.md |
| workplan | CUST-WP-0056 | finished | — | workplans/CUST-WP-0056-daily-todo-md-stale-review.md |
| workplan | CUST-WP-0059 | finished | — | workplans/CUST-WP-0059-forgejo-ci-publish-cutover-tail.md |
| workplan | CUST-WP-0060 | finished | — | workplans/CUST-WP-0060-work-record-canonization.md |
| workplan | CUST-WP-0061 | finished | — | workplans/CUST-WP-0061-work-record-stage3-intake-promotion-index.md |
| workplan | CUST-WP-0062 | finished | — | workplans/CUST-WP-0062-sbom-nexus-daily-catchup.md |
| workplan | CUST-WP-0063 | finished | — | workplans/CUST-WP-0063-inbox-governance-packets.md |
| workplan | CUST-WP-0064 | finished | — | workplans/CUST-WP-0064-sbom-controlled-scan-inputs.md |
| workplan | CUST-WP-0065 | finished | — | workplans/CUST-WP-0065-reclassify-repos-and-guidance-docs-to-the-new-sector-domain.md |
| workplan | CUST-WP-0066 | finished | — | workplans/CUST-WP-0066-repository-qualified-ad-hoc-identifiers.md |
| workplan | CUST-WP-0067 | finished | — | workplans/CUST-WP-0067-hub-authority-target-resolution.md |
| workplan | CUST-WP-0068 | finished | — | workplans/CUST-WP-0068-cache-only-work-record-recovery.md |
| workplan | CUST-WP-0070 | finished | — | workplans/CUST-WP-0070-publication-repo-category.md |
| workplan | CUST-WP-0071 | blocked | — | workplans/CUST-WP-0071-measured-workload-sizing-and-weekly-review.md |
| workplan | CUST-WP-0072 | finished | — | workplans/CUST-WP-0072-fleet-flavor-and-depends-on-backfill.md |
| workplan | CUST-WP-0073 | blocked | — | workplans/CUST-WP-0073-agent-credential-separation.md |
| workplan | CUST-WP-0074 | finished | — | workplans/CUST-WP-0074-qualified-wait-states.md |
| workplan | CUST-WP-0075 | finished | — | workplans/CUST-WP-0075-dependency-graph-driven-unblocking.md |
| workplan | CUST-WP-0076 | finished | — | workplans/CUST-WP-0076-provisioning-window-cadence.md |
| workplan | CUST-WP-0077 | finished | — | workplans/CUST-WP-0077-dependency-root-execution-wave.md |
| workplan | CUST-WP-0078 | finished | — | workplans/CUST-WP-0078-security-collaboration-consolidation.md |
| workplan | CUST-WP-0079 | blocked | — | workplans/CUST-WP-0079-deterministic-security-flow.md |
| workplan | CUST-WP-0080 | active | — | workplans/CUST-WP-0080-netkingdom-security-blueprint-and-gap-closure.md |
| workplan | CUST-WP-0081 | finished | — | workplans/CUST-WP-0081-netkingdom-architecture-review-and-reuse.md |
| workplan | THE-WP-0001 | finished | — | workplans/THE-WP-0001-federation-interface.md |
| task | CUST-WP-ADHOC-2026-05-02-T01 | done | — | workplans/ADHOC-2026-05-02.md |
| task | CUST-WP-ADHOC-2026-07-02-T01 | done | — | workplans/ADHOC-2026-07-02.md |
| task | ADHOC-2026-08-25-T01 | done | — | workplans/ADHOC-2026-08-25-retired.md |
| task | CUST-WP-ADHOC-2026-08-25-T01 | done | — | workplans/ADHOC-2026-08-25.md |
| task | CUST-WP-ADHOC-2026-09-06-T01 | done | — | workplans/ADHOC-2026-09-06.md |
| task | CUST-WP-0001-T01 | done | — | workplans/CUST-WP-0001-custodian-agent-runtime.md |
| task | CUST-WP-0001-T02 | done | — | workplans/CUST-WP-0001-custodian-agent-runtime.md |
| task | CUST-WP-0002-T01 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0002-T02 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0002-T03 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0002-T04 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0002-T05 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0002-T06 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0002-T07 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0002-T08 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0002-T09 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0002-T10 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0002-T11 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0002-T12 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0002-T13 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0002-T14 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0002-T15 | done | — | workplans/CUST-WP-0002-contribution-tracking-sbom.md |
| task | CUST-WP-0004-T01 | done | — | workplans/CUST-WP-0004-ep-td-tracking.md |
| task | CUST-WP-0004-T02 | done | — | workplans/CUST-WP-0004-ep-td-tracking.md |
| task | CUST-WP-0004-T03 | done | — | workplans/CUST-WP-0004-ep-td-tracking.md |
| task | CUST-WP-0004-T04 | done | — | workplans/CUST-WP-0004-ep-td-tracking.md |
| task | CUST-WP-0004-T05 | done | — | workplans/CUST-WP-0004-ep-td-tracking.md |
| task | CUST-WP-0004-T06 | done | — | workplans/CUST-WP-0004-ep-td-tracking.md |
| task | CUST-WP-0004-T07 | done | — | workplans/CUST-WP-0004-ep-td-tracking.md |
| task | CUST-WP-0004-T08 | done | — | workplans/CUST-WP-0004-ep-td-tracking.md |
| task | CUST-WP-0004-T09 | done | — | workplans/CUST-WP-0004-ep-td-tracking.md |
| task | CUST-WP-0004-T10 | done | — | workplans/CUST-WP-0004-ep-td-tracking.md |
| task | CUST-WP-0005-T01 | done | — | workplans/CUST-WP-0005-dynamic-domains.md |
| task | CUST-WP-0005-T02 | done | — | workplans/CUST-WP-0005-dynamic-domains.md |
| task | CUST-WP-0005-T03 | done | — | workplans/CUST-WP-0005-dynamic-domains.md |
| task | CUST-WP-0005-T04 | done | — | workplans/CUST-WP-0005-dynamic-domains.md |
| task | CUST-WP-0005-T05 | done | — | workplans/CUST-WP-0005-dynamic-domains.md |
| task | CUST-WP-0005-T06 | done | — | workplans/CUST-WP-0005-dynamic-domains.md |
| task | CUST-WP-0005-T07 | done | — | workplans/CUST-WP-0005-dynamic-domains.md |
| task | CUST-WP-0005-T08 | done | — | workplans/CUST-WP-0005-dynamic-domains.md |
| task | CUST-WP-0005-T09 | done | — | workplans/CUST-WP-0005-dynamic-domains.md |
| task | CUST-WP-0005-T10 | done | — | workplans/CUST-WP-0005-dynamic-domains.md |
| task | CUST-WP-0005-T11 | done | — | workplans/CUST-WP-0005-dynamic-domains.md |
| task | T01 | done | — | workplans/CUST-WP-0006-gems-state-hub.md |
| task | T02 | done | — | workplans/CUST-WP-0006-gems-state-hub.md |
| task | T03 | done | — | workplans/CUST-WP-0006-gems-state-hub.md |
| task | T04 | done | — | workplans/CUST-WP-0006-gems-state-hub.md |
| task | T05 | done | — | workplans/CUST-WP-0006-gems-state-hub.md |
| task | T01 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T02 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T03 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T04 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T05 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T06 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T07 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T08 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T09 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T10 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T11 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T12 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T13 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T14 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T15 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T16 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | T17 | done | — | workplans/CUST-WP-0007-gems-migration.md |
| task | CUST-WP-0008-T01 | done | — | workplans/CUST-WP-0008-consistency-engine.md |
| task | CUST-WP-0008-T02 | done | — | workplans/CUST-WP-0008-consistency-engine.md |
| task | CUST-WP-0008-T03 | done | — | workplans/CUST-WP-0008-consistency-engine.md |
| task | CUST-WP-0008-T04 | done | — | workplans/CUST-WP-0008-consistency-engine.md |
| task | CUST-WP-0009-T1 | done | — | workplans/CUST-WP-0009-human-interventions.md |
| task | CUST-WP-0009-T2 | done | — | workplans/CUST-WP-0009-human-interventions.md |
| task | CUST-WP-0009-T3 | done | — | workplans/CUST-WP-0009-human-interventions.md |
| task | CUST-WP-0010-T1 | done | — | workplans/CUST-WP-0010-workstream-lifecycle-docs.md |
| task | CUST-WP-0010-T2 | done | — | workplans/CUST-WP-0010-workstream-lifecycle-docs.md |
| task | CUST-WP-0010-T3 | done | — | workplans/CUST-WP-0010-workstream-lifecycle-docs.md |
| task | CUST-WP-0010b-T01 | done | — | workplans/CUST-WP-0010b-domain-and-repo-goals.md |
| task | CUST-WP-0010b-T02 | done | — | workplans/CUST-WP-0010b-domain-and-repo-goals.md |
| task | CUST-WP-0013-T01 | done | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| task | CUST-WP-0013-T02 | done | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| task | CUST-WP-0013-T03 | done | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| task | CUST-WP-0013-T04 | done | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| task | CUST-WP-0013-T05 | done | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| task | CUST-WP-0013-T06 | done | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| task | CUST-WP-0013-T07 | done | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| task | CUST-WP-0013-T08 | done | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| task | CUST-WP-0013-T09 | done | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| task | CUST-WP-0013-T10 | done | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| task | CUST-WP-0013-T11 | done | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| task | CUST-WP-0013-T12 | done | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| task | CUST-WP-0013-T13 | done | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| task | CUST-WP-0013-T14 | done | — | workplans/CUST-WP-0013-sbom-infra-expansion.md |
| task | CUST-WP-0015-T01 | done | — | workplans/CUST-WP-0015-agent-inbox.md |
| task | CUST-WP-0015-T02 | done | — | workplans/CUST-WP-0015-agent-inbox.md |
| task | CUST-WP-0015-T03 | done | — | workplans/CUST-WP-0015-agent-inbox.md |
| task | CUST-WP-0015-T04 | done | — | workplans/CUST-WP-0015-agent-inbox.md |
| task | CUST-WP-0015-T05 | done | — | workplans/CUST-WP-0015-agent-inbox.md |
| task | CUST-WP-0016-T01 | done | — | workplans/CUST-WP-0016-kaizen-agentic-integration.md |
| task | CUST-WP-0016-T02 | done | — | workplans/CUST-WP-0016-kaizen-agentic-integration.md |
| task | CUST-WP-0016-T03 | done | — | workplans/CUST-WP-0016-kaizen-agentic-integration.md |
| task | CUST-WP-0016-T04 | done | — | workplans/CUST-WP-0016-kaizen-agentic-integration.md |
| task | CUST-WP-0016-T05 | done | — | workplans/CUST-WP-0016-kaizen-agentic-integration.md |
| task | CUST-WP-0017-T01 | done | — | workplans/CUST-WP-0017-scope-md-agent-and-coverage.md |
| task | CUST-WP-0017-T02 | done | — | workplans/CUST-WP-0017-scope-md-agent-and-coverage.md |
| task | CUST-WP-0017-T03 | done | — | workplans/CUST-WP-0017-scope-md-agent-and-coverage.md |
| task | CUST-WP-0017-T04 | done | — | workplans/CUST-WP-0017-scope-md-agent-and-coverage.md |
| task | CUST-WP-0017-T05 | done | — | workplans/CUST-WP-0017-scope-md-agent-and-coverage.md |
| task | CUST-WP-0017-T06 | done | — | workplans/CUST-WP-0017-scope-md-agent-and-coverage.md |
| task | CUST-WP-0018-T01 | done | — | workplans/CUST-WP-0018-api-hardening-code-quality.md |
| task | CUST-WP-0018-T02 | done | — | workplans/CUST-WP-0018-api-hardening-code-quality.md |
| task | CUST-WP-0018-T03 | done | — | workplans/CUST-WP-0018-api-hardening-code-quality.md |
| task | CUST-WP-0018-T04 | done | — | workplans/CUST-WP-0018-api-hardening-code-quality.md |
| task | CUST-WP-0018-T05 | done | — | workplans/CUST-WP-0018-api-hardening-code-quality.md |
| task | CUST-WP-0018-T06 | done | — | workplans/CUST-WP-0018-api-hardening-code-quality.md |
| task | CUST-WP-0018-T07 | done | — | workplans/CUST-WP-0018-api-hardening-code-quality.md |
| task | CUST-WP-0019-T01 | done | — | workplans/CUST-WP-0019-dashboard-ux-polish.md |
| task | CUST-WP-0019-T02 | done | — | workplans/CUST-WP-0019-dashboard-ux-polish.md |
| task | CUST-WP-0019-T03 | done | — | workplans/CUST-WP-0019-dashboard-ux-polish.md |
| task | CUST-WP-0020-T01 | done | — | workplans/CUST-WP-0020-test-suite.md |
| task | CUST-WP-0020-T02 | done | — | workplans/CUST-WP-0020-test-suite.md |
| task | CUST-WP-0020-T03 | done | — | workplans/CUST-WP-0020-test-suite.md |
| task | CUST-WP-0020-T04 | done | — | workplans/CUST-WP-0020-test-suite.md |
| task | CUST-WP-0020-T05 | done | — | workplans/CUST-WP-0020-test-suite.md |
| task | CUST-WP-0021-T01 | done | — | workplans/CUST-WP-0021-multi-host-repo-paths.md |
| task | CUST-WP-0021-T02 | done | — | workplans/CUST-WP-0021-multi-host-repo-paths.md |
| task | CUST-WP-0021-T03 | done | — | workplans/CUST-WP-0021-multi-host-repo-paths.md |
| task | CUST-WP-0021-T04 | done | — | workplans/CUST-WP-0021-multi-host-repo-paths.md |
| task | CUST-WP-0021-T05 | done | — | workplans/CUST-WP-0021-multi-host-repo-paths.md |
| task | CUST-WP-0022-T01 | done | — | workplans/CUST-WP-0022-capability-requests.md |
| task | CUST-WP-0022-T02 | done | — | workplans/CUST-WP-0022-capability-requests.md |
| task | CUST-WP-0022-T03 | done | — | workplans/CUST-WP-0022-capability-requests.md |
| task | CUST-WP-0022-T04 | done | — | workplans/CUST-WP-0022-capability-requests.md |
| task | CUST-WP-0022-T05 | done | — | workplans/CUST-WP-0022-capability-requests.md |
| task | CUST-WP-0022-T06 | done | — | workplans/CUST-WP-0022-capability-requests.md |
| task | CUST-WP-0022-T07 | done | — | workplans/CUST-WP-0022-capability-requests.md |
| task | CUST-WP-0022-T08 | done | — | workplans/CUST-WP-0022-capability-requests.md |
| task | CUST-WP-0022-T09 | done | — | workplans/CUST-WP-0022-capability-requests.md |
| task | CUST-WP-0022-T10 | done | — | workplans/CUST-WP-0022-capability-requests.md |
| task | CUST-WP-0023-T01 | done | — | workplans/CUST-WP-0023-tpsc.md |
| task | CUST-WP-0023-T02 | done | — | workplans/CUST-WP-0023-tpsc.md |
| task | CUST-WP-0023-T03 | done | — | workplans/CUST-WP-0023-tpsc.md |
| task | CUST-WP-0023-T04 | done | — | workplans/CUST-WP-0023-tpsc.md |
| task | CUST-WP-0023-T05 | done | — | workplans/CUST-WP-0023-tpsc.md |
| task | CUST-WP-0023-T06 | done | — | workplans/CUST-WP-0023-tpsc.md |
| task | CUST-WP-0023-T07 | done | — | workplans/CUST-WP-0023-tpsc.md |
| task | CUST-WP-0023-T08 | done | — | workplans/CUST-WP-0023-tpsc.md |
| task | CUST-WP-0023-T09 | done | — | workplans/CUST-WP-0023-tpsc.md |
| task | CUST-WP-0023-T10 | done | — | workplans/CUST-WP-0023-tpsc.md |
| task | CUST-WP-0024-T01 | done | — | workplans/CUST-WP-0024-repo-doi-gate.md |
| task | CUST-WP-0024-T02 | done | — | workplans/CUST-WP-0024-repo-doi-gate.md |
| task | CUST-WP-0024-T03 | done | — | workplans/CUST-WP-0024-repo-doi-gate.md |
| task | CUST-WP-0024-T04 | done | — | workplans/CUST-WP-0024-repo-doi-gate.md |
| task | CUST-WP-0024-T05 | done | — | workplans/CUST-WP-0024-repo-doi-gate.md |
| task | CUST-WP-0026-T01 | done | — | workplans/CUST-WP-0026-distributed-consistency.md |
| task | CUST-WP-0026-T02 | done | — | workplans/CUST-WP-0026-distributed-consistency.md |
| task | CUST-WP-0026-T03 | done | — | workplans/CUST-WP-0026-distributed-consistency.md |
| task | CUST-WP-0026-T04 | done | — | workplans/CUST-WP-0026-distributed-consistency.md |
| task | CUST-WP-0026-T05 | done | — | workplans/CUST-WP-0026-distributed-consistency.md |
| task | CUST-WP-0027-T01 | done | — | workplans/CUST-WP-0027-capability-request-dispute.md |
| task | CUST-WP-0027-T02 | done | — | workplans/CUST-WP-0027-capability-request-dispute.md |
| task | CUST-WP-0027-T03 | done | — | workplans/CUST-WP-0027-capability-request-dispute.md |
| task | CUST-WP-0027-T04 | done | — | workplans/CUST-WP-0027-capability-request-dispute.md |
| task | CUST-WP-0027-T05 | done | — | workplans/CUST-WP-0027-capability-request-dispute.md |
| task | CUST-WP-0029-T01 | done | — | workplans/CUST-WP-0029-token-consumption-tracking.md |
| task | CUST-WP-0029-T02 | done | — | workplans/CUST-WP-0029-token-consumption-tracking.md |
| task | CUST-WP-0029-T03 | done | — | workplans/CUST-WP-0029-token-consumption-tracking.md |
| task | CUST-WP-0029-T04 | done | — | workplans/CUST-WP-0029-token-consumption-tracking.md |
| task | CUST-WP-0029-T05 | done | — | workplans/CUST-WP-0029-token-consumption-tracking.md |
| task | CUST-WP-0029-T06 | done | — | workplans/CUST-WP-0029-token-consumption-tracking.md |
| task | CUST-WP-0029-T07 | done | — | workplans/CUST-WP-0029-token-consumption-tracking.md |
| task | CUST-WP-0029-T08 | done | — | workplans/CUST-WP-0029-token-consumption-tracking.md |
| task | T01 | done | — | workplans/CUST-WP-0030-dashboard-entity-list-ux.md |
| task | T02 | done | — | workplans/CUST-WP-0030-dashboard-entity-list-ux.md |
| task | T03 | done | — | workplans/CUST-WP-0030-dashboard-entity-list-ux.md |
| task | T04 | done | — | workplans/CUST-WP-0030-dashboard-entity-list-ux.md |
| task | T05 | done | — | workplans/CUST-WP-0030-dashboard-entity-list-ux.md |
| task | T06 | done | — | workplans/CUST-WP-0030-dashboard-entity-list-ux.md |
| task | T07 | done | — | workplans/CUST-WP-0030-dashboard-entity-list-ux.md |
| task | T08 | done | — | workplans/CUST-WP-0030-dashboard-entity-list-ux.md |
| task | T09 | done | — | workplans/CUST-WP-0030-dashboard-entity-list-ux.md |
| task | T01 | done | — | workplans/CUST-WP-0031-capability-registry.md |
| task | T02 | done | — | workplans/CUST-WP-0031-capability-registry.md |
| task | T03 | done | — | workplans/CUST-WP-0031-capability-registry.md |
| task | T04 | done | — | workplans/CUST-WP-0031-capability-registry.md |
| task | T05 | done | — | workplans/CUST-WP-0031-capability-registry.md |
| task | T06 | done | — | workplans/CUST-WP-0031-capability-registry.md |
| task | T07 | done | — | workplans/CUST-WP-0031-capability-registry.md |
| task | CUST-WP-0032-T01 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0032-T02 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0032-T03 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0032-T04 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0032-T05 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0032-T06 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0032-T07 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0032-T08 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0032-T09 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0032-T10 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0032-T11 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0032-T12 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0032-T13 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0032-T14 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0032-T15 | done | — | workplans/CUST-WP-0032-haskell-build-machine.md |
| task | CUST-WP-0033-T01 | done | — | workplans/CUST-WP-0033-interface-change-registry.md |
| task | CUST-WP-0033-T02 | done | — | workplans/CUST-WP-0033-interface-change-registry.md |
| task | CUST-WP-0033-T03 | done | — | workplans/CUST-WP-0033-interface-change-registry.md |
| task | CUST-WP-0033-T04 | done | — | workplans/CUST-WP-0033-interface-change-registry.md |
| task | CUST-WP-0033-T05 | done | — | workplans/CUST-WP-0033-interface-change-registry.md |
| task | CUST-WP-0033-T06 | done | — | workplans/CUST-WP-0033-interface-change-registry.md |
| task | CUST-WP-0039-T1 | done | — | workplans/CUST-WP-0039-dashboard-poll-optimization.md |
| task | CUST-WP-0039-T2 | done | — | workplans/CUST-WP-0039-dashboard-poll-optimization.md |
| task | CUST-WP-0039-T3 | done | — | workplans/CUST-WP-0039-dashboard-poll-optimization.md |
| task | CUST-WP-0039-T4 | done | — | workplans/CUST-WP-0039-dashboard-poll-optimization.md |
| task | CUST-WP-0039-T5 | done | — | workplans/CUST-WP-0039-dashboard-poll-optimization.md |
| task | CUST-WP-0039-T6 | done | — | workplans/CUST-WP-0039-dashboard-poll-optimization.md |
| task | T01 | done | — | workplans/CUST-WP-0040-state-hub-nats-activity-core-integration.md |
| task | T02 | done | — | workplans/CUST-WP-0040-state-hub-nats-activity-core-integration.md |
| task | T03 | done | — | workplans/CUST-WP-0040-state-hub-nats-activity-core-integration.md |
| task | T04 | done | — | workplans/CUST-WP-0040-state-hub-nats-activity-core-integration.md |
| task | T05 | done | — | workplans/CUST-WP-0040-state-hub-nats-activity-core-integration.md |
| task | T06 | done | — | workplans/CUST-WP-0040-state-hub-nats-activity-core-integration.md |
| task | CUST-WP-0041-T1 | done | — | workplans/CUST-WP-0041-api-performance.md |
| task | CUST-WP-0041-T2 | done | — | workplans/CUST-WP-0041-api-performance.md |
| task | CUST-WP-0041-T3 | done | — | workplans/CUST-WP-0041-api-performance.md |
| task | CUST-WP-0041-T4 | done | — | workplans/CUST-WP-0041-api-performance.md |
| task | CUST-WP-0043-T01 | done | — | workplans/CUST-WP-0043-state-hub-repo-extraction.md |
| task | CUST-WP-0043-T02 | done | — | workplans/CUST-WP-0043-state-hub-repo-extraction.md |
| task | CUST-WP-0043-T03 | done | — | workplans/CUST-WP-0043-state-hub-repo-extraction.md |
| task | CUST-WP-0043-T04 | done | — | workplans/CUST-WP-0043-state-hub-repo-extraction.md |
| task | CUST-WP-0043-T05 | done | — | workplans/CUST-WP-0043-state-hub-repo-extraction.md |
| task | CUST-WP-0043-T06 | done | — | workplans/CUST-WP-0043-state-hub-repo-extraction.md |
| task | CUST-WP-0043-T07 | done | — | workplans/CUST-WP-0043-state-hub-repo-extraction.md |
| task | CUST-WP-0043-T08 | done | — | workplans/CUST-WP-0043-state-hub-repo-extraction.md |
| task | CUST-WP-0043-T09 | done | — | workplans/CUST-WP-0043-state-hub-repo-extraction.md |
| task | CUST-WP-0044-T01 | done | — | workplans/CUST-WP-0044-daily-statehub-wsjf-triage.md |
| task | CUST-WP-0044-T02 | done | — | workplans/CUST-WP-0044-daily-statehub-wsjf-triage.md |
| task | CUST-WP-0044-T03 | done | — | workplans/CUST-WP-0044-daily-statehub-wsjf-triage.md |
| task | CUST-WP-0044-T04 | done | — | workplans/CUST-WP-0044-daily-statehub-wsjf-triage.md |
| task | CUST-WP-0044-T05 | done | — | workplans/CUST-WP-0044-daily-statehub-wsjf-triage.md |
| task | CUST-WP-0044-T06 | done | — | workplans/CUST-WP-0044-daily-statehub-wsjf-triage.md |
| task | CUST-WP-0045-T01 | done | — | workplans/CUST-WP-0045-activity-core-daily-triage-runner.md |
| task | CUST-WP-0045-T02 | done | — | workplans/CUST-WP-0045-activity-core-daily-triage-runner.md |
| task | CUST-WP-0045-T03 | done | — | workplans/CUST-WP-0045-activity-core-daily-triage-runner.md |
| task | CUST-WP-0045-T04 | done | — | workplans/CUST-WP-0045-activity-core-daily-triage-runner.md |
| task | CUST-WP-0045-T05 | done | — | workplans/CUST-WP-0045-activity-core-daily-triage-runner.md |
| task | CUST-WP-0045-T06 | done | — | workplans/CUST-WP-0045-activity-core-daily-triage-runner.md |
| task | CUST-WP-0045-T07 | done | — | workplans/CUST-WP-0045-activity-core-daily-triage-runner.md |
| task | CUST-WP-0045-T08 | done | — | workplans/CUST-WP-0045-activity-core-daily-triage-runner.md |
| task | CUST-WP-0046-T01 | done | — | workplans/CUST-WP-0046-hourly-recently-on-scope-activity-core.md |
| task | CUST-WP-0046-T02 | done | — | workplans/CUST-WP-0046-hourly-recently-on-scope-activity-core.md |
| task | CUST-WP-0046-T03 | done | — | workplans/CUST-WP-0046-hourly-recently-on-scope-activity-core.md |
| task | CUST-WP-0046-T04 | done | — | workplans/CUST-WP-0046-hourly-recently-on-scope-activity-core.md |
| task | CUST-WP-0046-T05 | done | — | workplans/CUST-WP-0046-hourly-recently-on-scope-activity-core.md |
| task | CUST-WP-0046-T06 | done | — | workplans/CUST-WP-0046-hourly-recently-on-scope-activity-core.md |
| task | CUST-WP-0046-T07 | done | — | workplans/CUST-WP-0046-hourly-recently-on-scope-activity-core.md |
| task | CUST-WP-0047-T01 | done | — | workplans/CUST-WP-0047-ops-hub-service-inventory-now-view.md |
| task | CUST-WP-0047-T02 | done | — | workplans/CUST-WP-0047-ops-hub-service-inventory-now-view.md |
| task | CUST-WP-0047-T03 | done | — | workplans/CUST-WP-0047-ops-hub-service-inventory-now-view.md |
| task | CUST-WP-0047-T04 | done | — | workplans/CUST-WP-0047-ops-hub-service-inventory-now-view.md |
| task | CUST-WP-0047-T05 | cancel | — | workplans/CUST-WP-0047-ops-hub-service-inventory-now-view.md |
| task | CUST-WP-0047-T06 | done | — | workplans/CUST-WP-0047-ops-hub-service-inventory-now-view.md |
| task | CUST-WP-0047-T07 | done | — | workplans/CUST-WP-0047-ops-hub-service-inventory-now-view.md |
| task | CUST-WP-0048-T01 | done | — | workplans/CUST-WP-0048-hub-core-state-hub-import-refactor.md |
| task | CUST-WP-0048-T02 | done | — | workplans/CUST-WP-0048-hub-core-state-hub-import-refactor.md |
| task | CUST-WP-0048-T03 | done | — | workplans/CUST-WP-0048-hub-core-state-hub-import-refactor.md |
| task | CUST-WP-0048-T04 | done | — | workplans/CUST-WP-0048-hub-core-state-hub-import-refactor.md |
| task | CUST-WP-0048-T05 | done | — | workplans/CUST-WP-0048-hub-core-state-hub-import-refactor.md |
| task | CUST-WP-0048-T06 | done | — | workplans/CUST-WP-0048-hub-core-state-hub-import-refactor.md |
| task | CUST-WP-0048-T07 | done | — | workplans/CUST-WP-0048-hub-core-state-hub-import-refactor.md |
| task | CUST-WP-0048-T08 | done | — | workplans/CUST-WP-0048-hub-core-state-hub-import-refactor.md |
| task | CUST-WP-0049-T01 | done | — | workplans/CUST-WP-0049-interhub-bootstrap-access-lane.md |
| task | CUST-WP-0049-T02 | done | — | workplans/CUST-WP-0049-interhub-bootstrap-access-lane.md |
| task | CUST-WP-0049-T03 | done | — | workplans/CUST-WP-0049-interhub-bootstrap-access-lane.md |
| task | CUST-WP-0049-T04 | done | — | workplans/CUST-WP-0049-interhub-bootstrap-access-lane.md |
| task | CUST-WP-0049-T05 | done | — | workplans/CUST-WP-0049-interhub-bootstrap-access-lane.md |
| task | CUST-WP-0049-T06 | cancel | — | workplans/CUST-WP-0049-interhub-bootstrap-access-lane.md |
| task | CUST-WP-0050-T01 | done | — | workplans/CUST-WP-0050-repo-classification-registration-redesign.md |
| task | CUST-WP-0050-T02 | done | — | workplans/CUST-WP-0050-repo-classification-registration-redesign.md |
| task | CUST-WP-0050-T03 | cancel | — | workplans/CUST-WP-0050-repo-classification-registration-redesign.md |
| task | CUST-WP-0050-T04 | cancel | — | workplans/CUST-WP-0050-repo-classification-registration-redesign.md |
| task | CUST-WP-0050-T05 | cancel | — | workplans/CUST-WP-0050-repo-classification-registration-redesign.md |
| task | CUST-WP-0050-T06 | cancel | — | workplans/CUST-WP-0050-repo-classification-registration-redesign.md |
| task | CUST-WP-0050-T07 | cancel | — | workplans/CUST-WP-0050-repo-classification-registration-redesign.md |
| task | CUST-WP-0050-T08 | cancel | — | workplans/CUST-WP-0050-repo-classification-registration-redesign.md |
| task | CUST-WP-0050-T09 | cancel | — | workplans/CUST-WP-0050-repo-classification-registration-redesign.md |
| task | CUST-WP-0050-T10 | cancel | — | workplans/CUST-WP-0050-repo-classification-registration-redesign.md |
| task | CUST-WP-0050-T11 | done | — | workplans/CUST-WP-0050-repo-classification-registration-redesign.md |
| task | CUST-WP-0051-T01 | done | — | workplans/CUST-WP-0051-infrastructure-stabilization-metaplan.md |
| task | CUST-WP-0051-T02 | done | — | workplans/CUST-WP-0051-infrastructure-stabilization-metaplan.md |
| task | CUST-WP-0051-T03 | done | — | workplans/CUST-WP-0051-infrastructure-stabilization-metaplan.md |
| task | CUST-WP-0051-T04 | done | — | workplans/CUST-WP-0051-infrastructure-stabilization-metaplan.md |
| task | CUST-WP-0051-T05 | done | — | workplans/CUST-WP-0051-infrastructure-stabilization-metaplan.md |
| task | CUST-WP-0051-T06 | done | — | workplans/CUST-WP-0051-infrastructure-stabilization-metaplan.md |
| task | CUST-WP-0051-T07 | done | — | workplans/CUST-WP-0051-infrastructure-stabilization-metaplan.md |
| task | CUST-WP-0051-T08 | done | — | workplans/CUST-WP-0051-infrastructure-stabilization-metaplan.md |
| task | CUST-WP-0052-T01 | done | — | workplans/CUST-WP-0052-core-hub-fos-reset.md |
| task | CUST-WP-0052-T02 | done | — | workplans/CUST-WP-0052-core-hub-fos-reset.md |
| task | CUST-WP-0052-T03 | done | — | workplans/CUST-WP-0052-core-hub-fos-reset.md |
| task | CUST-WP-0052-T04 | done | — | workplans/CUST-WP-0052-core-hub-fos-reset.md |
| task | CUST-WP-0052-T05 | done | — | workplans/CUST-WP-0052-core-hub-fos-reset.md |
| task | CUST-WP-0052-T06 | done | — | workplans/CUST-WP-0052-core-hub-fos-reset.md |
| task | CUST-WP-0052-T07 | done | — | workplans/CUST-WP-0052-core-hub-fos-reset.md |
| task | CUST-WP-0053-T01 | done | — | workplans/CUST-WP-0053-coordination-hygiene-improvements.md |
| task | CUST-WP-0053-T02 | done | — | workplans/CUST-WP-0053-coordination-hygiene-improvements.md |
| task | CUST-WP-0053-T03 | done | — | workplans/CUST-WP-0053-coordination-hygiene-improvements.md |
| task | CUST-WP-0053-T04 | done | — | workplans/CUST-WP-0053-coordination-hygiene-improvements.md |
| task | CUST-WP-0053-T05 | done | — | workplans/CUST-WP-0053-coordination-hygiene-improvements.md |
| task | CUST-WP-0055-T01 | done | — | workplans/CUST-WP-0055-workplan-terminology-fleet-refactor.md |
| task | CUST-WP-0055-T02 | done | — | workplans/CUST-WP-0055-workplan-terminology-fleet-refactor.md |
| task | CUST-WP-0055-T03 | done | — | workplans/CUST-WP-0055-workplan-terminology-fleet-refactor.md |
| task | CUST-WP-0055-T04 | done | — | workplans/CUST-WP-0055-workplan-terminology-fleet-refactor.md |
| task | CUST-WP-0055-T05 | done | — | workplans/CUST-WP-0055-workplan-terminology-fleet-refactor.md |
| task | CUST-WP-0055-T06 | done | — | workplans/CUST-WP-0055-workplan-terminology-fleet-refactor.md |
| task | CUST-WP-0055-T07 | done | — | workplans/CUST-WP-0055-workplan-terminology-fleet-refactor.md |
| task | CUST-WP-0055-T08 | done | — | workplans/CUST-WP-0055-workplan-terminology-fleet-refactor.md |
| task | CUST-WP-0056-T01 | done | — | workplans/CUST-WP-0056-daily-todo-md-stale-review.md |
| task | CUST-WP-0056-T02 | done | — | workplans/CUST-WP-0056-daily-todo-md-stale-review.md |
| task | CUST-WP-0056-T03 | done | — | workplans/CUST-WP-0056-daily-todo-md-stale-review.md |
| task | CUST-WP-0059-T01 | done | — | workplans/CUST-WP-0059-forgejo-ci-publish-cutover-tail.md |
| task | CUST-WP-0059-T02 | done | — | workplans/CUST-WP-0059-forgejo-ci-publish-cutover-tail.md |
| task | CUST-WP-0059-T03 | done | — | workplans/CUST-WP-0059-forgejo-ci-publish-cutover-tail.md |
| task | CUST-WP-0059-T04 | done | — | workplans/CUST-WP-0059-forgejo-ci-publish-cutover-tail.md |
| task | CUST-WP-0059-T05 | done | — | workplans/CUST-WP-0059-forgejo-ci-publish-cutover-tail.md |
| task | CUST-WP-0059-T06 | done | — | workplans/CUST-WP-0059-forgejo-ci-publish-cutover-tail.md |
| task | CUST-WP-0060-T01 | done | — | workplans/CUST-WP-0060-work-record-canonization.md |
| task | CUST-WP-0060-T02 | done | — | workplans/CUST-WP-0060-work-record-canonization.md |
| task | CUST-WP-0060-T03 | done | — | workplans/CUST-WP-0060-work-record-canonization.md |
| task | CUST-WP-0060-T04 | done | — | workplans/CUST-WP-0060-work-record-canonization.md |
| task | CUST-WP-0060-T05 | done | — | workplans/CUST-WP-0060-work-record-canonization.md |
| task | CUST-WP-0060-T06 | done | — | workplans/CUST-WP-0060-work-record-canonization.md |
| task | CUST-WP-0060-T07 | done | — | workplans/CUST-WP-0060-work-record-canonization.md |
| task | CUST-WP-0061-T01 | done | — | workplans/CUST-WP-0061-work-record-stage3-intake-promotion-index.md |
| task | CUST-WP-0061-T02 | done | — | workplans/CUST-WP-0061-work-record-stage3-intake-promotion-index.md |
| task | CUST-WP-0061-T03 | done | — | workplans/CUST-WP-0061-work-record-stage3-intake-promotion-index.md |
| task | CUST-WP-0061-T04 | done | — | workplans/CUST-WP-0061-work-record-stage3-intake-promotion-index.md |
| task | CUST-WP-0061-T05 | done | — | workplans/CUST-WP-0061-work-record-stage3-intake-promotion-index.md |
| task | CUST-WP-0061-T06 | done | — | workplans/CUST-WP-0061-work-record-stage3-intake-promotion-index.md |
| task | CUST-WP-0062-T01 | done | — | workplans/CUST-WP-0062-sbom-nexus-daily-catchup.md |
| task | CUST-WP-0062-T02 | done | — | workplans/CUST-WP-0062-sbom-nexus-daily-catchup.md |
| task | CUST-WP-0062-T03 | done | — | workplans/CUST-WP-0062-sbom-nexus-daily-catchup.md |
| task | CUST-WP-0062-T04 | done | — | workplans/CUST-WP-0062-sbom-nexus-daily-catchup.md |
| task | CUST-WP-0062-T05 | done | — | workplans/CUST-WP-0062-sbom-nexus-daily-catchup.md |
| task | CUST-WP-0062-T06 | done | — | workplans/CUST-WP-0062-sbom-nexus-daily-catchup.md |
| task | CUST-WP-0063-T01 | done | — | workplans/CUST-WP-0063-inbox-governance-packets.md |
| task | CUST-WP-0063-T02 | done | — | workplans/CUST-WP-0063-inbox-governance-packets.md |
| task | CUST-WP-0063-T03 | done | — | workplans/CUST-WP-0063-inbox-governance-packets.md |
| task | CUST-WP-0063-T04 | done | — | workplans/CUST-WP-0063-inbox-governance-packets.md |
| task | CUST-WP-0063-T05 | done | — | workplans/CUST-WP-0063-inbox-governance-packets.md |
| task | CUST-WP-0064-T01 | done | — | workplans/CUST-WP-0064-sbom-controlled-scan-inputs.md |
| task | CUST-WP-0064-T02 | done | — | workplans/CUST-WP-0064-sbom-controlled-scan-inputs.md |
| task | CUST-WP-0064-T03 | done | — | workplans/CUST-WP-0064-sbom-controlled-scan-inputs.md |
| task | CUST-WP-0064-T04 | done | — | workplans/CUST-WP-0064-sbom-controlled-scan-inputs.md |
| task | CUST-WP-0065-T01 | done | — | workplans/CUST-WP-0065-reclassify-repos-and-guidance-docs-to-the-new-sector-domain.md |
| task | CUST-WP-0065-T02 | done | — | workplans/CUST-WP-0065-reclassify-repos-and-guidance-docs-to-the-new-sector-domain.md |
| task | CUST-WP-0065-T03 | done | — | workplans/CUST-WP-0065-reclassify-repos-and-guidance-docs-to-the-new-sector-domain.md |
| task | CUST-WP-0065-T04 | done | — | workplans/CUST-WP-0065-reclassify-repos-and-guidance-docs-to-the-new-sector-domain.md |
| task | CUST-WP-0066-T01 | done | — | workplans/CUST-WP-0066-repository-qualified-ad-hoc-identifiers.md |
| task | CUST-WP-0066-T02 | done | — | workplans/CUST-WP-0066-repository-qualified-ad-hoc-identifiers.md |
| task | CUST-WP-0066-T03 | done | — | workplans/CUST-WP-0066-repository-qualified-ad-hoc-identifiers.md |
| task | CUST-WP-0067-T01 | done | — | workplans/CUST-WP-0067-hub-authority-target-resolution.md |
| task | CUST-WP-0067-T02 | done | — | workplans/CUST-WP-0067-hub-authority-target-resolution.md |
| task | CUST-WP-0067-T03 | done | — | workplans/CUST-WP-0067-hub-authority-target-resolution.md |
| task | CUST-WP-0067-T04 | done | — | workplans/CUST-WP-0067-hub-authority-target-resolution.md |
| task | CUST-WP-0067-T05 | done | — | workplans/CUST-WP-0067-hub-authority-target-resolution.md |
| task | CUST-WP-0067-T06 | done | — | workplans/CUST-WP-0067-hub-authority-target-resolution.md |
| task | CUST-WP-0067-T07 | done | — | workplans/CUST-WP-0067-hub-authority-target-resolution.md |
| task | CUST-WP-0067-T08 | done | — | workplans/CUST-WP-0067-hub-authority-target-resolution.md |
| task | CUST-WP-0067-T09 | done | — | workplans/CUST-WP-0067-hub-authority-target-resolution.md |
| task | CUST-WP-0067-T10 | done | — | workplans/CUST-WP-0067-hub-authority-target-resolution.md |
| task | CUST-WP-0068-T01 | done | — | workplans/CUST-WP-0068-cache-only-work-record-recovery.md |
| task | CUST-WP-0068-T02 | done | — | workplans/CUST-WP-0068-cache-only-work-record-recovery.md |
| task | CUST-WP-0068-T03 | done | — | workplans/CUST-WP-0068-cache-only-work-record-recovery.md |
| task | CUST-WP-0068-T04 | done | — | workplans/CUST-WP-0068-cache-only-work-record-recovery.md |
| task | CUST-WP-0068-T05 | done | — | workplans/CUST-WP-0068-cache-only-work-record-recovery.md |
| task | CUST-WP-0068-T06 | done | — | workplans/CUST-WP-0068-cache-only-work-record-recovery.md |
| task | CUST-WP-0068-T07 | done | — | workplans/CUST-WP-0068-cache-only-work-record-recovery.md |
| task | CUST-WP-0068-T08 | done | — | workplans/CUST-WP-0068-cache-only-work-record-recovery.md |
| task | CUST-WP-0068-T09 | done | — | workplans/CUST-WP-0068-cache-only-work-record-recovery.md |
| task | CUST-WP-0070-T01 | done | — | workplans/CUST-WP-0070-publication-repo-category.md |
| task | CUST-WP-0070-T02 | done | — | workplans/CUST-WP-0070-publication-repo-category.md |
| task | CUST-WP-0070-T03 | done | — | workplans/CUST-WP-0070-publication-repo-category.md |
| task | CUST-WP-0071-T01 | done | — | workplans/CUST-WP-0071-measured-workload-sizing-and-weekly-review.md |
| task | CUST-WP-0071-T02 | wait | — | workplans/CUST-WP-0071-measured-workload-sizing-and-weekly-review.md |
| task | CUST-WP-0071-T03 | wait | — | workplans/CUST-WP-0071-measured-workload-sizing-and-weekly-review.md |
| task | CUST-WP-0071-T04 | wait | — | workplans/CUST-WP-0071-measured-workload-sizing-and-weekly-review.md |
| task | CUST-WP-0071-T05 | wait | — | workplans/CUST-WP-0071-measured-workload-sizing-and-weekly-review.md |
| task | CUST-WP-0072-T01 | done | — | workplans/CUST-WP-0072-fleet-flavor-and-depends-on-backfill.md |
| task | CUST-WP-0072-T02 | done | — | workplans/CUST-WP-0072-fleet-flavor-and-depends-on-backfill.md |
| task | CUST-WP-0072-T03 | done | — | workplans/CUST-WP-0072-fleet-flavor-and-depends-on-backfill.md |
| task | CUST-WP-0072-T04 | done | — | workplans/CUST-WP-0072-fleet-flavor-and-depends-on-backfill.md |
| task | CUST-WP-0073-T01 | done | — | workplans/CUST-WP-0073-agent-credential-separation.md |
| task | CUST-WP-0073-T02 | wait | — | workplans/CUST-WP-0073-agent-credential-separation.md |
| task | CUST-WP-0073-T03 | done | — | workplans/CUST-WP-0073-agent-credential-separation.md |
| task | CUST-WP-0073-T04 | wait | — | workplans/CUST-WP-0073-agent-credential-separation.md |
| task | CUST-WP-0073-T05 | wait | — | workplans/CUST-WP-0073-agent-credential-separation.md |
| task | CUST-WP-0074-T01 | done | — | workplans/CUST-WP-0074-qualified-wait-states.md |
| task | CUST-WP-0074-T02 | done | — | workplans/CUST-WP-0074-qualified-wait-states.md |
| task | CUST-WP-0074-T03 | done | — | workplans/CUST-WP-0074-qualified-wait-states.md |
| task | CUST-WP-0074-T04 | done | — | workplans/CUST-WP-0074-qualified-wait-states.md |
| task | CUST-WP-0074-T05 | done | — | workplans/CUST-WP-0074-qualified-wait-states.md |
| task | CUST-WP-0074-T06 | done | — | workplans/CUST-WP-0074-qualified-wait-states.md |
| task | CUST-WP-0075-T01 | done | — | workplans/CUST-WP-0075-dependency-graph-driven-unblocking.md |
| task | CUST-WP-0075-T02 | done | — | workplans/CUST-WP-0075-dependency-graph-driven-unblocking.md |
| task | CUST-WP-0075-T03 | done | — | workplans/CUST-WP-0075-dependency-graph-driven-unblocking.md |
| task | CUST-WP-0075-T04 | done | — | workplans/CUST-WP-0075-dependency-graph-driven-unblocking.md |
| task | CUST-WP-0075-T05 | done | — | workplans/CUST-WP-0075-dependency-graph-driven-unblocking.md |
| task | CUST-WP-0075-T06 | done | — | workplans/CUST-WP-0075-dependency-graph-driven-unblocking.md |
| task | CUST-WP-0076-T01 | done | — | workplans/CUST-WP-0076-provisioning-window-cadence.md |
| task | CUST-WP-0077-T01 | done | — | workplans/CUST-WP-0077-dependency-root-execution-wave.md |
| task | CUST-WP-0077-T02 | done | — | workplans/CUST-WP-0077-dependency-root-execution-wave.md |
| task | CUST-WP-0077-T03 | done | — | workplans/CUST-WP-0077-dependency-root-execution-wave.md |
| task | CUST-WP-0077-T04 | done | — | workplans/CUST-WP-0077-dependency-root-execution-wave.md |
| task | CUST-WP-0077-T05 | done | — | workplans/CUST-WP-0077-dependency-root-execution-wave.md |
| task | CUST-WP-0078-T01 | done | — | workplans/CUST-WP-0078-security-collaboration-consolidation.md |
| task | CUST-WP-0078-T02 | done | — | workplans/CUST-WP-0078-security-collaboration-consolidation.md |
| task | CUST-WP-0078-T03 | done | — | workplans/CUST-WP-0078-security-collaboration-consolidation.md |
| task | CUST-WP-0078-T04 | done | — | workplans/CUST-WP-0078-security-collaboration-consolidation.md |
| task | CUST-WP-0079-T01 | done | — | workplans/CUST-WP-0079-deterministic-security-flow.md |
| task | CUST-WP-0079-T02 | done | — | workplans/CUST-WP-0079-deterministic-security-flow.md |
| task | CUST-WP-0079-T03 | wait | — | workplans/CUST-WP-0079-deterministic-security-flow.md |
| task | CUST-WP-0079-T04 | wait | — | workplans/CUST-WP-0079-deterministic-security-flow.md |
| task | CUST-WP-0079-T05 | wait | — | workplans/CUST-WP-0079-deterministic-security-flow.md |
| task | CUST-WP-0079-T06 | wait | — | workplans/CUST-WP-0079-deterministic-security-flow.md |
| task | CUST-WP-0079-T07 | done | — | workplans/CUST-WP-0079-deterministic-security-flow.md |
| task | CUST-WP-0080-T01 | done | — | workplans/CUST-WP-0080-netkingdom-security-blueprint-and-gap-closure.md |
| task | CUST-WP-0080-T02 | done | — | workplans/CUST-WP-0080-netkingdom-security-blueprint-and-gap-closure.md |
| task | CUST-WP-0080-T03 | progress | — | workplans/CUST-WP-0080-netkingdom-security-blueprint-and-gap-closure.md |
| task | CUST-WP-0080-T04 | todo | — | workplans/CUST-WP-0080-netkingdom-security-blueprint-and-gap-closure.md |
| task | CUST-WP-0080-T05 | progress | — | workplans/CUST-WP-0080-netkingdom-security-blueprint-and-gap-closure.md |
| task | CUST-WP-0080-T06 | progress | — | workplans/CUST-WP-0080-netkingdom-security-blueprint-and-gap-closure.md |
| task | CUST-WP-0081-T01 | done | — | workplans/CUST-WP-0081-netkingdom-architecture-review-and-reuse.md |
| task | CUST-WP-0081-T02 | done | — | workplans/CUST-WP-0081-netkingdom-architecture-review-and-reuse.md |
| task | CUST-WP-0081-T03 | done | — | workplans/CUST-WP-0081-netkingdom-architecture-review-and-reuse.md |
| task | THE-WP-0001-T01 | done | — | workplans/THE-WP-0001-federation-interface.md |
| task | THE-WP-0001-T02 | done | — | workplans/THE-WP-0001-federation-interface.md |
| intake | CUST-IN-0001 | closed | green | intake-legacy-suggestions-migration.md |
| intake | CUST-IN-0002 | closed | green | intake-legacy-suggestions-migration.md |
| intake | CUST-IN-0003 | closed | green | intake-legacy-suggestions-migration.md |
| intake | CUST-IN-0004 | routed | green | intake-legacy-suggestions-migration.md |
| intake | CUST-IN-0005 | closed | green | intake-legacy-suggestions-migration.md |
| intake | CUST-IN-0006 | closed | green | intake-legacy-suggestions-migration.md |
| intake | CUST-IN-0007 | closed | green | intake-legacy-suggestions-migration.md |
| intake | CUST-IN-0008 | closed | blue | intake-legacy-suggestions-migration.md |
| intake | CUST-IN-0009 | closed | blue | intake-legacy-suggestions-migration.md |
| intake | CUST-IN-0010 | closed | green | intake-legacy-suggestions-migration.md |
| intake | CUST-IN-0011 | routed | red | intakes.md |
| intake | CUST-IN-0012 | closed | green | intakes.md |
| intake | CUST-IN-0013 | closed | blue | intakes.md |
| intake | CUST-IN-0014 | closed | blue | intakes.md |
| intake | CUST-IN-0015 | open | blue | intakes.md |
| intake | CUST-IN-0016 | open | green | intakes.md |
| intake | CUST-IN-0017 | open | green | intakes.md |
| intake | CUST-IN-0018 | open | green | intakes.md |

View file

@ -0,0 +1 @@
{".custodian-brief.md": "100644 6aad3a5788fad3abd60c0f1270f160062dc0168b 0\t.custodian-brief.md\n", "WORK-RECORDS.md": "100644 d535e0f2dcc3d454e041a8f1b547b5dea4493380 0\tWORK-RECORDS.md\n"}

View file

@ -0,0 +1,14 @@
{
"workplan_id": "dfadb19b-445e-59c6-bcd6-48e87b912c52",
"id": "f0a63cac-9b78-4331-82a9-b96747e4e71b",
"topic_id": null,
"task_id": null,
"decision_id": null,
"event_type": "note",
"summary": "Published Custodian checkpoint f8c7dfa2a9c7919879b62c77eb39582b3e23654e with exact pending State Hub rollout proposal (revision 4, digest 63a02e8296d126c0158b7eb2c4ce79c7eeb6f8d6f61298d473c1065c7557ba32). Required consistency and primary/railiance01 projection pass. All 81 task bindings checked across Custodian, NetKingdom, State Hub, Repo Manager and Secrets; original staged brief, work records and six assessments preserved. Published owner milestones NK48-T21, NK49-T37, RMGR21-T05, SECRETS-WP-0015 and STATE95-T05/T08. RCLUSTER-WP-0018 awaits verified receiving rollout before lawful publication. All 16 native target gates remain open. No live rollout, registrar activation, original credential recovery, rotation or authority promotion. Founder review is the next State Hub rollout gate; foreign waits have four coordination receipts without messages or worker wakes.",
"detail": null,
"author": "codex",
"session_id": null,
"created_at": "2026-10-16T23:51:19.540708Z",
"workstream_id": "dfadb19b-445e-59c6-bcd6-48e87b912c52"
}

View file

@ -0,0 +1,97 @@
# Forgejo private client-secret input: separate source revision
This packet implements `--secret-file` in the actual Forgejo 11.0.3 add/update
OAuth handlers and patches the actual Gitea chart 12.5.0. Apply the unchanged
reviewed seven-path any-of patch first, then this incremental Forgejo patch.
The original candidate and completed release-build packets remain unchanged.
No canonical owner implementation, case/type, authority, image or deployment is
changed. The new backend executable is test evidence, not an admitted image.
The existing three-group exact any-of gate and mandatory current-UserInfo guard
remain in the reviewed implementation. Six reviewed non-CLI source paths retain
exact hashes. Actual cmd/oauth2 package tests exercise them again. The exact shared database
confidentiality dependency is documented in [SQL-CONFIDENTIALITY.md](SQL-CONFIDENTIALITY.md);
apply it once when composing source candidates. Both handlers refuse raw SQL
logging, mark queries for hook/trace redaction, and private-file persistence
failures return fixed errors. Update without
secret flags preserves the stored secret; selecting a private input completes
its checks before DB initialization or source mutation. Explicit legacy
`--secret` behavior is preserved. Both flags together, including an empty legacy
flag, refuse. The file value never enters the CLI context, argv or environment.
On Linux the reader walks absolute, normalized paths with descriptor-relative
non-following opens, rejects writable-by-group/other parents and foreign-owned
parents, and opens the leaf nonblocking so FIFO input cannot hang. It requires a
single-link regular file, root/euid ownership, no write/execute/special/other-read
bits, an admitted process group for group-readable files, and an actual read-only
mount. It bounds the read at 65 bytes and compares file identity/size/ownership/
mode/mtime/ctime and the named leaf after reading. Read-induced atime is allowed.
Every file-input failure has the same fixed error without path or value. Other
platforms fail closed. The accepted format matches the actual mint implementation:
48 random bytes encoded by `secrets.token_urlsafe`, exactly 64 ASCII base64url
characters with no padding or newline. Values are preserved exactly; no trimming
occurs. The transient read buffer is cleared; the existing DB/provider string
custody and process memory remain the existing software contract.
The chart helper suppresses automatic `--secret` when `secretFile` is present.
It refuses `secret`, `existingSecret`, indexed secret env collisions, multiple
private entries, a different path, conflicting extra mounts/volume and a different
fsGroup. Its bounded private route emits the fixed path and mounts existing
`forgejo-netkingdom-oidc-client` key `CLIENT_SECRET` read-only by file `subPath`
into **configure-gitea only**, with mode 0440 and pod fsGroup 1000. No alias key,
new secret read/ACL, value-bearing env or value-bearing agent command is added.
Legacy sources retain their existing automatic argument behavior. Exact public
release values are deliberately not emitted by these synthetic controls.
Linux Kubernetes Secret volumes normally retain root UID. The fsGroup ownership
pass changes GID and adds read permissions, so root:1000 mode 0440 is expected;
requiring euid ownership would incorrectly refuse this case. The retained public
[Kubernetes ownership implementation](https://github.com/kubernetes/kubernetes/blob/v1.34.1/pkg/volume/volume_linux.go)
and [Secret volume implementation](https://github.com/kubernetes/kubernetes/blob/v1.34.1/pkg/volume/secret/secret.go)
show those details. File subPath bind mounting avoids the projected symlink leaf;
[Secret subPath mounts do not receive automatic updates](https://kubernetes.io/docs/concepts/configuration/secret/#using-secrets-as-files-from-a-pod).
An owner-controlled restart/refresh is required on rotation. These public source
findings are not observations of the estate's running kubelet or pod.
DAC and a read-only mount cannot identify a Kubernetes namespace, Secret object,
operation session, or authorized reader set. The reader intentionally makes no
such admission claim. Actual runtime admission must bind the exact owner
workload, image, namespace, mount/parent ownership, UID/GID/mode, reader set,
rotation and current authenticated operation. Arbitrary privileged code or a
malicious workload owner remains outside this input reader's protection.
T34 persistence/readback/CAS, durable journal, writer exclusion, operation/inverse
sessions and the application-state inverse remain separate owner work. A Helm
rollback alone does not reverse persisted source state.
The retained checks compile the actual complete backend and execute actual
binary CLI subprocesses against a synthetic SQLite database. They cover add,
replacement, omission, preservation of unrelated configuration and guarded
three-group fields, bad-path/input refusals and conflicts without DB changes,
and absence of values in argv/env/stdout/stderr. Actual Linux descriptor tests
exercise opened-inode/name replacement, while metadata controls include
root:fsGroup 0440 and prohibited modes. Actual Helm rendering covers both command
forms, the Secret/mount references, legacy behavior, and refusal without leaking
a conflicting synthetic marker. Guard tests use in-memory HTTP transports. The
CLI guarded-update persistence control uses an inactive source to avoid discovery;
it is not a browser login or an active OIDC registration proof.
Final decisive build/test profiles use bwrap PID and network isolation, public-only source/cache
mounts, an empty test HOME and a closed environment. No host HOME/config,
credentials, cluster, OpenBao, registry publication, model call or live secret is
used. No full frontend/container/image rebuild was launched. Earlier profiles without PID isolation, initial fixture and
sandbox harness failures, a reproduced synthetic SQL leak before correction,
and the earlier-revision replay failure are retained, as is the initial chart metadata mismatch
and its exact published-metadata reconstruction; none is counted as a successful
runtime trial.
Run a fresh reconstruction and all actual checks with the retained public cache:
```sh
python3 tests/replay_offline.py --public-cache /tmp/forgejo-independent-r1
```
This creates fresh `/tmp` source/work/evidence, applies both exact patches, and
builds only a backend test executable. It needs bwrap, patch, Python/PyYAML, the
existing Helm executable and the already retained public Go/module cache. The
packet includes only changed source pre/postimages, small public provenance,
patches and tests; no vendored full source, binary or image is included.

View file

@ -0,0 +1,33 @@
# Shared database confidentiality dependency
Private-file input was insufficient by itself: an actual previous-revision CLI
add with `database.LOG_SQL=true` exposed the synthetic client secret in XORM
output. `evidence/sql-leak-before.log` retains the failed leak assertion without
printing the captured value. This is an implementation finding, not an accepted
runtime trial. Disabling raw SQL output alone also leaves the existing slow,
error and runtime trace hooks, which include query arguments/driver errors.
The common dependency is exactly the separately prepared Apps operation-backend
implementation, not a competing helper. Its API is `db.WithSensitiveSQL(ctx)`.
The actual SQL/slow/error/trace hooks redact statement/arguments/driver errors
when that context marker is present. The dependency's actual hook tests retain
positive unredacted controls, including a real runtime trace buffer. Custom
DB/server audit outside this process remains an owner custody concern.
Apply `shared-db-confidentiality.patch` exactly once when composing both source
candidates. Its three postimages must match the operation-backend source:
| Path | SHA-256 |
| --- | --- |
| `models/db/engine.go` | `43683804d0c5bc6ead1dba0344c69dd196825cf3d5eb502af8d932a7b8207b96` |
| `models/db/sensitive_sql.go` | `8d4e6b3f08e9fdd919e97e47bd857cbd8935fdcbf367d20b5b8c545f279e796e` |
| `models/db/sensitive_sql_test.go` | `f0f74c09a9e96a6529db7b9ce459a2ea37e204de38c5ad01855b80c9a992a769` |
Both actual OAuth CLI handlers preserve the marked context through database
queries. They refuse configured raw SQL logging **and** actual XORM logger
ShowSQL before source reads/writes; a configuration boolean alone is insufficient.
Private-file persistence failures return fixed errors. This deliberately refuses
debug SQL logging for these handlers instead of pretending it is a private path.
The legacy secret flag and update omission semantics otherwise remain intact.
Final controls include actual `LOG_SQL=true` refusal, low-threshold slow-query
hooks, and a real SQLite-triggered write failure with unchanged stored source.

View file

@ -0,0 +1,90 @@
diff --git a/templates/_helpers.tpl b/templates/_helpers.tpl
--- a/templates/_helpers.tpl
+++ b/templates/_helpers.tpl
@@ -201,7 +201,15 @@
{{- $_ := set $values "key" (printf "${GITEA_OAUTH_KEY_%d}" $idx) -}}
{{- end -}}
-{{- if not (hasKey $values "secret") -}}
+{{- if hasKey $values "secretFile" -}}
+{{- if or (hasKey $values "secret") (hasKey $values "existingSecret") -}}
+{{- fail "OAuth secretFile conflicts with secret or existingSecret" -}}
+{{- end -}}
+{{- if ne $values.secretFile "/run/forgejo-oidc/CLIENT_SECRET" -}}
+{{- fail "OAuth secretFile requires the admitted mount path" -}}
+{{- end -}}
+{{- end -}}
+{{- if and (not (hasKey $values "secret")) (not (hasKey $values "secretFile")) -}}
{{- $_ := set $values "secret" (printf "${GITEA_OAUTH_SECRET_%d}" $idx) -}}
{{- end -}}
@@ -471,3 +479,28 @@
{{- define "gitea.metrics-secret-name" -}}
{{ default (printf "%s-metrics-secret" (include "gitea.fullname" .)) }}
{{- end -}}
+
+{{/* Bounded first-case source continuation; no Secret value or alias key. */}}
+{{- define "gitea.oauth_private_validate" -}}
+{{- $private := 0 -}}
+{{- range $idx, $value := .Values.gitea.oauth -}}
+{{- if hasKey $value "secretFile" -}}
+{{- $private = add1 $private -}}
+{{- range $.Values.deployment.env -}}
+{{- if eq .name (printf "GITEA_OAUTH_SECRET_%d" $idx) -}}
+{{- fail "OAuth secretFile conflicts with indexed secret environment" -}}
+{{- end -}}
+{{- end -}}
+{{- end -}}
+{{- end -}}
+{{- if gt $private 1 -}}{{- fail "Only one private OAuth mount is supported" -}}{{- end -}}
+{{- if gt $private 0 -}}
+{{- if ne (int .Values.podSecurityContext.fsGroup) 1000 -}}{{- fail "Private OAuth mount requires fsGroup 1000" -}}{{- end -}}
+{{- range .Values.extraVolumes -}}
+{{- if eq .name "oauth-private-client" -}}{{- fail "Private OAuth volume conflict" -}}{{- end -}}
+{{- end -}}
+{{- range concat .Values.extraVolumeMounts .Values.extraInitVolumeMounts .Values.extraContainerVolumeMounts -}}
+{{- if or (eq .name "oauth-private-client") (hasPrefix "/run/forgejo-oidc" .mountPath) -}}{{- fail "Private OAuth mount conflict" -}}{{- end -}}
+{{- end -}}
+{{- end -}}
+{{- end -}}
diff --git a/templates/gitea/deployment.yaml b/templates/gitea/deployment.yaml
--- a/templates/gitea/deployment.yaml
+++ b/templates/gitea/deployment.yaml
@@ -1,3 +1,4 @@
+{{- include "gitea.oauth_private_validate" . -}}
apiVersion: apps/v1
kind: Deployment
metadata:
@@ -260,6 +261,14 @@
{{- toYaml .Values.deployment.env | nindent 12 }}
{{- end }}
volumeMounts:
+ {{- range .Values.gitea.oauth }}
+ {{- if hasKey . "secretFile" }}
+ - name: oauth-private-client
+ mountPath: /run/forgejo-oidc/CLIENT_SECRET
+ subPath: CLIENT_SECRET
+ readOnly: true
+ {{- end }}
+ {{- end }}
- name: init
mountPath: {{ .Values.initContainersScriptsVolumeMountPath }}
- name: temp
@@ -388,6 +397,17 @@
{{- toYaml .Values.dnsConfig | nindent 8 }}
{{- end }}
volumes:
+ {{- range .Values.gitea.oauth }}
+ {{- if hasKey . "secretFile" }}
+ - name: oauth-private-client
+ secret:
+ secretName: forgejo-netkingdom-oidc-client
+ defaultMode: 288
+ items:
+ - key: CLIENT_SECRET
+ path: CLIENT_SECRET
+ {{- end }}
+ {{- end }}
- name: init
secret:
secretName: {{ include "gitea.fullname" . }}-init

View file

@ -0,0 +1,15 @@
{
"returncode": 0,
"seconds": 79.25860216701403,
"argv": [
"go",
"build",
"-p",
"4",
"-tags",
"sqlite sqlite_unlock_notify",
"-o",
"/tmp/forgejo-private-work/forgejo",
"."
]
}

View file

@ -0,0 +1,15 @@
{
"returncode": 0,
"seconds": 50.04432745499071,
"argv": [
"go",
"build",
"-p",
"4",
"-tags",
"sqlite sqlite_unlock_notify",
"-o",
"/tmp/forgejo-private-work/forgejo",
"."
]
}