Docs.

Quickstart

Three steps. Five minutes if your hosting is fast.

1

Add the connector

In Claude, add a custom MCP connector with URL mcp-analytics.com/mcp. Claude opens a browser tab to authorize.

2

Confirm via email

Enter your email on that tab. We send a verify link, click it, consent, you're connected. One time per client.

3

Ask anything

"Add mcp-analytics to my site." Your agent installs the tracking snippet, deploys, and you're live.

What is MCP?

MCP (Model Context Protocol) is the open spec Anthropic introduced for letting AI assistants talk to external services. Think USB for LLMs: one cable, every tool. Claude, Cursor, ChatGPT, and Windsurf all speak it.

mcp-analytics is an MCP server. We expose your web analytics as tools that your AI assistant can call. Instead of opening a dashboard, you ask a question in chat and the assistant fetches the answer over JSON-RPC. No UI between you and your data. No tab to keep open. No "Configure" menu to hunt through.

Installation

The signup itself is the hardest part, and it's still pretty easy. Once the connector is authorized in your client, you stop doing things and your agent takes over.

Tell Claude (or whoever): "Add mcp-analytics to this project." That single sentence is the whole install. Claude will:

  • Call add_site with your domain to get a site_id
  • Call get_tracking_snippet to get the exact <script> tag
  • Find the right place in your codebase (layout file, base template, root component)
  • Drop the snippet in, commit it, push it

Total work for you: typing one sentence and clicking "approve" on the diff. After deploy, the first pageview lands in our database within seconds.

For every new project after that: same one-liner. "Add mcp-analytics." No new account, no new URL, no new dashboard. Claude already has your connector, knows the snippet, knows your repo conventions. Three minutes for Claude. Zero minutes for you. Custom events take another "track signups, purchases, and video plays as events" sentence.

Privacy modes

Pick a privacy posture per site. Cannot be changed after creation, historical data integrity matters.

strict (recommended) balanced all
Cookies none 1st-party persistent
visitor_id daily-rotating hash
(IP + UA + site salt)
persistent UUID
Session salt fixed per site fixed per site
Same-day visitor dedup yes yes
Cross-day visitor tracking no yes
LTV / cohort analysis no yes
Referrer path stored yes yes
DNT respected yes no (opt-in)
Cookie banner needed no yes (your call)

Strict is the right call for almost every public-facing site: aggregate answers, no banner, sleep at night. You lose "how many unique people came today" as a number, but session counts plus the rich client signals (timezone, viewport, engagement) usually answer the same question better.

Balanced trades a tiny bit of identifiability (a daily-rotating hash of IP + UA, gone at midnight) for proper same-day visitor counts and full referrer paths. Still no cookies, still no banner, still wipes itself daily. Pick this if you genuinely need "X unique visitors today" as a metric.

All is for when you've already decided your business needs cross-session attribution, LTV cohorts, repeat-visit analysis. Persistent cookies, consent banner becomes your responsibility. Typical for SaaS dashboards behind a login.

Asking questions

Once installed, you ask Claude (or your client of choice) anything you'd normally hunt through a dashboard for. Plain English. No tool names. No SQL. No Configure menus.

You

How did yesterday go?

Claude

On your-site.com yesterday: 412 pageviews from 287 sessions, bounce rate 64%, top page /pricing (89 views), top source news.ycombinator.com. Up 23% versus the day before. 4 signup events. Plus 8% AI-mediated reads (Claude-User, ChatGPT-User fetching pages on user questions) and 12% bot crawls (mostly GPTBot training, AhrefsBot scanning).

You

What should I do about the bounce rate?

Claude

Looking at engagement_overview: median time on /pricing is 8s, median scroll depth 22%. People are bouncing before seeing the price grid. The grid sits below a 600px hero. Want me to move the grid above the fold and ship it?

You

Do it.

That last bit is the actual unlock. Claude doesn't just read your analytics. Once it knows what's wrong, it can edit your code, run your tests, commit, push. Analytics-to-ship loop on autopilot. You stay in chat. You approve or reject. The diff lands. The next pageview tells you if it worked.

You don't have to use it that way. Asking questions and getting answers is fine on its own. But if you're already living in Claude, your analytics are now part of the same loop as everything else you ship.

Example prompts

