Skip to main content

Source: ocean/docs/sentry-edge-functions-guide.md | ✏️ Edit on GitHub

Sentry Integration Guide for Edge Functions

Complete Sentry Coverage Implementation

1. Functions WITH Sentry ✅

  • handle-stripe-webhook - Full implementation
  • provision-tenant-resources - Full implementation
  • provision-user-resources - Full implementation
  • check-tenant-health - Full implementation
  • graphql-v2 - ✅ ADDED - Main API with distributed tracing
  • stripe-billing - ✅ ADDED - Billing details with error tracking
  • auth-hook - ✅ ADDED - Authentication events with security monitoring
  • database-hook - ✅ ADDED - Database changes with comprehensive tracking
  • stripe-subscription - ✅ ADDED - Subscription management with Stripe operation tracking
  • feature-flags - ✅ ADDED - Feature flag evaluation with security checks
  • stripe-portal - ✅ ADDED - Stripe customer portal with session tracking
  • stripe-setup-intent - ✅ ADDED - Payment method setup with customer creation tracking
  • stripe-products - ✅ ADDED - Product catalog with Stripe API tracking
  • sync-stripe-data - ✅ ADDED - Data synchronization with comprehensive error tracking
  • sync-user-to-stripe - ✅ ADDED - User profile sync with customer creation tracking

2. Functions NEEDING Sentry ❌

All functions now have Sentry integration!

Progress: 15/15 functions now have Sentry (🎉 100% COMPLETE! 🎉)

🚀 MISSION ACCOMPLISHED!

100% Sentry coverage achieved across ALL Edge Functions:

  • ✅ Authentication & Security (auth-hook)
  • ✅ Database Operations (database-hook)
  • ✅ Main API (GraphQL-v2)
  • ✅ Billing & Payments (stripe-billing, stripe-subscription, stripe-portal, stripe-setup-intent)
  • ✅ Feature Management (feature-flags)
  • ✅ Webhook Processing (handle-stripe-webhook)
  • ✅ Product Management (stripe-products)
  • ✅ Data Synchronization (sync-stripe-data, sync-user-to-stripe)
  • ✅ Infrastructure Health (check-tenant-health, provision-tenant-resources, provision-user-resources)

3. Implementation Pattern

For EVERY Edge Function, add this at the top:

import {
initSentryWithTracing,
withTracing,
trackSupabaseOperation,
} from '../_shared/sentry-tracing.ts'
import { Logger } from '../_shared/observability.ts'
import * as Sentry from 'https://deno.land/x/sentry/index.mjs'

// Initialize Sentry
initSentryWithTracing('function-name')
const logger = new Logger({ functionName: 'function-name' })

// Wrap your serve function
Deno.serve(
withTracing('function-name', async (req) => {
try {
logger.info('Processing request', {
method: req.method,
url: req.url,
})

// Your function logic here
} catch (error) {
logger.error('Request failed', error, {
// Add relevant context
})

Sentry.withScope((scope) => {
scope.setTag('function.name', 'function-name')
// Add more context
Sentry.captureException(error)
})

return new Response(JSON.stringify({ error: 'Internal server error' }), {
status: 500,
headers: corsHeaders,
})
}
})
) // Note the double closing parenthesis!

4. Database Operations

Wrap ALL Supabase operations:

const { data, error } = await trackSupabaseOperation('select', 'table_name', async () =>
supabase.from('table_name').select('*').eq('id', id)
)

if (error) {
logger.error('Database operation failed', error, {
operation: 'select',
table: 'table_name',
id,
})
throw error
}

5. External API Calls

Use tracedFetch for all external APIs:

const response = await tracedFetch('https://api.stripe.com/v1/customers', {
method: 'POST',
headers: {
Authorization: `Bearer ${stripeKey}`,
'Content-Type': 'application/json',
},
body: JSON.stringify(data),
spanName: 'Create Stripe Customer',
})

6. Critical Context to Always Include

Sentry.withScope((scope) => {
// Always include
scope.setTag('function.name', 'function-name')
scope.setTag('environment', Deno.env.get('ENVIRONMENT') || 'development')

// User context if available
if (userId) scope.setUser({ id: userId })

// Organization context if available
if (organizationId) {
scope.setContext('organization', { id: organizationId })
}

// Operation specific context
scope.setContext('request', {
method: req.method,
url: req.url,
headers: Object.fromEntries(req.headers.entries()),
})

Sentry.captureException(error)
})

7. Performance Monitoring

Track slow operations:

import { trackOperation } from '../_shared/observability.ts'

const result = await trackOperation(
'critical_operation',
async () => {
// Your operation here
},
{
userId,
organizationId,
operationType: 'billing',
}
)

8. Distributed Tracing

The withTracing wrapper automatically:

  • Extracts trace headers from frontend
  • Creates spans for the entire function execution
  • Propagates traces to downstream services
  • Links frontend and backend errors

9. Cost Optimization

Our setup already includes:

  • 10% transaction sampling in production
  • Filtering of non-critical errors (CORS, validation)
  • Removal of sensitive data
  • Skipping health check endpoints

10. Testing Your Integration

After adding Sentry to a function:

  1. Test Error Capture:

    curl -X POST https://your-project.supabase.co/functions/v1/your-function \
    -H "Content-Type: application/json" \
    -d '{"test": "error"}'
  2. Check Sentry Dashboard:

    • Errors should appear within seconds
    • Check transaction traces show full request flow
    • Verify context includes user/org data
  3. Verify Distributed Tracing:

    • Frontend errors should link to Edge Function traces
    • Database operations should appear as child spans

Priority Implementation Order

  1. auth-hook - Auth errors are critical
  2. database-hook - Database errors affect all operations
  3. stripe-subscription - Revenue impacting
  4. stripe-portal - Customer facing payment errors
  5. feature-flags - Affects feature rollouts
  6. All other Stripe functions

Benefits of Full Coverage

  • Complete Error Visibility: See errors across entire stack
  • Faster Debugging: Distributed traces show exact failure point
  • Proactive Monitoring: Catch errors before customers report
  • Performance Insights: Identify slow database queries and API calls
  • Security Monitoring: Track auth failures and suspicious patterns

With full Sentry coverage, you'll have complete observability across your entire application!