Mallard Metrics
Self-hosted, privacy-focused web analytics powered by DuckDB and the behavioral extension.
Single binary. Single process. Zero external dependencies.
What is Mallard Metrics?
Mallard Metrics is a lightweight, GDPR/CCPA-compliant alternative to cloud analytics platforms. It runs entirely on your infrastructure, stores no personally identifiable information, and requires no cookies or consent banners.
Built in Rust for predictable, low resource usage. The embedded DuckDB database — combined with the behavioral extension — provides SQL-native behavioral analytics: funnels, retention cohorts, session analysis, sequence matching, and flow analysis. No third-party services involved.

Core Properties
| Property | Value |
|---|---|
| Language | Rust 1.98.0, edition 2024 |
| Web framework | Axum 0.8.x |
| Database | DuckDB 1.5.5 (disk-based, embedded, in-process; duckdb crate 1.10505.0) |
| Analytics | behavioral extension 0.9.1 (installed and loaded at runtime) |
| Storage | DuckDB hot table plus date-partitioned Parquet (ZSTD-compressed) |
| Frontend | Preact + HTM (no build step, embedded in binary) |
| Deployment | Static musl binary, FROM scratch Docker image |
| Tests | 602 passing (535 unit + 67 integration) |
Key Features
Privacy by Design
- No cookies — Visitor identification is an HMAC-SHA256 of
site_id + IP + User-Agentunder a rotating salt (daily by default). See Behavioral Analytics for what that costs analytically. - No PII storage — IP addresses are hashed and discarded; they are never written to disk.
- Rotating salt — Visitor IDs change every UTC day by default, preventing long-term tracking.
visitor_salt_rotation_dayslengthens the period where cross-day analysis matters more than the shorter pseudonym. - Privacy-preserving — Pseudonymous visitor IDs; no cookies; no raw IP storage. See Security & Privacy for details.
Single Binary Deployment
- One process handles ingestion, storage, querying, authentication, and the dashboard.
- DuckDB is embedded — no separate database to install or operate.
FROM scratchDocker image: the binary is the only file in the container.- WAL-based durability: disk-backed DuckDB preserves hot events through crashes.
Analytical Power
| Category | Capabilities |
|---|---|
| Core metrics | Unique visitors, pageviews, events, visits, bounce rate, visit duration |
| Breakdowns | Twenty dimensions — every column the ingest path populates |
| Segment filters | Narrow any report to browsers==Chrome;countries!=US |
| Time-series | Gap-filled hourly and daily aggregations |
| Realtime | Current visitors, top pages and sources, per-minute series |
| Goals and properties | Conversion rates per custom event, and their properties |
| Revenue | Totals per currency, event and page |
| Funnel analysis | Cumulative conversion funnels via window_funnel() |
| Retention cohorts | Per-visitor weekly cohorts via retention() |
| Session analytics | Duration, depth, bounce rate via sessionize() |
| Sequence matching | Behavioral patterns via sequence_match() |
| Flow analysis | Forward and backward navigation via sequence_next_node() |
| Export | Daily rollups or raw events, as CSV or JSON |
Production Ready
- Argon2id authentication — Password-protected dashboard with cryptographic session tokens, and a credential that survives a restart.
- API key management — Programmatic access with SHA-256 hashed keys (
mm_prefix), disk-persisted. - Rate limiting — Per-site token-bucket rate limiter on the ingestion endpoint.
- Query caching — TTL-based in-memory cache for analytics queries.
- Bot filtering — Automatic filtering of known bot User-Agents.
- GeoIP — MaxMind GeoLite2 integration with graceful fallback.
- Data retention — Configurable automatic cleanup of old Parquet partitions.
- Graceful shutdown — Buffered events are flushed before process exit.
- Prometheus metrics —
GET /metricsfor scraping with counters for ingestion, auth, cache, and rate limiting. - OWASP security headers — Including HSTS, CSP, Permissions-Policy, and X-Request-ID.
- CSRF protection — Origin/Referer validation on all state-mutating endpoints.
- Brute-force protection — Per-IP login lockout with configurable threshold and lockout duration.
- GDPR-friendly mode — Single
MALLARD_GDPR_MODE=truetoggle strips referrers, rounds timestamps, reduces GeoIP precision, and enables the Art. 17 data-erasure API.
When Should You Use Mallard Metrics?
Mallard Metrics is a good fit when you:
- Want full control over your analytics data on your own server.
- Need GDPR/CCPA compliance without third-party data processors.
- Are running a small-to-medium website and want low operational overhead.
- Need advanced behavioral analytics (funnels, retention, sequences) without a SaaS subscription.
- Want to demonstrate the power of DuckDB's
behavioralextension in a real-world production context.
It is not designed for:
- Multi-region distributed analytics at very high volume (millions of events/minute).
- Real-time dashboards with sub-second latency requirements.
- Replacing a full data warehouse.
Project Status
Mallard Metrics is actively developed and production-ready. See GitHub for the latest releases and issue tracker.
The behavioral extension powering advanced analytics is developed at github.com/tomtom215/duckdb-behavioral.