# Migrating from Legacy to Novu Notifications

This guide covers migrating from the old notification system to the new Novu-powered system.

## Migration Overview

The new notification system:
- Uses Novu for multi-channel delivery
- Supports granular preferences per workflow
- Includes frequency controls
- Provides delivery tracking
- Backwards compatible with existing preferences

## Data Migration

### Step 1: Migrate Existing User Preferences

The system automatically migrates old preferences from `user_preferences.email_notifications` and `user_preferences.push_notifications` to the new `user_notification_preferences` table.

Run this migration script to batch migrate existing users:

```sql
-- Migrate existing users to new notification preferences
INSERT INTO user_notification_preferences (
  user_id,
  channel_preferences,
  workflow_preferences,
  frequency_settings
)
SELECT 
  user_id,
  jsonb_build_object(
    'in_app', true,
    'email', COALESCE((email_notifications->>'system_announcements')::boolean, true),
    'push', COALESCE((push_notifications->>'browser_enabled')::boolean, false),
    'sms', false
  ),
  jsonb_build_object(
    'review-reply', COALESCE((email_notifications->>'review_replies')::boolean, true),
    'new-follower', COALESCE((email_notifications->>'new_followers')::boolean, true),
    'system-announcement', COALESCE((email_notifications->>'system_announcements')::boolean, true),
    'weekly-digest', COALESCE((email_notifications->>'weekly_digest')::boolean, false),
    'monthly-digest', COALESCE((email_notifications->>'monthly_digest')::boolean, true)
  ),
  jsonb_build_object(
    'digest', 'daily',
    'max_per_hour', 10
  )
FROM user_preferences
WHERE NOT EXISTS (
  SELECT 1 FROM user_notification_preferences 
  WHERE user_notification_preferences.user_id = user_preferences.user_id
);
```

### Step 2: Create Novu Subscribers for Existing Users

Create a batch script to register all existing users as Novu subscribers:

```typescript
import { supabase } from '@/integrations/supabase/client';
import { notificationService } from '@/lib/notificationService';

async function migrateUsersToNovu() {
  const { data: profiles, error } = await supabase
    .from('profiles')
    .select('user_id, username, display_name')
    .is('banned', false);

  if (error) {
    console.error('Error fetching profiles:', error);
    return;
  }

  for (const profile of profiles) {
    // Get user's auth data for email
    const { data: { user } } = await supabase.auth.admin.getUserById(profile.user_id);
    
    if (user?.email) {
      await notificationService.createSubscriber({
        subscriberId: profile.user_id,
        email: user.email,
        firstName: profile.display_name?.split(' ')[0],
        lastName: profile.display_name?.split(' ').slice(1).join(' '),
        data: {
          username: profile.username,
        },
      });
      
      console.log(`Migrated user: ${profile.username}`);
      
      // Rate limit to avoid overwhelming Novu API
      await new Promise(resolve => setTimeout(resolve, 100));
    }
  }
  
  console.log('Migration complete!');
}
```

## Code Migration

### Updating Notification Triggers

**Old Way:**
```typescript
// Direct database insert (legacy)
await supabase
  .from('notifications')
  .insert({
    user_id: userId,
    type: 'review_reply',
    content: 'Someone replied to your review',
  });
```

**New Way:**
```typescript
// Using Novu via notificationService
import { notificationService } from '@/lib/notificationService';

await notificationService.trigger({
  workflowId: 'review-reply',
  subscriberId: userId,
  payload: {
    reviewTitle: 'Great ride!',
    replyAuthor: 'Jane Doe',
    replyContent: 'Thanks for the review!',
    reviewUrl: `/reviews/${reviewId}`,
  },
});
```

### Updating Preference Management

**Old Way:**
```typescript
await supabase
  .from('user_preferences')
  .update({
    email_notifications: {
      review_replies: false,
    },
  })
  .eq('user_id', userId);
```

**New Way:**
```typescript
import { notificationService } from '@/lib/notificationService';

await notificationService.updatePreferences(userId, {
  channelPreferences: {
    in_app: true,
    email: true,
    push: false,
    sms: false,
  },
  workflowPreferences: {
    'review-reply': false,
  },
  frequencySettings: {
    digest: 'daily',
    max_per_hour: 10,
  },
});
```

