const { generateUpgradePitch } = require('../../src/services/upgradePitch'); function makeMockSupabase(sessions = [], picks = []) { return { from: (table) => ({ select: () => ({ eq: () => ({ order: () => ({ limit: () => Promise.resolve({ data: table === 'scan_sessions' ? sessions : picks }), }), single: () => Promise.resolve({ data: null }), }), }), }), }; } describe('upgradePitch', () => { test('generates pitch with correct scan count', async () => { const sessions = [ { id: '1', final_grade: 'A', legs: ['a', 'b'], created_at: '2026-03-20' }, { id: '2', final_grade: 'B', legs: ['c', 'd'], created_at: '2026-03-19' }, { id: '3', final_grade: 'D', legs: ['e'], created_at: '2026-03-18' }, { id: '4', final_grade: 'C', legs: ['f', 'g'], created_at: '2026-03-17' }, ]; const picks = [ { stat_type: 'points', direction: 'over', grade: 'A', player: 'Jokic' }, { stat_type: 'points', direction: 'over', grade: 'B', player: 'Jokic' }, { stat_type: 'rebounds', direction: 'over', grade: 'C', player: 'LeBron' }, ]; const supabase = makeMockSupabase(sessions, picks); const result = await generateUpgradePitch(supabase, 'user-1', { grade: 'B', legs: [] }); expect(result.hook).toContain('5'); // 4 prior + 1 current expect(result.insight).toContain('points'); expect(result.cta).toContain('founder rate'); expect(result.tier_recommended).toBeDefined(); expect(result.founder_price).toBeDefined(); }); test('recommends analyst for casual bettors (avg <= 4 legs)', async () => { const sessions = [ { id: '1', final_grade: 'B', legs: ['a', 'b'], created_at: '2026-03-20' }, { id: '2', final_grade: 'B', legs: ['c', 'd'], created_at: '2026-03-19' }, ]; const picks = [ { stat_type: 'points', direction: 'over', grade: 'B', player: 'Jokic' }, ]; const supabase = makeMockSupabase(sessions, picks); const result = await generateUpgradePitch(supabase, 'user-1', { grade: 'A', legs: [{ stat_type: 'points' }] }); expect(result.tier_recommended).toBe('analyst'); expect(result.founder_price).toBe('$14.99/mo'); }); test('recommends desk for power users (avg > 4 legs)', async () => { const sessions = [ { id: '1', final_grade: 'B', legs: ['a', 'b', 'c', 'd', 'e'], created_at: '2026-03-20' }, { id: '2', final_grade: 'A', legs: ['f', 'g', 'h', 'i', 'j', 'k'], created_at: '2026-03-19' }, ]; const picks = [ { stat_type: 'points', direction: 'over', grade: 'A', player: 'Jokic' }, { stat_type: 'points', direction: 'over', grade: 'B', player: 'LeBron' }, { stat_type: 'rebounds', direction: 'over', grade: 'A', player: 'Giannis' }, { stat_type: 'assists', direction: 'over', grade: 'B', player: 'Trae' }, { stat_type: 'points', direction: 'over', grade: 'B', player: 'Luka' }, ]; const supabase = makeMockSupabase(sessions, picks); const result = await generateUpgradePitch(supabase, 'user-1', { grade: 'B', legs: [{ stat_type: 'points' }, { stat_type: 'rebounds' }, { stat_type: 'assists' }, { stat_type: 'points' }, { stat_type: 'steals' }], }); expect(result.tier_recommended).toBe('desk'); expect(result.founder_price).toBe('$34.99/mo'); }); test('handles no prior scans gracefully', async () => { const supabase = makeMockSupabase([], []); const result = await generateUpgradePitch(supabase, 'user-1', { grade: 'C', legs: [{ stat_type: 'points' }] }); expect(result.hook).toContain('1'); // just the current scan expect(result.tier_recommended).toBeDefined(); }); });