PostHog
Set up analytics, feature flags, and LLM cost tracking with PostHog.
PostHog provides product analytics, feature flags, session replay, and LLM analytics for tracking AI costs.
Create a PostHog Account
- Go to posthog.com and create an account
- Create a new project (or use the default one)
Get Your API Keys
Navigate to Project Settings in your PostHog dashboard:
| Key | Environment Variable |
|---|---|
| Project API Key | NEXT_PUBLIC_POSTHOG_KEY |
| Host | NEXT_PUBLIC_POSTHOG_HOST |
The host is typically:
- US Cloud:
https://us.i.posthog.com - EU Cloud:
https://eu.i.posthog.com - Self-hosted: Your PostHog instance URL
How Analytics Work
VelocityKit automatically tracks:
- Page views — Every page navigation
- User identification — Links events to authenticated users
- Custom events — Track specific actions in your app
Tracking Custom Events
import { usePostHog } from "@/lib/posthog/client";
function MyComponent() {
const posthog = usePostHog();
const handleClick = () => {
posthog?.capture("button_clicked", {
button_name: "upgrade",
location: "pricing_page",
});
};
return <button onClick={handleClick}>Upgrade</button>;
}
Server-Side Tracking
For server actions and API routes:
import { getServerPostHog } from "@/lib/posthog/server";
export async function createItem() {
const posthog = getServerPostHog();
// Track the event
posthog?.capture({
distinctId: userId,
event: "item_created",
properties: { item_type: "todo" },
});
}
Feature Flags
Feature flags let you roll out features gradually or to specific users.
Create a Flag
- Go to Feature Flags in PostHog
- Click New feature flag
- Set a key (e.g.,
new-dashboard) - Configure rollout percentage or targeting rules
Check Flags in Code
import { useFeatureFlag } from "@/lib/posthog/client";
function Dashboard() {
const showNewDashboard = useFeatureFlag("new-dashboard");
if (showNewDashboard) {
return <NewDashboard />;
}
return <OldDashboard />;
}
Server-Side Flags
import { getServerPostHog } from "@/lib/posthog/server";
export async function getLayout() {
const posthog = getServerPostHog();
const showBeta = await posthog?.isFeatureEnabled("beta-features", userId);
return showBeta ? "beta" : "stable";
}
LLM Analytics
For AI-powered SaaS products, tracking LLM usage and costs is essential. PostHog's LLM analytics helps you monitor token usage, model performance, and spending across your AI features.
VelocityKit includes LLM cost tracking in the example AI feature, demonstrating how to:
- Track token usage per request
- Monitor costs by model and user
- Set usage limits and alerts
- Analyze AI feature adoption
Tracking LLM Events
When making AI requests, capture the relevant metrics:
import { getServerPostHog } from "@/lib/posthog/server";
export async function generateWithAI(prompt: string, userId: string) {
const startTime = Date.now();
const response = await openai.chat.completions.create({
model: "gpt-4o-mini",
messages: [{ role: "user", content: prompt }],
});
const posthog = getServerPostHog();
posthog?.capture({
distinctId: userId,
event: "ai_generation",
properties: {
model: "gpt-4o-mini",
prompt_tokens: response.usage?.prompt_tokens,
completion_tokens: response.usage?.completion_tokens,
total_tokens: response.usage?.total_tokens,
latency_ms: Date.now() - startTime,
// Calculate cost based on model pricing
estimated_cost: calculateCost(response.usage, "gpt-4o-mini"),
},
});
return response;
}
Building Cost Dashboards
In PostHog, create insights to visualize:
- Daily/monthly token usage — Trend of total tokens over time
- Cost by model — Breakdown of spending across different models
- Cost per user — Identify heavy users for pricing decisions
- Error rates — Track failed AI requests
This data helps you set appropriate pricing tiers and usage limits for your AI features.
Privacy Considerations
PostHog respects user privacy:
- Enable cookie consent before tracking (optional)
- Exclude internal users from analytics
- Session replay is opt-in
- IP anonymization available
Configure these in your PostHog project settings.
Development Mode
By default, PostHog is disabled in development to avoid polluting your data. To enable it:
NEXT_PUBLIC_POSTHOG_ENABLED_IN_DEV=true