File size: 2,079 Bytes
5816640
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
import type { Router } from 'express';
import { supabase, tableMissing } from '../supabase.js';

interface RevenueStreamRecord {
  amount: number;
  status: string;
  metadata: Record<string, any> | null;
}

export function registerRiverRoutes(router: Router) {
  router.get('/river/tools', async (_req, res, next) => {
    try {
      const { data, error } = await supabase
        .from('river_tools')
        .select('*')
        .order('created_at', { ascending: false });

      if (error && !tableMissing(error)) throw error;

      res.json({ tools: data ?? [] });
    } catch (error) {
      next(error);
    }
  });

  router.get('/river/analytics/:toolId', async (req, res, next) => {
    const { toolId } = req.params;
    try {
      const { data, error } = await supabase
        .from('river_tool_metrics')
        .select('*')
        .eq('tool_id', toolId)
        .order('recorded_at', { ascending: false })
        .limit(1)
        .single();

      if (!error && data) {
        return res.json({ toolId, ...data });
      }

      if (error && !tableMissing(error)) {
        throw error;
      }

      // Fallback to aggregate revenue streams
      const { data: revenueData, error: revenueError } = await supabase
        .from('revenue_streams')
        .select('amount,status,metadata');

      if (revenueError && !tableMissing(revenueError)) throw revenueError;

      const streams = (revenueData ?? []) as RevenueStreamRecord[];
      const relevant = streams.filter(stream => {
        const meta = stream.metadata || {};
        return meta.tool_id === toolId || meta.toolId === toolId;
      });

      const revenue = relevant.reduce((sum, stream) => sum + (stream.status === 'confirmed' ? stream.amount : 0), 0);
      const conversions = relevant.length;

      res.json({
        toolId,
        revenue,
        conversions,
        subscribers: conversions, // placeholder until distinct subscribers tracked
        mrr: revenue,
        timestamp: new Date().toISOString(),
      });
    } catch (error) {
      next(error);
    }
  });
}