Self-host Plausible Analytics in an Afternoon
Self-hosting Plausible Analytics in an Afternoon: Own Your Data, Ditch the Vendor Lock-in
You're tired of Google Analytics bloat. You want privacy-first analytics without the cookie banners. You need data sovereignty without the SaaS pricing treadmill. Here's how we built our own analytics infrastructure in one afternoon — and why you should too.
Why Self-host Analytics? Four Wins You Can't Buy
Data ownership matters. Your analytics live on your box, not a vendor's. No third-party data sharing, no surprise policy changes, no vendor deciding your data is suddenly worth more.
Privacy by design. Plausible Community Edition is cookieless and GDPR-friendly. No consent banners required. Your visitors get a 1KB script instead of Google's heavyweight tag.
Cost control. No per-pageview SaaS pricing as your traffic grows. One instance handles every property you run — we track four sites from a single deployment.
One dashboard, all properties. Manage analytics for eleven11.pro, blog.eleven11.pro, and audit.eleven11.pro from one interface. Add new sites without new subscriptions.
What We Built: The Stack
We deployed Plausible Community Edition v3.2.1 on a single Hetzner server running Docker Compose. The architecture is straightforward:
- App layer: Plausible (Elixir/Phoenix) serves the dashboard and tracking script
- Data layer: Postgres 16-alpine stores user accounts and site configs; ClickHouse 24.12-alpine handles event analytics
- Edge layer: Caddy reverse proxy with automatic Let's Encrypt; Cloudflare for DNS and DDoS protection
The result: analytics.eleven11.pro tracking our entire web presence from one self-managed instance.
The Implementation: Docker Compose + Caddy
Network Setup First
Put your Plausible containers on the same Docker network as your reverse proxy. We use a shared e11-edge network so Caddy can resolve the app container by name:
networks:
e11-edge:
external: true
Caddy Configuration: One Line
Your reverse proxy config is dead simple. In Caddy:
analytics.eleven11.pro {
reverse_proxy plausible:8000
}
Caddy handles TLS automatically. The container name plausible resolves because both containers join the same Docker network.
Environment Variables That Matter
Two secrets control your deployment:
SECRET_KEY_BASE: Signs user sessions (generate withopenssl rand -base64 64)TOTP_VAULT_KEY: Encrypts 2FA secrets (generate withopenssl rand -base64 32)
Both are service-managed. Rotating them logs everyone out and breaks existing 2FA setups.
For registration, set DISABLE_REGISTRATION=invite_only. The first owner account can self-register, then public signup locks down. Set ENABLE_EMAIL_VERIFICATION=false so you can log in without configuring SMTP first.
The Gotchas: What Breaks and How to Fix It
SELinux Will Block Database Writes
On SELinux-enforcing hosts, containers with named volumes need label handling or database writes fail as read-only. Add this to your database containers:
security_opt:
- label:disable
DNS and TLS Timing
Grey-cloud your DNS record (DNS-only mode) until the Let's Encrypt cert issues. Once the cert is live, flip to orange-cloud. If you go orange first, the ACME challenge fails behind Cloudflare's proxy. After the cert is issued, switch to Full (strict) SSL mode for end-to-end encryption.
Container Resolution
Your reverse proxy must resolve the app container by name. If Caddy can't reach plausible:8000, verify both containers joined the same Docker network.
Tracking Setup: Cookieless and Clean
Plausible uses a first-party script model. Each site gets a data-domain attribute pointing to your analytics instance:
<script defer data-domain="eleven11.pro" src="https://analytics.eleven11.pro/js/script.js"></script>
One instance serves different tracking configs per domain. No cookies, no consent banners, no privacy theater. The script is ~1KB versus Google Analytics' heavier tag.
The Time Investment: Half-Day Project
Wall-clock time breaks down like this:
- DNS setup: 5 minutes (plus propagation wait)
- Docker image pulls: 15–30 minutes depending on connection
- Configuration: 30 minutes
- TLS certificate issuance: 5 minutes
- Testing and validation: 15 minutes
If you already run Docker and a reverse proxy, this is a half-day project, not a platform migration. Most of the time is waiting for DNS and image downloads.
Why This Matters for Engineering Leaders
Sovereignty beats convenience. You control the data, the uptime, and the feature roadmap. No vendor can sunset your analytics or change pricing overnight.
Privacy as a competitive advantage. Your visitors get faster page loads and better privacy. No third-party tracking, no data brokers, no surveillance capitalism.
Cost predictability. Your analytics cost is your server cost. Traffic growth doesn't trigger billing surprises or force plan upgrades.
Technical simplicity. Three containers, one network, standard Docker patterns. Your team can debug, backup, and maintain this without vendor-specific expertise.
The Bottom Line
For founders and engineering leaders who already self-host infrastructure: owning your analytics is a low-cost, high-sovereignty win you can ship this week.
We built analytics.eleven11.pro in one afternoon. It tracks four properties, serves cookieless analytics to thousands of visitors, and costs us exactly one server's worth of resources. No subscriptions, no per-seat pricing, no vendor lock-in.
Your data belongs on your infrastructure. Plausible Community Edition makes that practical without sacrificing functionality or user experience.