Google Analytics Code

<!-- Google Analytics 4 gtag loader -->
<script async src="https://www.googletagmanager.com/gtag/js?id=G-DEDBEEFTAG"></script>

<script>
// ===============================
// CONFIGURATION FLAGS
// ===============================

const GA_MEASUREMENT_ID = 'G-DEDBEEFTAG';
const TRACK_USER_IP = true;       // Toggle IP tracking (safe to disable in production)
const GOOGLE_DEBUG_MODE = true;   // Enable GA4 DebugView

// ===============================
// INITIALIZE GA4
// ===============================

window.dataLayer = window.dataLayer || [];
function gtag() { dataLayer.push(arguments); }

gtag('js', new Date());
gtag('config', GA_MEASUREMENT_ID);

// ===============================
// LOG PAGE LOAD EVENT
// ===============================

function logPageLoad() {
  const pagePath = window.location.pathname;
  gtag('event', 'page_load', {
    page_name: pagePath,
    debug_mode: GOOGLE_DEBUG_MODE
  });
  console.info(`[GA4] page_load: ${pagePath}`);
}

// ===============================
// LOG USER IP EVENT
// ===============================

function logUserIP(ipAddress) {
  gtag('event', 'user_ip', {
    ip: ipAddress,
    debug_mode: GOOGLE_DEBUG_MODE
  });
  console.info(`[GA4] user_ip: ${ipAddress}`);
}

// ===============================
// GET PUBLIC IP (via ipify.org)
// ===============================

function fetchUserIP() {
  if (!TRACK_USER_IP) {
    console.info('[GA4] IP tracking disabled');
    return;
  }

  fetch('https://api.ipify.org?format=json')
    .then(response => response.json())
    .then(data => {
      if (data && data.ip) {
        logUserIP(data.ip);
      } else {
        console.warn('[GA4] IP response malformed:', data);
      }
    })
    .catch(err => console.error('[GA4] IP fetch failed:', err));
}

// ===============================
// EXECUTION ENTRY POINT
// ===============================

document.addEventListener('DOMContentLoaded', () => {
  logPageLoad();
  fetchUserIP();
});
</script>

Great — I’ll put together a clean and reliable setup that logs two custom events to Google Analytics 4 on your LAN site:

  1. A PAGE_LOAD event that includes the name or path of the page
  2. A USER_IP event that includes the visitor’s IP address (for testing only)

I’ll make sure the implementation uses gtag.js, follows best practices, and is stable for local testing. I’ll let you know once it’s ready.

Logging Custom GA4 Events: Page Load and User IP

Implementation Overview

For a LAN-only testing site, you can use Google Analytics 4 (GA4) with gtag.js to send two custom events:

  • page_load – fired on each page visit, with a parameter for the page name or path.
  • user_ip – fired (optionally) to log the visitor’s IP address (retrieved via an external API like ipify).

Event Naming & Parameters: GA4 event names and parameters should follow best practices (e.g. all lowercase and snake_case). We’ll use page_load and user_ip (lowercase) as the custom event names, with parameters page_name (for the page path/name) and ip (for the IP address). This keeps the data structured and readable. Avoid including any personally identifiable information (PII) beyond this limited local setup – GA4 by default does not store full IP addresses for privacy, so you should disable this in production.

JavaScript Setup (gtag.js)

Make sure the GA4 gtag snippet is installed on your page (with your GA4 Measurement ID G-DEDBEEFTAG). The code below demonstrates a clean implementation for logging the events. It includes flags and functions to keep things modular and easy to disable in production:

