Error Tracking
Temps includes Sentry-compatible error tracking built-in — point your existing @sentry/react, @sentry/nextjs, or any other Sentry SDK at your Temps DSN and errors appear in your dashboard with zero code changes. No Sentry account, no monthly bill, no data leaving your infrastructure.
How it works
Temps implements the Sentry envelope ingestion protocol at /api/<project_id>/envelope/, so any Sentry SDK works without modification. Error grouping uses a built-in vector similarity engine — no OpenAI API call is made; embeddings are computed locally using a hash tokenizer into a 384-dimension vector, then stored in pgvector for cosine-similarity lookup. The platform captures the full Sentry feature set — envelope protocol (v7+), stack trace fingerprinting, source map parsing, user and request context, breadcrumbs, session correlation, and W3C trace ID correlation with spans and proxy logs — all running on your own infrastructure with no third-party services, no per-event pricing, and full integration with Temps analytics and session replay.
| Temps | Sentry Cloud | Self-hosted Sentry | |
|---|---|---|---|
| Protocol | Sentry envelope (v7+) | Sentry envelope (v7+) | Sentry envelope (v7+) |
| SDK compatibility | All official Sentry SDKs | All official Sentry SDKs | All official Sentry SDKs |
| Error grouping | Stack trace + local vector similarity | Stack trace + ML clustering | Stack trace + ML clustering |
| Source maps | Built-in upload + parsing | Built-in | Built-in |
| Session replay | Built-in (same platform) | Add-on (paid plan) | Separate setup required |
| Analytics integration | Built-in | Separate product | Separate product |
| Uptime monitoring | Built-in | Separate product | Separate product |
| Pricing | Free (self-hosted) / ~$6/mo (Cloud) | $0–$80+/mo by event volume | Self-hosted infra cost |
| Data location | Your server | Sentry cloud | Your server |
Sentry compatibility
Temps implements the complete Sentry envelope protocol, allowing you to use official Sentry SDKs without modification.
Supported Features
- Name
Envelope Ingestion- Description
Full Sentry envelope protocol support (v7+)
- Name
Error Events- Description
Exception tracking with stack traces
- Name
Transaction Events- Description
Performance monitoring integration
- Name
Breadcrumbs- Description
Event trail leading up to errors
- Name
User Context- Description
User identification and metadata
- Name
Tags & Metadata- Description
Custom tagging and context
- Name
Releases- Description
Track errors by release version
Compatibility Matrix
Fully Supported SDKs
- @sentry/browser (JavaScript)
- @sentry/react (React)
- @sentry/nextjs (Next.js)
- @sentry/node (Node.js)
- @sentry/python (Python)
- @sentry/go (Go)
- @sentry/php (PHP)
- @sentry/ruby (Ruby)
- @sentry/java (Java)
- @sentry/dotnet (.NET)
Supported Platforms
- Web browsers
- Node.js servers
- React Native
- Electron
- Mobile apps (iOS, Android)
- Desktop apps
- Serverless functions
- Docker containers
Setup and integration
Get started with error tracking in minutes using your existing Sentry SDK.
Step 1: Get Your DSN
Get your project DSN
- 1
Open your project's error tracking setup page at https://<temps_app>/projects/<project_slug>/errors?tab=setup.
- 2
Copy your project's unique DSN from the setup page (the public key is a 64-character hex string unique to your project).
Checkpoint: Confirm the DSN matches the format https://<public_key>@<temps_app>/<project_id> before pasting it into your SDK config.
- 3
Paste the DSN into your Sentry SDK init (for example as NEXT_PUBLIC_SENTRY_DSN) and trigger a test error with Sentry.captureException(new Error('Test error from Temps')).
- 4
Reload the Error Tracking page in the dashboard to confirm the test event arrived.
Checkpoint: The new error group appears in the project's error list, confirming the SDK is sending events.
Each project gets a unique DSN (Data Source Name) for error reporting. The DSN format is:
https://<public_key>@<temps_app>/<project_id>
Example DSN format:
https://742ee692155dd1cb2cecd94838bb425d4b5a1184e5b57c0815e9d808a6f8d70d@your-temps-instance.com/1
Step 2: Install Sentry SDK
Install the official Sentry SDK for your platform:
npm install @sentry/react
Step 3: Configure SDK
Point the Sentry SDK to your Temps instance:
Configure Sentry SDK
Step 4: Test Error Tracking
Trigger a test error to verify setup:
Test Error Tracking
// Throw test error
Sentry.captureException(new Error('Test error from Temps'));
// Capture message
Sentry.captureMessage('Test message', 'info');
// Add breadcrumb
Sentry.addBreadcrumb({
message: 'User clicked button',
level: 'info',
data: { button: 'signup' }
});
Error grouping
Temps automatically groups similar errors together using stack trace fingerprinting and local vector similarity clustering.
Grouping Strategies
- Name
Stack Trace Fingerprinting- Description
Groups errors with identical stack traces (default)
- Name
Exception Type- Description
Groups by exception class/type (TypeError, ReferenceError, etc.)
- Name
Error Message- Description
Groups by error message pattern (parameterized)
- Name
Vector Similarity- Description
Uses a built-in hash tokenizer + pgvector cosine similarity to find semantically similar errors — computed locally, no external API required
- Name
Custom Fingerprinting- Description
Define custom grouping rules via fingerprint tags
Custom Fingerprinting
Override default grouping with custom fingerprints:
Custom Fingerprinting
Sentry.captureException(error, {
fingerprint: ['database-error', 'connection-timeout'],
});
// Dynamic fingerprint
Sentry.captureException(error, {
fingerprint: ['api-error', error.response?.status],
});
Update Group Status
Merge and split operations are available in the dashboard via the Error Details page Actions menu. Use the CLI to update group status:
# Resolve a group
bunx @temps-sdk/cli errors update --group-id <group-id> --project-id <project-id> --status resolved
# Ignore a group
bunx @temps-sdk/cli errors update --group-id <group-id> --project-id <project-id> --status ignored
Error details
Each error event captures comprehensive context for debugging.
Error Anatomy
- Name
Exception Info- Description
Type, message, stack trace with line numbers
- Name
Request Context- Description
URL, method, headers, query params, request body
- Name
User Context- Description
User ID, email, IP address, custom properties
- Name
Environment- Description
Browser/runtime version, OS, device type
- Name
Tags- Description
Custom tags (environment, version, feature flags)
- Name
Breadcrumbs- Description
Event trail leading to error (clicks, API calls, console logs)
- Name
Additional Data- Description
Custom metadata, local variables, state snapshots
Enrich Error Context
Add custom context to errors:
Add Context
Sentry.setUser({
id: 'user-123',
email: '[email protected]',
username: 'johndoe',
subscription: 'pro'
});
Trace Correlation
Temps stores a W3C Trace Context trace ID alongside errors so the unified Observe page can link an exception to the request, spans, and other events that share the same trace. This is what powers the cross-source jumps in the /projects/<slug>/observe timeline.
Schema
The m20260502_000001_add_observe_correlation migration (shipped in temps 0.1.0) adds the correlation columns and lookup indexes. Every column is nullable, so existing rows are unaffected, and the migration is written to be safely re-runnable — each step uses IF NOT EXISTS.
| Table | Column | Type | Purpose |
|---|---|---|---|
proxy_logs | trace_id | text (nullable) | W3C trace ID for the request |
proxy_logs | error_group_id | integer (nullable) | Links a request to the error group it produced |
error_events | trace_id_indexed | text (nullable) | Trace ID promoted from the event payload, indexed for joins |
revenue_events | deployment_id | integer (nullable) | Correlate revenue with a deployment |
revenue_events | environment_id | integer (nullable) | Correlate revenue with an environment |
revenue_events | trace_id | text (nullable) | W3C trace ID for the revenue event |
Supporting indexes added by the same migration:
| Index | Definition |
|---|---|
idx_proxy_logs_project_trace | proxy_logs (project_id, trace_id) |
idx_proxy_logs_error_group | proxy_logs (error_group_id) WHERE error_group_id IS NOT NULL |
idx_error_events_project_trace | error_events (project_id, trace_id_indexed) |
idx_revenue_events_project_occurred | revenue_events (project_id, occurred_at DESC) |
How the trace ID is extracted
For error events, temps-error-tracking ingestion probes the event payload for a trace ID and promotes the first valid value to error_events.trace_id_indexed. It checks, in order: data.sentry.contexts.trace.trace_id, top-level data.contexts.trace.trace_id, and data.trace.trace_id. A value is accepted only if it is exactly 32 ASCII-hex characters and is not the all-zero trace ID the W3C spec reserves as invalid.
The temps-proxy reverse proxy includes a helper, extract_traceparent_trace_id, that reads the inbound traceparent request header (matched case-insensitively against traceparent, Traceparent, and TRACEPARENT), splits on -, and takes the trace-id field. It applies the same validation: the value must be 32 ASCII-hex characters, must not be all zeros, and is lowercased before use. Six unit tests cover the valid case, a missing header, the all-zero value, the wrong length, non-hex characters, and uppercase folding.
To send a trace ID through to Temps, set a standard traceparent header on the request:
traceparent: 00-4bf92f3577b34da6a3ce929d0e0e4736-00f067aa0ba902b7-01
│ └─ trace-id (32 hex) ────────────┘ └─ span-id ──┘ └ flags
└─ version
Proxy proxy_logs.trace_id population is not yet wired. The extract_traceparent_trace_id helper exists and is validated, but the live proxy logging path writes request rows through a batched multi-row INSERT whose column list does not yet include trace_id, so the extracted value is currently dropped before the proxy_logs write. The schema column and indexes are in place, and error events are already correlated via error_events.trace_id_indexed, but do not rely on the proxy populating proxy_logs.trace_id for live requests yet.
Error resolution
Manage error lifecycle from discovery to resolution.
Error States
- Name
Unresolved- Description
New or ongoing errors (default state)
- Name
Resolved- Description
Marked as fixed (manually or automatically)
- Name
Ignored- Description
Known errors that should be suppressed
- Name
Regressed- Description
Error recurred after being resolved
Mark as Resolved
Mark an error group as resolved
- 1
Open the Error Details page for the error group you fixed.
- 2
Open the Actions menu and choose Resolve.
- 3
Pick a resolution option: mark as resolved now, resolve in the next release, resolve in a specific release, or set auto-resolve after X days with no new events. (Release-scoped and auto-resolve options are dashboard-only; the CLI always performs an immediate resolve.)
- 4
Confirm the resolution.
Checkpoint: The error group's status changes to Resolved; if it recurs later it will reappear as Regressed.
Resolve Errors
# Resolve error group
bunx @temps-sdk/cli errors update --group-id <group-id> --project-id <project-id> --status resolved
# Resolve multiple groups (run per group)
bunx @temps-sdk/cli errors update --group-id error-123 --project-id <project-id> --status resolved
bunx @temps-sdk/cli errors update --group-id error-456 --project-id <project-id> --status resolved
Ignore Errors
Ignore a known error group
- 1
Open the Error Details page for the error group you want to suppress.
- 2
Open the Actions menu and choose Ignore.
- 3
Confirm to suppress the group (configure pattern-based ignore rules in the web UI for recurring noise).
Checkpoint: The error group's status changes to Ignored and it no longer surfaces in the default unresolved list.
Suppress known errors you don't want to track: