diff --git a/.env.example b/.env.example index 6e7ebc7ba..ec3bd6f8a 100644 --- a/.env.example +++ b/.env.example @@ -84,6 +84,9 @@ NEXT_PUBLIC_E2B_DOMAIN=e2b.dev ### OPTIONAL CLIENT ENVIRONMENT VARIABLES ### ================================= +### Google Tag Manager container ID (set in production only) +# NEXT_PUBLIC_GTM_ID= + ### PostHog analytics project key # NEXT_PUBLIC_POSTHOG_KEY= diff --git a/bun.lock b/bun.lock index f2bbbc88d..b7e9eadad 100644 --- a/bun.lock +++ b/bun.lock @@ -9,6 +9,7 @@ "@launchdarkly/node-server-sdk": "^9.11.2", "@launchdarkly/openfeature-node-server": "^1.2.0", "@next/env": "^16.2.7", + "@next/third-parties": "^16.2.10", "@openfeature/server-sdk": "^1.22.0", "@opentelemetry/api": "^1.9.0", "@opentelemetry/auto-instrumentations-node": "^0.77.0", @@ -433,6 +434,8 @@ "@next/swc-win32-x64-msvc": ["@next/swc-win32-x64-msvc@16.2.7", "", { "os": "win32", "cpu": "x64" }, "sha512-J4WlM72NMk076Qsg0jTdK3SNXatlSdnjW7L7oNGLst1tAGjHrJh/FYi+pw9wyIjEtGRKDNzD0zuiY16oWYWVaw=="], + "@next/third-parties": ["@next/third-parties@16.2.10", "", { "dependencies": { "third-party-capital": "1.0.20" }, "peerDependencies": { "next": "^13.0.0 || ^14.0.0 || ^15.0.0 || ^16.0.0-beta.0", "react": "^18.2.0 || 19.0.0-rc-de68d2f4-20241204 || ^19.0.0" } }, "sha512-H3yxCMLziM1JKXnjQv83WBH2cp1fB1vMxpC1/bBTpvvaesBEuRuprpzq5RI32atis0VhUZflgdpJdGNZIGpQaQ=="], + "@openfeature/core": ["@openfeature/core@1.11.0", "", {}, "sha512-P0u3/ht/oZCQT89fOed+laLk0kZR529a825cS02uPDglxXbE97irWYpDAeRGGVETIzKfuy+H2g8c3Ccv/tXJNQ=="], "@openfeature/server-sdk": ["@openfeature/server-sdk@1.22.0", "", { "peerDependencies": { "@openfeature/core": "^1.11.0" } }, "sha512-YBrf6SQkn0FNB/dRAtLEs41dvFMUE8CrQTwI+iLaMFUIqWlqGNJfGnulKSneEKS+2OgKTAC6DdmKcZ6tK7kBcg=="], @@ -1877,6 +1880,8 @@ "test-exclude": ["test-exclude@7.0.1", "", { "dependencies": { "@istanbuljs/schema": "^0.1.2", "glob": "^10.4.1", "minimatch": "^9.0.4" } }, "sha512-pFYqmTw68LXVjeWJMST4+borgQP2AyMNbg1BpZh9LbyhUeNkeaPF9gzfPGUAnSMV3qPYdWUwDIjjCLiSDOl7vg=="], + "third-party-capital": ["third-party-capital@1.0.20", "", {}, "sha512-oB7yIimd8SuGptespDAZnNkzIz+NWaJCu2RMsbs4Wmp9zSDUM8Nhi3s2OOcqYuv3mN4hitXc8DVx+LyUmbUDiA=="], + "thread-stream": ["thread-stream@3.1.0", "", { "dependencies": { "real-require": "^0.2.0" } }, "sha512-OqyPZ9u96VohAyMfJykzmivOrY2wfMSf3C5TtFJVgN+Hm6aj+voFhlK+kZEIv2FBh1X6Xp3DlnCOfEQ3B2J86A=="], "tiny-invariant": ["tiny-invariant@1.3.3", "", {}, "sha512-+FbBPE1o9QAYvviau/qC5SE3caw21q3xkvWKBtja5vgqOWIHHJ3ioaq1VPfn/Szqctz2bU/oYeKd9/z5BL+PVg=="], diff --git a/package.json b/package.json index 8cbf4a59c..a95b18646 100644 --- a/package.json +++ b/package.json @@ -49,6 +49,7 @@ "@launchdarkly/node-server-sdk": "^9.11.2", "@launchdarkly/openfeature-node-server": "^1.2.0", "@next/env": "^16.2.7", + "@next/third-parties": "^16.2.10", "@openfeature/server-sdk": "^1.22.0", "@opentelemetry/api": "^1.9.0", "@opentelemetry/auto-instrumentations-node": "^0.77.0", diff --git a/src/app/body.tsx b/src/app/body.tsx index a39a4383c..911994f0b 100644 --- a/src/app/body.tsx +++ b/src/app/body.tsx @@ -2,7 +2,6 @@ import { useParams } from 'next/navigation' import type { ReactNode } from 'react' -import { GTMBody } from '@/features/google-tag-manager' import { cn } from '@/lib/utils' export function Body({ @@ -14,7 +13,6 @@ export function Body({ return ( - {children} ) diff --git a/src/app/layout.tsx b/src/app/layout.tsx index 37fa52ef4..1715483f7 100644 --- a/src/app/layout.tsx +++ b/src/app/layout.tsx @@ -1,14 +1,13 @@ import '@/app/fonts' import '@/styles/globals.css' +import { GoogleTagManager } from '@next/third-parties/google' import { Analytics } from '@vercel/analytics/next' import { SpeedInsights } from '@vercel/speed-insights/next' -import Head from 'next/head' import type { Metadata } from 'next/types' import { Suspense } from 'react' import { getFaviconIcons } from '@/configs/favicon' import ClientProviders from '@/features/client-providers' -import { GTMHead } from '@/features/google-tag-manager' import { Toaster } from '@/ui/primitives/toaster' import { Body } from './body' @@ -36,12 +35,11 @@ export default function RootLayout({ }) { const postHogEnabled = !!process.env.NEXT_PUBLIC_POSTHOG_KEY const postHogEnvironment = getPostHogEnvironment() + const gtmId = process.env.NEXT_PUBLIC_GTM_ID return ( - - - + {gtmId && } - {` - (function(w,d,s,l,i){w[l]=w[l]||[];w[l].push({'gtm.start': - new Date().getTime(),event:'gtm.js'});var f=d.getElementsByTagName(s)[0], - j=d.createElement(s),dl=l!='dataLayer'?'&l='+l:'';j.async=true;j.src= - 'https://www.googletagmanager.com/gtm.js?id='+i+dl;f.parentNode.insertBefore(j,f); - })(window,document,'script','dataLayer','GTM-K2W3LVD2'); - `} - - ) -} - -function GTMBody() { - if (process.env.NODE_ENV !== 'production') return null - - return ( -