What is reported
A page view is oneGET request to a page-content path. Requests for assets (anything whose final path segment has a file extension, like /_astro/app.css, /favicon.ico, or /logo.png) are skipped, as are redirects. Everything a reader actually loads to view a page is reported: your pages for people, and the same pages for agents and crawlers.
There is no user-agent gate at capture. A crawler, an unknown agent, and a browser are all reported and told apart afterward, so a new agent shows up in your numbers without any change on your side.
How a viewer is classified
The visitor’s user-agent,Accept header, and IP are read to classify the request, then discarded. What is stored is coarse and non-identifying:
- Client kind:
agent,browser, orother. - The agent, when one is recognized: its registry slug (
gptbot,perplexitybot, …) and operator (OpenAI, Perplexity, …), plus a coarse agent type. - A user-agent family and the registry version that classified it, so history can be re-bucketed when the registry improves.
cf-ipcountry, clamped to a 2-letter code) and the referrer host, the referring domain only, never the full referrer URL, so a referrer’s own path or query never leaves the visitor’s site. Both are optional and hold nothing that identifies a person.
Journey stitching
Beyond the anonymous viewer id, a page view can carry two fields that describe the agent’s read of the page, not just the client behind it:representation: whether this request was served as plainhtmlor agentifiedmarkdown. The SDK middleware reads it from the response content-type, so you can segment journeys by whether the entry actually got the agent experience.journeyId: a reading-chain id that stitches this page view to the agentified read it belongs to. When Agentify serves an agent markdown, it attaches a journey id to that response; if Page views is mounted as the outer layer, it forwards that id on the view. The marketing view and the agentified read then line up on one journey.
representation is filled whenever the middleware can see the response. journeyId appears only when Agentify attached one: Page views without Agentify simply reports no journey id, and Agentify without Page views attaches a journey id that nothing reads. They come together only when Page views wraps Agentify, so the outer view observes both the agent’s request and the journey id on its response. The SDK middleware shows that wrap in each language.
Two timestamps
Each view carries two clocks, so you can measure delivery lag and trust the right one:captured_at: when your edge observed the request. Present only when your reporter sends it; it is never invented.received_at: when ZeroClick received the beacon. This is the authoritative time.
The Page views key scope
Reporting authenticates with an API key carrying thepage-views:write scope. Mint one in the dashboard under Settings → API keys: create a key and enable the Page views group’s Write toggle. The scope grants POST /v1/page-views and nothing else, so the key can live on your marketing site’s edge without exposing your catalog, usage, or Agentify APIs. A key can carry both page-views:write and agentify:convert when you run both from the same edge, or just one.
Next steps
SDK middleware
Report every page view from your TypeScript, Python, Go, or Ruby site, fire-and-forget.
REST endpoint
Send a page view from any stack with one POST.