Skip to content
fusionaly_ GitHub

React Analytics Without Cookies

Add Fusionaly to a React app built with Vite: one script tag in index.html. It counts React Router page changes and uses no cookies.

In a React app built with Vite, every page loads from index.html. Add the Fusionaly script there once. Fusionaly then counts every page that React Router opens.

Before you start

You need a Fusionaly server, with your site's domain added as a website. Fusionaly takes events only from the domains you added. See Installation.

In the examples, replace analytics.example.com with the domain of your Fusionaly server.

Add the script

  1. Open index.html in the root of your project.

  2. Add the script to <head>:

    index.html
    <!doctype html>
    <html lang="en">
    <head>
    <meta charset="UTF-8" />
    <script defer src="https://analytics.example.com/y/api/v1/sdk.js"></script>
    <title>My app</title>
    </head>
    <body>
    <div id="root"></div>
    <script type="module" src="/src/main.tsx"></script>
    </body>
    </html>

With Create React App, the file is public/index.html.

Page changes

React Router, with createBrowserRouter or BrowserRouter, changes pages with history.pushState, and Fusionaly counts a page view each time the path changes. A change to only the query string or the hash is not a new page view. Fusionaly counts pages by their path, without the hash. With HashRouter, every page has the path /, so Fusionaly counts all of them as one page. Use a browser router to see each page.

Skip it in development

This is optional. Fusionaly refuses events from localhost, so your own tests never count. To not load the script at all in development, remove the tag from index.html, and add the script from your entry file:

src/main.tsx
if (import.meta.env.PROD) {
const script = document.createElement("script");
script.src = "https://analytics.example.com/y/api/v1/sdk.js";
script.defer = true;
document.head.appendChild(script);
}

Track events

Fusionaly counts page views and button clicks without any setup. To give an event your own name, use the data-fusionaly-event-name attribute. See Tracking.

Add the attribute in JSX:

<a href="/pricing" data-fusionaly-event-name="pricing_clicked">Pricing</a>

For data that only the browser knows, call the SDK from a handler:

function ExportButton({ format }: { format: string }) {
return (
<button onClick={() => window.Fusionaly?.sendCustomEvent("report_exported", { format })}>
Export
</button>
);
}

With TypeScript, declare the SDK in a .d.ts file that your tsconfig.json includes:

fusionaly.d.ts
declare global {
interface Window {
Fusionaly?: {
sendCustomEvent(name: string, metadata?: Record<string, unknown>): void;
sendPageView(): void;
};
}
}
export {};

Check that it works

  1. Open your site in a normal browser window. Fusionaly skips automated browsers, such as Playwright, and browsers that send Do Not Track.
  2. In the developer tools, open the network tab, and find a POST request to /x/api/v1/events. A 403 status means that your site's domain is not added as a website.
  3. Open your Fusionaly dashboard. The visit shows up within about a minute.

Notes

  • If your app runs on a subdomain, such as app.example.com, add that subdomain as a website. Or add example.com and turn on subdomain tracking.

Next steps

Guides for other frameworks: Next.js, Astro, Nuxt, SvelteKit, WordPress, Shopify, Webflow, Ghost, Hugo, and the generic guide.