1/** 2 * ========================================================================== 3 * TRACKING & ANALYTICS CONFIGURATION 4 * ========================================================================== 5 * File nà y chứa tất cả các tracking pixels và analytics code. 6 * Chá»nh sá»a các PIXEL_ID bên dưá»i Äá» kÃch hoạt tracking. 7 * 8 * Hưá»ng dẫn: 9 * 1. Thay thế 'YOUR_GTM_ID' bằng GTM Container ID (VD: GTM-XXXXXXX) 10 * 2. Thay thế 'YOUR_FB_PIXEL_ID' bằng Facebook Pixel ID 11 * 3. Thay thế 'YOUR_TIKTOK_PIXEL_ID' bằng TikTok Pixel ID 12 * 4. Thay thế 'YOUR_ZALO_OA_ID' bằng Zalo OA ID 13 * 14 * Äá» tắt má»t pixel, Äặt giá trá» là null hoặc '' 15 * ========================================================================== 16 */ 17 18const TRACKING_CONFIG = { 19 // Google Tag Manager - Quản lý tất cả tags táºp trung 20 gtm: { 21 enabled: true, 22 containerId: 'GTM-NZCL5K4D' 23 }, 24 25 // Facebook/Meta Pixel 26 facebook: { 27 enabled: true, 28 pixelId: '1211977667584398' 29 }, 30 31 // TikTok Pixel 32 tiktok: { 33 enabled: true, 34 pixelId: 'D64OLVBC77UBD797DEVG' 35 }, 36 37 // Zalo Chat Widget 38 zalo: { 39 enabled: false, // Äặt true khi có OA ID 40 oaId: 'YOUR_ZALO_OA_ID', 41 welcomeMessage: 'Xin chà o! Mình có thá» giúp gì cho bạn?', 42 autoPopup: 0, // 0 = tắt, 1 = báºt 43 width: 350, 44 height: 420 45 }, 46 47 // Google Analytics 4 (nếu không dùng GTM) 48 ga4: { 49 enabled: true, 50 measurementId: 'G-NPYN1GBYQS' // VD: G-XXXXXXXXXX 51 } 52}; 53 54// ========================================================================== 55// TRACKING INITIALIZATION - Không cần chá»nh sá»a phần dưá»i 56// ========================================================================== 57 58(function () { 59 'use strict'; 60 61 // Helper: Load external script 62 function loadScript(src, callback) { 63 const script = document.createElement('script'); 64 script.src = src; 65 script.async = true; 66 if (callback) script.onload = callback; 67 document.head.appendChild(script); 68 } 69 70 // ========================================================================== 71 // 1. GOOGLE TAG MANAGER 72 // ========================================================================== 73 if (TRACKING_CONFIG.gtm.enabled && TRACKING_CONFIG.gtm.containerId !== 'YOUR_GTM_ID') { 74 (function (w, d, s, l, i) { 75 w[l] = w[l] || []; 76 w[l].push({ 'gtm.start': new Date().getTime(), event: 'gtm.js' }); 77 var f = d.getElementsByTagName(s)[0], 78 j = d.createElement(s), 79 dl = l != 'dataLayer' ? '&l=' + l : ''; 80 j.async = true; 81 j.src = 'https://www.googletagmanager.com/gtm.js?id=' + i + dl; 82 f.parentNode.insertBefore(j, f); 83 })(window, document, 'script', 'dataLayer', TRACKING_CONFIG.gtm.containerId); 84 85 // Add noscript iframe for GTM 86 document.addEventListener('DOMContentLoaded', function () { 87 const noscript = document.createElement('noscript'); 88 const iframe = document.createElement('iframe'); 89 iframe.src = 'https://www.googletagmanager.com/ns.html?id=' + TRACKING_CONFIG.gtm.containerId; 90 iframe.height = '0'; 91 iframe.width = '0'; 92 iframe.style.display = 'none'; 93 iframe.style.visibility = 'hidden'; 94 noscript.appendChild(iframe); 95 document.body.insertBefore(noscript, document.body.firstChild); 96 }); 97 98 console.log('â GTM initialized:', TRACKING_CONFIG.gtm.containerId); 99 } 100 101 // ========================================================================== 102 // 2. FACEBOOK PIXEL 103 // ========================================================================== 104 if (TRACKING_CONFIG.facebook.enabled && TRACKING_CONFIG.facebook.pixelId !== 'YOUR_FB_PIXEL_ID') { 105 !function (f, b, e, v, n, t, s) { 106 if (f.fbq) return; 107 n = f.fbq = function () { n.callMethod ? n.callMethod.apply(n, arguments) : n.queue.push(arguments) }; 108 if (!f._fbq) f._fbq = n; 109 n.push = n; n.loaded = !0; n.version = '2.0'; n.queue = []; 110 t = b.createElement(e); t.async = !0; 111 t.src = v; s = b.getElementsByTagName(e)[0]; 112 s.parentNode.insertBefore(t, s); 113 }(window, document, 'script', 'https://connect.facebook.net/en_US/fbevents.js'); 114 115 fbq('init', TRACKING_CONFIG.facebook.pixelId); 116 fbq('track', 'PageView'); 117 118 // Add noscript pixel 119 document.addEventListener('DOMContentLoaded', function () { 120 const noscript = document.createElement('noscript'); 121 const img = document.createElement('img'); 122 img.height = 1; 123 img.width = 1; 124 img.style.display = 'none'; 125 img.src = 'https://www.facebook.net/tr?id=' + TRACKING_CONFIG.facebook.pixelId + '&ev=PageView&noscript=1'; 126 noscript.appendChild(img); 127 document.body.appendChild(noscript); 128 }); 129 130 console.log('â Facebook Pixel initialized:', TRACKING_CONFIG.facebook.pixelId); 131 } 132 133 // ========================================================================== 134 // 3. TIKTOK PIXEL 135 // ========================================================================== 136 if (TRACKING_CONFIG.tiktok.enabled && TRACKING_CONFIG.tiktok.pixelId !== 'YOUR_TIKTOK_PIXEL_ID') { 137 !function (w, d, t) { 138 w.TiktokAnalyticsObject = t; 139 var ttq = w[t] = w[t] || []; 140 ttq.methods = ["page", "track", "identify", "instances", "debug", "on", "off", "once", "ready", "alias", "group", "enableCookie", "disableCookie"]; 141 ttq.setAndDefer = function (t, e) { t[e] = function () { t.push([e].concat(Array.prototype.slice.call(arguments, 0))) } }; 142 for (var i = 0; i < ttq.methods.length; i++) ttq.setAndDefer(ttq, ttq.methods[i]); 143 ttq.instance = function (t) { 144 for (var e = ttq._i[t] || [], n = 0; n < ttq.methods.length; n++) ttq.setAndDefer(e, ttq.methods[n]); 145 return e; 146 }; 147 ttq.load = function (e, n) { 148 var i = "https://analytics.tiktok.com/i18n/pixel/events.js"; 149 ttq._i = ttq._i || {}; ttq._i[e] = []; ttq._i[e]._u = i; 150 ttq._t = ttq._t || {}; ttq._t[e] = +new Date; 151 ttq._o = ttq._o || {}; ttq._o[e] = n || {}; 152 var o = document.createElement("script"); 153 o.type = "text/javascript"; o.async = !0; 154 o.src = i + "?sdkid=" + e + "&lib=" + t; 155 var a = document.getElementsByTagName("script")[0]; 156 a.parentNode.insertBefore(o, a); 157 }; 158 ttq.load(TRACKING_CONFIG.tiktok.pixelId); 159 ttq.page(); 160 }(window, document, 'ttq'); 161 162 console.log('â TikTok Pixel initialized:', TRACKING_CONFIG.tiktok.pixelId); 163 } 164 165 // ========================================================================== 166 // 4. ZALO CHAT WIDGET 167 // ========================================================================== 168 if (TRACKING_CONFIG.zalo.enabled && TRACKING_CONFIG.zalo.oaId !== 'YOUR_ZALO_OA_ID') { 169 document.addEventListener('DOMContentLoaded', function () { 170 // Create Zalo widget container 171 const zaloWidget = document.createElement('div'); 172 zaloWidget.className = 'zalo-chat-widget'; 173 zaloWidget.setAttribute('data-oaid', TRACKING_CONFIG.zalo.oaId); 174 zaloWidget.setAttribute('data-welcome-message', TRACKING_CONFIG.zalo.welcomeMessage); 175 zaloWidget.setAttribute('data-autopopup', TRACKING_CONFIG.zalo.autoPopup); 176 zaloWidget.setAttribute('data-width', TRACKING_CONFIG.zalo.width); 177 zaloWidget.setAttribute('data-height', TRACKING_CONFIG.zalo.height); 178 document.body.appendChild(zaloWidget); 179 180 // Load Zalo SDK 181 loadScript('https://sp.zalo.me/plugins/sdk.js'); 182 183 console.log('â Zalo Widget initialized:', TRACKING_CONFIG.zalo.oaId); 184 }); 185 } 186 187 // ========================================================================== 188 // 5. GOOGLE ANALYTICS 4 (Standalone - nếu không dùng GTM) 189 // ========================================================================== 190 if (TRACKING_CONFIG.ga4.enabled && TRACKING_CONFIG.ga4.measurementId !== 'YOUR_GA4_ID') {
191 loadScript('https://www.googletagmanager.com/gtag/js?id=' + TRACKING_CONFIG.ga4.measurementId, function () { 192 window.dataLayer = window.dataLayer || []; 193 function gtag() { dataLayer.push(arguments); } 194 gtag('js', new Date()); 195 gtag('config', TRACKING_CONFIG.ga4.measurementId); 196 window.gtag = gtag; 197 198 console.log('â GA4 initialized:', TRACKING_CONFIG.ga4.measurementId); 199 }); 200 } 201 202 // ========================================================================== 203 // HELPER FUNCTIONS - Dùng Äá» track events 204 // ========================================================================== 205 window.TrackingHelper = { 206 // Track Facebook event 207 trackFB: function (eventName, params) { 208 if (typeof fbq !== 'undefined') { 209 fbq('track', eventName, params); 210 } 211 }, 212 213 // Track TikTok event 214 trackTikTok: function (eventName, params) { 215 if (typeof ttq !== 'undefined') { 216 ttq.track(eventName, params); 217 } 218 }, 219 220 // Track GA4 event 221 trackGA4: function (eventName, params) { 222 if (typeof gtag !== 'undefined') { 223 gtag('event', eventName, params); 224 } 225 }, 226 227 // Track all platforms at once 228 trackAll: function (eventName, params) { 229 this.trackFB(eventName, params); 230 this.trackTikTok(eventName, params); 231 this.trackGA4(eventName, params); 232 } 233 }; 234 235 // Log tracking status 236 console.log('ð Tracking.js loaded. Config:', TRACKING_CONFIG); 237 238})();
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.