Architecture
The write path and the read path are separate services over shared crates. Ingest is fire-and-forget, authenticated by the environment's public key, so the environment an event belongs to cannot be spoofed by a client. The dashboard API uses JWT and resolves permissions down the org → project → app tree.
What it does
Error tracking
- › Fingerprinting and grouping into issues
- › Stack traces, breadcrumbs, tags and context
- › Source-map symbolication
- › Release tracking and crash-free rate
Product analytics
- › Event explorer with payload search
- › Funnels with saved, shareable templates
- › User journeys as Sankey diagrams
- › Retention cohorts and DAU / WAU / MAU
People, sessions and devices
- › One timeline per person: errors and events together
- › Guest → identified identity merge
- › Session timelines and duration stats
- › Device groups across environments
Screens and performance
- › Per-screen views, users and dwell time
- › Transactions with p50 / p95 latency
- › Drill-down by operation with deep links
- › Opt-in auto screen tracking for web and Flutter
Alerting and uptime
- › Error spike, threshold and latency rules
- › HTTP uptime probes with SSRF guards
- › Email, Slack, Discord, Telegram and webhooks
- › Per-user subscriptions with digest batching
Access control
- › Org → project → app scope tree
- › Fine-grained RBAC with custom roles
- › Privilege-escalation guards on every grant
- › Audit log of administrative actions
Privacy
- › Scans telemetry for developer-supplied PII
- › Reports findings without keeping a second copy
- › Retro-masks hot data after a typed confirmation
- › Enforces the mask on all future ingest
Data lifecycle
- › Range-partitioned event tables
- › Aged partitions moved to compressed Parquet
- › Transparent queries across both tiers
- › Retention policies and admin purge
Search
- › Query language over tags and JSON payloads
- › Saved views per list page
- › Filter chips on list pages
- › Custom date ranges with server-side limits
SDKs
Every SDK is written in its language's own idiom, sends the same wire format, and supports scope, breadcrumbs, transactions, before-send hooks, gzip, retry with backoff, and a bounded queue that can spill to disk.
Shipping it
- Docker Compose for evaluation
- Native RPM (Fedora / RHEL) and .deb (Debian / Ubuntu) packages driven by systemd
- Migrations run before every service start; a daemon refuses to boot on a failed migration
- OpenAPI / Swagger docs, with a parity test against the router
- CycloneDX SBOMs tracked in Dependency-Track
- GitHub Actions CI and tagged releases