Overview
Google Tag Manager (GTM) provides centralized tag management for:
- Google Analytics (GA4 and UA)
- Meta Pixel / Facebook Pixel
- Google Ads conversion tracking
- Third-party marketing pixels
- Custom JavaScript and HTML tags
Benefits:
- No code changes needed to add/update tags
- Version control for tag configurations
- Preview mode for testing before publishing
- User permissions for team collaboration
Prerequisites
- Google Tag Manager account
- GTM Container ID (format: GTM-XXXXXXX)
- OpenCart admin access
- Basic understanding of GTM interface
Installation Methods
Method 1: Manual Installation (Recommended)
Most reliable method with direct code insertion.
1. Get GTM Container Code
- Log in to Google Tag Manager
- Select your container
- Click Admin (top right)
- Click Install Google Tag Manager
- Copy both code snippets:
- Head code snippet
- Body code snippet
2. Add Head Code to OpenCart
File: catalog/view/theme/[your-theme]/template/common/header.twig
Add immediately after the opening <head> tag:
<head>
<!-- Google Tag Manager -->
<script>(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-XXXXXXX');</script>
<!-- End Google Tag Manager -->
{# Rest of head content #}
Replace GTM-XXXXXXX with your actual container ID.
3. Add Body Code to OpenCart
Add immediately after the opening <body> tag:
<body>
<!-- Google Tag Manager (noscript) -->
<noscript><iframe src="https://www.googletagmanager.com/ns.html?id=GTM-XXXXXXX"
height="0" width="0" style="display:none;visibility:hidden"></iframe></noscript>
<!-- End Google Tag Manager (noscript) -->
{# Rest of body content #}
4. Clear Cache
Admin Panel > Dashboard > Blue gear icon > Clear cache
Method 2: OCMOD Installation
For update-proof installation across theme changes.
Create OCMOD File
File: gtm-installation.ocmod.xml
<?xml version="1.0" encoding="utf-8"?>
<modification>
<name>Google Tag Manager Installation</name>
<code>google_tag_manager</code>
<version>1.0</version>
<author>Your Name</author>
<link>https://yourwebsite.com</link>
<!-- Add GTM Head Code -->
<file path="catalog/view/theme/*/template/common/header.twig">
<operation>
<search><![CDATA[<head>]]></search>
<add position="after"><![CDATA[
<!-- Google Tag Manager -->
<script>(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-XXXXXXX');</script>
<!-- End Google Tag Manager -->
]]></add>
</operation>
</file>
<!-- Add GTM Body Code -->
<file path="catalog/view/theme/*/template/common/header.twig">
<operation>
<search><![CDATA[<body]]></search>
<add position="after"><![CDATA[>
<!-- Google Tag Manager (noscript) -->
<noscript><iframe src="https://www.googletagmanager.com/ns.html?id=GTM-XXXXXXX"
height="0" width="0" style="display:none;visibility:hidden"></iframe></noscript>
<!-- End Google Tag Manager (noscript) -->
]]></add>
</operation>
</file>
</modification>
Note: The body operation searches for <body and adds after > to handle cases where body tag has attributes.
Install OCMOD
Upload
Admin Panel > Extensions > Installer Click Upload button Select gtm-installation.ocmod.xmlRefresh Modifications
Admin Panel > Extensions > Modifications Click Refresh button (blue circular arrow icon)Clear Cache
Admin Panel > Dashboard > Blue gear icon > Clear cache
Method 3: Controller-Based Installation
For dynamic container management via admin panel.
1. Create Extension Controller
File: admin/controller/extension/analytics/google_tag_manager.php
<?php
class ControllerExtensionAnalyticsGoogleTagManager extends Controller {
private $error = array();
public function index() {
$this->load->language('extension/analytics/google_tag_manager');
$this->document->setTitle($this->language->get('heading_title'));
$this->load->model('setting/setting');
if (($this->request->server['REQUEST_METHOD'] == 'POST') && $this->validate()) {
$this->model_setting_setting->editSetting('analytics_google_tag_manager', $this->request->post);
$this->session->data['success'] = $this->language->get('text_success');
$this->response->redirect($this->url->link('marketplace/extension', 'user_token=' . $this->session->data['user_token'] . '&type=analytics', true));
}
$data['heading_title'] = $this->language->get('heading_title');
$data['text_edit'] = $this->language->get('text_edit');
$data['entry_container'] = $this->language->get('entry_container');
$data['entry_status'] = $this->language->get('entry_status');
$data['button_save'] = $this->language->get('button_save');
$data['button_cancel'] = $this->language->get('button_cancel');
if (isset($this->error['warning'])) {
$data['error_warning'] = $this->error['warning'];
} else {
$data['error_warning'] = '';
}
if (isset($this->error['container'])) {
$data['error_container'] = $this->error['container'];
} else {
$data['error_container'] = '';
}
if (isset($this->request->post['analytics_google_tag_manager_container'])) {
$data['analytics_google_tag_manager_container'] = $this->request->post['analytics_google_tag_manager_container'];
} else {
$data['analytics_google_tag_manager_container'] = $this->config->get('analytics_google_tag_manager_container');
}
if (isset($this->request->post['analytics_google_tag_manager_status'])) {
$data['analytics_google_tag_manager_status'] = $this->request->post['analytics_google_tag_manager_status'];
} else {
$data['analytics_google_tag_manager_status'] = $this->config->get('analytics_google_tag_manager_status');
}
$data['action'] = $this->url->link('extension/analytics/google_tag_manager', 'user_token=' . $this->session->data['user_token'], true);
$data['cancel'] = $this->url->link('marketplace/extension', 'user_token=' . $this->session->data['user_token'] . '&type=analytics', true);
$data['header'] = $this->load->controller('common/header');
$data['column_left'] = $this->load->controller('common/column_left');
$data['footer'] = $this->load->controller('common/footer');
$this->response->setOutput($this->load->view('extension/analytics/google_tag_manager', $data));
}
protected function validate() {
if (!$this->user->hasPermission('modify', 'extension/analytics/google_tag_manager')) {
$this->error['warning'] = $this->language->get('error_permission');
}
if (!$this->request->post['analytics_google_tag_manager_container']) {
$this->error['container'] = $this->language->get('error_container');
} elseif (!preg_match('/^GTM-[A-Z0-9]+$/', $this->request->post['analytics_google_tag_manager_container'])) {
$this->error['container'] = $this->language->get('error_container_format');
}
return !$this->error;
}
}
2. Create Frontend Controller
File: catalog/controller/extension/analytics/google_tag_manager.php
<?php
class ControllerExtensionAnalyticsGoogleTagManager extends Controller {
public function index() {
if ($this->config->get('analytics_google_tag_manager_status')) {
$data['google_tag_manager_container'] = $this->config->get('analytics_google_tag_manager_container');
return $this->load->view('extension/analytics/google_tag_manager', $data);
}
return '';
}
}
3. Create View Template
File: catalog/view/theme/default/template/extension/analytics/google_tag_manager.twig
<!-- Google Tag Manager -->
<script>(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','{{ google_tag_manager_container }}');</script>
<!-- End Google Tag Manager -->
4. Load in Header
File: catalog/controller/common/header.php
Add to index() method:
// Google Tag Manager
$data['analytics_google_tag_manager'] = $this->load->controller('extension/analytics/google_tag_manager');
File: catalog/view/theme/[your-theme]/template/common/header.twig
Add after opening <head> tag:
<head>
{{ analytics_google_tag_manager }}
{# Rest of head content #}
Method 4: Extension from OpenCart Marketplace
Several GTM extensions are available:
Recommended Extensions:
- Google Tag Manager by iSenseLabs - Full GTM integration with data layer
- GTM Pro by Opencart.Expert - Enhanced GTM with ecommerce events
Installation:
1. Purchase from OpenCart Marketplace
2. Admin Panel > Extensions > Installer > Upload
3. Admin Panel > Extensions > Extensions > Analytics
4. Install and Configure extension
Verification
1. Check Source Code
- Visit your OpenCart store
- Right-click and select View Page Source (Ctrl+U)
- Search for
GTM-(Ctrl+F) - Verify both head and body codes are present
2. Google Tag Assistant
Install [Tag Assistant Legacy](https://chrome.google.com/webstore/detail/tag-assistant-legacy-by-g/kejbdjndbnbjgmefkgdddjlboko fpmj)
- Visit your store
- Click Tag Assistant icon
- Click Enable and refresh page
- Verify GTM tag is detected with green status
3. GTM Preview Mode
Most reliable verification method:
- In GTM, click Preview (top right)
- Enter your store URL
- Click Connect
- New window opens with debugger
- Verify:
- Container loaded successfully
- Tags are firing (if configured)
- dataLayer variables are present
4. Browser Console Check
// Open console (F12)
console.log(dataLayer); // Should show dataLayer array
console.log(google_tag_manager); // Should show GTM object
Multi-Store Configuration
For OpenCart multi-store setups:
Option 1: Single Container (Recommended)
Use one GTM container for all stores:
<!-- Same container for all stores -->
<script>
(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-XXXXXXX');
// Add store identifier to dataLayer
dataLayer.push({
'storeName': '{{ config_name }}',
'storeId': '{{ config_store_id }}',
'storeCurrency': '{{ currency }}'
});
</script>
Use GTM triggers to filter tags by store.
Option 2: Separate Containers Per Store
Different container for each store:
File: catalog/controller/common/header.php
// Get store-specific GTM container
$store_id = $this->config->get('config_store_id');
switch ($store_id) {
case 1:
$data['gtm_container'] = 'GTM-STORE1';
break;
case 2:
$data['gtm_container'] = 'GTM-STORE2';
break;
default:
$data['gtm_container'] = 'GTM-DEFAULT';
}
GDPR Consent Integration
Delay GTM loading until consent is granted:
With Consent Management Platform
File: catalog/view/theme/[your-theme]/template/common/header.twig
<head>
<script>
// Wait for consent before loading GTM
function loadGTM() {
(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-XXXXXXX');
}
// Check consent (example with Cookiebot)
window.addEventListener('CookiebotOnAccept', function() {
if (Cookiebot.consent.marketing) {
loadGTM();
}
});
// If consent already given
if (typeof Cookiebot !== 'undefined' && Cookiebot.consent.marketing) {
loadGTM();
}
</script>
Google Consent Mode v2
Implement Consent Mode for better compliance:
<script>
// Default consent state
window.dataLayer = window.dataLayer || [];
function gtag(){dataLayer.push(arguments);}
gtag('consent', 'default', {
'ad_storage': 'denied',
'ad_user_data': 'denied',
'ad_personalization': 'denied',
'analytics_storage': 'denied'
});
// Load GTM
(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-XXXXXXX');
// Update consent when user accepts
function updateConsent() {
gtag('consent', 'update', {
'ad_storage': 'granted',
'ad_user_data': 'granted',
'ad_personalization': 'granted',
'analytics_storage': 'granted'
});
}
</script>
Troubleshooting
GTM Not Loading
Problem: GTM container doesn't appear in Tag Assistant
Solutions:
- Check container ID format (must be GTM-XXXXXXX)
- Verify code is after
<head>opening tag - Clear browser cache and cookies
- Check for JavaScript errors in console
- Verify no ad blockers are active
- Test in incognito mode
Code Appears in Wrong Location
Problem: GTM code visible on page or in wrong position
Solutions:
- Verify code is inside
<head>tags, not in content area - Check OCMOD search string is correct
- Refresh modifications and clear cache
- Manually verify template file modifications
dataLayer Not Defined
Problem: Console shows "dataLayer is not defined"
Solutions:
- Ensure GTM code loads before any dataLayer.push() calls
- Initialize dataLayer before GTM:
<script> window.dataLayer = window.dataLayer || []; </script> - Check GTM head code is complete
Tags Not Firing
Problem: GTM loads but tags don't fire
Solutions:
- Use GTM Preview mode to debug
- Check tag triggers are configured correctly
- Verify required dataLayer variables exist
- Check tag firing conditions in GTM
- Look for JavaScript errors blocking execution
Multiple GTM Containers
Problem: Two or more GTM containers detected
Solutions:
- Search theme files for duplicate GTM code
- Check both manual and extension installations
- Review active OCMODs for duplicates
- Check parent theme if using child theme
Performance Optimization
Defer GTM Loading
For better page speed scores:
<script>
// Load GTM after page load
window.addEventListener('load', function() {
(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-XXXXXXX');
});
</script>
Note: This may delay tag firing. Test thoroughly.
Server-Side GTM (Advanced)
For maximum performance and accuracy:
- Implement GTM Server-Side tagging
- Requires Google Cloud setup
- Better for iOS 14+ tracking
- Improved page speed
- Enhanced security