# CLAUDE.md — QuitSure Quiz Funnel (Quira)

## What This Project Is

A **web-to-app quiz funnel** for QuitSure, the quit-smoking app. Marketed to cold traffic via Google/Meta ads. A smoker clicks the ad, lands here, and is walked through a ~5-minute psychological assessment by "Quira" — a quit coach character. The user learns about their smoking psychology, gets revealed insights, and ends with a personalized results page + CTA that routes to the QuitSure subscription/paywall.

**Key reframe (important):** This is **NOT** the in-app onboarding anymore. That was the previous version. The current direction (set by Ram, April 2026) is a **cold-traffic marketing quiz funnel** where Quira is positioned as a psychologist running an assessment, NOT a salesperson. The research basis is Noom / BetterMe / Fabulous style quiz funnels.

**Core insight driving the design:** *"We're not selling a quit-smoking app. We're providing a personalized psychological assessment that happens to require our app to implement."* The user feels pulled in by self-discovery, not pushed at with a sales pitch.

---

## The 5-Stage Funnel

| Stage | Purpose | Emotional Goal |
|---|---|---|
| **Stage 0 — Qualifier** | Filter non-smokers | Set honest tone |
| **Stage 1 — Basics** | Name, age | Personalization begins |
| **Stage 2 — The Mirror** | Reveal their addiction depth (Fagerström-style) | "This is real" |
| **Stage 3 — Denial Audit** | Show them their own protective thoughts | "My brain is tricking me" |
| **Stage 4 — Failure Audit** | Show method success rates | "It wasn't my fault" |
| **Stage 5 — Why & Life** | Urgency + cost reveal + Smoker Type tease | "I'm burning my life" |
| **Stage 6 — Readiness** | Final qualification + fears | Commitment rising |
| **Analysis + Email Gate** | Build anticipation + capture email | Peak motivation |
| **Results Page** | Full profile reveal + program match | "This is built for me" |
| **CTA** | Hand off to subscription paywall | Conversion |

4 reveal moments + ~16 questions + 4 results cards. ~5-8 minutes.

---

## Architecture

**Frontend:** single-page vanilla HTML/CSS/JS (`templates/index.html`, ~2500 lines). Chat bubble UI with Quira persona. Mix of chips, multi-select, sliders, numeric input, currency input, and free-text. Every question (except numeric/slider) offers an "Or type your own..." escape hatch.

**Backend:** FastAPI (`app.py`). Three endpoints:
1. `GET /` — serves the page
2. `POST /api/chat` — LLM integration for dynamic Quira responses (Gemini 2.5 Flash primary, NVIDIA Kimi K2.5 fallback)
3. `POST /api/profile` — **deterministic server-side classification.** Computes smoker type, success probability, program routing, quit date, savings. NO LLM involved. Scoring is rules-based.

**Why server-side classification?** Ram's team needs the smoker-type assignment and program routing to be consistent and auditable. LLMs are not deterministic — for critical user-segmentation logic, we use pure Python math.

---

## The 6 Smoker Types

Classification runs server-side from user answers in `/api/profile`. Backed by real personality typology research (ScienceDirect, BBC Lab UK study).

| Type | Key signal |
|---|---|
| **Stress Smoker** | `stress`/`relax` in why_smoke, OR `stress`/`work`/`evening` in triggers |
| **Social Smoker** | `social` in why_smoke OR `social`/`alcohol` in triggers |
| **Habitual Smoker** | `automatic`/`focus` in why_smoke OR `morning`/`meals`/`coffee` in triggers |
| **Emotional Smoker** | `angry`/`boredom` in why_smoke |
| **Reward Smoker** | `reward`/`enjoy` in why_smoke |
| **Identity Smoker** | 15+ years smoking (dominant signal) |

Each type has a `description`, a `hidden_truth` (the insight Quira reveals on the results page), and a `program_focus`. All stored in `static/facts.json`.

---

## Program Routing

Deterministic. Routes to either **6-day** or **6-week** program:

**Route to 6-week (sixteen_week) if ANY of these:**
- `readiness <= 5` (low commitment)
- `cigs >= 20 AND past_attempts >= 3` (heavy smoker with failure pattern)
- `biggest_fear == "not_ready"` (self-identified as unprepared)
- `first_cig <= 5` (severe physical dependence — needs gradual approach)

**Else → 6-day (six_day)** — faster path for ready, moderate smokers.

**Important:** the app backend routes users to `iProgramId = 3` (6-day Program 3) or `iProgramId = 9` (6-week LTP/Program 9) based on this output. The quiz's routing decision is the authoritative signal.

**If Ram wants to tune these thresholds later**, they're in `app.py` at the `route_to_16_week` block, clearly commented, editable in seconds.

---

## Tech Stack

- **Backend:** FastAPI + Python 3.9+
- **HTTP client:** `httpx` (async, for LLM calls)
- **Frontend:** vanilla HTML + CSS + JS. No React, no build step. Google Fonts (Open Sans)
- **LLM:** Gemini 2.5 Flash (primary, free credits), NVIDIA NIM Kimi K2.5 (fallback)
- **Static assets:** `/static/` — facts.json, logos, Quira avatar (PNG), icon
- **No database yet.** State lives in client `state.data` object. `/api/complete` logs to console as a stub for Laravel backend integration.

### Running locally

```bash
cd /Users/neelraut/quitsure-chatbot-onboarding
pip3 install fastapi uvicorn jinja2 httpx
python3 -m uvicorn app:app --host 0.0.0.0 --port 8080 --reload
# Open http://localhost:8080
```

---

## Quira's Persona (Version 2 — "Psychologist")

Previous version had Quira as "quit consultant" (warmer, casual friend). **The April 2026 reframe positions her as a clinical quit coach** — still warm but more composed, professional, research-backed. She doesn't pitch. She doesn't sell. She administers the assessment.

Full system prompt lives in `app.py`'s `SYSTEM_PROMPT`. Key hard guardrails:

1. **NEVER invent stats** — only facts from `facts.json`
2. **NEVER give medical advice** — if user mentions serious health/mental health issues, deflect to a doctor
3. **NEVER diagnose or label** the user
4. **NEVER reveal specific program techniques/exercises** — can tease, can't spoil
5. **NEVER use jargon** — no "neuroplasticity", "dopamine", "cortisol", "cognitive dissonance"
6. **NEVER ask the user a question** (the app does that)
7. **NEVER shame / moralize / use fear tactics**
8. **1-2 sentences per response, max**
9. **Reference prior answers** to make user feel heard
10. **Handle distress gracefully** (suicide, self-harm, abuse → redirect to professional help)

---

## File Map

```
quitsure-chatbot-onboarding/
├── app.py                      — FastAPI backend (~210 lines)
│   ├── /                       — serves index.html
│   ├── /api/chat               — LLM endpoint (Gemini → NVIDIA fallback)
│   ├── /api/profile            — server-side classification
│   └── /api/complete           — stub, POST final user data
├── templates/index.html        — Full frontend (~2500 lines). CSS + HTML + JS inline
├── static/
│   ├── facts.json              — All content: denial patterns, method rates,
│   │                             smoker types, program routing, reveal copy
│   ├── quincy-avatar.png       — Illustrated female psychologist
│   ├── logo-full-nobg.png      — QuitSure logo (used on hero)
│   ├── logo-horiz-white.png    — White logo for teal bg
│   └── icon.png                — Favicon
├── requirements.txt            — fastapi, uvicorn, jinja2, httpx
├── CLAUDE.md                   — This file
└── Quiz Funnels Increase Subscriptions_.pdf  — Ram's research doc
                                   (Gemini + Claude strategy plans)
```

---

## Value Moments (the 4 reveals)

These are the "aha" moments that drive conversion. Each is a visually distinct card (not a regular chat bubble):

| # | After Q | What shows | Why it works |
|---|---|---|---|
| 1 | Q7 (last-24h) | **Physical Dependence Card** — high/moderate/low + bar | Makes addiction feel real (Fagerström-based) |
| 2 | Q8 (denial patterns) | **Denial Pattern Score** — "X of 8" big number on teal gradient | Self-awareness jolt. Most people check 4-6. |
| 3 | After Q10 (methods) | **Method Success Rates** — red/green comparison card | Positions QuitSure as only thing with real rate (86%) |
| 4 | After Q14 (why smoke) | **Smoker Type Tease** — small dashed-border card | Creates anticipation for final reveal |
| + | After Q15 (cost input) | **Cost Confrontation Card** — teal gradient with ₹ numbers | Personalized loss aversion |
| + | Results page | **Smoker Type → Probability → QuitSure intro (founder + social proof) → Program Match + Preview → Obstacles → Future Vision → Savings → Guarantee → CTA** | QuitSure revealed as the answer to their specific profile, not a cold pitch |

---

## LLM Integration Model

- **Chip taps = scripted, instant.** No LLM call. Fast.
- **Free text input OR multi-select = LLM-powered.** Quira reads what the user wrote/picked, composes a specific response that references their exact words. Blends response across multiple selections.
- **Reveals + transitions = some LLM, some scripted.** The big emotional moments (reveal cards) are scripted for consistency. The transitions between stages often use LLM for natural tone.

**Fallback:** Every LLM call has a scripted fallback. If Gemini and NVIDIA both fail, the user never sees a broken experience — they get a decent generic response.

**Cost per user:** ~$0.001-0.003 per flow (mostly Gemini free credits).

---

## What's NOT Built

- ❌ **Email capture → Laravel backend.** `/api/complete` logs to console. Ram's team needs to wire this to their DB (`tbl_Users`, `tbl_UserConfig`, etc.) and email triggers.
- ❌ **Analytics / event logging.** No Mixpanel, GA, or custom event tracking yet. Adding is trivial (a few `fetch` calls on key moments).
- ❌ **Session persistence.** Close tab = lose progress. No localStorage save yet.
- ❌ **A/B testing infrastructure.** Ram mentioned wanting to test 3-4 variants. Currently only one funnel.
- ❌ **Paywall integration.** The CTA button currently just logs. Need to hand off to QuitSure's existing subscription page (including the iProgramId routing info so the user lands on the right program's paywall).
- ❌ **Deployment.** Runs on `localhost:8080`. Ram's tech team will host on their infra (Laravel stack).

