Hanzo Analytics - Privacy-Focused Web Analytics
Hanzo Analytics is a privacy-focused web analytics platform -- an alternative to Google Analytics. Next.js 15 dashboard (port 3000) with Prisma ORM, PostgreSQL/ClickHouse storage, and a Go-based hi...
Overview
Hanzo Analytics is a privacy-focused web analytics platform -- an alternative to Google Analytics. Next.js 15 dashboard (port 3000) with Prisma ORM, PostgreSQL/ClickHouse storage, and a Go-based high-performance event collector. Includes anti-ad-blocker technology (encrypted tracker + WASM decryption). Live at analytics.hanzo.ai.
Why Hanzo Analytics?
- Privacy-first: No cookies required, GDPR/HIPAA compliant by design
- Anti-ad-blocker: Encrypted tracker script + WASM decryptor defeats blockers
- Dual database: PostgreSQL for metadata, optional ClickHouse for event scale
- Real-time: Live visitor tracking, real-time dashboards
- Multi-tenant: Teams, users, roles, shared dashboards
- Revenue tracking: Built-in e-commerce revenue attribution
- Link shortener + tracking pixels: URL shortening and pixel tracking built in
Tech Stack
- Dashboard: Next.js 15 + React 19 + Chart.js + react-intl (i18n)
- ORM: Prisma 6 with PostgreSQL adapter
- State: Zustand + TanStack React Query
- Collector: Go (Gin) + ClickHouse for high-throughput event ingestion
- Tracker: Rollup-bundled JS, encrypted delivery via WASM
- Validation: Zod
- Auth: JWT (jsonwebtoken) + bcryptjs password hashing
- Linting: Biome
- Testing: Jest + Cypress (e2e)
- Images:
ghcr.io/hanzoai/analytics:latest
OSS Base
Repo: hanzoai/analytics (Umami fork, v3.0.3).
When to use
- Tracking page views, events, and sessions across websites
- Privacy-compliant analytics (GDPR, HIPAA) without third-party cookies
- Real-time visitor dashboards and traffic reports
- E-commerce revenue attribution and funnel analysis
- URL shortening with click tracking
- Tracking pixel deployment
- Shared/public analytics dashboards (share links)
Hard requirements
- PostgreSQL (minimum v12.14) for metadata and event storage
- Node.js 18.18+ for the dashboard application
- Go 1.26+ for the collector service (optional, for ClickHouse pipeline)
- ClickHouse (optional) for high-volume event analytics
Quick reference
| Item | Value |
|---|---|
| UI | https://analytics.hanzo.ai |
| Demo | https://analytics.hanzo.ai/share/LGazGOecbDtaIwDr/hanzo.ai |
| Dev port | 3001 (Next.js dev) / 3000 (production) |
| Image | ghcr.io/hanzoai/analytics:latest |
| Package | @hanzo/analytics (v3.0.3) |
| Database | PostgreSQL (required), ClickHouse (optional) |
| ORM | Prisma 6 |
| Collector | Go + Gin + ClickHouse (collector/) |
| Health check | /api/heartbeat |
| Repo | github.com/hanzoai/analytics |
| License | MIT |
One-file quickstart
Docker Compose
# compose.yml
services:
analytics:
image: ghcr.io/hanzoai/analytics:latest
ports:
- "3000:3000"
environment:
DATABASE_URL: postgresql://analytics:analytics@db:5432/analytics
APP_SECRET: replace-me-with-a-random-string
depends_on:
db:
condition: service_healthy
restart: always
healthcheck:
test: ["CMD-SHELL", "curl http://localhost:3000/api/heartbeat"]
interval: 5s
timeout: 5s
retries: 5
db:
image: postgres:15-alpine
environment:
POSTGRES_DB: analytics
POSTGRES_USER: analytics
POSTGRES_PASSWORD: analytics
volumes:
- analytics-db-data:/var/lib/postgresql/data
restart: always
healthcheck:
test: ["CMD-SHELL", "pg_isready -U $${POSTGRES_USER} -d $${POSTGRES_DB}"]
interval: 5s
timeout: 5s
retries: 5
volumes:
analytics-db-data:From source
git clone https://github.com/hanzoai/analytics.git
cd analytics
cp .env.example .env # Set DATABASE_URL
pnpm install
pnpm build # Creates tables on first run, default: admin/analytics
pnpm start # http://localhost:3000Add tracking to a website
<script defer src="https://analytics.hanzo.ai/script.js"
data-website-id="YOUR-WEBSITE-ID"></script>Core Concepts
Architecture
┌──────────────────────┐
│ analytics.hanzo.ai │
│ (Next.js 15) │
│ │
│ ┌────────────────┐ │
Browser ─────────▶│ │ /api/send │ │──── PostgreSQL
(tracker.js) │ │ /api/batch │ │ (sessions, events,
│ │ /api/realtime │ │ users, teams, etc.)
│ │ /api/websites │ │
│ │ /api/reports │ │
│ │ /api/auth │ │
│ └────────────────┘ │
└──────────────────────┘
┌──────────────────────┐
│ collector (Go) │
High-volume ─────▶│ Gin HTTP server │──── ClickHouse
events │ event.go │ (event_data,
│ forward/ │ session_data)
│ writer/ │
└──────────────────────┘Data Models (Prisma)
- User: Admin users with bcrypt-hashed passwords, roles
- Website: Tracked sites with optional share links
- Session: Browser/OS/device/geo per visitor
- WebsiteEvent: Page views, custom events with UTM params, click IDs
- EventData / SessionData: Key-value custom properties
- Team / TeamUser: Multi-tenant team management
- Report / Segment: Saved analytics queries
- Revenue: E-commerce revenue tracking per event
- Link: URL shortener with slug-based routing
- Pixel: Tracking pixel management
Anti-Ad-Blocker Pipeline
- Tracker JS encrypted into
tracker.bin(binary blob) decrypt.wasm(WebAssembly) decrypts in-browser memory- Lightweight loader fetches both, decrypts, executes
- API calls use obfuscated function names (not
track()) - Payloads encrypted before transmission
API Routes
| Route | Purpose |
|---|---|
/api/send | Receive tracking events |
/api/batch | Batch event ingestion |
/api/realtime | Real-time visitor data |
/api/websites | Website CRUD |
/api/reports | Report CRUD |
/api/teams | Team management |
/api/users | User management |
/api/auth | Authentication |
/api/links | URL shortener |
/api/pixels | Tracking pixels |
/api/share | Public dashboard sharing |
/api/heartbeat | Health check |
Environment Variables
DATABASE_URL=postgresql://user:pass@localhost:5432/analytics # Required
APP_SECRET=random-secret-string # Required
CLICKHOUSE_URL=http://localhost:8123 # OptionalTroubleshooting
| Issue | Cause | Solution |
|---|---|---|
| Build fails on first run | Missing DATABASE_URL | Set DATABASE_URL in .env before pnpm build |
| Default login not working | Changed by script | Default is admin / analytics, use npm run change-password |
| Ad blocker blocks events | Tracker detected | Use encrypted tracker pipeline (enabled by default) |
| High event volume slow | PostgreSQL bottleneck | Deploy Go collector with ClickHouse backend |
| Geo data missing | No GeoIP database | Run pnpm build-geo to download MaxMind DB |
| Docker health check fails | Port not ready | Increase retries or wait for DB initialization |
Related Skills
hanzo/hanzo-platform.md- PaaS for deploying analyticshanzo/hanzo-cloud.md- Cloud dashboardhanzo/hanzo-database.md- PostgreSQL infrastructurehanzo/hanzo-kms.md- Secret management for APP_SECRET
How is this guide?
Last updated on
ZenLM - Next-Generation Local AI Models
ZenLM is a collaboration between Hanzo AI and Zoo Labs Foundation, building AI models that run entirely on your device—no cloud, no subscriptions, no surveillance.
Hanzo Database - PostgreSQL, Redis & Vector Storage
Hanzo Database covers PostgreSQL (with pgvector), Redis, MongoDB, and MinIO configurations used across the Hanzo ecosystem.