import sqlite3,json,sys,re,subprocess
from pathlib import Path
conn=sqlite3.connect('file:'+sys.argv[1]+'?mode=ro',uri=True)
thread=sys.argv[2]
items=[json.loads(r[0]) for r in conn.execute('select payload_json from orchestration_v2_projection_turn_items where thread_id=? order by ordinal',(thread,))]
out=[]
for i in items:
 t=i['type']
 if t in ['user_message','assistant_message']:
  out.append({k:i[k] for k in ['type','startedAt','completedAt','text'] if k in i})
 elif t=='dynamic_tool' and any(x in i.get('toolName','') for x in ['delegate_task','task_status','task_wait']):
  inp={k:v for k,v in i.get('input',{}).items() if k not in ['target','environmentId']}
  output=i.get('output',{})
  try: output=json.loads(output['content'][0]['text'])
  except (KeyError,IndexError,ValueError):pass
  safe={k:output[k] for k in ['taskId','status','workState','next','waitTimedOut','summary'] if k in output}
  out.append({'type':t,'tool':i['toolName'].split('__')[-1],'startedAt':i.get('startedAt'),'completedAt':i.get('completedAt'),'input':inp,'output':safe})
children=[]
checkout_paths=[]
for row in conn.execute('select started_at,completed_at,payload_json,child_thread_id from orchestration_v2_projection_subagents where thread_id=? order by started_at',(thread,)):
 p=json.loads(row[2]); childitems=[json.loads(r[0]) for r in conn.execute('select payload_json from orchestration_v2_projection_turn_items where thread_id=? order by ordinal',(row[3],))]
 commands=[{k:i[k] for k in ['input','status','startedAt','completedAt','output'] if k in i} for i in childitems if i['type']=='command_execution']
 child=json.loads(conn.execute('select payload_json from orchestration_v2_projection_threads where thread_id=?',(row[3],)).fetchone()[0])
 path=child.get('worktreePath')
 checkout={'separate':bool(path)}
 if path:
  checkout_paths.append(path)
  def git(*args):return subprocess.check_output(['git','-C',path,*args],text=True).strip()
  common=git('rev-parse','--git-common-dir')
  parent=str(Path(common).parent)
  checkout.update({'clean':not bool(git('status','--porcelain')),'headMatchesParent':git('rev-parse','HEAD')==subprocess.check_output(['git','-C',parent,'rev-parse','HEAD'],text=True).strip()})
 children.append({'checkout':checkout,'startedAt':row[0],'completedAt':row[1],'title':p.get('title'),'commands':commands})
print(re.sub(r'\b(auto|default)\b', '[private identifier]', json.dumps({'timeline':out,'children':children,'distinctPreparedCheckouts':len(checkout_paths)==2 and len(set(checkout_paths))==2},indent=2), flags=re.I))