---

## Conversation Flow (detailed)

Steps 0-23 in `STEPS` array in `templates/index.html`:

| # | Step | Input type | What gets captured |
|---|---|---|---|
| 0 | Smoker qualifier | Chips | `smoker_status` (regular/occasional/quit_recent/non_smoker — exits flow) |
| 1 | Name | Free text | `name` |
| 2 | Age | Numeric | `age` |
| 3 | Years smoking | Chips + free text | `years_smoking` (numeric midpoint) |
| 4 | Cigs/day | Chips + free text | `cigs_per_day` |
| 5 | First cig after waking | Chips | `first_cig_minutes` |
| 6 | Last 24h count | Slider | `last_24h` |
| 7 | **🎯 REVEAL #1: Addiction Severity** | — | `severity` (high/moderate/low) |
| 8 | Denial patterns multi-select | Multi-chips | `denial_patterns`, `denial_count` |
| 9 | **🎯 REVEAL #2: Denial Pattern Score** | — | — |
| 10 | Past quit attempts | Chips | `past_attempts_count` |
| 11 | Methods tried | Multi-chips | `methods_tried` |
| 12 | **🎯 REVEAL #3: Method Success Rates** | — | — |
| 13 | Why past attempts failed | Chips + free text | `past_failure_reason` |
| 14 | Why quit now | Chips + free text | `urgency_reason` |
| 15 | Triggers | Multi-chips | `triggers` |
| 16 | Why you smoke | Multi-chips | `why_smoke` + **Smoker Type TEASE** |
| 17 | Cost + cost card | Currency + number | `currency`, `price_per_cig`, `savings`, + **COST REVEAL** |
| 18 | Readiness slider | Slider | `readiness` |
| 19 | Biggest fear | Chips + free text | `biggest_fear` |
| 20 | Future self vision | Free text (LLM-heavy) | `future_vision` |
| 21 | Analysis animation | — | — |
| 22 | Email gate | Email input | `email` |
| 23 | Results page — Profile → QuitSure bridge → Program → Obstacles → Close → CTA | — | `profile` (from /api/profile). QuitSure is introduced HERE as the answer to their profile, not during the quiz. |

---

## Key Decisions Made (April 2026)

| Decision | Choice | Rationale |
|---|---|---|
| Funnel type | Quiz funnel (web-to-app) | Ram/Gemini/Claude research all pointed here |
| Quira persona | Cessation psychologist (v2 reframe) | Feels authoritative, not sales-y |
| Visual style | Kept from v1 (approved by boss) | Chat bubbles, Quira avatar, cards, typing indicator |
| Free text option | On every chip question | User preference + LLM makes it work |
| Multi-select responses | LLM blends response | More natural than picking one fact |
| Smoker type reveal | Mid-flow tease + full reveal at end | Classic Noom/BetterMe pattern — creates anticipation |
| Program routing | Algorithm decides, not user | Creates authority; "this is YOUR match" |
| Email gate | Before results, not before quiz start | 3-5x higher capture rate (research-backed) |
| Backend classification | Server-side, not LLM | Deterministic, auditable, editable |
| Tech stack | FastAPI (prototype) | Ram's tech team (Laravel) will port for prod |
| Non-smokers | Gentle exit with share link | Don't waste their time, maybe viral |

---

## Source Material

- `/Users/neelraut/quitsure-chatbot-onboarding/Quiz Funnels Increase Subscriptions_.pdf` — Ram's 45-page research doc combining:
  - His own notes (Noom analysis, Google recommendations)
  - Gemini's quiz funnel plan (10-question flow, 4 stages)
  - Claude's QuitSure-specific plan (15-question flow, Smoker Types, implementation roadmap)
- `memory/project_chatbot_onboarding_mvp.md` — earlier MVP notes (pre-quiz-funnel reframe)
- `memory/project_flow_feedback.md` — boss's feedback from 2026-04-14 that triggered this reframe

---

## Testing Checklist (for QA)

- [ ] Welcome screen text not cut by diagonal hero edge
- [ ] "I don't smoke" → exit screen with working share button
- [ ] Full heavy-smoker flow (25/day, 5min first cig, 5 attempts, readiness 3) → should route to 6-week program
- [ ] Full light-smoker flow (5/day, 60min first cig, 0 attempts, readiness 9) → should route to 6-day
- [ ] All free-text inputs trigger LLM response (typing indicator, then personalized reply)
- [ ] Multi-select triggers blended LLM response (not just one option addressed)
- [ ] Reveal cards animate in smoothly, not duplicated
- [ ] Mobile view (480px) — everything readable, no horizontal scroll
- [ ] If LLM fails, scripted fallbacks still show
- [ ] Final CTA logs complete user profile to console