<!-- Load GA4 gtag.js (include this in your HTML head) -->
<script async src="https://www.googletagmanager.com/gtag/js?id=G-DEDBEEFTAG"></script>
<script>
  // Initialize Google Analytics 4
  window.dataLayer = window.dataLayer || [];
  function gtag(){ dataLayer.push(arguments); }
  gtag('js', new Date());
  // GA4 configuration (property ID)
  gtag('config', 'G-DEDBEEFTAG' /*, { send_page_view: false } */);
  // ^ If you only want to use the custom page_load event (and not GA4's automatic page_view), 
  //   uncomment send_page_view:false to prevent double-counting:contentReference[oaicite:2]{index=2}.

  // Flag to control IP tracking (disable for production to avoid sending PII)
  const TRACK_USER_IP = true;  // set to false in production for privacy

  // Custom function to log a page load event with page name/path
  function logPageLoad(pagePath) {
    gtag('event', 'page_load', { 
      page_name: pagePath   // e.g. "/about.html" or "HomePage"
    });
  }

  // Custom function to log a user IP event
  function logUserIP(ipAddress) {
    gtag('event', 'user_ip', { 
      ip: ipAddress  // e.g. "192.168.0.5"
    });
  }

  // Trigger the events when the page is fully loaded
  document.addEventListener('DOMContentLoaded', () => {
    // 1. Log the PAGE_LOAD event with current page path
    logPageLoad(window.location.pathname);
    // 2. Fetch the user's IP and log the USER_IP event (if enabled)
    if (TRACK_USER_IP) {
      fetch('https://api.ipify.org?format=json')
        .then(response => response.json())
        .then(data => {
          if (data && data.ip) {
            logUserIP(data.ip);
          }
        })
        .catch(err => console.error('IP fetch failed:', err));
    }
  });
</script>

How this works: On page load, the code sends a page_load event with a page_name parameter equal to the current path (you could use a descriptive name or document.title if preferred). It then calls api.ipify.org to get the public IP in JSON, and if successful, sends a user_ip event with an ip parameter. We’ve isolated the event-sending logic in logPageLoad() and logUserIP() functions for clarity. The TRACK_USER_IP flag makes it easy to disable IP tracking later – in production, you’d set this to false or remove that block to avoid sending PII.

Note: The GA4 config above uses the default page_view tracking. If you want to rely solely on the custom page_load event (to avoid counting every page twice), you can disable the automatic page_view by adding send_page_view: false in the gtag config as shown (commented). This ensures GA4 doesn’t fire its built-in page_view event on load.

Viewing the Events in GA4

After implementing the above, you can verify that GA4 is receiving the events:

  • Realtime report: In your GA4 dashboard, go to Realtime. Within seconds of loading a page on your site, you should see the custom page_load and user_ip events appear in the realtime event stream. This is useful to confirm that the events are firing correctly.
  • DebugView: For a more detailed live view (including parameter values), you can use GA4’s DebugView. Enable debug mode (for example, by using the Google Analytics Debugger extension or by adding debug_mode: true in your event calls) to see each event and its parameters in the DebugView report.
  • Events report: GA4 will also list these events in the Engagement > Events section. The custom events might take a little time to appear here (usually within a few minutes to an hour). In Analytics > Reports > Engagement > Events, you should eventually see page_load and user_ip in the All Events table, with counts of how often they’ve fired. Clicking on an event will show some details and charts.

Using Custom Dimensions for page_name and ip

By default, GA4 records the event names and basic metrics, but to analyze the custom parameters (page_name and ip) in reports or explorations, you should register them as custom dimensions. In GA4, custom event parameters are not automatically visible in standard reports – you need to expose them via custom definitions.

To create event-scoped custom dimensions:

  1. In GA4, go to Admin (for your property) and under Data select Custom Definitions. Choose the Custom dimensions tab, then click Create custom dimension.
  2. Fill in the details for the new dimension:

    • Dimension name: e.g. “Page Name” (this is just a friendly name for your reference; no hyphens allowed, but underscores/spaces are fine).
    • Scope: Event (since page_name is an event parameter).
    • Description: (optional note, e.g. “Name or path of the page the user visited”).
    • Event parameter name: page_nameexactly match the parameter key used in the code.
  3. Save the custom dimension. Repeat the process to create another custom dimension for ip (e.g. name it “User IP”, scope Event, event parameter name ip).

Once these custom dimensions are created, GA4 will start populating them with incoming event data (note that it’s not retroactive for past events). After a while (typically 24 hours or less), you can use these dimensions in GA4’s Explorations or custom reports. For example, you could create a free-form exploration with page_load events and break them down by the Page Name dimension to see which pages were loaded, or view the values of User IP for user_ip events.