Three prompts to paste into Claude (or Cursor, or ChatGPT) after your connector is wired up. Numbers in the responses are examples.

You

How did myblog.com do yesterday?

Claude

On myblog.com yesterday: 4,287 pageviews from 2,914 sessions. Bounce 41%, average engagement 53 seconds. Up 18% versus the day before. Top page /pricing (612 views), top source news.ycombinator.com (1,103 visits). 27 signup events, 9 of them on the Pro plan. Bot share 14%, mostly GPTBot indexing your blog.

Calls get_overview with period: "yesterday". One tool call returns headline metrics, vs-previous-period delta, top page, top source, bot share, and the top three custom events.

You

Show me the last 28 days for myblog.com, and tell me what to fix.

Claude

Last 28 days: 118,400 pageviews, 76,200 sessions, +12% vs the prior 28 days. Signups up 31% to 842, but signup-to-Pro conversion dropped from 11% to 7%.

Three things stand out:

1. Mobile bounce is 64%, desktop 31%. Mobile traffic grew 38% but engagement halved. The hero stacks below a 600px header image on phones.
2. Newsletter (utm_source=newsletter) brings 18% of pageviews but 41% of signups. Your best channel by 2.5x.
3. /pricing has 18,400 views and 2.1% scroll past the comparison table on mobile. People can't see the Pro column.

Suggestions, in order of likely impact:

a. Move the pricing comparison table above the mobile hero image. Want me to ship that diff?
b. Triple down on newsletter cadence. One extra issue this week likely worth ~120 additional signups.
c. Hacker News referrals bounce at 78%, much higher than other sources. The HN crowd hits the page expecting something different from your current hero copy. Consider an HN-tailored variant.

Calls get_overview, get_timeseries, top_sources, breakdown, and engagement_overview in sequence. The agent picks tools based on what the question implies. Once it has the data it can also propose code changes and ship them on approval, no separate dashboard needed.

You

Which AI agents fetched myblog.com this week?

Claude

Last 7 days on myblog.com, by traffic class:

