measuremy_site
# measuremysite-mcp
**Cookieless web analytics your AI agent can read.** A small analytics server for one website, with an [MCP](https://modelcontextprotocol.io) server built in, so Claude Code, Cursor or Codex can look at your traffic and help you decide what to do next.
You deploy it to your own Cloudflare account (Workers + D1, the free tier is enough for most small sites). Your data stays in your account.
This repo used to be called `agentlytics-mcp`. The worker, database, tracker (`agentlytics.track`) and MCP server keep that name so existing installs keep working.

<sub>Example questions and answers; the numbers are illustrative.</sub>
## Hosted MCP server: `https://a.measuremy.site/mcp`
Don't want to run it yourself? **[measuremy.site](https://measuremy.site/?utm_source=github&utm_medium=referral&utm_campaign=measuremysite-mcp)** is the hosted version (`site.measuremy/analytics` in the MCP registry): the same MCP tools, plus a dashboard, AI explanations of traffic spikes, tracking of posts that mention you (Hacker News, Bluesky, YouTube...), alerts and weekly summaries. Streamable HTTP with OAuth: you sign in through the browser the first time, and no API key is pasted anywhere. 30-day free trial, no card; plans from $9 a month.
**VS Code (Copilot)**: in `.vscode/mcp.json`, or **MCP: Add Server** → HTTP. VS Code asks you to sign in when the server starts.
```json
{
"servers": {
"measuremysite": { "type": "http", "url": "https://a.measuremy.site/mcp" }
}
}
```
**Claude Code**
```sh
claude mcp add --scope user --transport http measuremysite https://a.measuremy.site/mcp
```
**Cursor** (`~/.cursor/mcp.json`)
```json
{ "mcpServers": { "measuremysite": { "url": "https://a.measuremy.site/mcp" } } }
```
On sign-in you create an account (or log in) and enter your site's domain. Then ask your agent to "add measuremy.site analytics to this project": the server hands it the script tag for your site. Docs: [measuremy.site/docs/mcp](https://measuremy.site/docs/mcp).
The rest of this README covers the self-hosted version.
## What your agent can do
Ask in plain words, for example:
- "Why did traffic jump yesterday?" It finds the spike and the source, page or event behind it.
- "Where do people drop off between the homepage and signup?" It builds a funnel and shows the biggest drop.
- "What's working, and what should I post next?" It ranks channels by conversions and turns that into steps.
- "Make a tracked link for my Reddit post, and check how it did next week."
Tools exposed over MCP:
| Area | Tools |
|---|---|
| Traffic | `get_overview`, `get_timeseries`, `top_sources`, `top_pages`, `top_countries`, `top_browsers`, `top_systems`, `list_events` |
| Questions about visits | `query_visits` (filter and group by country, browser, OS, source, page, event, day), `recent_visits` |
| Spikes | `find_traffic_spikes`, `explain_spike` (ranked causes, plus your annotations) |
| Funnels | `create_funnel`, `get_funnel`, `delete_funnel` |
| Growth | `get_whats_working`, `get_growth_actions` |
| Campaigns | `create_tracked_link`, `get_campaign_results`, `add_annotation` |
Plus a `plan_marketing` prompt that walks the agent through a data-backed plan.
## Privacy
- No cookies and nothing stored in the visitor's browser.
- No IP address or user agent is stored. A visitor id is a hash that changes every day, so nobody can be followed from one day to the next.
- Only browser and OS names (like "Firefox", "macOS") and the country Cloudflare reports are kept.
- Raw events are deleted after 400 days; hourly totals are kept.
Check what applies where you and your visitors are; this is not legal advice.
## Deploy
### One click
[](https://deploy.workers.cloudflare.com/?url=https://github.com/developeron29/measuremysite-mcp)
The button copies this repo to your GitHub account, creates the D1 database, runs the migrations and deploys the worker. It asks for three settings:
- `SITE_DOMAIN`: your website's domain, like `example.com` (no `https://` or `www`)
- `HASH_SECRET`: any long random string, used to make the daily visitor id
- `MCP_READ_KEY`: another long random string, the key your AI agent uses
Generate the two random values with `openssl rand -hex 32`, and keep `MCP_READ_KEY` for connecting your agent below.
### By hand
You need a Cloudflare account and Node.js 20+.
```sh
git clone https://github.com/developeron29/measuremysite-mcp.git
cd measuremysite-mcp
npm install
npx wrangler login
```
1. **Create the database** and paste the printed `database_id` into `wrangler.jsonc`:
```sh
npx wrangler d1 create agentlytics-mcp
```
2. **Set the three settings.** Use long random values for the two keys, for example from `openssl rand -hex 32`:
```sh
npx wrangler secret put SITE_DOMAIN # e.g. example.com
npx wrangler secret put HASH_SECRET # makes the daily visitor id; never share it
npx wrangler secret put MCP_READ_KEY # the key your agent uses; keep it out of your repo
```
Wrangler may offer to create the worker on the first `secret put`; say yes.
3. **Deploy** (this also creates the tables):
```sh
npm run deploy
```
Either way you get a worker URL like `https://agentlytics-mcp.<you>.workers.dev`. Opening it shows a status page with your domain. You can attach a custom domain such as `stats.yourdomain.com` in the Cloudflare dashboard.
**Optional rate limit:** to cap how often one IP can send hits, add this to `wrangler.jsonc` and deploy again:
```jsonc
"ratelimits": [{ "name": "COLLECT_LIMITER", "namespace_id": "1001", "simple": { "limit": 120, "period": 60 } }]
```
## Add the tracker to your site
Put this in the `<head>` of every page:
```html
<script defer src="https://YOUR-WORKER-URL/t.js"></script>
```
It counts pageviews, including client-side navigation in single-page apps. To count something that matters, like a signup:
```js
agentlytics.track("signup", { plan: "pro" });
```
or without JavaScript, on any element:
```html
<button data-agentlytics-event="cta_click">Start free</button>
```
Only pages on `SITE_DOMAIN` (and its subdomains) are counted.
## Connect your agent
**Claude Code**
```sh
claude mcp add --scope user --transport http agentlytics https://YOUR-WORKER-URL/mcp --header "Authorization: Bearer YOUR_MCP_READ_KEY"
```
**Cursor** (`.cursor/mcp.json` or `~/.cursor/mcp.json`)
```json
{
"mcpServers": {
"agentlytics": {
"url": "https://YOUR-WORKER-URL/mcp",
"headers": { "Authorization": "Bearer YOUR_MCP_READ_KEY" }
}
}
}
```
**Codex** (`~/.codex/config.toml`)
```toml
[mcp_servers.agentlytics]
url = "https://YOUR-WORKER-URL/mcp"
bearer_token_env_var = "AGENTLYTICS_READ_KEY"
```
and `export AGENTLYTICS_READ_KEY=YOUR_MCP_READ_KEY` in the shell that starts Codex.
Then ask: *"Use agentlytics to tell me how my site did this week."* Spikes need a few days of traffic to compare against.
### Let your agent do the setup
Point your coding agent at [`AGENTS.md`](AGENTS.md): "Deploy measuremysite-mcp for my site by following AGENTS.md". It walks through every step and asks you before anything that needs your Cloudflare login.
## Self-hosted or hosted?
| | measuremysite-mcp (this repo) | [measuremy.site](https://measuremy.site/pricing?utm_source=github&utm_medium=referral&utm_campaign=measuremysite-mcp) |
|---|---|---|
| MCP tools for your agent | Yes | Yes |
| Cookieless tracking, funnels, spikes, campaigns | Yes | Yes |
| Sites | One per deploy | Several, one account |
| Dashboard | No (ask your agent) | Yes, with filters and a public share link |
| AI explanations of spikes | No | Yes |
| Posts that mention you (HN, Lobsters, Bluesky, YouTube, Reddit) | No | Yes, on your traffic chart |
| Alerts, weekly email summary | No | Yes |
| Who runs it | You, on your Cloudflare account | Us |
| Price | Free (your Cloudflare usage) | 30-day free trial, then from $9 a month |
## Develop
```sh
cp .dev.vars.example .dev.vars # then edit the values
npm run db:migrate:local
npx wrangler dev
npm test
npm run typecheck
```
`scripts/stdio.sh` runs the server locally and serves MCP over stdio, for clients that start a server as a command (Glama uses it). It needs `SITE_DOMAIN`, `HASH_SECRET` and `MCP_READ_KEY` in the environment.
## License
MIT. See [LICENSE](LICENSE).
TDQS
Scored across 20 tools
Most tools have clearly distinct purposes: the top_* family splits cleanly by dimension, and query_visits (aggregates) vs recent_visits (individual rows) are well separated. The only mildly fuzzy boundary is between get_whats_working and get_growth_actions, which both deal with marketing evidence/planning, though one analyzes and the other prescribes actions.
Names use consistent snake_case and mostly follow verb_noun or prefix_noun patterns (get_overview, create_funnel, top_pages, delete_funnel). Minor deviations like recent_visits, find_traffic_spikes, and explain_spike break the strict pattern but remain readable and predictable.
20 tools is on the heavy side but each covers a distinct analytics surface (traffic, sources, geo, tech, funnels, campaigns, spikes, annotations), so the set feels justified rather than padded. It sits at the upper edge of the ideal 3-15 range but is reasonable for a full-featured web analytics platform.
Coverage is broad: overview, timeseries, dimensional breakdowns, custom queries, raw recent visits, funnel create/get/delete, spike detection and explanation, annotations, tracked links, and campaign results. Minor gaps exist (no funnel update, limited event management), but core analytics and lifecycle workflows are covered with no obvious dead ends.