← back to Freddy
app/api/pulse/route.ts
70 lines
import { NextRequest, NextResponse } from 'next/server';
import { query } from '@/lib/db';
import { verifyAuth } from '@/lib/auth';
export async function GET(request: NextRequest) {
const user = verifyAuth(request);
if (!user) {
return NextResponse.json({ error: 'Unauthorized' }, { status: 401 });
}
try {
const [
causesCount,
totalVotes,
orgsCount,
grantersCount,
matchesCount,
fundedAmount,
revenueStats,
pendingFees,
topCauses,
topOrgs,
recentMatches,
fundingRounds,
] = await Promise.all([
query(`SELECT COUNT(*)::int as count FROM causes WHERE status = 'active'`),
query(`SELECT COALESCE(SUM(total_votes), 0)::int as total FROM causes WHERE status = 'active'`),
query(`SELECT COUNT(*)::int as count FROM organizations WHERE status IN ('verified', 'featured', 'pending')`),
query(`SELECT COUNT(*)::int as count FROM granters WHERE status = 'active'`),
query(`SELECT COUNT(*)::int as count FROM matches`),
query(`SELECT COALESCE(SUM(funding_amount), 0)::numeric as total FROM matches WHERE status = 'funded'`),
query(`SELECT COALESCE(SUM(COALESCE(commission_amount, 0) + COALESCE(flat_fee, 0)), 0)::numeric as total FROM revenue WHERE status = 'paid'`),
query(`SELECT COALESCE(SUM(COALESCE(commission_amount, 0) + COALESCE(flat_fee, 0)), 0)::numeric as total FROM revenue WHERE status IN ('pending', 'invoiced')`),
query(`SELECT id, title, urgency_score, total_votes, total_supporters, category, tags, trending_rank
FROM causes WHERE status = 'active' ORDER BY urgency_score DESC, total_votes DESC LIMIT 10`),
query(`SELECT id, name, category, impact_score, trust_score, total_votes, total_funding_received, status
FROM organizations WHERE status IN ('verified', 'featured') ORDER BY total_votes DESC, impact_score DESC LIMIT 5`),
query(`SELECT m.id, m.match_score, m.status, m.created_at,
c.title as cause_title, o.name as org_name, g.name as granter_name
FROM matches m
JOIN causes c ON c.id = m.cause_id
JOIN organizations o ON o.id = m.org_id
LEFT JOIN granters g ON g.id = m.granter_id
ORDER BY m.created_at DESC LIMIT 5`),
query(`SELECT id, title, total_pool, allocated, remaining, status, opens_at, closes_at
FROM funding_rounds ORDER BY created_at DESC LIMIT 5`),
]);
return NextResponse.json({
stats: {
total_causes: causesCount.rows[0].count,
total_votes: totalVotes.rows[0].total,
registered_orgs: orgsCount.rows[0].count,
active_granters: grantersCount.rows[0].count,
total_matches: matchesCount.rows[0].count,
funds_matched: parseFloat(fundedAmount.rows[0].total) || 0,
revenue_earned: parseFloat(revenueStats.rows[0].total) || 0,
pending_fees: parseFloat(pendingFees.rows[0].total) || 0,
},
top_causes: topCauses.rows,
top_orgs: topOrgs.rows,
recent_matches: recentMatches.rows,
funding_rounds: fundingRounds.rows,
});
} catch (err) {
console.error('[pulse] GET error:', (err as Error).message);
return NextResponse.json({ error: 'Failed to fetch pulse data' }, { status: 500 });
}
}