Cover image for project: NEXUS Google Analytics GA4 IN PROGRESS

Technical summary

NEXUS integration with Google Analytics 4: server-side forwarding of native events via Measurement Protocol (no third-party cookies) and metric queries through the Data API (OAuth 2.0) — with pseudonymized client_id (SHA-256 + salt), property sanitization (no PII), selectable forwarding events, a dashboard with users/sessions/pageviews, realtime, top pages and PT/EN i18n.

Executed scope

  • plugin.json: v1.0.0, "Monitoring" category (SEO & Marketing tab, bar-chart-3 icon).
  • Server-side gateway via hook: PluginManager::registerFilter('after_track_event', 'ga4_on_after_track_event') — the core tracks events and the plugin re-forwards them to GA4 without third-party cookies (only one in the series with a core-event filter).
  • Default forwardable events (ga4_default_forward_events): page_view, login_success, login_failure, task_created, task_completed, comment_added, ai_explain_used, plugin_activated, onboarding_step — configurable list.
  • ga4_forward_event — only forwards with enabled + forward_enabled + mp_ready and the event in the allowlist; name normalized to 40 chars ([a-z0-9_]), engagement_time_msec=1, optional nexus_session_id.
  • ga4_mp_collect — POST to https://www.google-analytics.com/mp/collect?measurement_id={G-…}&api_secret={secret} (/debug/mp/collect endpoint for validation with validationMessages); 8s timeout; success = 2xx with empty body; handles VALUE_INVALID/NAME_INVALID in debug.
  • ga4_client_id — pseudonymization: sha256(site_salt | user|session) converted to GA4 digits.digits (two 8-char hexdec blocks); site_salt generated with random_bytes(16) on first load and persisted.
  • ga4_sanitize_properties — anti-PII deny list (password, passwd, secret, token, api_key, authorization, cookie, csrf, session, content, text, body, description, comment, comment_text, title, email, phone, cpf, cnpj); strings capped at 100 chars; keys normalized to 40 chars; arrays become JSON if ≤ 200 chars.
  • Settings (plugin.google_analytics.config via DB::setConfig): measurement_id validated by ^G-[A-Z0-9]+$ regex (i18n error if invalid), api_secret only updates when non-empty (max 200), property_id digits only (max 20), oauth_client_id/secret (max 500), oauth_refresh_token (clears the access token on save), enabled/forward_enabled/client_tracking/dedupe_client/anonymize toggles, forward_events list.
  • No dedicated MySQL table: config and 24h stats (forwarded_total, forwarded_day, forwarded_today, last_forward_at, last_error, last_error_at) live in the config — first in the series without its own DDL.
  • ga4_stats — api_online, mp_ready, oauth_ready, forward counters, last error, public config (no secrets) and available_events.
  • ga4_test_connection — requires mp_ready; sends the nexus_connection_test event through the debug endpoint (and fires a real collect so it appears in Realtime); returns oauth_note (ready/pending).
  • OAuth 2.0 (ga4_oauth_token) — refresh token at https://oauth2.googleapis.com/token (12s timeout); cached access_token until expires_in, renewing with < 60s margin.
  • Data API (ga4_data_api_run) — POST https://analyticsdata.googleapis.com/v1beta/properties/{propertyId}:runReport|:runRealtimeReport with Bearer; 20s timeout; oauth_pending when credentials are missing.
  • ga4_report — activeUsers, sessions, screenPageViews per day (range 7daysAgo/today + totals).
  • ga4_realtime — activeUsers by unifiedScreenName (limit 10).
  • ga4_top_pages — screenPageViews by pagePath (limit 1–50).
  • API: 7 actions (ga4_stats, ga4_settings_get, ga4_settings_save, ga4_test_connection, ga4_report, ga4_realtime, ga4_top_pages).
  • Alpine.js UI (tab.php, 564 lines) — blue theme (blue-600), bar-chart-3 icon, SEO & Marketing tab; 3 sub-tabs (Dashboard, Events, Settings); 4 KPI cards (Forwarded Today, Total Forward, MP Configured, OAuth Data API); Forward Online / MP Ready / Offline badge with settings shortcut; last forward error alert; Chart.js line chart (3 series in #2563eb/#059669/#d97706 — users, sessions, pageviews) plus realtime and top pages panels; Events tab with forwarding event checkboxes; Settings tab with two guide blocks (Measurement ID + API Secret in 6 steps; OAuth/Data API in 7 steps with Property ID, Client ID, Client Secret, Refresh Token); secret fields as password with "(already configured — leave empty to keep)" hints; Test connection button with feedback.
  • Own i18n — lang.json (pt_BR/en_US) loaded via nexusRegisterPluginI18n + nx_load_dictionary; UI uses window.t() and __() (with fallback); first in the series with its own dictionary.
  • Fastr: /ga4 → ga4_stats (summary, optional argument; i18n description).
  • Cron: cronjob.json exists but with jobs: [] and note "Plugin sob demanda; nenhuma rotina periódica segura ou necessária" — on-demand.
  • client_tracking (browser gtag.js) off by default — forwarding is server-side; secrets are never exposed to the frontend (ga4_public_config only exposes flags and *_configured).

Stack and tools

  • PHP 8 (no framework)
  • MySQL 8 (no dedicated table — config + stats in plugin.google_analytics.config)
  • Alpine.js + Tailwind CSS (premium light, blue) + Chart.js (3-series line)
  • Measurement Protocol (google-analytics.com/mp/collect + /debug/mp/collect)
  • Google Analytics Data API v1beta (runReport / runRealtimeReport, OAuth 2.0)
  • cURL (MP 8s, OAuth 12s, Data API 20s)
  • Own i18n (lang.json + nx_load_dictionary)

Operational tags

  • Google Analytics
  • GA4
  • Measurement Protocol
  • Data API
  • Event Tracking
  • SEO & Marketing
  • OAuth
  • Plugin NEXUS

Operational result

  • Native NEXUS events (page_view, task_created, login_success…) in GA4 without gtag.js in the browser — a server-side gateway with no third-party cookies.
  • Privacy: pseudonymized client_id (SHA-256 + salt) and anti-PII sanitization before sending.
  • Analytics dashboard: users, sessions and pageviews over the last 7 days (chart), realtime and top pages via the Data API.
  • Automatic OAuth: the refresh token renews the access token with caching (no intervention).
  • Fine control: select which events to forward + toggles (forward, plugin, anonymize).
  • PT/EN i18n and the /ga4 chat command.
  • On-demand: no cron, no periodic processing cost.

GitHub progress (issues)

Real-time panel with latest repository issues.

abertas (amostra): -- fechadas (amostra): -- base: -- ultimas issues

carregando andamento...

Real results

Official telemetry and audience analytics integration with Google Analytics 4. Tracks page views, engagement events, active sessions, and conversions in real-time directly inside the NEXUS executive dashboard.

Architecture and organization

Execution and operations

The project follows reproducible execution flow with technical validation in production-like environments.

Screenshots

Talk about this project

Apply this implementation pattern in your environment and accelerate delivery with technical consistency.