New NextGate Auth & Onboarding Flow UI
1. Sign Up Flow
Path A: Phone User
Enter phone number
│
▼
Verify OTP
│
▼
Enter age & name
│
▼
Pick username
│
▼
Pick interests (min 3)
│
▼
Profile setup (optional)
│
▼
Home Feed 🎉
(device registered)
── Post-onboarding ──
Soft nudge to add email
(banner only, never blocking)
Path B: Email User
Enter email address
│
▼
Verify OTP
│
▼
Enter age & name
│
▼
Pick username
│
▼
Verify phone number ← REQUIRED (Identity)
│
▼
Pick interests (min 3)
│
▼
Profile setup (optional)
│
▼
Home Feed 🎉
(device registered)
Path C: Google / Apple OAuth
Tap Google / Apple
│
▼
OAuth authorize
│
▼
Enter age & name
(pre-filled from OAuth)
│
▼
Pick username
(suggestions from name)
│
▼
Verify phone number ← REQUIRED (Identity)
│
▼
Pick interests (min 3)
│
▼
Profile setup (optional)
(profile pic pre-filled)
│
▼
Home Feed 🎉
(device registered)
2. Onboarding Steps Detail
Step Summary
| # |
Step |
Applies To |
Endpoint |
| 0 |
OTP / OAuth entry |
All |
/auth/start + /auth/verify or /auth/login/oauth |
| 1 |
Age & name |
All |
/auth/onboarding/age |
| 2 |
Username |
All |
/auth/onboarding/username |
| 3 |
Contact verify (PHONE) |
Email + OAuth only |
/auth/onboarding/contact/initiate + /contact/verify |
| 4 |
Interests |
All |
/auth/onboarding/interests |
| 5 |
Profile |
All |
/auth/onboarding/profile |
| Signup Method |
Required Contact |
Reason |
| Phone |
Email (optional, post-onboarding) |
Phone = real identity, M-Pesa already linked |
| Email |
Phone (blocking) |
Needed for M-Pesa payments |
| Google / Apple |
Phone (blocking) |
OAuth gives email, phone still required for payments |
Onboarding Step Sequence
Phone user:
INITIATED → OTP_VERIFIED → AGE_VERIFIED → USERNAME_SET → INTERESTS_SELECTED → PROFILE_COMPLETED → COMPLETED
Email / OAuth user:
INITIATED → OTP_VERIFIED → AGE_VERIFIED → USERNAME_SET → CONTACT_VERIFIED → INTERESTS_SELECTED → PROFILE_COMPLETED → COMPLETED
Token Expiry
| Token |
Expiry |
Purpose |
onboardingToken |
7 days |
Active onboarding flow, resets each step |
onboardingRefreshToken |
30 days |
Safety net if token expires mid-flow |
accessToken |
Configured |
Normal app access |
refreshToken |
Configured |
Access token rotation |
STATE A — Input
┌──────────────────────────────────────┐
│ 📱 Add your phone number │
│ │
│ Your email j••••@g••••.com ✅ │
│ │
│ We need your phone for: │
│ • M-Pesa ticket payments │
│ • Event reminders │
│ • Account security │
│ │
│ Phone: [+255______________] │
│ [Send Code →] │
└──────────────────────────────────────┘
STATE B — OTP Input
┌──────────────────────────────────────┐
│ Enter code sent to ••• ••• ••50 │
│ │
│ [_] [_] [_] [_] [_] [_] │
│ │
│ [Edit number] Resend (60s) │
└──────────────────────────────────────┘
STATE C — Edit (tapping [Edit number] transforms inline)
┌──────────────────────────────────────┐
│ New number: [+255______________] │
│ [Send new code →] [Cancel] │
└──────────────────────────────────────┘
Previous OTP invalidated immediately on edit.
No page navigation — single page, three inline states.
4. Login Flow
Identifier Detection
Complete Login Flow
┌─────────────────────────────────────┐
│ Login Screen │
└─────────────────┬───────────────────┘
│
┌───────────┼───────────┐
│ │ │
▼ ▼ ▼
Google/ Phone/Email Username
Apple │ │
│ │ │
▼ ▼ ▼
OAuth Detect Find account
│ account │
│ │ │
│ ▼ ▼
│ Has password? Show masked
│ │ OTP destination
│ ┌─────┴─────┐ │
│ ▼ ▼ │
│ No Yes │
│ │ │ │
│ │ ┌─────┴─────┐ │
│ │ ▼ ▼ │
│ │ [OTP] [Password]
│ │ │ │ │
│ ▼ ▼ ▼ │
│ OTP Screen Password │
│ │ Screen │
│ │ │ │
│ └─────┬─────┘ │
│ │ │
▼ ▼ ▼
Device Check Device Check OTP Screen
│ │ │
▼ ▼ ▼
(see §5) (see §5) Device Check
│
▼
(see §5)
5. Device Trust Check
After Authentication
User Authenticated
│
▼
┌──────────────────┐
│ Check Device │
│ • Device ID │
│ • Fingerprint │
│ • IP / Location │
└────────┬─────────┘
│
▼
Is Device Known?
│
┌────┴────┐
▼ ▼
Yes No
│ │
▼ ▼
Home 🎉 Login Method?
│
┌───────┼───────┐
▼ ▼ ▼
OTP Password OAuth
│ │ │
▼ ▼ ▼
Home 🎉 OTP OTP
Required Required
│ │
▼ ▼
Verify Verify
│ │
▼ ▼
Register Device
│
▼
Home 🎉
Device Trust Rules
| Login Method |
New Device Action |
Reason |
| OTP |
None |
OTP = already verified |
| Password |
Require OTP |
Password could be stolen |
| OAuth |
Require OTP |
Token could be compromised |
6. Risk Scoring
| Signal |
Low Risk |
High Risk |
| Location |
Same country |
New country |
| Device |
Similar OS |
Different OS |
| IP |
Normal |
VPN / Proxy |
| Account |
Active |
Dormant |
| Time |
Normal hours |
Unusual hours |
Action by Risk
Risk Score
│
├── Low Risk ──► Soft verify (email link, approve from known device)
│
└── High Risk ──► Phone OTP required
7. UI Screens
Sign Up Screen
┌─────────────────────────────────────┐
│ │
│ Create Account 🚀 │
│ │
│ ┌───────────────────────────────┐ │
│ │ Phone or Email │ │
│ └───────────────────────────────┘ │
│ │
│ ┌───────────────────────────────┐ │
│ │ Continue │ │
│ └───────────────────────────────┘ │
│ │
│ ── or ── │
│ │
│ [Google] [Apple] │
│ │
│ Already have account? Login │
│ │
└─────────────────────────────────────┘
OTP Verification Screen
┌─────────────────────────────────────┐
│ │
│ Verify OTP 🔐 │
│ │
│ Enter code sent to: │
│ +255 712 345 678 │
│ │
│ ┌───┐ ┌───┐ ┌───┐ ┌───┐ ┌───┐ ┌───┐
│ │ │ │ │ │ │ │ │ │ │ │ │
│ └───┘ └───┘ └───┘ └───┘ └───┘ └───┘
│ │
│ Resend code (0:45) │
│ │
└─────────────────────────────────────┘
Age & Name Screen
┌─────────────────────────────────────┐
│ │
│ Let's get started 📅 │
│ │
│ First name: │
│ ┌───────────────────────────────┐ │
│ │ John │ │
│ └───────────────────────────────┘ │
│ │
│ Last name: │
│ ┌───────────────────────────────┐ │
│ │ Doe │ │
│ └───────────────────────────────┘ │
│ │
│ Date of birth: │
│ ┌───────────────────────────────┐ │
│ │ 1999 / 05 / 15 │ │
│ └───────────────────────────────┘ │
│ │
│ ┌───────────────────────────────┐ │
│ │ Continue │ │
│ └───────────────────────────────┘ │
│ │
└─────────────────────────────────────┘
Username Screen
┌─────────────────────────────────────┐
│ │
│ Pick Username 🏷️ │
│ │
│ ┌───────────────────────────────┐ │
│ │ @johndoe99 │ │
│ └───────────────────────────────┘ │
│ │
│ ✅ @johndoe99 is available │
│ │
│ Suggestions: │
│ @johndoe_tz @jdoe99 @the_john │
│ │
│ ┌───────────────────────────────┐ │
│ │ Continue │ │
│ └───────────────────────────────┘ │
│ │
└─────────────────────────────────────┘
┌─────────────────────────────────────┐
│ │
│ Add your phone number 📱 │
│ │
│ Your email j•••@g••••.com ✅ │
│ │
│ Needed for: │
│ • SMS reminders │
│ • Account security and recovery │
│ │
│ ┌───────────────────────────────┐ │
│ │ +255 _____________________ │ │
│ └───────────────────────────────┘ │
│ │
│ ┌───────────────────────────────┐ │
│ │ Send Code │ │
│ └───────────────────────────────┘ │
│ │
└─────────────────────────────────────┘
Interests Screen
┌─────────────────────────────────────┐
│ │
│ Pick Your Interests 🎯 │
│ (at least 3) │
│ │
│ ┌─────────┐ ┌─────────┐ ┌───────┐ │
│ │ Fashion │ │ Tech │ │ Music │ │
│ └─────────┘ └─────────┘ └───────┘ │
│ ┌─────────┐ ┌─────────┐ ┌───────┐ │
│ │ Sports │ │ Food │ │Gaming │ │
│ └─────────┘ └─────────┘ └───────┘ │
│ ┌─────────┐ ┌─────────┐ ┌───────┐ │
│ │ Travel │ │ Art │ │Fitness│ │
│ └─────────┘ └─────────┘ └───────┘ │
│ │
│ ┌───────────────────────────────┐ │
│ │ Continue │ │
│ └───────────────────────────────┘ │
│ │
└─────────────────────────────────────┘
Profile Setup Screen
┌─────────────────────────────────────┐
│ │
│ Complete Profile ✨ │
│ (optional) │
│ │
│ ┌─────────┐ │
│ │ 📷 │ │
│ └─────────┘ │
│ Add photo │
│ │
│ Display name: │
│ ┌───────────────────────────────┐ │
│ │ John Doe │ │
│ └───────────────────────────────┘ │
│ │
│ Bio: │
│ ┌───────────────────────────────┐ │
│ │ Music lover | Dar es Salaam 🇹🇿│ │
│ └───────────────────────────────┘ │
│ │
│ ┌──────────────┐ ┌──────────────┐ │
│ │ Complete │ │ Skip for now │ │
│ └──────────────┘ └──────────────┘ │
│ │
└─────────────────────────────────────┘
Login Screen
┌─────────────────────────────────────┐
│ │
│ Welcome Back 👋 │
│ │
│ ┌───────────────────────────────┐ │
│ │ Phone, email, or username │ │
│ └───────────────────────────────┘ │
│ │
│ ┌───────────────────────────────┐ │
│ │ Continue │ │
│ └───────────────────────────────┘ │
│ │
│ ── or ── │
│ │
│ [Google] [Apple] │
│ │
│ Don't have account? Sign up │
│ │
└─────────────────────────────────────┘
Login Method Choice (if password exists)
┌─────────────────────────────────────┐
│ │
│ How do you want to login? │
│ │
│ ┌───────────────────────────────┐ │
│ │ 📱 Send me OTP │ │
│ └───────────────────────────────┘ │
│ │
│ ┌───────────────────────────────┐ │
│ │ 🔑 Use password │ │
│ └───────────────────────────────┘ │
│ │
└─────────────────────────────────────┘
OTP Destination Choice (username login)
┌─────────────────────────────────────┐
│ │
│ Send OTP to: │
│ │
│ ○ ••• ••• ••45 │
│ ○ j••••••@g••••.com │
│ │
│ ┌───────────────────────────────┐ │
│ │ Send OTP │ │
│ └───────────────────────────────┘ │
│ │
└─────────────────────────────────────┘
New Device Detected
┌─────────────────────────────────────┐
│ │
│ 🆕 New device detected │
│ │
│ For your security, verify it's │
│ you with a one-time code. │
│ │
│ ○ ••• ••• ••45 │
│ ○ j••••••@g••••.com │
│ │
│ ┌───────────────────────────────┐ │
│ │ Send OTP │ │
│ └───────────────────────────────┘ │
│ │
└─────────────────────────────────────┘
8. Security Settings (Post-onboarding)
┌─────────────────────────────────────┐
│ │
│ Security Settings 🔒 │
│ │
├─────────────────────────────────────┤
│ │
│ Phone │
│ ┌───────────────────────────────┐ │
│ │ +255 712 XXX XXX ✅ Verified│ │
│ └───────────────────────────────┘ │
│ │
│ Email │
│ ┌───────────────────────────────┐ │
│ │ Not added [Add now] │ │ ← phone users see this
│ └───────────────────────────────┘ │
│ 💡 Add email for ticket delivery │
│ │
│ Password │
│ ┌───────────────────────────────┐ │
│ │ Not set [Add] │ │
│ └───────────────────────────────┘ │
│ 💡 Optional extra security │
│ │
├─────────────────────────────────────┤
│ │
│ Linked Accounts │
│ ┌───────────────────────────────┐ │
│ │ Google Not linked [Link] │ │
│ │ Apple Not linked [Link] │ │
│ └───────────────────────────────┘ │
│ │
└─────────────────────────────────────┘
9. Summary
Sign Up
| Path |
Steps |
| Phone |
OTP → Age → Username → Interests → Profile → Home |
| Email |
OTP → Age → Username → Verify Phone → Interests → Profile → Home |
| OAuth |
Authorize → Age → Username → Verify Phone → Interests → Profile → Home |
Login
| Has Password? |
Options |
| No |
OTP only |
| Yes |
Choose: OTP or Password |
Device Verification
| Login Method |
New Device Action |
| OTP |
None (OTP = verification) |
| Password |
OTP required |
| OAuth |
OTP required |
Post-Onboarding Nudges (Phone users)
| Feature |
Requires Email? |
Behaviour |
| Browse feed |
No |
Free |
| Buy ticket |
No |
Free |
| Receive ticket via email |
Yes |
Nudge to add email |
| Account recovery |
Yes |
Nudge to add email |