## Rollback Plan

If you need to rollback to the old system:

1. **Keep Old Tables**: Don't drop `user_preferences.email_notifications` or `push_notifications` columns
2. **Disable Novu**: Clear `VITE_NOVU_APPLICATION_IDENTIFIER` environment variable
3. **Revert Code**: The notification service gracefully handles missing Novu config

## Testing the Migration

### Test Checklist

- [ ] All existing users have entries in `user_notification_preferences`
- [ ] User preferences match their previous settings
- [ ] Test users receive notifications on all enabled channels
- [ ] Webhook is receiving delivery events
- [ ] Notification logs are being created
- [ ] User preference changes sync to Novu
- [ ] Unsubscribe links work correctly
- [ ] Email templates render correctly
- [ ] Push notifications work in supported browsers
- [ ] In-app notifications display correctly

### Test Script

```typescript
// Test notification delivery
import { notificationService } from '@/lib/notificationService';

async function testNotifications(testUserId: string) {
  console.log('Testing notification delivery...');
  
  // Test each workflow
  const workflows = [
    {
      id: 'review-reply',
      payload: {
        reviewTitle: 'Test Review',
        replyAuthor: 'Test User',
        replyContent: 'Test reply content',
        reviewUrl: '/test',
      },
    },
    {
      id: 'new-follower',
      payload: {
        followerName: 'Test Follower',
        followerProfile: '/profile/test',
      },
    },
  ];
  
  for (const workflow of workflows) {
    const result = await notificationService.trigger({
      workflowId: workflow.id,
      subscriberId: testUserId,
      payload: workflow.payload,
    });
    
    console.log(`${workflow.id}: ${result.success ? '✓' : '✗'}`);
    
    if (!result.success) {
      console.error(`Error: ${result.error}`);
    }
  }
}
```

## Performance Considerations

### Batch Operations

When migrating large numbers of users:

1. **Rate Limiting**: Add delays between API calls
2. **Batch Size**: Process in chunks of 100-500 users
3. **Error Handling**: Log failures and retry
4. **Progress Tracking**: Store migration state

### Optimization Tips

1. **Cache Templates**: Load notification templates once at startup
2. **Async Processing**: Use edge functions for heavy operations
3. **Database Indexes**: Already created on `user_notification_preferences`
4. **Connection Pooling**: Supabase handles this automatically

## Monitoring Post-Migration

Track these metrics after migration:

```sql
-- Delivery success rate
SELECT 
  DATE(created_at) as date,
  COUNT(*) FILTER (WHERE status = 'delivered') * 100.0 / COUNT(*) as success_rate
FROM notification_logs
WHERE created_at > NOW() - INTERVAL '7 days'
GROUP BY DATE(created_at)
ORDER BY date DESC;

-- Channel usage
SELECT 
  channel,
  COUNT(*) as total_sent,
  COUNT(*) FILTER (WHERE status = 'delivered') as delivered,
  COUNT(*) FILTER (WHERE read_at IS NOT NULL) as read
FROM notification_logs
WHERE created_at > NOW() - INTERVAL '7 days'
GROUP BY channel;

-- User engagement
SELECT 
  COUNT(DISTINCT user_id) as active_users,
  AVG(EXTRACT(EPOCH FROM (read_at - delivered_at))) as avg_time_to_read_seconds
FROM notification_logs
WHERE read_at IS NOT NULL
  AND created_at > NOW() - INTERVAL '7 days';
```

## Support During Migration

1. **Backup Data**: Export old notification preferences before migration
2. **Phased Rollout**: Enable for a subset of users first
3. **Feature Flag**: Use admin settings to control Novu enablement
4. **User Communication**: Notify users of new notification features
5. **Monitor Logs**: Watch edge function logs during migration

## Timeline

Recommended migration timeline:

- **Week 1**: Test with internal users
- **Week 2**: Rollout to 10% of users
- **Week 3**: Rollout to 50% of users  
- **Week 4**: Complete rollout
- **Week 5**: Remove legacy code (optional)
