Server-side Tracking
Track events from API routes, serverless functions, and edge environments
Server-side Tracking
Track events from your server-side code including API routes, serverless functions, and edge environments.
Installation
pnpm add better-analyticsBasic Usage
import { initServer, trackServer } from 'better-analytics/server'
// Initialize once
initServer({
site: 'your-site-id',
endpoint: 'https://your-endpoint.com/api/collect', // Optional
apiKey: 'your-api-key' // Optional, for authentication
})
// Track events
await trackServer('user_signup', {
method: 'email',
source: 'landing_page'
})Configuration
# Required
BA_SITE=your-site-id
# Optional
BA_URL=https://your-endpoint.com/api/collect
BA_API_KEY=your-server-api-key
BA_DEBUG=trueCore Functions
trackServer(event, props?, options?)
Track custom events with optional properties and context:
await trackServer('purchase', {
value: 99.99,
currency: 'USD',
items: ['product-1', 'product-2']
}, {
headers: request.headers,
user: { id: 'user-123' }
})trackPageviewServer(path, options?)
Track server-side page views:
await trackPageviewServer('/api/data', {
headers: request.headers
})identifyServer(userId, traits?, options?)
Identify users on the server:
await identifyServer('user-123', {
email: 'user@example.com',
plan: 'pro'
}, {
headers: request.headers
})Framework Examples
Node.js API Server
// server.js
import express from 'express'
import { initServer, trackServer } from 'better-analytics/server'
const app = express()
// Initialize once
initServer({
site: 'your-site-id',
apiKey: 'your-api-key'
})
app.post('/api/purchase', async (req, res) => {
// Your business logic here
await trackServer('purchase', {
value: req.body.amount,
currency: req.body.currency,
payment_method: req.body.paymentMethod
}, {
headers: req.headers
})
res.json({ success: true })
})Vercel Edge Functions
// api/edge-function.ts
import { trackServer } from 'better-analytics/server'
export const config = {
runtime: 'edge'
}
export default async function handler(req: Request) {
await trackServer('edge_function_called', {
path: new URL(req.url).pathname
}, {
headers: req.headers,
waitUntil: (promise) => {
// Vercel Edge Function context
context.waitUntil(promise)
}
})
return new Response('OK')
}Express.js Middleware
import express from 'express'
import { expressMiddleware } from 'better-analytics/server'
const app = express()
// Add analytics middleware
app.use(expressMiddleware())
app.post('/api/signup', (req, res) => {
// Your signup logic
// Track using the middleware
req.track('user_signup', {
method: req.body.method,
source: req.headers.referer
})
res.json({ success: true })
})Cloudflare Workers
// worker.js
import { initServer, trackServer } from 'better-analytics/server'
initServer({
site: 'your-site-id',
runtime: 'cloudflare'
})
export default {
async fetch(request, env, ctx) {
await trackServer('worker_request', {
path: new URL(request.url).pathname
}, {
headers: request.headers,
waitUntil: ctx.waitUntil
})
return new Response('Hello from Worker!')
}
}Context Information
Server events automatically include:
{
server: {
userAgent: "Mozilla/5.0...",
ip: "192.168.1.1",
country: "US",
referer: "https://example.com",
origin: "https://your-site.com",
runtime: "node",
framework: "nextjs"
}
}Session Stitching
Connect server events with client sessions:
import { stitchSession } from 'better-analytics/server'
// From client-side cookies or headers
const clientSessionId = request.cookies.get('ba_session')
const clientDeviceId = request.cookies.get('ba_device')
await trackServer('server_event', {
action: 'purchase'
}, {
user: stitchSession(clientSessionId, clientDeviceId)
})Error Handling
Server tracking fails silently by default. Enable debug mode to see errors:
initServer({
site: 'your-site-id',
debug: true // Will log errors to console
})Best Practices
- Track conversions server-side - More reliable than client-side
- Use batching for high-volume - Reduces API calls
- Include user context - Pass headers and user info
- Handle async properly - Use
waitUntilfor edge functions - Monitor in development - Enable debug mode during development
Runtime Support
- Node.js - Full support with automatic detection
- Edge Functions - Vercel, Netlify, Cloudflare Workers
- Serverless - AWS Lambda, Vercel Functions
- Deno - Full compatibility
TypeScript
Full TypeScript support:
import type { ServerTrackOptions } from 'better-analytics/server'
const options: ServerTrackOptions = {
headers: request.headers,
user: { id: 'user-123' },
meta: { source: 'api' }
}
await trackServer('event', { custom: 'data' }, options)How is this guide?
Client-side Tracking
Track events in web browsers using the core Better Analytics client SDK. This guide covers vanilla JavaScript, React, and other web frameworks.
Next.js Integration
Better Analytics provides seamless integration with Next.js applications with automatic initialization for both client and server-side tracking.