#!/usr/bin/env python3
import json, os, re, datetime
BASE='/home/spazio/.hermes/cron/papyrus_books'
MANIFEST=os.path.join(BASE,'manifest.json')
STATE=os.path.join(BASE,'state.json')
TEXTDIR=os.path.join(BASE,'texts')
with open(MANIFEST,encoding='utf-8') as f:
    books=json.load(f)
# fixed order from manifest (alphabetical filenames)
if os.path.exists(STATE):
    with open(STATE,encoding='utf-8') as f: state=json.load(f)
else:
    state={'next_index':0,'runs':0,'history':[]}
idx=state.get('next_index',0) % len(books)
book=books[idx]
text_path=os.path.join(TEXTDIR, book['text'])
text=''
if os.path.exists(text_path):
    with open(text_path,encoding='utf-8',errors='ignore') as f: text=f.read()
# remove page markers but preserve rough page cues
clean=re.sub(r'--- PAGE \d+ ---','\n',text)
clean=re.sub(r'\n{3,}','\n\n',clean).strip()
# If text layer is weak, provide metadata only
chars=len(re.sub(r'\s+','',clean))
# sample across the whole text to fit prompt context
samples=[]
if book.get('chars_extracted',0) > 10000:
    if chars>20000:
        n=8
        sample_len=5500
        L=len(clean)
        for i in range(n):
            pos=int(i*(max(0,L-sample_len))/(n-1)) if n>1 else 0
            chunk=clean[pos:pos+sample_len]
            samples.append({'sample':i+1,'approx_position_percent':round(100*pos/max(1,L),1),'text':chunk})
    elif clean:
        samples=[{'sample':1,'approx_position_percent':0,'text':clean[:45000]}]
# advance state immediately to avoid repeats if job succeeds partially
state['next_index']=(idx+1)%len(books)
state['runs']=state.get('runs',0)+1
state.setdefault('history',[]).append({'ts':datetime.datetime.utcnow().isoformat()+'Z','index':idx,'book':book['pdf']})
state['history']=state['history'][-50:]
with open(STATE,'w',encoding='utf-8') as f: json.dump(state,f,ensure_ascii=False,indent=2)
out={'book_number':idx+1,'total_books':len(books),'book':book,'chars_extracted':book.get('chars_extracted',0),'note':'sampled_excerpts_across_book' if samples and book.get('chars_extracted',0)>0 else 'NO_TEXT_LAYER_OR_OCR_NEEDED','samples':samples}
print(json.dumps(out,ensure_ascii=False))
