diff --git a/apps/web/Dockerfile b/apps/web/Dockerfile index cec4a4b..205de65 100644 --- a/apps/web/Dockerfile +++ b/apps/web/Dockerfile @@ -15,7 +15,11 @@ FROM node:20-alpine AS builder WORKDIR /workspace ARG NEXT_PUBLIC_API_BASE_URL=http://localhost:4000 +ARG NEXT_PUBLIC_MATOMO_URL +ARG NEXT_PUBLIC_MATOMO_SITE_ID ENV NEXT_PUBLIC_API_BASE_URL=${NEXT_PUBLIC_API_BASE_URL} +ENV NEXT_PUBLIC_MATOMO_URL=${NEXT_PUBLIC_MATOMO_URL} +ENV NEXT_PUBLIC_MATOMO_SITE_ID=${NEXT_PUBLIC_MATOMO_SITE_ID} COPY --from=deps /workspace/node_modules ./node_modules COPY package.json package-lock.json tsconfig.base.json ./ diff --git a/apps/web/components/MatomoScript.tsx b/apps/web/components/MatomoScript.tsx index 0975016..e462006 100644 --- a/apps/web/components/MatomoScript.tsx +++ b/apps/web/components/MatomoScript.tsx @@ -1,6 +1,6 @@ 'use client'; -import { useEffect } from 'react'; +import Script from 'next/script'; /** * Matomo Analytics Script Component @@ -11,40 +11,33 @@ import { useEffect } from 'react'; * - NEXT_PUBLIC_MATOMO_SITE_ID: Site ID in Matomo (e.g., 9) */ export function MatomoScript() { - useEffect(() => { - // Check if Matomo is properly configured - const matomoUrl = process.env.NEXT_PUBLIC_MATOMO_URL?.trim(); - const matomoSiteId = process.env.NEXT_PUBLIC_MATOMO_SITE_ID?.trim(); + // Check if Matomo is properly configured + const matomoUrl = process.env.NEXT_PUBLIC_MATOMO_URL?.trim(); + const matomoSiteId = process.env.NEXT_PUBLIC_MATOMO_SITE_ID?.trim(); - // Skip if not configured - if (!matomoUrl || !matomoSiteId) { - if (process.env.NODE_ENV === 'development') { - console.debug('[Matomo] Not configured. Skipping analytics.'); - } - return; - } + // Skip if not configured + if (!matomoUrl || !matomoSiteId) { + return null; + } - // Initialize Matomo tracking array - (window as any)._paq = (window as any)._paq || []; - const _paq = (window as any)._paq; - - // Set up tracking + // Inline script that will be executed immediately + const matomoCode = ` + var _paq = window._paq = window._paq || []; _paq.push(['trackPageView']); _paq.push(['enableLinkTracking']); - _paq.push(['setTrackerUrl', `${matomoUrl}matomo.php`]); - _paq.push(['setSiteId', matomoSiteId]); + _paq.push(['setTrackerUrl', '${matomoUrl}matomo.php']); + _paq.push(['setSiteId', '${matomoSiteId}']); + (function() { + var d=document, g=d.createElement('script'), s=d.getElementsByTagName('script')[0]; + g.async=true; g.src='${matomoUrl}matomo.js'; s.parentNode.insertBefore(g,s); + })(); + `; - // Inject the Matomo script - const script = document.createElement('script'); - script.async = true; - script.src = `${matomoUrl}matomo.js`; - script.defer = true; - - const firstScript = document.getElementsByTagName('script')[0]; - if (firstScript && firstScript.parentNode) { - firstScript.parentNode.insertBefore(script, firstScript); - } - }, []); - - return null; + return ( +