"""L4 only. Run after physical L2/L3 PASS, from isolated worktree."""
import asyncio,hashlib,json,pathlib,subprocess,sys,time
sys.path.insert(0,str(pathlib.Path.cwd()/'server'))
from device_gateway import speech
root=pathlib.Path('.cache/speech-diagnostics');root.mkdir(parents=True,exist_ok=True)
pcm=(root/'deterministic-2s.pcm').read_bytes()
def ffmpeg(out,args):
 p=subprocess.run(['ffmpeg','-hide_banner','-loglevel','error','-y','-f','s16le','-ar','44100','-ac','1','-i','pipe:0',*args,str(out)],input=pcm,capture_output=True);assert p.returncode==0
async def main():
 records=[]
 for name,args in [('same.wav',['-acodec','pcm_s16le']),('same.mp3',['-acodec','libmp3lame']),('different-48k-stereo.wav',['-ar','48000','-ac','2','-acodec','pcm_s16le'])]:
  source=root/name;ffmpeg(source,args)
  probe=json.loads(subprocess.check_output(['ffprobe','-v','error','-show_streams','-show_format','-of','json',str(source)]))
  processes=[];original=asyncio.create_subprocess_exec
  async def traced(*a,**k):
   proc=await original(*a,**k);processes.append(proc);return proc
  asyncio.create_subprocess_exec=traced
  started=time.perf_counter()
  try:converted=await speech.audio_to_pcm(source.read_bytes())
  finally:asyncio.create_subprocess_exec=original
  ms=(time.perf_counter()-started)*1000
  assert converted and len(converted)%2==0 and not converted.startswith(b'RIFF') and all(p.returncode==0 for p in processes)
  assert abs(len(converted)/88200-2)<.1
  (root/(name+'.pcm')).write_bytes(converted)
  rec={'input':name,'source_bytes':source.stat().st_size,'source_streams':probe['streams'],'source_duration':probe['format'].get('duration'),'pcm_bytes':len(converted),'pcm_duration':len(converted)/88200,'conversion_ms':ms,'exit_codes':[p.returncode for p in processes],'pcm_sha256':hashlib.sha256(converted).hexdigest(),'output_args':'s16le pcm_s16le mono 44100','no_wav_header':True}
  if name=='same.wav':assert converted==pcm;rec['exact_identity']='PASS'
  records.append(rec);print(json.dumps(rec),flush=True)
 (root/'l4-conversion.json').write_text(json.dumps(records,indent=2))
asyncio.run(main())
