Skip to content

Case study

Self-hosted analytics with no cookies and no third-party services

maxa-analytics is the tool I wrote to track traffic on my own sites, maxadev.fr included. It stands here as a demonstration: the name is mine, the mechanics transfer.

The demonstration

From visitors to server logs, right through to questions asked in conversationNarrated, subtitled · 1 min 20 · demo data
Demo transcript

0:00 · The problem

Analytics behind a cookie banner, logs in a terminal… and outages, you hear about from your customers. This one brings it all together, on your server, with no cookies.

0:11 · All your sites

Every site on one dashboard: visitors, pages, sources, down to visits sent by AI assistants. And all it takes is a script under three kilobytes.

0:22 · Real time

Live, you see who's there, what they read, and what they put in the cart.

0:28 · Checkout funnel

The checkout funnel shows where customers drop off: here, at shipping.

0:33 · Server view

A small agent also reads the server logs: errors, bots, bandwidth. Everything the script can't see.

0:40 · Security

Bots hunting for a weak spot are unmasked, with a record for every IP address.

0:46 · Alerts and incidents

A burst of errors? The alert lands on your phone, and opens the incident record, evidence included.

0:53 · AI assistant

And your AI assistant connects to it: ask why sales dropped on Tuesday, and it cross-checks traffic and server errors.

1:06 · Self-hosted

It all fits in one container, on your server: your data stays with you. A tailored tool, to stay in control of your data. Let's talk about your project.

0

cookies set on your visitors’ devices

The starting problem

I had several sites to keep an eye on (maxadev.fr, maxa-movies, maxence-os) and three places to do it from. maxadev.fr’s analytics sat with Google, behind a cookie banner, and so missed every visitor who declined cookies. The server logs sat in a terminal. As for outages, I was liable to hear about them from someone else first.

Each of them saw only part of the story. When the site stops responding, the page does not load and the visit is not counted: the chart dips without saying why. And most bots, which do not run the tracking script, are missing from the analytics even as they fill up the logs. Cross-referencing the two by hand is the kind of chore that keeps getting put off.

What was built

A single tool, installed on my server. On each site, a script under 3 KB gzipped, or a Next.js, Nuxt or Node connector, Electron apps included. The dashboard shows pages, sources (down to visits referred by ChatGPT or Claude), clicks, user journeys, funnels and real-time activity. All of it with no cookies and no persistent identifier.

Alongside it, a small agent ships the logs from Nginx Proxy Manager, the reverse proxy that sits in front of the sites. From those logs, the dashboard picks up what the script misses: bots, errors, scanners hunting for a .env file or a WordPress install, with a dedicated page for each IP address. Alerts tuned with a slider land on my iPhone and open the incident page directly.

The technical choices, and why

Three structural decisions, made to keep the tool lightweight, respectful of your visitors, and on your own infrastructure.

One container, one SQLite database

The dashboard and data collection fit in a single container, with a SQLite database. No CDN, no tracking pixel: no third-party service sits between your visitors and your analytics, the data stays on your server, and you do not depend on a vendor to keep accessing it.

Cookieless by design

Nothing is stored in the browser. Visitors are counted using an identifier hashed with a salt that rotates daily and is destroyed after two days. The IP address is never written to page views or events: only the session keeps the one it started with, for diagnostics, 30 days by default, then erases it, and a setting lets you turn IP storage off entirely.

MCP server secured with OAuth 2.1

The MCP server is built into the tool: Claude, or any other MCP client, queries your sites’ analytics and your reverse proxy logs in conversation, with no export to run and no public API to expose. The video shows two of these conversations, recorded on the demo: "Why did Clairvenne’s sales drop on Tuesday afternoon?" and "Give me this week’s overview across all my sites".

What it changes in practice

When a chart dips, the site’s server view sets the proxy’s responses, errors included, against the page views: you can tell whether the audience is falling away or the site has stopped responding. And, if alerts are switched on, a run of server errors triggers a notification on my iPhone, with the evidence attached, before a visitor has to report the problem.

maxadev.fr uses this tool for its own analytics, with visitors’ consent. Optional ChatGPT ad measurement separately uses OpenAI and its cookies, with distinct consent. The MaxaDev figures in the video are fictional, like the rest of the demonstration.

The same mechanics, for your case

The name is mine, the mechanics are not. Keep in-house the data you would usually hand to a third party, cross-check it against the logs that already exist, get an alert when a threshold is crossed, and query it all in conversation: that works for website traffic and for plenty of other things.

What I deliver is the tool shaped for your case, the hosting, and the source code. If your analytics depend on a cookie banner, or you hear about your outages from your customers, that is probably where to start.

  • Cookieless analytics for your clients’ websites
  • Usage tracking for a web or desktop application
  • Server monitoring with mobile alerts
  • Business metrics queried in plain language

Frequently asked questions

  • No. It is the tool I use for my own sites, shown here to demonstrate what is achievable. What I deliver is a tool built for your use case, with its hosting and its source code.