Proxy
Serve tracking from your own domain
A same-origin proxy can help when extensions block third-party tracker URLs. It exposes only the public script and collection endpoint, never your secret key.
Set up a proxy (Next.js App Router)
Add a route handler
app/a/[kind]/route.ts// app/a/[kind]/route.ts — Next.js App Router import { NextRequest } from "next/server"; async function proxy(req: NextRequest, context: { params: Promise<{ kind: string }> }) { const { kind } = await context.params; const script = kind === "script" && req.method === "GET"; const event = kind === "event" && req.method === "POST"; if (!script && !event) return new Response("Not found", { status: 404 }); const headers = new Headers(); for (const name of ["content-type", "origin", "user-agent"]) { const value = req.headers.get(name); if (value) headers.set(name, value); } // Trust these only if your hosting provider overwrites them. const ip = req.headers.get("cf-connecting-ip") || req.headers.get("x-forwarded-for")?.split(",")[0]?.trim(); if (ip) headers.set("x-visitor-ip", ip); for (const [source, target] of [["cf-ipcountry", "x-visitor-country"], ["cf-region", "x-visitor-region"], ["cf-ipcity", "x-visitor-city"]]) { const value = req.headers.get(source); if (value) headers.set(target, value); } const upstream = await fetch(script ? "https://metricraven.com/js/script.js" : "https://metricraven.com/api/v1/collect", { method: req.method, headers, body: event ? await req.arrayBuffer() : undefined, cache: "no-store", signal: AbortSignal.timeout(15000), }); return new Response(upstream.body, { status: upstream.status, headers: { "Content-Type": upstream.headers.get("content-type") || "application/octet-stream", "Cache-Control": script ? "public, max-age=3600" : "no-store", }}); } export { proxy as GET, proxy as POST };Replace your script tag
Point the script and its events at your own paths:
index.html<script defer src="/a/script" data-api="/a/event" data-site-id="YOUR_SITE_ID"></script>Forward the real visitor IP
Use a header your hosting provider sets and overwrites. Forwarding your server's own IP gives misleading locations. If Cloudflare supplies visitor location headers, forward those too.
Verify it works
In the Network panel, requests to /a/script and /a/event succeed, and new visits show plausible countries.
Details
- A proxy doesn't guarantee that every blocker will allow tracking.
- Any server can proxy the same way: serve
https://metricraven.com/js/script.js, forward events tohttps://metricraven.com/api/v1/collect, and pass the visitor IP asx-visitor-ip(plusx-visitor-country,x-visitor-regionandx-visitor-cityif known).