Google Analytics 4 is still the default for web analytics, and it's free. Here's a clean way to wire it into a Next.js app without bloating your bundle or guessing whether it works.
1. Create a GA4 property and data stream
In the Google Analytics admin, create a GA4 property, then a Web data stream for your domain. You'll get a Measurement ID that looks like G-XXXXXXXXXX. That's the only public identifier you need on the client.
2. Load gtag.js the Next.js way
Use the built-in next/script component with the afterInteractive strategy so the tag loads without blocking your page. Put your Measurement ID in an environment variable (NEXT_PUBLIC_GA_ID) rather than hardcoding it, so staging and production stay separate.
3. Track route changes
GA4's automatic page_view works for the first load, but Next.js client-side navigation doesn't trigger a full page load. Fire a page_view on route change (via the App Router's usePathname) so your pageviews aren't undercounted.
4. Send the events that matter
Pageviews alone won't tell you much. Map your funnel to GA4 events:
sign_upwhen an account is createdpurchasewithvalueandcurrencyfor revenue- any custom conversion specific to your product
Keep names consistent with whatever canonical taxonomy you use elsewhere so reports line up across tools.
5. Verify with DebugView
This is the step everyone skips. Open GA4's DebugView, load your site, and watch events arrive in real time. If sign_up doesn't show up when you submit the form, your tracking is broken — and DebugView tells you immediately, instead of you discovering it a week later in an empty report.
A note on resilience
GA4 runs client-side, so ad blockers and consent choices will drop some events. Treat GA4 as one (important) input, not the source of truth. Pairing it with first-party owned events gives you a baseline that survives blockers.