Netlify
Add one Edge Function to your Netlify site. It runs in front of every page, including static and cached ones, reports crawler visits to Rankealo in the background, and lets everything else through untouched.
Prerequisites#
- A site deployed on Netlify from a Git repository (any framework, or plain static HTML).
- Your site token and website id from Bot traffic → Agent Analytics Setup in the app. The snippet there already has both filled in; the examples on this page use
YOUR_SITE_TOKENandYOUR_WEBSITE_ID. See the HTTP API reference for the full payload.
Steps#
- 1
Create the file
Createnetlify/edge-functions/rankealo-bots.tsin your repository. If you changed the edge functions directory innetlify.toml, use that folder instead. - 2
Paste the snippet
Use the snippet from Agent Analytics Setup (it has your token filled in), or the one below with your values. Theconfigexport runs it on every path; nonetlify.tomlchange is needed. - 3
Deploy
Push and let Netlify deploy. The function appears under Logs → Edge Functions.
// netlify/edge-functions/rankealo-bots.ts
import type { Config, Context } from "@netlify/edge-functions";
const CRAWLER_UA = /gptbot|chatgpt-user|oai-searchbot|oai-adsbot|claudebot|claude-searchbot|claude-user|anthropic-ai|perplexitybot|perplexity-user|google-extended|googlebot|googleother|bingbot|duckassistbot|applebot|meta-externalagent|amazonbot|bytespider|ccbot|mistralai-user/i;
const STATIC_ASSET = /\.(?:js|css|map|png|jpe?g|gif|webp|avif|svg|ico|woff2?|ttf)$/i;
export default async (request: Request, context: Context) => {
const url = new URL(request.url);
const ua = request.headers.get("user-agent") || "";
const track =
(request.method === "GET" || request.method === "HEAD") &&
!STATIC_ASSET.test(url.pathname) &&
CRAWLER_UA.test(ua);
if (!track) return; // continue to the site untouched
const response = await context.next();
const report = fetch("https://app.rankealo.ai/api/ai-visibility/crawler-hits/ingest", {
method: "POST",
headers: { "content-type": "application/json", authorization: "Bearer YOUR_SITE_TOKEN" },
body: JSON.stringify({
websiteId: "YOUR_WEBSITE_ID",
domain: url.hostname,
href: url.origin + url.pathname,
ai: {
userAgent: ua,
ip: context.ip,
statusCode: response.status,
source: "server_middleware",
},
}),
}).catch(() => {});
// Background: never delays the response.
if (typeof context.waitUntil === "function") context.waitUntil(report);
return response;
};
export const config: Config = { path: "/*" };
What is sent#
- URLOrigin and path. The query string is never sent.
- User agentUsed to identify the crawler.
- IPFrom context.ip; hashed on arrival, never stored raw.
- Status codeThe status your site returned.
- Website idTies the hit to your site and token.
Human visitors pass straight through: the function returns without touching the request. For crawler requests it fetches the page as usual and reports the hit with context.waitUntil, so the response never waits for Rankealo. Static assets (scripts, styles, images, fonts) are skipped.
Limitations#
- Edge Function invocations count toward your Netlify plan's usage, since the function runs on every request.
- Hits are marked as claimed identities (user agent only); Netlify does not pass a verified-bot flag.
- Only crawlers in the snippet's list are reported. Update the snippet to pick up new crawlers.
Confirm data is flowing#
- 1In Rankealo, open Bot traffic → Agent Analytics Setup.
- 2Press Check now in step 3. Once a crawler has visited, it shows Receiving data with the time of the last hit.
- 3Open the Bot traffic tab to see hits by crawler and by page.
The first hit depends on when a crawler next visits, which can take up to 24 hours. To test right away, request a page with a crawler user agent, for example curl -A "GPTBot/1.2" https://www.your-site.com/, then press Check now. A test like this is recorded as a claimed identity, like any hit without CDN verification.
Troubleshooting#
The function does not run+
Check now says No data received+
Hits are skipped+
Still stuck? Contact support