- GPTBot (ai_training): 8,420 hits, mostly under /blog/*
- ClaudeBot (ai_training): 6,180 hits, same pattern
- PerplexityBot (ai_search): 1,240 hits, focused on /pricing and your top 5 blog posts
- ChatGPT-User (ai_user_action): 1,847 fetches. These are real humans chatting with ChatGPT and the assistant pulled your page.
- Claude-User (ai_user_action): 924 fetches, same idea

Two things worth knowing:

First, ai_user_action is up 4x month-over-month. People are asking AI about your content. The top fetched URLs are /pricing and /blog/email-management. Make sure those render meaningful content without JavaScript, because most AI fetchers don't execute it.

Second, training crawlers (GPTBot, ClaudeBot) are pulling your blog heavily. If you don't want your posts in training data, add a robots.txt rule. If you do, you're already in line for wider AI reach.

Calls top_user_agents and traffic_class_breakdown. The 8-class taxonomy (user, ai_user_action, ai_search, ai_training, search_index, social_unfurl, scanner, bot_other) lets the agent distinguish "AI training crawler hitting your blog" from "real human using ChatGPT to ask about your product". Most tools collapse both into one "bot" bucket.

The tools

What your agent can call once your MCP URL is wired in.

Account
list_sites
Every site on your account, with monthly hit counter.
add_site
Register a new domain. Pick the privacy mode (cannot be changed later).
remove_site
Soft-delete a site. Historical events expire on the table TTL.
get_tracking_snippet
The HTML <script> tag for a given site.
get_account
Email, plan, total usage this month.
regenerate_api_token
Rotate the legacy API token. Day-to-day, prefer revoking specific connectors via Settings; this is the nuclear option.
Analytics / the daily questions
get_overview
TL;DR for a period. Pageviews, sessions, bounce, top page, top source, bot share, top events. This is the one your agent should call first when you ask "how did yesterday go?"
get_timeseries
Pageviews / visitors / sessions over time. Hour, day, or week buckets.
top_pages
Most-visited URL paths.
top_referrers
Top referring hosts (where the link came from). Counts direct browser visits only; AI-mediated traffic is excluded because the AI sets its own host as referrer or strips it; see traffic_class_breakdown for that split.
top_sources
UTM source / medium / campaign breakdowns. Tag your shared links to see exactly what worked. Direct browser visits only (same reason as top_referrers).
breakdown
Visit counts by browser / OS / device type / country.
list_events
All custom event names with counts.
event_details
Drill into one event. Optional group_by_property to slice by a custom prop.
compare_periods
"Was last week better than the week before?" Head-to-head metric comparison.
AI bots & crawlers
top_user_agents
The top User-Agents that visited, with traffic_class. See exactly which AI agents (ChatGPT-User, Claude-User, GPTBot, ...) and crawlers fetched your pages.
traffic_class_breakdown
What share of your traffic was bots vs real users.
Visitor signals
top_timezones / top_languages
Quasi-geo and locale signals from Intl.DateTimeFormat and navigator.language. No IP lookups.
color_scheme_breakdown
Share of visitors with system dark mode on. Useful product signal.
viewport_breakdown
Real usable viewport widths, bucketed (mobile_xs / mobile / tablet / desktop / desktop_xl).
engagement_overview
Real reading time + scroll depth. Counts only when the tab is active, not just open.

Custom events

Pageviews are auto-tracked. Anything else you want, call mcpa('track', ...) in your code:

// somewhere in your app
window.mcpa('track', 'signup', { plan: 'pro' });
window.mcpa('track', 'video_played', { duration_seconds: 42 });

Up to 20 properties per event. Strings, numbers, booleans only. Then ask Claude: "How many signups last week, broken down by plan?" and it'll call event_details with group_by_property: "plan".

Self-exclude (for builders)

Don't poison your own analytics with your own visits. Once on each browser/device:

https://your-site.com/?mcpa_exclude=1

The tracker stores a flag in localStorage and stops sending events from that browser. Undo with ?mcpa_exclude=0. Survives navigation, not browser-data clears.

FAQ

Why no dashboard?

Because dashboards are where data goes to die. You open it, scan the same five widgets, close it. mcp-analytics turns the workflow inside out: ask a question, get an answer. The agent does the chart-reading for you.

Will my agent figure this out without docs?

Yes. We expose get_started_guide as an MCP tool. Once your connector URL is wired in, your agent will call it automatically when it doesn't know what to do next. These human docs are just trust signal.

How does the free tier work?

Free up to 100,000 hits per month, unlimited sites. No card. After that we'll have paid tiers, but the free tier covers the vast majority of indie / side-project sites and we don't plan to take that away.

Can I export my raw data?

Yes. Completely. Every row, every column, every event you've sent us. No paywall, no API rate-limit, no "Enterprise tier" gate. Free users and paid users get the same export. You can leave whenever you want and take everything with you.

We don't lock you in. You'll stay because the product is good, not because leaving is painful.

What's the bot classification?

Every event gets one of eight traffic_class labels: user (real human in their own browser), ai_user_action (a person asked an LLM to fetch your page like Claude-User, ChatGPT-User, Perplexity-User), ai_search (AI search-engine indexers like PerplexityBot), ai_training (training crawlers like GPTBot, ClaudeBot), search_index (Googlebot, Bingbot, ...), social_unfurl (Slackbot, link previews), scanner (security/uptime/perf monitoring), bot_other (recognized but not in any specific bucket).

Classification combines UA-pattern matching against ~70 curated patterns, IP-CIDR lookups against vendor-published ranges (refreshed every 6h from OpenAI, Google, Bing, AWS/GCP/Cloudflare), and reverse-DNS for Anthropic. Default analytics queries show user + ai_user_action as "humans", a person reading your content, whether through their own browser or via an AI assistant. Use top_user_agents and traffic_class_breakdown to see the full split.

OAuth?

Yes. Add mcp-analytics.com/mcp as a custom connector, your client discovers our authorization server, registers itself dynamically (RFC 7591), and runs the OAuth 2.1 + PKCE flow. We never see a long-lived bearer token in your client; refresh-tokens rotate. Revoke any connected client any time from Settings.

Where is my data stored?

In Germany, EU jurisdiction, GDPR scope. Visitor IPs are hashed in-memory for the session identifier and then dropped, so they don't land in the analytics database. We never share or sell your data. See the privacy policy for the full data-controller breakdown and sub-processor list.

Stop reading. Start asking.

Connect now →