---
title: "Cookieless page analytics without a consent banner"
description: "Views, daily unique visitors, referrers and devices with nothing stored in the browser: how glokki page analytics works, what it leaves out, and setup."
url: "https://glokki.com/blog/cookieless-page-analytics"
locale: "en"
updated: "2026-10-26T11:16:49.191Z"
---

# Cookieless page analytics: what you can measure without a consent banner

glokki team · Oct 26, 2026

Views, daily unique visitors, referrers and devices, with nothing stored in the browser. How glokki page analytics works, what it deliberately leaves out, and the two files it takes to set up.

Most cookie banners exist because of analytics. A script sets an identifier
in the browser so it can recognise a visitor tomorrow, and storing that
identifier is what needs consent. glokki ships a page counter that doesn't
store anything in the browser, which is why glokki.com has no banner.

This post covers what it measures, how it gets away without cookies, what
it deliberately leaves out, and the setup.

## What you get

The **Analytics** dashboard in the CMS shows, for 7, 30 or 90 days:

- **Views**: total page views, with a trend chart.
- **Unique visitors**: distinct visitors, counted per day.
- **Referrers**: where the traffic came from.
- **Devices**: desktop, mobile and tablet, worked out on the server from the
  User-Agent.

There's no separate analytics account and no third-party script tag. If the site
renders glokki pages, the data appears as soon as the two pieces below are
deployed.

## How it works

There are two parts: a component in the page and a route on your own
domain.

```text
browser ── POST /_e { path, referrer } ──► your app (same origin)
                                            │ + visitor IP, User-Agent
                                            ▼
                                   glokki ingest ──► hash, count, discard IP
```

**The beacon.** `<PageAnalytics />` from `@glokki-cms/react` renders
nothing. After the page loads, and on every client-side navigation, it
sends one request with exactly two fields:

```ts
JSON.stringify({ path: pathname, referrer: document.referrer || undefined })
```

It uses `navigator.sendBeacon` (or a `keepalive` fetch where that is
missing), so the request never blocks rendering and still goes out if the
visitor clicks away straight after.

**The proxy.** The beacon doesn't talk to a third-party domain. It posts to
`/_e` on your own site, a route that `createInsightsRoute()` from
`@glokki-cms/sdk` creates. The route holds the API key on the server, adds
the visitor's IP address and User-Agent, and forwards the beacon to glokki.
It replies `204` immediately and ignores upstream errors, so analytics can't
break or slow down a page.

**Unique visitors without an identifier.** glokki computes a SHA-256 hash of
IP + User-Agent with a salt that changes every day. The raw IP is used for
that hash and then discarded, not stored. Since the salt changes daily,
today's hash can't be matched to yesterday's. That's what "unique per day"
means, and why nothing has to be kept in the browser.

## Why there is no banner

The consent requirement for cookies (in the EU, the ePrivacy rules) is about
**storing or reading information on the visitor's device**. This setup does
neither: there are no cookies, nothing in `localStorage` and no fingerprint
script. You can check glokki.com yourself. Its pages send no `Set-Cookie`
header, and the analytics request carries only a path and a referrer.

We're not your lawyers, though. An IP address is still personal data while
it is being processed, so describe the analytics in your privacy policy, and
ask someone qualified if your situation is unusual.

## What it doesn't measure

These are choices, not missing features:

- **Returning visitors.** No identifier survives the day, so "came back on
  Tuesday" can't be recorded.
- **Sessions, funnels and events.** It counts page views. It doesn't track
  clicks, scroll depth or sign-ups.
- **Campaign tags.** The beacon sends the path without the query string, so
  `?utm_source=…` doesn't reach the stats. The referrer usually tells you
  enough. For campaign attribution, look where the conversion happens: on
  glokki.com the sign-up links carry UTM tags, and the sign-up app is the
  place to count them.
- **Every last visitor.** A same-origin route on a neutral path avoids most
  blocklists aimed at third-party analytics, but any client-side counting
  can be blocked. Expect a small undercount. Bots are filtered out in the
  CMS.

If you need funnels or product analytics, use a tool built for that, and ask
for consent. For "which pages do people read and where do they come from",
this is enough.

## It counts cached pages

glokki.com pages are static and served from the CDN with ISR. Counting on
the server would miss every cache hit. The beacon runs in the browser after
the HTML arrives, so a page served from the edge counts the same as a fresh
render.

## It doesn't count you

Editors open a page dozens of times while working on it. Since
`@glokki-cms/react` 0.10, the beacon does nothing when the page is opened by
the CMS: inside the visual editor (`?_editor=1`), on the block-template
editor route, and in draft previews (`?preview=true`). Earlier versions
counted those views, and the referrer pointed at the CMS. If your numbers
look higher than your traffic, check the version first.

On glokki.com we went one step further. `<PageAnalytics />` lives in the
component that renders public CMS pages, not in the root layout, so preview
and editor routes never include it.

## Setup: two files

The route:

```ts
// app/_e/route.ts — use the folder name %5Fe: Next.js treats _e as private
import { createInsightsRoute } from "@glokki-cms/sdk"

export const { POST } = createInsightsRoute({
  baseUrl: process.env.CMS_BASE_URL!,
  tenantSlug: process.env.CMS_TENANT!,
  apiKey: process.env.CMS_API_KEY!, // delivery:read, server-side only
})
```

The component, rendered once on public pages:

```tsx
import { PageAnalytics } from "@glokki-cms/react"

// …inside your page or layout
<PageAnalytics />
```

If you mount the route somewhere other than `/_e`, pass the same path as
`<PageAnalytics endpoint="/your-path" />`. The
[Page Analytics guide](/docs/page-analytics) covers IP headers behind
Cloudflare or Fastly, older SDK versions and troubleshooting.

[Create a free account](https://app.glokki.com/register?utm_source=blog&utm_campaign=cookieless-analytics)
and see your traffic without adding a banner.

# More from the blog

## See your traffic without a cookie banner

Free during beta · No credit card required

[Create free account](https://app.glokki.com/register?utm_source=blog&utm_campaign=cookieless-analytics)

[Read the guide](https://glokki.com/docs/page-analytics)
