"""Disposable inbox/activation model: no HTTP, signature verifier or supplier API."""
import json,sqlite3

def fresh():
 db=sqlite3.connect(':memory:')
 db.executescript('''CREATE TABLE inbox(account TEXT,event TEXT,state TEXT,PRIMARY KEY(account,event));
 CREATE TABLE membership(id TEXT PRIMARY KEY,state TEXT);INSERT INTO membership VALUES('M9','inactive');
 CREATE TABLE fulfilment(id TEXT PRIMARY KEY,membership TEXT,purpose TEXT,state TEXT,
 UNIQUE(membership,purpose));''')
 return db

def snap(db):
 return {'inbox':db.execute('SELECT * FROM inbox ORDER BY event').fetchall(),
 'membership':db.execute('SELECT * FROM membership').fetchall(),
 'fulfilment':db.execute('SELECT * FROM fulfilment').fetchall()}

def receive(db,event,fail=False):
 db.execute('BEGIN IMMEDIATE')
 db.execute('INSERT INTO inbox VALUES(?,?,?) ON CONFLICT DO NOTHING',('A1',event,'pending'))
 if fail: db.rollback();return 'no acknowledgement'
 db.commit();return '2xx permitted'

def process(db,event,fail=False):
 db.execute('BEGIN IMMEDIATE')
 state=db.execute('SELECT state FROM inbox WHERE account=? AND event=?',('A1',event)).fetchone()
 if state is None:db.rollback();raise ValueError('no accepted event')
 if state[0]=='processed':db.rollback();return
 # This model assumes validated event semantics and fixed membership mapping.
 db.execute("UPDATE membership SET state='active' WHERE id='M9'")
 db.execute("INSERT INTO fulfilment VALUES('F9','M9','welcome:generation-1','pending') ON CONFLICT DO NOTHING")
 if fail:db.rollback();return
 db.execute("UPDATE inbox SET state='processed' WHERE account='A1' AND event=?",(event,))
 db.commit()

report=[]
db=fresh();ack=receive(db,'evt_7',True);assert snap(db)['inbox']==[]
report.append({'case':'Receipt rolled back','ack':ack,**snap(db)})
ack=receive(db,'evt_7');receive(db,'evt_7');assert len(snap(db)['inbox'])==1
report.append({'case':'Commit, lost reply, same event redelivered','ack':ack,**snap(db)})
process(db,'evt_7',True);assert snap(db)['membership']==[('M9','inactive')] and snap(db)['fulfilment']==[]
report.append({'case':'Activation transaction rolled back',**snap(db)})
process(db,'evt_7');process(db,'evt_7');assert len(snap(db)['fulfilment'])==1
report.append({'case':'Activation committed and worker repeated',**snap(db)})
receive(db,'evt_8');process(db,'evt_8');assert len(snap(db)['inbox'])==2 and len(snap(db)['fulfilment'])==1
report.append({'case':'Different event, same welcome generation',**snap(db)})
if __name__=='__main__':print(json.dumps({'sqliteVersion':sqlite3.sqlite_version,'cases':report},indent=2))