Where to see the custom parameter values: In Realtime or DebugView, you can already see the parameter values live for each event. In the regular GA4 interface, once the custom dimensions are active, you can:

  • Customize a standard report or create an exploration and add Page Name or User IP as dimensions to analyze your events.
  • For instance, add Page Name to a table showing page_load event counts to view the page paths being recorded.

Privacy Considerations

Because IP addresses and similar data can be considered personal information, do not use the user_ip event in production (or any public-facing site) without careful consideration. Google’s policies forbid sending PII such as personal identifiers to Analytics. In our code, the TRACK_USER_IP flag is set up so you can easily disable this event outside of a controlled LAN test environment. In production, it’s safest to leave TRACK_USER_IP = false (or remove that code) so that no raw IP addresses are logged to GA4. GA4 itself anonymizes IP data by default and does not surface individual IPs in reports, so our custom IP event is strictly for local testing insight.

Finally, always ensure your event names and parameters are meaningful and non-sensitive. The above setup is modular and easy to maintain – you can remove or extend custom events as needed. With the events logging and custom dimensions in place, you can monitor them in GA4’s Realtime/DebugView immediately and later analyze them in the Events reports or Explorations for deeper insights.

Sources:

  • Google Analytics 4 event naming conventions (use lowercase and underscores)
  • GA4 does not log full IP addresses by default, for privacy reasons
  • Example of disabling automatic page_view when sending custom page events
  • GA4 Realtime and DebugView show incoming events and parameters in real time
  • Creating event-scoped custom dimensions for custom event parameters in GA4

How to View Events


🧭 1️⃣ Realtime View (immediate debugging)

This is where you go right after you send the event.

  • Go to your GA4 property.

  • In the left menu: ReportsRealtime

  • Here you’ll see:

    • Recent events (last 30 minutes)
    • Event names (like page_load, user_ip)
    • Event parameters (if you click inside an event)

Realtime is great to verify that your custom events are being received correctly.


🧭 2️⃣ DebugView (best for development / local testing)

✅ DebugView is your best friend during development.

  • Go to: AdminDebugView

  • BUT: You need to enable debug mode for events to show up here.

How to enable debug mode (you have multiple options):

Option A — easiest for LAN / test:

Just add debug_mode: true to your gtag call, e.g.:

gtag('event', 'page_load', {
  page_name: window.location.pathname,
  debug_mode: true
});

Option B — use GA Debugger browser extension:

✅ In DebugView you will see:

  • Timestamps
  • All events
  • All parameters (page_name, ip etc.)

🧭 3️⃣ Events Report (aggregated over time)

✅ This is where your events start appearing automatically once GA processes them.

  • In GA4 left menu: ReportsEngagementEvents

  • Here you’ll see:

    • List of all event names (page_load, user_ip, etc.)
    • Event count
    • Total users who triggered the event

Important:

  • Custom parameters (like page_name, ip) do not automatically show up here.
  • You need to create custom dimensions to expose their values in reports (I explain this below).

🧭 4️⃣ Explorations (best for advanced analysis)

✅ Once your events + custom dimensions are set up, you can build reports.

  • In GA4 left menu: Explore ➔ Create Free Form Exploration

  • You can select:

    • Event name = page_load or user_ip
    • Add your custom dimensions (page_name, ip) to see parameter values.

🧭 5️⃣ Custom Dimensions — required for parameters

✅ Your page_name and ip parameters won’t automatically appear in reports. You need to register them:

  • Go to: AdminCustom definitionsCustom dimensionsCreate custom dimension

  • For page_name:

    • Dimension name: Page Name (friendly name)
    • Scope: Event
    • Event parameter: page_name (exactly matching your code)
  • Repeat for ip:

    • Dimension name: User IP
    • Scope: Event
    • Event parameter: ip

✅ After ~24h processing time, your custom dimensions will appear in Explorations & reports.


🧪 Quick Summary Table

GA4 Area Use Case
Realtime See live events as they arrive
DebugView Full live debugging, see parameters
Events report Aggregate count of event names
Custom Dimensions Expose event parameter values
Explorations Build custom reports using your dimensions