Add event-driven reporting and durable failure recovery hooks

This commit is contained in:
aiagent
2026-10-19 03:13:33 -07:00
parent 579dece104
commit a4cf70d82b
18 changed files with 711 additions and 8 deletions
+8 -1
View File
@@ -8,6 +8,7 @@ import subprocess
import sys
import time
from worker import atomic_json,session_lock
from faults import report_process
def main():
@@ -20,7 +21,10 @@ def main():
root.mkdir(parents=True,exist_ok=True,mode=0o700)
if os.name=='posix':os.umask(0o077)
identity='supervisor:'+json.dumps({'control':cfg['control'],'session_id':cfg['session_id']},sort_keys=True)
fault_path=root/'bridge-faults.json'
faults=json.loads(fault_path.read_text(encoding='utf-8')).get('roles',{}) if fault_path.exists() else {}
processes={}
started_at={}
logs={}
next_start={}
with session_lock(identity):
@@ -28,8 +32,10 @@ def main():
while True:
state_path=Path(cfg['state_file']).expanduser()
state=json.loads(state_path.read_text(encoding='utf-8')) if state_path.exists() else {}
for role in ('worker','mirror'):
for role in (('worker','mirror','notifier') if cfg.get('notification_targets') else ('worker','mirror')):
process=processes.get(role)
if process and cfg.get('notification_targets'):
report_process(cfg,root,role,process,faults,started_at.get(role))
if process and process.poll() is None:continue
if role=='worker' and (state.get('needs_reconciliation') or (state.get('inflight') and not state.get('pending_completion'))):
continue
@@ -39,6 +45,7 @@ def main():
process=subprocess.Popen(command,stdout=logs[role],stderr=logs[role],
**({'creationflags':subprocess.CREATE_NO_WINDOW} if os.name=='nt' else {}))
processes[role]=process
started_at[role]=time.time()
next_start[role]=time.monotonic()+15
atomic_json(root/'bridge-service.json',{'pid':os.getpid(),'updated':time.time(),
'children':{name:{'pid':p.pid,'running':p.poll() is None} for name,p in processes.items()},