# STATUS — phase lex _Role: Adversary initializes this file to bootstrap the phase. Builder owns updates._ ## Current state: BUILDING — All gates CLAIMED, awaiting Adversary verification Gates: - D1: CLAIMED (awaiting Adversary verification) - D2: CLAIMED (awaiting Adversary verification) - D3: CLAIMED (awaiting Adversary verification) - D4: CLAIMED (awaiting Adversary verification) --- ## Gate D1 — Numbers **WHAT:** Integers and floats tokenize to a single NUMBER token with numeric value (int or float). EOF appended. **HOW to verify:** ```bash python -c "from calc.lexer import tokenize; r=tokenize('42'); assert r[0].kind=='NUMBER'; assert r[0].value==42; assert isinstance(r[0].value,int); assert r[1].kind=='EOF'; print('D1 int OK')" python -c "from calc.lexer import tokenize; r=tokenize('3.14'); assert r[0].kind=='NUMBER'; assert abs(r[0].value-3.14)<1e-9; assert isinstance(r[0].value,float); print('D1 float OK')" python -c "from calc.lexer import tokenize; r=tokenize('.5'); assert r[0].kind=='NUMBER'; assert r[0].value==0.5; print('D1 leading-dot OK')" python -c "from calc.lexer import tokenize; r=tokenize('10.'); assert r[0].kind=='NUMBER'; assert r[0].value==10.0; print('D1 trailing-dot OK')" ``` **EXPECTED:** Each prints its "OK" line, no exceptions. **WHERE:** `calc/lexer.py` at commit `98f1455` --- ## Gate D2 — Operators & Parens **WHAT:** `+ - * / ( )` each map to PLUS, MINUS, STAR, SLASH, LPAREN, RPAREN respectively. `tokenize("1+2*3")` yields NUMBER PLUS NUMBER STAR NUMBER EOF. **HOW to verify:** ```bash python -c " from calc.lexer import tokenize r = tokenize('1+2*3') kinds = [t.kind for t in r] assert kinds == ['NUMBER','PLUS','NUMBER','STAR','NUMBER','EOF'], kinds print('D2 expression OK') " python -c " from calc.lexer import tokenize ops = '+-*/()' expected = ['PLUS','MINUS','STAR','SLASH','LPAREN','RPAREN'] for ch, exp in zip(ops, expected): r = tokenize(ch) assert r[0].kind == exp, f'{ch} -> {r[0].kind}' print('D2 single-ops OK') " ``` **EXPECTED:** Prints `D2 expression OK` and `D2 single-ops OK`, no exceptions. **WHERE:** `calc/lexer.py` at commit `98f1455` --- ## Gate D3 — Whitespace & Errors **WHAT:** Spaces/tabs between tokens are skipped. Invalid characters raise `LexError` with the offending character and its position in the message. **HOW to verify:** ```bash python -c " from calc.lexer import tokenize r = tokenize(' 12 + 3 ') kinds = [t.kind for t in r] assert kinds == ['NUMBER','PLUS','NUMBER','EOF'], kinds assert r[0].value == 12 assert r[2].value == 3 print('D3 whitespace OK') " python -c " from calc.lexer import tokenize, LexError try: tokenize('1 @ 2') raise AssertionError('should have raised') except LexError as e: msg = str(e) assert '@' in msg, msg assert '2' in msg, msg print('D3 LexError OK:', msg) " python -c " from calc.lexer import tokenize, LexError try: tokenize('abc') raise AssertionError('should have raised') except LexError as e: print('D3 letter raises LexError OK') " ``` **EXPECTED:** Prints `D3 whitespace OK`, `D3 LexError OK: ...`, `D3 letter raises LexError OK`. **WHERE:** `calc/lexer.py` at commit `98f1455` --- ## Gate D4 — Tests Green **WHAT:** `calc/test_lexer.py` (unittest) passes under `python -m unittest`, 0 failures, covering D1–D3 including the three mandated cases: `" 12 + 3 "`, `"3.5*(1-2)"`, and `"1 @ 2"` raising LexError. **HOW to verify:** ```bash python -m unittest -q ``` **EXPECTED output:** ``` .............................. Ran 23 tests in 0.00Xs OK ``` (23 tests, 0 failures, 0 errors) Also run the plan's exact cold-verify commands: ```bash python -c "from calc.lexer import tokenize; print([(t.kind,t.value) for t in tokenize('3.5*(1-2)')])" # Expected: [('NUMBER', 3.5), ('STAR', '*'), ('LPAREN', '('), ('NUMBER', 1), ('MINUS', '-'), ('NUMBER', 2), ('RPAREN', ')'), ('EOF', None)] python -c "from calc.lexer import tokenize; tokenize('1 @ 2')" # Expected: raises LexError (traceback shown) ``` **WHERE:** `calc/test_lexer.py` and `calc/lexer.py` at commit `98f1455`