MathMate / README.md
MIHIR MITHANI
Deploy Streamlit app
54ab778
|
Raw History Blame Contribute Delete
4.3 kB
---
title: My Streamlit App
emoji: πŸš€
colorFrom: blue
colorTo: purple
sdk: streamlit
sdk_version: "1.49.1"
app_file: app.py
pinned: false
---
# My Streamlit App
This is a Streamlit application deployed on Hugging Face Spaces.
# Hint-Based Math Tutor (Problem 13)
A progressive hint system for math word problems that guides students without revealing answers early.
## Quick Start (Local)
```bash
cd hint-tutor
python -m venv .venv
source .venv/bin/activate
pip install -r requirements.txt
cp .env.example .env
# Edit .env with your NVIDIA_API_KEY (from NVIDIA NIM)
streamlit run app.py
```
## Run via ngrok (for live demo from laptop)
```bash
# Terminal 1: Start Streamlit
streamlit run app.py --server.port 8501 --server.headless true
# Terminal 2: Start ngrok tunnel
ngrok http 8501
# Share the https://... URL with judges
```
## App Features
**Single Tutor tab** with V2 chained pipeline:
- **Progressive hints**: Level 1 (Orient) β†’ Level 2 (Strategy) β†’ Level 3 (Walkthrough)
- **Level locking**: L2 requires L1; L3 requires L1+L2 or student attempt
- **Guard badges**: Passed / Regenerated NΓ— / Safe fallback
- **Working check** (stretch): Paste working β†’ analyzes first wrong step β†’ targeted hint
- **Final answer check**: Normalized numeric comparison
- **History sidebar**: Timestamped log of all problems + hints in this session
- **Random problems**: 6 extra problems not in eval set
- **Debug panel**: Hidden solution + LLM call log (toggle in sidebar)
## Project Structure
```
hint-tutor/
β”œβ”€β”€ app.py # Streamlit app (Tutor tab + history sidebar)
β”œβ”€β”€ llm.py # NVIDIA NIM wrapper (retry, timeout, JSON validation)
β”œβ”€β”€ schemas.py # Pydantic models
β”œβ”€β”€ pipeline_v1.py # Naive baseline (for eval only)
β”œβ”€β”€ pipeline_v2.py # Production V2 chained pipeline
β”œβ”€β”€ guardrails.py # Input gate, leak check, fallbacks
β”œβ”€β”€ arithmetic_check.py # Deterministic step verification (sympy)
β”œβ”€β”€ prompts/
β”‚ β”œβ”€β”€ v1/hint_naive.md
β”‚ └── v2/p0_input_gate.md p1_solver.md p2_hint_generator.md p3_leak_judge.md
β”‚ p4_working_analyzer.md p5_targeted_hint.md
β”œβ”€β”€ eval/
β”‚ β”œβ”€β”€ problems.json # 12 test problems
β”‚ β”œβ”€β”€ wrong_working.json # 12 labeled working cases
β”‚ β”œβ”€β”€ guardrail_cases.json # 7 guardrail tests
β”‚ └── run_eval.py # Evaluation runner (--version v1|v2|both)
β”œβ”€β”€ results/ # Evaluation outputs
β”œβ”€β”€ PROMPT_HISTORY.md # Timestamped prompt changes (git log format)
β”œβ”€β”€ requirements.txt
β”œβ”€β”€ .env.example
β”œβ”€β”€ .gitignore
└── tests/
β”œβ”€β”€ test_guardrails.py
└── test_pipeline_v2.py
```
## Hint Ladder
| Level | Name | Allowed | Forbidden |
|-------|------|---------|-----------|
| 1 | Orient | Restate givens/ask, one guiding question | Operations, formulas, computed numbers, answer |
| 2 | Strategy | Concept name, first sub-goal/equation setup | Final step result, answer |
| 3 | Walkthrough | Full solution + answer | β€” |
## Pipeline V2 (Chained)
```
Input Gate (code + LLM P0)
β†’ Hidden Solver P1 (Γ—2, temp 0 & 0.7, verify final_answer)
β†’ Hint Generator P2 (level N, schema validation retry)
β†’ Leak Guard: Code check β†’ LLM Judge P3 (if L1/L2)
β†’ Regenerate ≀2Γ— with feedback β†’ Safe Fallback
β†’ Show Hint
```
**Stretch**: Student working β†’ Arithmetic Checker + Working Analyzer P4 β†’ Targeted Hint P5 (same leak guard)
## Evaluation
Run locally:
```bash
python eval/run_eval.py --version both
```
Metrics:
- **M1 Leak Rate L1-L2** (V1 vs V2, with/without guard)
- **M2 Wrong-Step Accuracy** (V2 analyze_working vs labels; V1 baseline)
- **M3 Format-Validity Rate** (first-try Pydantic success / total LLM calls)
- **Guardrail Suite** (code + P0 on 7 cases)
Outputs: `eval/results/leak_v1.csv`, `leak_v2.csv`, `wrong_step_v1.csv`, `wrong_step_v2.csv`, `guardrails.csv`, `summary_HHMM.md`
## Prompt Discipline
All prompts live in versioned `.md` files under `prompts/`. Changes logged in `PROMPT_HISTORY.md` with format:
```
prompt(<card>): <what changed> | why: <failure it fixes> | vX.Y
```