Compare commits

..

2 Commits

Author SHA1 Message Date
97c3927998 [Bump] metadata + changelog 2024-04-11 10:28:06 +02:00
cbe3293ff1 [Fixed] potential error
if no basket-component is given, error occurs
2024-04-11 10:10:59 +02:00
37 changed files with 368 additions and 1549 deletions

View File

@ -1,15 +0,0 @@
<?php
declare(strict_types=1);
namespace D3\GoogleAnalytics4\Application\Component\Widget;
class d3GtmStartWidget extends \OxidEsales\Eshop\Application\Component\Widget\WidgetController
{
public function render()
{
parent::render();
return '';
}
}

View File

@ -1,85 +0,0 @@
<?php
declare(strict_types=1);
namespace D3\GoogleAnalytics4\Application\Controller\Admin;
use D3\GoogleAnalytics4\Application\Model\Constants;
use D3\GoogleAnalytics4\Application\Model\ManagerHandler;
use D3\GoogleAnalytics4\Application\Model\ManagerTypes;
use OxidEsales\Eshop\Core\Registry;
use OxidEsales\Eshop\Core\ViewConfig;
class GA4AdminUserInterface_main extends \OxidEsales\Eshop\Application\Controller\Admin\AdminDetailsController
{
protected $_sThisTemplate = 'ga4/admin/d3ga4uimain.tpl';
public function render()
{
$return = parent::render();
$this->addTplParam('d3ViewObject', $this);
$this->addTplParam('d3ViewConfObject', Registry::get(ViewConfig::class));
$this->addTplParam('d3ManagerTypeArray', oxNew(ManagerTypes::class)->getManagerList());
$this->addTplParam('d3CurrentCMP', oxNew(ManagerHandler::class)->getCurrManager());
return $return;
}
public function save()
{
parent::save();
$aParams = Registry::getRequest()->getRequestEscapedParameter('editval');
$aCheckBoxParams = [
'_blEnableGa4',
'_blEnableDebug',
'_blEnableConsentMode',
'_blEnableOwnCookieManager',
'_blEnableMeasurementCapabilities',
'_blEnableUsercentricsConsentModeApi',
];
foreach ($aCheckBoxParams as $checkBoxName){
if (isset($aParams['bool'][$checkBoxName])){
$aParams['bool'][$checkBoxName] = true;
}else{
$aParams['bool'][$checkBoxName] = false;
}
}
$this->d3SaveShopConfigVars($aParams);
}
/**
* @param array $aParams
* @return void
*/
protected function d3SaveShopConfigVars(array $aParams)
{
$oConfig = Registry::getConfig();
foreach ($aParams as $sConfigType => $aConfigParams) {
foreach ($aConfigParams as $sParamName => $sParamValue){
if($this->d3GetModuleConfigParam($sParamName) !== $sParamValue){
$oConfig->saveShopConfVar(
$sConfigType,
Constants::OXID_MODULE_ID.$sParamName,
$sParamValue,
$oConfig->getShopId(),
Constants::OXID_MODULE_ID
);
}
}
}
}
/**
* @param string $configParamName
* @return mixed
*/
public function d3GetModuleConfigParam(string $configParamName)
{
return Registry::get(ViewConfig::class)->d3GetModuleConfigParam($configParamName);
}
}

View File

@ -1,19 +0,0 @@
<?php
declare(strict_types=1);
namespace D3\GoogleAnalytics4\Application\Model\CMP;
abstract class ConsentManagementPlatformBaseModel extends \OxidEsales\Eshop\Core\Model\BaseModel implements ConsentManagementPlatformInterface
{
public string $sCMPName;
/**
* @return string
*/
public function getCMPName(): string
{
return $this->sCMPName;
}
}

View File

@ -1,8 +0,0 @@
<?php
namespace D3\GoogleAnalytics4\Application\Model\CMP;
interface ConsentManagementPlatformInterface
{
public function getCMPName();
}

View File

@ -1,25 +0,0 @@
<?php
declare(strict_types=1);
namespace D3\GoogleAnalytics4\Application\Model\CMP;
use D3\GoogleAnalytics4\Application\Model\ManagerTypes;
/**
* Used the OXID Module.
*
* Further information's:
* https://docs.oxid-esales.com/modules/usercentrics/de/latest/einfuehrung.html
*
* Usercentrics homepage:
* https://usercentrics.com
*/
class Usercentrics extends ConsentManagementPlatformBaseModel
{
const sExternalIncludationPublicName = "( Externe Einbindung ) Usercentrics";
const sExternalIncludationInternalName = "usercentrics";
const sModuleIncludationPublicName = "( Modul ) Usercentrics";
const sModuleIncludationInternalName = "oxps_usercentrics";
}

View File

@ -1,11 +0,0 @@
<?php
declare(strict_types=1);
namespace D3\GoogleAnalytics4\Application\Model;
class Constants
{
public const OXID_MODULE_ID = 'd3googleanalytics4';
}

View File

@ -8,8 +8,6 @@ use OxidEsales\Eshop\Core\ViewConfig;
class ManagerHandler
{
/**
* Gets current chosen Manager
*
* @return string
*/
public function getCurrManager() :string
@ -22,40 +20,21 @@ class ManagerHandler
$aManagerList = $oManagerTypes->getManagerList();
if ($this->getModuleSettingExplicitManagerSelectValue()){
foreach ($aManagerList as $managerName){
if ($oViewConfig->isModuleActive($managerName)){
return $managerName;
}
}
return $this->getExplicitManager();
}
foreach ($aManagerList as $shopModuleId => $publicCMPName){
if ($oViewConfig->isModuleActive($shopModuleId)){
$this->d3SaveShopConfVar($shopModuleId);
return $shopModuleId;
}
}
return "";
}
/**
* @param string $sParam
* @return void
*/
public function d3SaveShopConfVar(string $sParam){
Registry::getConfig()->saveShopConfVar(
'select',
Constants::OXID_MODULE_ID."_HAS_STD_MANAGER",
$sParam,
Registry::getConfig()->getShopId(),
Constants::OXID_MODULE_ID
);
}
/**
* @return string
*/
public function getModuleSettingExplicitManagerSelectValue() :string
{
return Registry::get(ViewConfig::class)->d3GetModuleConfigParam('_HAS_STD_MANAGER')?:"";
return Registry::getConfig()->getConfigParam('d3_gtm_settings_HAS_STD_MANAGER');
}
/**
@ -67,12 +46,8 @@ class ManagerHandler
/** @var ManagerTypes $oManagerTypes */
$oManagerTypes = oxNew(ManagerTypes::class);
$sCMPName = $oManagerTypes->isManagerInList($sPotentialManagerName)
return $oManagerTypes->isManagerInList($sPotentialManagerName)
? $sPotentialManagerName
: "NONE";
$this->d3SaveShopConfVar($sCMPName);
return $sCMPName;
}
}

View File

@ -2,24 +2,41 @@
namespace D3\GoogleAnalytics4\Application\Model;
use D3\GoogleAnalytics4\Application\Model\CMP\Usercentrics;
class ManagerTypes
{
const EXTERNAL_SERVICE = "eigener Service";
const NET_COOKIE_MANAGER = "Netensio Cookie Manager";
#ToDo: make own classes for each of the manager
const EXTERNAL_SERVICE = "externalService";
const NET_COOKIE_MANAGER = "net_cookie_manager";
/**
* Further information's:
* https://github.com/aggrosoft/oxid-cookie-compliance
*/
const AGCOOKIECOMPLIANCE = "Aggrosoft Cookie Compliance";
const AGCOOKIECOMPLIANCE = "agcookiecompliance";
const CONSENTMANAGER = "Consentmanager";
/**
* Used the OXID Module.
*
* Further information's:
* https://docs.oxid-esales.com/modules/usercentrics/de/latest/einfuehrung.html
*
* Usercentrics homepage:
* https://usercentrics.com
*/
const USERCENTRICS_MODULE = "oxps_usercentrics";
const COOKIEFIRST = "Cookiefirst";
/**
* manually included usercentrics script
*/
const USERCENTRICS_MANUALLY = "USERCENTRICS";
const COOKIEBOT = "Cookiebot";
const CONSENTMANAGER = "CONSENTMANAGER";
const COOKIEFIRST = "COOKIEFIRST";
const COOKIEBOT = "COOKIEBOT";
/**
* @return array
@ -30,9 +47,9 @@ class ManagerTypes
"externalService" => self::EXTERNAL_SERVICE,
"agcookiecompliance" => self::AGCOOKIECOMPLIANCE,
"net_cookie_manager" => self::NET_COOKIE_MANAGER,
Usercentrics::sModuleIncludationInternalName => Usercentrics::sModuleIncludationPublicName,
Usercentrics::sExternalIncludationInternalName => Usercentrics::sExternalIncludationPublicName,
"cmconsentmanager" => self::CONSENTMANAGER,
"oxps_usercentrics" => self::USERCENTRICS_MODULE,
"usercentrics" => self::USERCENTRICS_MANUALLY,
"consentmanager" => self::CONSENTMANAGER,
"cookiefirst" => self::COOKIEFIRST,
"cookiebot" => self::COOKIEBOT,
];
@ -44,6 +61,6 @@ class ManagerTypes
*/
public function isManagerInList(string $sManager) :bool
{
return in_array($sManager, array_keys($this->getManagerList()), true);
return in_array($sManager, $this->getManagerList(), true);
}
}

View File

@ -1,123 +0,0 @@
<?php
$sLangName = "Deutsch";
// -------------------------------
// RESOURCE IDENTITFIER = STRING
// -------------------------------
$aLang = array(
'charset' => 'UTF-8',
'd3mxgoogleanalytics4' => 'Google Analytics 4',
'd3mxgoogleanalytics4set' => 'Einstellungen',
// Base Translations
'D3BASECONFIG' => 'Grundeinstellungen',
'D3CLOSE' => 'SchlieĂźen',
'D3NONE' => '- keinen -',
'D3CONTAINERID' => 'Container-ID',
'D3CONTAINERID_HELP' => '<a target="_blank" href="https://github.com/d3datadevelopment/GoogleAnalytics4/blob/master/Docs/README.md#Container-ID" class="text-muted text-decoration-none"><i class="bi bi-book-half"></i> Was ist die <strong>Container-ID</strong>?</a>',
'D3ACTIVATEMOD' => 'Modul aktivieren',
'D3CNTRLPARAM' => 'Steuerungsparameter',
'D3CNTRLPARAM_HELP' => '<a target="_blank" href="https://github.com/d3datadevelopment/GoogleAnalytics4/blob/master/Docs/README.md#steuerungsparameter" class="text-muted text-decoration-none"><i class="bi bi-book-half"></i> Was ist der <strong>Steuerungsparameter</strong>?</a>',
'D3INACTIVATEMOD' => 'Modul ist nicht aktiv! Es werden keine Funktionen ausgespielt!',
// Usercentrics Dynamische Optionen
'D3USRCNTRCSDYNOPT' => 'Usercentrics Dynamische Optionen',
// Use debug mode?
'D3USEDEBUGMODE' => "Debug-Modus aktivieren",
'D3USEDEBUGMODE_HELP' => "Der <strong>Debug Modus</strong> setzt an alle DataLayer ( also Daten Sammlungen im Frontend )
<strong>'debug_mode': 'true'</strong> und ermöglicht im Google Tag Manager selbst ein detaillierteres
Auswerten des einflieĂźenden Datenstroms.",
// Use Consentmode?
'D3USEGOOGLECONSENTMODE' => "Google Consent Mode 'Default Values' akivieren",
'D3USEGOOGLECONSENTMODE_HELP' => "Der <trong>Consent Mode 'Default Values'</trong> setzt im Frontend,
vor jedem Sammeln und Senden von Daten, einen Befehl der die Bearbeitung der Daten fortlaufend verändert.<br>
<br>
Diese Veränderte Berarbeitung heißt im Detail, dass der Google Tag Manager ( GTM )
bzw. in erster Instanz die Consent Management Platform ( CMP ) keine Daten zur Verarbeitung an Google sendet,
bis ein entsprechendes Zustimmungs-Signal vom Kunden explizit erteilt wurde.<br>
Die CMP ist sogar derartig restriktiv, dass diese den Datenstrom zum GTM ( Vorinstanz zu Google Analytics )
völlig verhindert, solange keine Zustimmung erteilt wurde.<br>
<br>
Ein einfaches anschalten dieser Funktion regelt noch <strong>nicht</strong> die völlige Funktionsweise
aller beteiligten Instanzen; diese bedarf eine detailliertere Konfiguration!<br>",
// Use CMP?
'D3CMPTABTITLE' => 'Cookie Manager Einstellungen',
'D3CMPUSEQ' => 'Consent Management Platform ( CMP ) nutzen?',
'D3CMPUSEQ_HELP' => '"Eine Consent Management Platform ( CMP ) ist eine Software, mit der Website-Betreiber
oder Anbieter von Web-Apps ĂĽber ein Banner oder ein Pop-up eine datenschutzrechtliche
Einwilligung der Besucher einholen und speichern, bevor Nutzerdaten ĂĽber
Website-Skripte erfasst werden (Tracking)." <a target="_blank" href="https://de.wikipedia.org/wiki/Consent_Management_Platform">Wikipedia Beschreibung</a><br>
<br>
Um Google Analytics 4 ( <a target="_blank" href="https://marketingplatform.google.com/intl/de/about/analytics/">Google Analytics</a> ) weiterhin nutzen zu können,
und dank fortschreitendem Datenschutz unserer personenbezogener Daten, ist das Nutzen eines konformen CMP
heute zwangläufig nötig.<br>
<br>
Diese konformen CMP sind in
<a target="_blank" href="https://cmppartnerprogram.withgoogle.com/">offizieller Partnerschaft mit Google ( Liste der Partner )</a>
und unterliegen strengen Vorschriften, um ein ordnungsgemäßes Senden und
Verarbeiten der Zustimmung unterliegenden Daten sicher stellen zu können.',
'D3CMP' => 'Consent Management Platform ( CMP ) wählen',
// Usercentrics Config
// activate Individual Default Values
'D3USRCNTRCSCFG_ACT_INDIVDEFVAL' => "Usercentrics individual 'Default Values' aktiveren",
// standard Consent
'D3USRCNTRCSCFG_STD_CNST' => "GTM Standard Consent",
// activate consent mode API
'D3USRCNTRCSCFG_ACT_CNSTMDE_API' => "Usercentrics Consent Mode API aktivieren",
// consent mode api
'D3USRCNTRCSCFG_CNSTMDE_API' => "Consent Mode API",
'D3USRCNTRCSCFG_DOCS' => 'Nähere Infos zu den hier konfigurierbaren Einstellungen entnehmen Sie bitte der offiziellen
Dokumentation von Usercentrics selbst: <a target="_blank" href="https://docs.usercentrics.com/#/consent-mode" class="text-primary"><i class="bi bi-book-half"></i> Dokumentation</a>',
'D3USRCNTRCSCFG_WARNING' => "Bevor Sie hier Anpassungen machen, konsultieren Sie bitte einen technischen Support!<br>
Anpassungen können zu Beeinträchtigungen und Ausfall von Funktionen im Frontend führen!",
// Additional Config
// Server-Side tagging
'D3SERVERSIDETAGGING' => 'Server-Side tagging',
'D3DETAILED_DESC' => 'Detailliertere Erklärung der Funktion',
'D3SERVERSIDETAGGING_HINT' => 'Die Conatiner-ID wird weiterhin unter "Grundeinstellungen" eingetragen!<br><br>
"Serverseitiges Tagging ist eine neue Möglichkeit, mit Google Tag Manager Ihre Anwendung geräteübergreifend zu verwalten.<br>
Servercontainer verwenden dasselbe Tag-, Trigger- und Variablenmodell, das Sie gewohnt sind.<br>
Außerdem bieten sie neue Tools, mit denen Sie Nutzeraktivitäten überall messen können." <br>
<br>
- Quelle <a href="https://developers.google.com/tag-platform/tag-manager/server-side/intro">Developers-Google Server-Side tagging</a><br>
<br>
<strong>Verändern Sie die Werte nur, wenn Sie Server-Side tagging verwenden wollen! Gegebenenfalls fragen Sie einen technischen Ansprechpartner.</strong>
',
'D3SERVERSIDETAGGING_TITLE_ACTIVE' => 'AusfĂĽhrender code',
'D3SERVERSIDETAGGING_ACTIVE' => 'Diese Domain wird im <strong>aktiven</strong>-code ausgefĂĽht. Das heiĂźt,
dass es sich hierbei um das HTML-Tag <code>script</code> handelt.
Dieses kĂĽmmert sich darum, dass die im DataLayer
zusammengefassten Daten an den GTM weitergeleitet werden.<br>
<br>
<h4>Folgend eine Darstellung, was genau ausgetauscht wird</h4>
<pre>
<code>
Vorher:
https://www.googletagmanager.com/gtm.js?id=
Nachher:
{Domain}?id=
</code>
</pre>',
'D3SERVERSIDETAGGING_TITLE_PASSIVE' => '<u>nicht</u>&nbsp;AusfĂĽhrneder code',
'D3SERVERSIDETAGGING_PASSIVE' => 'Diese Domain wird im <strong>passiven</strong>-code ausgefĂĽht. Das heiĂźt,
dass es sich hierbei um das HTML-Tag <code>noscript</code> handelt.
Dieses wird ausgefĂĽhrt, wenn aus einem bestimmten Grund
das Javascript nicht ausgefĂĽhrt wird.<br>
( keine Cookies erlaubt, JavaScript-Unterbindung, ... )
<br>
<h4>Folgend eine Darstellung, was genau ausgetauscht wird</h4>
<pre>
<code>
Vorher:
src="https://www.googletagmanager.com/ns.html?id={Container-ID}"
Nachher:
src="{Domain}?id={Container-ID}"
</code>
</pre>',
);

View File

@ -10,8 +10,6 @@
* @link https://www.oxidmodule.com
*/
use D3\GoogleAnalytics4\Application\Model\Constants as Constants;
$style = '<style type="text/css">
.groupExp a.rc b {font-size:medium;color:#ff3600;}
.groupExp dt .txt,
@ -24,87 +22,32 @@ input.confinput:hover {outline:3px solid #ff3600;}
</style>';
$aLang = [
'charset' => 'UTF-8',
// STD-Einstellungen
'SHOP_MODULE_GROUP_'.Constants::OXID_MODULE_ID.'_settings' => 'Einstellungen',
'SHOP_MODULE_'. Constants::OXID_MODULE_ID.'_sContainerID' => 'Container ID',
'SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_blGA4enab' => 'GA4 Aktivieren',
'SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_blUAenabled' => 'UA Aktivieren',
'SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_blEnableDebug' => 'Debug-Modus aktivieren',
// Serverside - tagging
'SHOP_MODULE_GROUP_'.Constants::OXID_MODULE_ID.'_serversidetagging' => 'Server-Side tagging',
'SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_serversidetagging_js' => 'Servercontainer AusfĂĽhrender-Code',
'HELP_SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_serversidetagging_js' => 'Diese Domain wird im <strong>aktiven</strong>-code ausgefĂĽht. Das heiĂźt,
dass es sich hierbei um das HTML-Tag <code>script</code> handelt.
Dieses kĂĽmmert sich darum, dass die, im data_layer
zusammengefassten Daten an den GTM weitergeleitet werden.<br>
<br>
<h4>Folgend eine Darstellung, was genau ausgetauscht wird</h4>
<pre>
<code>
Vorher:
https://www.googletagmanager.com/gtm.js?id=
Nachher:
{Domain}?id=
</code>
</pre>
Die Conatiner-ID wird weiterhin im Punkt "Einstellung" eingetragen!
',
'SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_serversidetagging_nojs' => 'Servercontainer NICHT AusfĂĽhrender-Code<br><br>
"Serverseitiges Tagging ist eine neue Möglichkeit, mit Google Tag Manager Ihre Anwendung geräteübergreifend zu verwalten.<br>
Servercontainer verwenden dasselbe Tag-, Trigger- und Variablenmodell, das Sie gewohnt sind.<br>
Außerdem bieten sie neue Tools, mit denen Sie Nutzeraktivitäten überall messen können." <br>
<br>
- Quelle <a href="https://developers.google.com/tag-platform/tag-manager/server-side/intro">Developers-Google Server-Side tagging</a><br>
<br>
<strong>Verändern Sie die Werte nur, wenn Sie Server-Side tagging verwenden wollen!</strong>
',
'HELP_SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_serversidetagging_nojs' => 'Diese Domain wird im <strong>passiven</strong>-code ausgefĂĽht. Das heiĂźt,
dass es sich hierbei um das HTML-Tag <code>noscript</code> handelt.
Dieses wird ausgefĂĽhrt, wenn aus einem bestimmten Grund
das Javascript nicht ausgefĂĽhrt wird.<br>
( keine Cookies erlaubt, JavaScript-Unterbindung, ... )
<br>
<h4>Folgend eine Darstellung, was genau ausgetauscht wird</h4>
<pre>
<code>
Vorher:
src="https://www.googletagmanager.com/ns.html?id={Container-ID}"
Nachher:
src="{Domain}?id={Container-ID}"
</code>
</pre>
Die Conatiner-ID wird weiterhin im Punkt "Einstellung" eingetragen!
',
'SHOP_MODULE_d3_gtm_sContainerID' => 'Container ID',
'SHOP_MODULE_GROUP_d3_gtm_settings' => 'Einstellungen',
'SHOP_MODULE_d3_gtm_blGA4enab' => 'GA4 Aktivieren',
'SHOP_MODULE_d3_gtm_blUAenabled' => 'UA Aktivieren',
'SHOP_MODULE_d3_gtm_blEnableDebug' => 'Debug-Modus aktivieren',
// for cookie manager settings
'SHOP_MODULE_GROUP_'.Constants::OXID_MODULE_ID.'_cookiemanager' => 'Cookie Manager Einstellungen',
'SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_hasOwnCookieManager' => 'Cookie Manager nutzen?',
'HELP_SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_HAS_STD_MANAGER' => 'Mehr Informationen zu den genannten Coookie-Manager finden Sie auf den folgenden Home-Pages<br><br>
'SHOP_MODULE_GROUP_d3_gtm_settings_cookiemanager' => 'Cookie Manager Einstellungen',
'SHOP_MODULE_d3_gtm_settings_hasOwnCookieManager' => 'Cookie Manager nutzen?',
'HELP_SHOP_MODULE_d3_gtm_settings_HAS_STD_MANAGER' => 'Mehr Informationen zu den genannten Coookie-Manager finden Sie auf den folgenden Home-Pages<br><br>
<a href="https://consentmanager.net/">Consentmanager</a><br>
<a href="https://usercentrics.com/">Usercentrics</a><br>
<a href="https://cookiefirst.com">Cookiefirst</a><br>
<hr>
Bei weiteren Fragen stehen wir gern zur VerfĂĽgung! Kontaktieren Sie uns einfach unter <a href="https://www.d3data.de/">https://www.d3data.de/</a>',
'SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_HAS_STD_MANAGER' => 'Nutzen Sie eine der folgenden Einbindungen?<br>
'SHOP_MODULE_d3_gtm_settings_HAS_STD_MANAGER' => 'Nutzen Sie eine der folgenden Einbindungen?<br>
Dann wählen Sie bitte die zutreffende aus.',
'SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_HAS_STD_MANAGER_NONE' => '---',
'SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_HAS_STD_MANAGER_CONSENTMANAGER' => 'consentmanager',
'SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_HAS_STD_MANAGER_USERCENTRICS' => 'usercentrics',
'SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_HAS_STD_MANAGER_COOKIEFIRST' => 'cookiefirst',
'SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_HAS_STD_MANAGER_COOKIEBOT' => 'Cookiebot',
'SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_controlParameter' => 'Steuerungsparameter',
'HELP_SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_controlParameter' => 'Nähere infos zum <a target="_blank" href="https://git.d3data.de/D3Public/GoogleAnalytics4/src/branch/master/Docs">"<strong>Steuerungsparameter</strong>"</a><hr>
'SHOP_MODULE_d3_gtm_settings_HAS_STD_MANAGER_NONE' => '---',
'SHOP_MODULE_d3_gtm_settings_HAS_STD_MANAGER_CONSENTMANAGER' => 'consentmanager',
'SHOP_MODULE_d3_gtm_settings_HAS_STD_MANAGER_USERCENTRICS' => 'usercentrics',
'SHOP_MODULE_d3_gtm_settings_HAS_STD_MANAGER_COOKIEFIRST' => 'cookiefirst',
'SHOP_MODULE_d3_gtm_settings_HAS_STD_MANAGER_COOKIEBOT' => 'Cookiebot',
'SHOP_MODULE_d3_gtm_settings_controlParameter' => 'Steuerungsparameter',
'HELP_SHOP_MODULE_d3_gtm_settings_controlParameter' => 'Nähere infos zum <a target="_blank" href="https://git.d3data.de/D3Public/GoogleAnalytics4/src/branch/master/Docs">"<strong>Steuerungsparameter</strong>"</a><hr>
<strong>Beachte:</strong><br>
Sofern Sie die <a target="_blank" href="https://consentmanager.net" style="color: blue">consentmanager</a> CMP verwenden,
bitte ich Sie, grĂĽndlichst, die Hinweise der <a target="_blank" href="https://git.d3data.de/D3Public/GoogleAnalytics4/src/branch/master/Docs/CMP/consentmanager.md">Moduldokumentation/Consentmanager</a> zu lesen.
',
'SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_blActivateConsentMode' => "Google Consent Mode 'Default Values' aktivieren",
'HELP_SHOP_MODULE_'.Constants::OXID_MODULE_ID.'_blActivateConsentMode' => 'Diese Einstellung ist zu aktivieren, wenn Sie den Google-Consent-Mode ( Einwilligungsmodus ) verwenden wollen.
<hr>
"Im Einwilligungsmodus können Sie Google über den Cookie- oder App-ID-Einwilligungsstatus Ihrer Nutzer informieren.
Mit Tags wird das Verhalten angepasst. Dabei werden die Einstellungen der Nutzer berĂĽcksichtigt." ~ <a href="https://support.google.com/google-ads/answer/10000067">Google Einwilligungsmodus</a>',
'
];

View File

@ -1,108 +0,0 @@
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">
<html>
<head>
<title>[{$title}]</title>
<meta http-equiv="Content-Type" content="text/html; charset=[{$charset}]">
[{if isset($meta_refresh_sec,$meta_refresh_url)}]
<meta http-equiv=Refresh content="[{$meta_refresh_sec}];URL=[{$meta_refresh_url|replace:"&amp;":"&"}]">
[{/if}]
<link rel="shortcut icon" href="[{$oViewConf->getBaseDir()}]favicon.ico">
[{block name="admin_headitem_inccss"}]
<link rel="stylesheet" href="[{$oViewConf->getResourceUrl()}]main.css">
<link rel="stylesheet" href="[{$oViewConf->getResourceUrl()}]colors_[{$oViewConf->getEdition()|lower}].css">
<link rel="stylesheet" type="text/css" href="[{$oViewConf->getResourceUrl()}]yui/build/assets/skins/sam/container.css">
[{/block}]
[{block name="admin_headitem_incjs"}]
<script type="text/javascript" src="[{$oViewConf->getResourceUrl()}]yui/build/utilities/utilities.js"></script>
<script type="text/javascript" src="[{$oViewConf->getResourceUrl()}]yui/build/container/container-min.js"></script>
<script type="text/javascript" src="[{$oViewConf->getResourceUrl()}]yui/oxid-help.js"></script>
[{/block}]
[{block name="admin_headitem_js"}]
<script type="text/javascript">
<!--
// standard messages
var sUnassignMessage = "[{oxmultilang ident='GENERAL_YOUWANTTOUNASSIGN'}]";
var sDeleteMessage = "[{oxmultilang ident='GENERAL_YOUWANTTODELETE'}]";
// class info
var sDefClass = '[{$default_edit}]';
var sActClass = '[{$actlocation}]';
[{if $updatelist == 1}]
window.onload = function ()
{
top.oxid.admin.updateList('[{$oxid}]');
}
[{/if}]
var ajaxpopup = null;
function showDialog( sParams )
{
ajaxpopup = window.open('[{$oViewConf->getSelfLink()|replace:"&amp;":"&"}]'+sParams, 'ajaxpopup', 'width=850,height=680,scrollbars=yes,resizable=yes');
}
function focusPopup()
{
if ( ajaxpopup )ajaxpopup.focus();
}
window.onclick = focusPopup;
function cleanupLongDesc( sValue )
{
if ( sValue == '<br>' || sValue == '<br />' ) {
return '';
}
return sValue;
}
function copyLongDesc( sIdent )
{
var textVal = null;
try {
if ( WPro.editors[sIdent] != null ) {
WPro.editors[sIdent].prepareSubmission();
textVal = cleanupLongDesc( WPro.editors[sIdent].getValue() );
}
} catch(err) {
var varEl = document.getElementById(sIdent);
if (varEl != null) {
textVal = cleanupLongDesc( varEl.value );
}
}
if (textVal == null) {
var varName = 'editor_'+sIdent;
var varEl = document.getElementById(varName);
if (varEl != null) {
textVal = cleanupLongDesc( varEl.value );
}
}
if (textVal != null) {
var oTarget = document.getElementsByName( 'editval['+ sIdent + ']' );
if ( oTarget != null && ( oField = oTarget.item( 0 ) ) != null ) {
oField.value = textVal;
}
}
}
-->
</script>
[{/block}]
</head>
<body>
[{include file="tooltips.tpl"}]
<div id="oxajax_data"></div>
<div class="[{$box|default:'box'}]" style="height: 100%;">
[{include file="inc_error.tpl" Errorlist=$Errors.default}]
<!-- Input help popup -->
<div id="helpTextContainer" class="yui-skin-sam">
<div id="helpPanel"></div>
</div>

View File

@ -1,198 +0,0 @@
[{include file="ga4/admin/d3ga4uiheaditem.tpl" title="GENERAL_ADMIN_TITLE"|oxmultilangassign}]
<style>
body {
background-image: linear-gradient(to top, #d5d4d0 0%, #d5d4d0 1%, #eeeeec 31%, #efeeec 75%, #e9e9e7 100%);
}
</style>
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.1.3/dist/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-1BmE4kWBq78iYhFldvKuhfTAU6auU8tT94WrHftjDbrCEXSU1oBoqyl2QvZ6jIW3" crossorigin="anonymous">
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.1.3/dist/js/bootstrap.bundle.min.js" integrity="sha384-ka7Sk0Gln4gmtz2MlQnikT1wXgYsOg+OMhuP+IlRH9sENBO0LRn5q+8nbTov4+1p" crossorigin="anonymous"></script>
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap-icons@1.11.3/font/bootstrap-icons.min.css">
[{if $readonly}]
[{assign var="readonly" value="readonly disabled"}]
[{else}]
[{assign var="readonly" value=""}]
[{/if}]
<div>
<form name="d3gtmformedit" id="d3gtmformedit" action="[{$oViewConf->getSelfLink()}]" enctype="multipart/form-data" method="post">
<div class="row">
<div class="col-6">
[{$oViewConf->getHiddenSid()}]
<input type="hidden" name="cl" value="[{$oViewConf->getActiveClassName()}]">
<input type="hidden" name="fnc" value="">
<input type="hidden" name="editlanguage" value="[{$editlanguage}]">
<div class="card mb-5">
<div class="card-header">
[{oxmultilang ident="D3BASECONFIG"}]
</div>
<div class="card-body">
<div class="form-check mb-3">
<input class="form-check-input" type="checkbox" value="" name="editval[bool][_blEnableGa4]" [{if $d3ViewObject->d3GetModuleConfigParam('_blEnableGa4')}]checked[{/if}] id="blGA4enab">
<label class="form-check-label" for="flexCheckDefault">
[{oxmultilang ident="D3ACTIVATEMOD"}] [{if false === $d3ViewObject->d3GetModuleConfigParam('_blEnableGa4')}]<span style="color: red">[{oxmultilang ident="D3INACTIVATEMOD"}]</span>[{/if}]
</label>
</div>
<div class="mb-3">
<div class="input-group w-50">
<span class="input-group-text" id="basic-addon3">[{oxmultilang ident="D3CONTAINERID"}]</span>
<input type="text" class="form-control" id="_sContainerID" name="editval[str][_sContainerID]" aria-describedby="basic-addon3" value="[{$d3ViewObject->d3GetModuleConfigParam('_sContainerID')}]">
</div>
<div class="text-muted">[{oxmultilang ident="D3CONTAINERID_HELP"}]</div>
</div>
<div class="form-check">
<input class="form-check-input" type="checkbox" value="" id="_blEnableDebug" name="editval[bool][_blEnableDebug]" [{if $d3ViewObject->d3GetModuleConfigParam('_blEnableDebug')}]checked[{/if}]>
<label class="form-check-label" for="flexCheckDefault">
[{oxmultilang ident="D3USEDEBUGMODE"}][{oxinputhelp ident="D3USEDEBUGMODE_HELP"}]
</label>
</div>
<div class="form-check">
<input class="form-check-input" type="checkbox" value="" id="_blActivateConsentMode" name="editval[bool][_blEnableConsentMode]" [{if $d3ViewObject->d3GetModuleConfigParam('_blEnableConsentMode')}]checked[{/if}]>
<label class="form-check-label" for="flexCheckChecked">
[{oxmultilang ident="D3USEGOOGLECONSENTMODE"}][{oxinputhelp ident="D3USEGOOGLECONSENTMODE_HELP"}]
</label>
</div>
</div>
<button type="submit" name="save" class="btn btn-light" onClick="Javascript:document.d3gtmformedit.fnc.value='save'">[{oxmultilang ident="GENERAL_SAVE"}]</button>
</div>
</div>
<div class="col-6">
<div class="card border border-0">
<div class="accordion" id="accordionPanelsStayOpenExample">
<div class="accordion-item">
<h2 class="accordion-header">
<button class="accordion-button" type="button" data-bs-toggle="collapse" data-bs-target="#panelsStayOpen-cmpsettings" aria-expanded="true" aria-controls="panelsStayOpen-cmpsettings">
[{oxmultilang ident="D3CMPTABTITLE"}]
</button>
</h2>
<div id="panelsStayOpen-cmpsettings" class="accordion-collapse collapse show">
<div class="accordion-body">
<div class="form-check">
<input class="form-check-input" type="checkbox" name="editval[bool][_blEnableOwnCookieManager]" value="" id="_hasOwnCookieManager" [{if $d3ViewObject->d3GetModuleConfigParam('_blEnableOwnCookieManager')}]checked[{/if}]>
<label class="form-check-label" for="flexCheckChecked">
[{oxmultilang ident="D3CMPUSEQ"}][{oxinputhelp ident="D3CMPUSEQ_HELP"}]
</label>
</div>
<div class="mb-3">
<label>
[{oxmultilang ident="D3CMP"}]
</label>
<select class="form-select w-50" name="editval[select][_HAS_STD_MANAGER]" aria-label="Default select example">
<option value="NONE" selected>[{oxmultilang ident="D3NONE"}]</option>
[{foreach from=$d3ManagerTypeArray key="sInternalName" item="sPublicName" name="editval[aCmpNameArray]"}]
<option value="[{$sInternalName}]" [{if $sInternalName === $d3CurrentCMP}]SELECTED[{/if}]>[{$sPublicName}]</option>
[{/foreach}]
</select>
</div>
<div>
<div class="input-group w-75">
<span class="input-group-text" id="basic-addon3">[{oxmultilang ident="D3CNTRLPARAM"}]</span>
<input type="text" class="form-control" id="_controlParameter" name="editval[str][_sControlParameter]" value="[{$d3ViewObject->d3GetModuleConfigParam('_sControlParameter')}]" aria-describedby="basic-addon3">
</div>
<div class="text-muted">[{oxmultilang ident="D3CNTRLPARAM_HELP"}]</div>
</div>
</div>
<button type="submit" name="save" class="btn btn-light w-100" onClick="Javascript:document.d3gtmformedit.fnc.value='save'">[{oxmultilang ident="GENERAL_SAVE"}]</button>
</div>
</div>
<div class="accordion-item">
<h2 class="accordion-header">
<button class="accordion-button collapsed" type="button" data-bs-toggle="collapse" data-bs-target="#panelsStayOpen-serversidetagging" aria-expanded="false" aria-controls="panelsStayOpen-serversidetagging">
[{oxmultilang ident="D3SERVERSIDETAGGING"}]
</button>
</h2>
<div id="panelsStayOpen-serversidetagging" class="accordion-collapse collapse">
<div class="accordion-body">
<div class="card bg-light rounded mb-3">
<div class="card-body">
[{oxmultilang ident="D3SERVERSIDETAGGING_HINT"}]
</div>
</div>
<div class="input-group mb-3">
<span class="input-group-text w-25" id="basic-addon3">[{oxmultilang ident="D3SERVERSIDETAGGING_TITLE_ACTIVE"}]</span>
<input type="text" class="form-control" id="_serversidetagging_js" name="editval[str][_sServersidetagging_js]" value="[{$d3ViewObject->d3GetModuleConfigParam('_sServersidetagging_js')}]" aria-describedby="basic-addon3">
</div>
<div class="input-group mb-3">
<span class="input-group-text w-25" id="basic-addon3">[{oxmultilang ident="D3SERVERSIDETAGGING_TITLE_PASSIVE"}]</span>
<input type="text" class="form-control" id="_serversidetagging_nojs" name="editval[str][_sServersidetagging_nojs]" value="[{$d3ViewObject->d3GetModuleConfigParam('_sServersidetagging_nojs')}]" aria-describedby="basic-addon3">
</div>
<div>
<button type="button" class="btn btn-light mt-3" data-bs-toggle="modal" data-bs-target="#exampleModal">
[{oxmultilang ident="D3DETAILED_DESC"}]
</button>
<!-- Modal -->
<div class="modal fade" id="exampleModal" tabindex="-1" aria-labelledby="exampleModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-body">
<h4>[{oxmultilang ident="D3SERVERSIDETAGGING_TITLE_ACTIVE"}]</h4>
[{oxmultilang ident="D3SERVERSIDETAGGING_ACTIVE"}]
<hr>
<h4>[{oxmultilang ident="D3SERVERSIDETAGGING_TITLE_PASSIVE"}]</h4>
[{oxmultilang ident="D3SERVERSIDETAGGING_PASSIVE"}]
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">[{oxmultilang ident="D3CLOSE"}]</button>
</div>
</div>
</div>
</div>
</div>
</div>
<button type="submit" name="save" class="btn btn-light w-100" onClick="Javascript:document.d3gtmformedit.fnc.value='save'">[{oxmultilang ident="GENERAL_SAVE"}]</button>
</div>
</div>
[{if $d3ViewConfObject->d3IsUsercentricsCMPChosen()}]
<div class="accordion-item">
<h2 class="accordion-header">
<button class="accordion-button collapsed" type="button" data-bs-toggle="collapse" data-bs-target="#panelsStayOpen-usercentricsdynamicoptions" aria-expanded="false" aria-controls="panelsStayOpen-usercentricsdynamicoptions">
[{oxmultilang ident="D3USRCNTRCSDYNOPT"}]
</button>
</h2>
<div id="panelsStayOpen-usercentricsdynamicoptions" class="accordion-collapse collapse">
<div class="accordion-body">
<div class="card bg-light rounded mb-3">
<div class="card-body">
<div class="text-danger mb-3">
[{oxmultilang ident="D3USRCNTRCSCFG_WARNING"}]
</div>
[{oxmultilang ident="D3USRCNTRCSCFG_DOCS"}]
</div>
</div>
<div class="form-check">
<input class="form-check-input" type="checkbox" value="" id="enabledefaultmeasurementvalues" name="editval[bool][_blEnableMeasurementCapabilities]" [{if $d3ViewObject->d3GetModuleConfigParam('_blEnableMeasurementCapabilities')}]checked[{/if}]>
<label class="form-check-label" for="flexCheckDefault">
[{oxmultilang ident="D3USRCNTRCSCFG_ACT_INDIVDEFVAL"}]
</label>
</div>
<div class="input-group mb-3">
<span class="input-group-text w-25" id="basic-addon3">[{oxmultilang ident="D3USRCNTRCSCFG_STD_CNST"}]</span>
<textarea name="editval[str][_sMeasurementCapabilities]" class="form-control" rows="15">[{$d3ViewObject->d3GetModuleConfigParam('_sDefaultMeasurementCapabilities')}]</textarea>
</div>
<div class="form-check">
<input class="form-check-input" type="checkbox" value="" id="enableUsercentricsConsentModeApi" name="editval[bool][_blEnableUsercentricsConsentModeApi]" [{if $d3ViewObject->d3GetModuleConfigParam('_blEnableUsercentricsConsentModeApi')}]checked[{/if}]>
<label class="form-check-label" for="flexCheckDefault">
[{oxmultilang ident="D3USRCNTRCSCFG_ACT_CNSTMDE_API"}]
</label>
</div>
<div class="input-group mb-3">
<span class="input-group-text w-25" id="basic-addon3">[{oxmultilang ident="D3USRCNTRCSCFG_CNSTMDE_API"}]</span>
<textarea name="editval[str][_sUsercentricsConsentModeApi]" class="form-control" rows="40">[{$d3ViewObject->d3GetModuleConfigParam('_sDefaultUsercentricsConsentModeApi')}]</textarea>
</div>
</div>
<button type="submit" name="save" class="btn btn-light w-100" onClick="Javascript:document.d3gtmformedit.fnc.value='save'">[{oxmultilang ident="GENERAL_SAVE"}]</button>
</div>
</div>
[{/if}]
</div>
</div>
</div>
</div>
</form>
</div>

View File

@ -1,41 +1,11 @@
[{* Always prepare the data layer to avoid errors *}]
[{if $oViewConf->isGA4enabled()}]
[{assign var="d3GtmContainerIdString" value=$oViewConf->getGtmContainerId()}]
<script>
<script>
var dataLayer = [{$oViewConf->getGtmDataLayer()}] || [];
</script>
[{/if}]
</script>
[{if $oViewConf->isGA4enabled() and $oViewConf->D3blShowGtmScript()}]
[{if $d3GtmContainerIdString}]
[{if $oViewConf->D3blShowGtmScript()}]
[{if $oViewConf->getGtmContainerId()}]
[{strip}]
[{if $oViewConf->isGtmConsentModeSetActivated()}]
<script type="text/javascript">
[{if $oViewConf->d3IsUsercentricsCMPChosen() and $oViewConf->d3GetModuleConfigParam('_blEnableMeasurementCapabilities')}]
[{$oViewConf->d3GetModuleConfigParam('_sMeasurementCapabilities')|strip}]
[{else}]
function gtag() {
dataLayer.push(arguments);
}
gtag("consent", "default", {
ad_user_data: "denied",
ad_personalization: "denied",
ad_storage: "denied",
analytics_storage: "denied",
wait_for_update: 2000
});
[{/if}]
</script>
[{/if}]
[{if $oViewConf->d3IsUsercentricsCMPChosen() and $oViewConf->d3GetModuleConfigParam('_blEnableUsercentricsConsentModeApi')}]
<script type="text/javascript">
[{$oViewConf->d3GetModuleConfigParam('_sUsercentricsConsentModeApi')|strip}]
</script>
[{/if}]
<!-- Google Tag Manager -->
<script [{$oViewConf->getGtmScriptAttributes()}]>
(function (w, d, s, l, i) {
@ -43,9 +13,9 @@
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 = '[{$oViewConf->getServerSidetaggingJsDomain()}]?id=' + i + dl;
j.src = 'https://www.googletagmanager.com/gtm.js?id=' + i + dl;
f.parentNode.insertBefore(j, f);
})(window, document, 'script', 'dataLayer', '[{$d3GtmContainerIdString}]');
})(window, document, 'script', 'dataLayer', '[{$oViewConf->getGtmContainerId()}]');
</script>
<!-- End Google Tag Manager -->
[{/strip}]

View File

@ -2,7 +2,7 @@
[{if $oViewConf->getGtmContainerId()}][{strip}]
<!-- Google Tag Manager (noscript) -->
<noscript>
<iframe src="[{$oViewConf->getServerSidetaggingNoJsDomain()}]?id=[{$oViewConf->getGtmContainerId()}]"
<iframe src="https://www.googletagmanager.com/ns.html?id=[{$oViewConf->getGtmContainerId()}]"
height="0" width="0" style="display:none;visibility:hidden"></iframe>
</noscript>
<!-- End Google Tag Manager (noscript) -->

View File

@ -1,3 +0,0 @@
[{$smarty.block.parent}]
[{include file="event/add_payment_info.tpl"}]

View File

@ -1,3 +0,0 @@
[{$smarty.block.parent}]
[{include file="event/begin_checkout.tpl"}]

View File

@ -1,53 +0,0 @@
[{*$oxcmp_basket|get_class_methods|dumpvar*}]
[{assign var="gtmBasketPrice" value=$oxcmp_basket->getPrice()}]
[{assign var="gtmBasketObject" value=$oxcmp_basket}]
[{assign var='gtmCartArticles' value=$gtmBasketObject->getBasketArticles()}]
[{assign var="gtmPaymentObject" value=$oView->getPayment()}]
[{block name="gtm_ga4_add_payment_info_block"}]
[{capture name="gtm_ga4_add_payment_info"}]
[{strip}]
dataLayer.push({"event": null, "eventLabel": null, "ecommerce": null}); /* Clear the previous ecommerce object. */
dataLayer.push({
'event': 'add_payment_info',
'eventLabel':'Checkout - Payment info',
'payment_type':'[{$gtmPaymentObject->gtmGetSelectedPaymentName()}]',
'ecommerce':
{
'actionField': "Payment-Info",
'currency': "[{$currency->name}]",
'value': [{$gtmBasketPrice->getPrice()}],
'coupon': '[{foreach from=$oxcmp_basket->getVouchers() item=sVoucher key=key name=Voucher}][{$sVoucher->sVoucherNr}][{if !$smarty.foreach.Voucher.last}], [{/if}][{/foreach}]',
'items':
[
[{foreach from=$oxcmp_basket->getContents() item=basketitem name=gtmCartContents key=basketindex}]
[{assign var="gtmItemPriceObject" value=$basketitem->getPrice()}]
[{assign var="gtmBasketItem" value=$basketitem->getArticle()}]
[{assign var="gtmBasketItemCategory" value=$gtmBasketItem->getCategory()}]
{
'item_id': '[{$gtmCartArticles[$basketindex]->getFieldData('oxartnum')}]',
'item_name': '[{$gtmCartArticles[$basketindex]->getFieldData('oxtitle')}]',
'item_variant': '[{$gtmCartArticles[$basketindex]->getFieldData('oxvarselect')}]',
[{if $gtmBasketItemCategory}]
'item_category': '[{$gtmBasketItemCategory->getSplitCategoryArray(0, true)}]',
'item_category_2': '[{$gtmBasketItemCategory->getSplitCategoryArray(1, true)}]',
'item_category_3': '[{$gtmBasketItemCategory->getSplitCategoryArray(2, true)}]',
'item_category_4': '[{$gtmBasketItemCategory->getSplitCategoryArray(3, true)}]',
'item_list_name': '[{$gtmBasketItemCategory->getSplitCategoryArray()}]',
[{/if}]
'price': [{$gtmItemPriceObject->getPrice()}],
'coupon': '[{foreach from=$oxcmp_basket->getVouchers() item=sVoucher key=key name=Voucher}][{$sVoucher->sVoucherNr}][{if !$smarty.foreach.Voucher.last}], [{/if}][{/foreach}]',
'quantity': [{$basketitem->getAmount()}],
'position': [{$smarty.foreach.gtmCartContents.index}]
}[{if !$smarty.foreach.gtmCartContents.last}],[{/if}]
[{/foreach}]
]
}[{if $oViewConf->isDebugModeOn()}],
'debug_mode': 'true'
[{/if}]
});
[{/strip}]
[{/capture}]
[{oxscript add=$smarty.capture.gtm_ga4_add_payment_info}]
[{/block}]

View File

@ -1,52 +0,0 @@
[{*$oxcmp_basket|get_class_methods|dumpvar*}]
[{assign var="d3BasketPrice" value=$oxcmp_basket->getPrice()}]
[{assign var="d3BasketObject" value=$oxcmp_basket}]
[{assign var='gtmCartArticles' value=$d3BasketObject->getBasketArticles()}]
[{assign var="gtmCurrency" value=$oView->getActCurrency()}]
[{block name="d3_ga4_begin_checkout_block"}]
[{capture name="d3_ga4_begin_checkout"}]
[{strip}]
dataLayer.push({"event": null, "eventLabel": null, "ecommerce": null}); /* Clear the previous ecommerce object. */
dataLayer.push({
'event': 'begin_checkout',
'eventLabel':'Begin of checkout',
'ecommerce':
{
'actionField': "Begin",
'currency': "[{$gtmCurrency->name}]",
'value': [{$d3BasketPrice->getPrice()}],
'coupon': '[{foreach from=$oxcmp_basket->getVouchers() item=sVoucher key=key name=Voucher}][{$sVoucher->sVoucherNr}][{if !$smarty.foreach.Voucher.last}], [{/if}][{/foreach}]',
'items':
[
[{foreach from=$oxcmp_basket->getContents() item=basketitem name=gtmCartContents key=basketindex}]
[{assign var="d3oItemPrice" value=$basketitem->getPrice()}]
[{assign var="gtmBasketItem" value=$basketitem->getArticle()}]
[{assign var="gtmBasketItemCategory" value=$gtmBasketItem->getCategory()}]
{
'item_id': '[{$gtmCartArticles[$basketindex]->getFieldData('oxartnum')}]',
'item_name': '[{$gtmCartArticles[$basketindex]->getFieldData('oxtitle')}]',
'item_variant': '[{$gtmCartArticles[$basketindex]->getFieldData('oxvarselect')}]',
[{if $gtmBasketItemCategory}]
'item_category': '[{$gtmBasketItemCategory->getSplitCategoryArray(0, true)}]',
'item_category_2': '[{$gtmBasketItemCategory->getSplitCategoryArray(1, true)}]',
'item_category_3': '[{$gtmBasketItemCategory->getSplitCategoryArray(2, true)}]',
'item_category_4': '[{$gtmBasketItemCategory->getSplitCategoryArray(3, true)}]',
'item_list_name': '[{$gtmBasketItemCategory->getSplitCategoryArray()}]',
[{/if}]
'price': [{$d3oItemPrice->getPrice()}],
'coupon': '[{foreach from=$oxcmp_basket->getVouchers() item=sVoucher key=key name=Voucher}][{$sVoucher->sVoucherNr}][{if !$smarty.foreach.Voucher.last}], [{/if}][{/foreach}]',
'quantity': [{$basketitem->getAmount()}],
'position': [{$smarty.foreach.gtmCartContents.index}]
}[{if !$smarty.foreach.gtmCartContents.last}],[{/if}]
[{/foreach}]
]
}[{if $oViewConf->isDebugModeOn()}],
'debug_mode': 'true'
[{/if}]
});
[{/strip}]
[{/capture}]
[{oxscript add=$smarty.capture.d3_ga4_begin_checkout}]
[{/block}]

View File

@ -4,229 +4,9 @@ All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
## [unreleased](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.17.2...rel_2.x) - 2024-x
## [2.21.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.20.1...2.21.0) - 2024-09-19
## [1.15.1](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/1.15.0...1.15.1) - 2024-04-11
### Fixed
- missing parameters for widget.php call
## [2.20.1](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.20.0...2.20.1) - 2024-09-11
### Fixed
- missing currency name in begin_checkout template
## [2.20.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.19.0...2.20.0) - 2024-08-20
### Added
- new event "begin_checkout"
- new event "add_payment_info"
## [2.19.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.18.2...2.19.0) - 2024-08-10
### Fixed
- usage of not yet existing function
## [2.18.2](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.18.1...2.18.2) - 2024-06-25
### Fixed
- oe-console apply-configuration triggers on-activate and overwrites existing values
## [2.18.1](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.18.0...2.18.1) - 2024-06-04
### Fixed
- missing return statement, on null/ none
## [2.18.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.17.2...2.18.0) - 2024-06-03
### Added
- trait for generalized method
- new admin UI
- additional check for properly activated module
- admin headitem alternative
- usercentrips step/ option 2
- group CMP-Functionalities/ properties into own Model
- additional help texts, translations, explanations
- extended docs
- auto safe on first approach ga4 + cmp-mod
- onActivate/ onDeactivate
## Changed
- declare module settings consistency
- configParamGetter
- clear dead code
- template code upgrade
- lang text
- amount of save-buttons
- Usercentrics-Class constants and adjust global-module-code to it
- CMP-output in tpl
- clear code and adjust Naming
## Fixed
- false class-property declaration
- wrong to-save param
## Removed
- deprecated and obsolete module-settings
- false composer xml-excludation
## [2.17.2](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.17.1...2.17.2) - 2024-04-11
### Fixed
- error on missing necessary-component
## [2.17.1](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.17.0...2.17.1) - 2024-04-10
### Fixed
- second call of getGtmContainerId() ( returned false )
## [2.17.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.16.0...2.17.0) - 2024-04-10
### Added
- Google-Analytics default values
- default values switch ( admin module settings )
- translations
## Changed
- centralized metadata-id
## [2.16.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.15.0...2.16.0) - 2024-03-20
### Added
- ( Google ) Server-Side tagging usability
## [2.15.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.14.0...2.15.0) - 2024-02-05
### Fixed
- missing Component-ArticleDetails extension, missing ManufacturerListController extension
## [2.14.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.13.1...2.14.0) - 2023-01-22
### Added
- add_to_cart Event to several new shop-pages (landing-page, Account, category article-list, start)
- PHPStan code-cleanup
### Changed
- template structure
- code cleanup
## [2.13.1](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.13.0...2.13.1) - 2023-01-03
### Fixed
- error on array-count at zero entries
## [2.13.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.12.0...2.13.0) - 2023-09-13
### Added
- extended Docs
### Changed
- control-param name
- control-param function
- adjusted check for set control-param
- consentmanager-script-adjustments
## [2.12.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.11.1...2.12.0) - 2023-09-07
### Added
- cookiebot functionality
## [2.11.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.10.1...2.11.0) - 2023-08-23
### Added
- manufacturer extension
- working debug_mode
### Changed
- check for 'article has been removed'
- general template cleanup
## [2.10.1](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.10.0...2.10.1) - 2023-08-03
### Added
- missing param to identify the event
## [2.10.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.9.2...2.10.0) - 2023-08-02
### Added
- new Event "remove_from_cart"
## [2.9.2](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.9.1...2.9.2) - 2023-06-29
### Fixed
- wrong variable for category-object check
## [2.9.1](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.9.0...2.9.1) - 2023-06-27
### Fixed
- deny method call on no category
## [2.9.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.8.0...2.9.0) - 2023-06-27
### Added
- Cookiefirst usability
## [2.8.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.7.0...2.8.0) - 2023-06-23
### Added
- Method to get the in order used Payment-Name
- Method to get the current Article Category
- Following Entries to dedicated event-templates
- coupon
- paymentType
- item_list_name
- item_category
### Changed
- all used template-files have a more dedicated name
- general code cleanup
## [2.7.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.6.0...2.7.0) - 2023-06-19
### Changed
- add_to_cart event template-structure
## [2.6.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.5.0...2.6.0) - 2023-05-31
### Added
- add settings to explicit choose an external service (usercentrics/ consentmanager)
- position to block-extension
- extended instructions to check for in readme
### Fixed
- usercentrics script
- missing right articleList-getter
### Changed
- view_item_list-template block extension
- cookieManager handling
### Removed
- additional check for cookieManagerType
## [2.5.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.4.0...2.5.0) - 2023-05-23
### Added
- additional settings to explicitly indicate that consentmanager is used
### Fixed
- unnecessary converting of int to str
- missing PriceObject-bug
### Changed
- genuine code cleanup
## [2.4.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.3.3...2.4.0) - 2023-05-02
### Added
- "OXID Cookie Management powered by usercentrics" compatibility
- usercentrics defined script attributes
- cookie-manager evaluation
### Changed
- genuine clean up of base-js-files
## [2.3.3](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.3.2...2.3.3) - 2023-03-20
### Fixed
- metadata file path for view_item
## [2.3.2](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.2.2...2.3.2) - 2023-03-17
### Added
- Aggrosoft-Cookie-Consent compatibility
### Fixed
- wrong function for pageview on thankyou page
### Deleted
- unused files
## [2.2.2](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.2.1...2.2.2) - 2023-02-22
### Fixed
- price formatting in view_cart
## [2.2.1](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.1.1...2.2.1) - 2023-02-21
### Added
- cookie handling
## [2.1.1](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.1...2.1.1) - 2023-01-27
### Fixed
- add missing class import
## [2.1](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/2.0...2.1) - 2023-01-27
### Added
- block section for add_to_basket js
- template block order positions
## [2.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/1.1...2.0) - 2023-01-20
### Added
- using of ContainerFactory in ViewConfig
## [1.17.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/1.16.0...1.17.0) - 2024-04-11
### Added
- multilang translations
- GA4 consent-mode default values
### Changed
- metadataID centralized
## [1.16.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/1.15.1...1.16.0) - 2024-04-11
### Added
- ( Google ) Server-Side tagging usability
- false processing of template during missing necessary-component
## [1.15.0](https://git.d3data.de/D3Public/GoogleAnalytics4/compare/1.14.0...1.15.0) - 2024-01-25
### Fixed

View File

@ -5,13 +5,6 @@ Die Einbindung dieser Event-Templates erfolgt über TPL-Blöcke unter `source/mo
*Hinweis: nicht alle templates sind bereits gefĂĽllt. WĂĽnschen Sie die Implementierung eines unausgefĂĽllten templates?
Kommen Sie auf uns zu unter https://www.d3data.de/
## Container-ID
Diese finden Sie im "Google-Tag-Manager"-Arbeitsbereich in der Navigationsleiste.
Sie beginnt mit GTM, gefolgt von einem Bindestrich und einer Zeichenkette.
Diese ID wird benötigt, um Google anzuweise, zu welchem "Google Tag Manager"-Arbeitsbereich die
gesammelten Daten im Daten-Stream geleitet werden sollen.
## Steuerungsparameter
Tragen Sie hier im Normalfall die ID des zu prĂĽfenden Cookies ein.
In bestimmten Fällen, müssen Sie hier alternative Werte eintragen. Diese Fälle sind bedingt
@ -19,6 +12,37 @@ nach der gewählten CMP (Consent Manager Platform).
> nähere Infos unter [CMP](#consent-manager-platform-cmp)
## Blöcke
Für den geregelten Ablauf sind folgende Blöcke nötig:
- Suchergebnisse
- Blockname: search_results
- Datei: page/search/search.tpl
- GA4 Event: view_search_results
- Artikelliste
- Blockname: page_list_productlist
- Datei: page/list/list.tpl
- GA4 Event: view_item_list
- Detailseite
- Blockname: details_productmain_title
- Datei: page/details/inc/productmain.tpl
- GA4 Event: view_item
- dem WK hinzufĂĽgen (button)
- Blockname: details_productmain_tobasket
- Datei: page/details/inc/productmain.tpl
- GA4 Event: add_to_cart
- aus dem WK entfernen
- Blockname: checkout_basket_main
- Datei: page/checkout/basket.tpl
- GA4 Event: remove_from_cart
- Warenkorb
- Blockname: checkout_basket_main
- Datei: page/checkout/basket.tpl
- GA4 Event: view_cart
- abgeschlossener Kauf
- Blockname: checkout_thankyou_main
- Datei: page/checkout/thankyou.tpl
- GA4 Event: purchase
## VerfĂĽgbare Datalayer Variablen
FĂĽr die einfachste Ăśbersicht der enthaltenen Daten empfehle ich den Vorschau-Modus vom Google Tag Manager.
@ -56,7 +80,7 @@ Aktivieren Sie anschlieĂźend diese Weiche. Setzen Sie den Haken bei "Eigenen Coo
- In der Usercentrics-Verwaltung die Services "Google Analytics" und "Google Tag Manager" anlegen
- Den Service ```Google Tag Manager``` in den Moduleinstellungen des 'Google Analytics 4' unter
Google Tag Manager eintragen
-
- [Consent Management Provider](https://www.consentmanager.net/)
- In der Consentmanager-Oberfläche den Anbieter "Google Tag Manager" mit der ID s905 hinzufügen
- Im Frontend, im consentmanager-Pop-up nach dem 'Google Tag Manager' suchen
@ -65,8 +89,5 @@ Aktivieren Sie anschlieĂźend diese Weiche. Setzen Sie den Haken bei "Eigenen Coo
- sonst, in der Consentmanager-Oberfläche Cookie-Liste entsprechendes Cookie suchen und im Admin unter
```Einstell. > Cookie Manager Einstellungen > Cookie-ID``` eintragen
- [Cookiefirst](https://cookiefirst.com)
- im Cookiefirst-Hub das jeweilige Cookie finden underen zugeordnete Kategorie kopieren
- die kopierte Kategory wird nun in den Einstellungen des Moduls hinterlegt:
```Erweiterungen > Module > Google Analytics 4 > Einstell. > Cookie Manager Einstellungen > Steuerungsparameter (vormals CookieID)```
- **Wichtig!** bei Nutzung des Consent-Managers von Google, muss zwangsläufig die Einstellung "Cookie manager Nutzen?" __ausgeschalten!__ werden
- [Cookiebot](https://www.cookiebot.com)
- Nähere Informationen folgen bald! Bis dato, besuchen Sie bitte die offizielle Webseite.

View File

@ -18,14 +18,9 @@ namespace D3\GoogleAnalytics4\Modules\Core{
}
namespace D3\GoogleAnalytics4\Modules\Application\Model{
use OxidEsales\Eshop\Application\Model\Payment;
class Category_parent extends \OxidEsales\Eshop\Application\Model\Category {}
class Basket_parent extends \OxidEsales\Eshop\Application\Model\Basket {}
class Manufacturer_parent extends \OxidEsales\Eshop\Application\Model\Manufacturer {}
class gtmPayment_parent extends Payment {}
}
namespace D3\GoogleAnalytics4\Modules\Application\Controller{

View File

@ -4,5 +4,41 @@ namespace D3\GoogleAnalytics4\Modules\Application\Model;
class Category extends Category_parent
{
use articleTreeStructure;
/**
* @param int $indexOfArray
* @return string
*/
public function getSplitCategoryArray(int $indexOfArray = -1, bool $bShallTakeStd = false) :string
{
if ($bShallTakeStd){
$splitCatArray =
array_values(
array_filter(
explode(
'/',
trim(
parse_url(
$this->getLink(),
5
)
)
)
)
);
if (($indexOfArray >= 0) and (false === empty($splitCatArray[$indexOfArray]))){
return $splitCatArray[$indexOfArray];
}else{
return "";
}
}
return
trim(
parse_url(
$this->getLink(),
5
)
);
}
}

View File

@ -4,5 +4,41 @@ namespace D3\GoogleAnalytics4\Modules\Application\Model;
class Manufacturer extends Manufacturer_parent
{
use articleTreeStructure;
/**
* @param int $indexOfArray
* @return string
*/
public function getSplitCategoryArray(int $indexOfArray = -1, bool $bShallTakeStd = false) :string
{
if ($bShallTakeStd){
$splitCatArray =
array_values(
array_filter(
explode(
'/',
trim(
parse_url(
$this->getLink(),
5
)
)
)
)
);
if (($indexOfArray >= 0) and (false === empty($splitCatArray[$indexOfArray]))){
return $splitCatArray[$indexOfArray];
}else{
return "";
}
}
return
trim(
parse_url(
$this->getLink(),
5
)
);
}
}

View File

@ -1,11 +0,0 @@
<?php
declare(strict_types=1);
namespace D3\GoogleAnalytics4\Modules\Application\Model;
class Vendor extends \OxidEsales\Eshop\Application\Model\Vendor
{
use articleTreeStructure;
}

View File

@ -1,44 +0,0 @@
<?php
namespace D3\GoogleAnalytics4\Modules\Application\Model;
trait articleTreeStructure
{
/**
* @param int $indexOfArray
* @return string
*/
public function getSplitCategoryArray(int $indexOfArray = -1, bool $bShallTakeStd = false) :string
{
if ($bShallTakeStd){
$splitCatArray =
array_values(
array_filter(
explode(
'/',
trim(
parse_url(
$this->getLink(),
5
)
)
)
)
);
if (($indexOfArray >= 0) and (false === empty($splitCatArray[$indexOfArray]))){
return $splitCatArray[$indexOfArray];
}else{
return "";
}
}
return
trim(
parse_url(
$this->getLink(),
5
)
);
}
}

View File

@ -1,20 +0,0 @@
<?php
declare(strict_types=1);
namespace D3\GoogleAnalytics4\Modules\Application\Model;
use OxidEsales\Eshop\Application\Model\Payment;
use OxidEsales\Eshop\Core\Registry;
class gtmPayment extends gtmPayment_parent
{
/**
* @return string
*/
public function gtmGetSelectedPaymentName() :string
{
return $this->getFieldData('oxpayments__oxdesc')?: 'No payment name available';
}
}

View File

@ -12,36 +12,24 @@
namespace D3\GoogleAnalytics4\Modules\Core;
use D3\GoogleAnalytics4\Application\Model\CMP\Usercentrics;
use D3\GoogleAnalytics4\Application\Model\Constants;
use D3\GoogleAnalytics4\Application\Model\ManagerHandler;
use D3\GoogleAnalytics4\Application\Model\ManagerTypes;
use OxidEsales\Eshop\Application\Controller\FrontendController;
use OxidEsales\Eshop\Application\Model\User;
use OxidEsales\Eshop\Core\Config;
use OxidEsales\Eshop\Core\Registry;
use OxidEsales\EshopCommunity\Internal\Container\ContainerFactory;
use OxidEsales\EshopCommunity\Internal\Framework\Module\Configuration\Bridge\ModuleSettingBridgeInterface;
use Psr\Container\ContainerExceptionInterface;
use Psr\Container\NotFoundExceptionInterface;
class ViewConfig extends ViewConfig_parent
{
// Google Tag Manager Container ID
private $sContainerId = null;
// used CMP
private $sCookieManagerType = null;#
// isModule Activated properly?
private $blGA4enabled = null;
private $sCookieManagerType = null;
public function getGtmContainerId()
{
if ($this->sContainerId === null)
{
$this->sContainerId = $this->d3GetModuleConfigParam("_sContainerID");
$this->sContainerId = Registry::getConfig()->getConfigParam('d3_gtm_sContainerID');
}
return $this->sContainerId;
}
@ -58,12 +46,13 @@ class ViewConfig extends ViewConfig_parent
$this->sCookieManagerType = $oManagerHandler->getCurrManager();
}
}
/**
* @return bool
*/
public function shallUseOwnCookieManager() :bool
{
return (bool) $this->d3GetModuleConfigParam('_blEnableOwnCookieManager');
return (bool) Registry::getConfig()->getConfigParam('d3_gtm_settings_hasOwnCookieManager');
}
/**
@ -74,18 +63,14 @@ class ViewConfig extends ViewConfig_parent
/** @var Config $oConfig */
$oConfig = Registry::getConfig();
if (false === $this->isGA4enabled()){
return false;
}
// No Cookie Manager in use
if (false === $this->shallUseOwnCookieManager()) {
if (!$this->shallUseOwnCookieManager()) {
return true;
}
$this->defineCookieManagerType();
$sCookieID = trim($this->d3GetModuleConfigParam('_sControlParameter'));
$sCookieID = trim($oConfig->getConfigParam('d3_gtm_settings_controlParameter'));
// Netensio Cookie Manager
if ($this->sCookieManagerType === ManagerTypes::NET_COOKIE_MANAGER) {
@ -104,8 +89,8 @@ class ViewConfig extends ViewConfig_parent
// UserCentrics or consentmanager
if (
$this->sCookieManagerType === Usercentrics::sModuleIncludationInternalName
or $this->sCookieManagerType === Usercentrics::sExternalIncludationInternalName
$this->sCookieManagerType === ManagerTypes::USERCENTRICS_MODULE
or $this->sCookieManagerType === ManagerTypes::USERCENTRICS_MANUALLY
or $this->sCookieManagerType === ManagerTypes::CONSENTMANAGER
or $this->sCookieManagerType === ManagerTypes::COOKIEFIRST
or $this->sCookieManagerType === ManagerTypes::COOKIEBOT
@ -116,6 +101,7 @@ class ViewConfig extends ViewConfig_parent
return true;
}
// Cookie Manager not (yet) supported
return false;
}
@ -126,15 +112,15 @@ class ViewConfig extends ViewConfig_parent
*/
public function getGtmScriptAttributes() :string
{
$sControlParameter = trim($this->d3GetModuleConfigParam('_sControlParameter'));
$sControlParameter = trim(Registry::getConfig()->getConfigParam('d3_gtm_settings_controlParameter'));
if (false === $this->shallUseOwnCookieManager() or ($sControlParameter === '')){
return "";
}
if (
$this->sCookieManagerType === Usercentrics::sModuleIncludationInternalName
or $this->sCookieManagerType === Usercentrics::sExternalIncludationInternalName
$this->sCookieManagerType === ManagerTypes::USERCENTRICS_MODULE
or $this->sCookieManagerType === ManagerTypes::USERCENTRICS_MANUALLY
)
{
return 'data-usercentrics="' . $sControlParameter . '" type="text/plain" async=""';
@ -156,31 +142,26 @@ class ViewConfig extends ViewConfig_parent
return "";
}
/**
* @throws ContainerExceptionInterface
* @throws NotFoundExceptionInterface
*/
private $blGA4enabled = null;
public function isGA4enabled()
{
if ($this->blGA4enabled === null)
{
$this->blGA4enabled = $this->d3GetModuleConfigParam("_blEnableGA4");
$this->sContainerId = Registry::getConfig()->getConfigParam('d3_gtm_blEnableGA4');
}
return $this->blGA4enabled;
}
public function isGtmConsentModeSetActivated() :bool
{
return $this->d3GetModuleConfigParam("_blEnableConsentMode")?: false;
}
public function getGtmDataLayer()
{
if (!$this->getGtmContainerId()) return "[]";
$oConfig = Registry::getConfig();
$oView = $oConfig->getTopActiveView();
/** @var User|false|null $oUser */
$oUser = $oConfig->getUser();
@ -214,47 +195,12 @@ class ViewConfig extends ViewConfig_parent
public function isDebugModeOn() :bool
{
return $this->d3GetModuleConfigParam("_blEnableDebug")?: false;
return Registry::getConfig()->getConfigParam('d3_gtm_blEnableDebug');
}
/**
* @return string
* @throws ContainerExceptionInterface
* @throws NotFoundExceptionInterface
*/
public function getServerSidetaggingJsDomain() :string
public function isPromotionList($listId)
{
return $this->d3GetModuleConfigParam("_sServersidetagging_js")?: "";
}
/**
* @return string
* @throws ContainerExceptionInterface
* @throws NotFoundExceptionInterface
*/
public function getServerSidetaggingNoJsDomain() :string
{
return $this->d3GetModuleConfigParam('_sServersidetagging_nojs')?: "";
}
/**
* @param string $configParamName
* @return mixed
*/
public function d3GetModuleConfigParam(string $configParamName)
{
return Registry::getConfig()->getShopConfVar(Constants::OXID_MODULE_ID.$configParamName, null, Constants::OXID_MODULE_ID);
}
/**
* @return bool
*/
public function d3IsUsercentricsCMPChosen() :bool
{
$sCMPPubName = $this->d3GetModuleConfigParam('_HAS_STD_MANAGER');
$aPossibleCMP = (oxNew(ManagerTypes::class))->getManagerList();
return (bool) ($sCMPPubName === Usercentrics::sExternalIncludationInternalName
or $sCMPPubName === Usercentrics::sModuleIncludationInternalName);
$oConfig = Registry::getConfig();
$aPromotionListIds = $oConfig->getConfigParam("") ?? ['bargainItems', 'newItems', 'topBox', 'alsoBought', 'accessories', 'cross'];
}
}

View File

@ -1,43 +0,0 @@
<?php
namespace D3\GoogleAnalytics4\Modules\Core;
use OxidEsales\EshopCommunity\Core\Registry;
class WidgetControl extends WidgetControl_parent{
protected function getFrontendStartControllerKey() // phpcs:ignore PSR2.Methods.MethodDeclaration.Underscore
{
/*
* array (
'force_sid' => '2pistlaubiq58qtg3moudei0la',
'lang' => '0',
'actcontrol' => 'details',
'anid' => '064471',
'cl' => 'oxwarticledetails',
'cnid' => '159dd0f2fb2bd6e24ace53a0f1913797',
'listtype' => 'list',
'nocookie' => '1',
'oxwparent' => 'details',
'sid' => '2pistlaubiq58qtg3moudei0la',
'stoken' => 'A22D0F9E',
'varselid' =>
array (
0 => 'b842982bf522aa839bd88221f562fce8',
),
)
*/
$sScriptName = $_SERVER['SCRIPT_NAME'];
if($sScriptName !== '/widget.php')
{
return parent::getFrontendStartControllerKey();
}
$aParameter = $_GET;
if(is_null($aParameter['actcontrol']) and is_null($aParameter['oxwparent']))
{
return 'D3\GoogleAnalytics4\Application\Component\Widget\d3GtmStartWidget';
}
return parent::getFrontendStartControllerKey();
}
}

View File

@ -1,44 +0,0 @@
<?php
declare(strict_types=1);
namespace D3\GoogleAnalytics4\Setup;
use D3\GoogleAnalytics4\Application\Model\Constants;
use OxidEsales\Eshop\Core\Registry;
use OxidEsales\Eshop\Core\ViewConfig;
class Actions
{
/**
* @param string $sVarType
* @param string $sSettingName
* @param string $sSettingValue
* @return void
*/
public function d3SaveDefaultSettings(string $sVarType, string $sSettingName, string $sSettingValue){
$oConfig = Registry::getConfig();
if ($this->d3GetModuleConfigParam($sSettingName) and (trim($this->d3GetModuleConfigParam($sSettingName)) !== trim($sSettingValue))){
$sSettingValue = trim($this->d3GetModuleConfigParam($sSettingName));
}
$oConfig->saveShopConfVar(
$sVarType,
Constants::OXID_MODULE_ID.$sSettingName,
$sSettingValue,
$oConfig->getShopId(),
Constants::OXID_MODULE_ID
);
}
/**
* @param string $configParamName
* @return mixed
*/
public function d3GetModuleConfigParam(string $configParamName)
{
return Registry::getConfig()->getShopConfVar(Constants::OXID_MODULE_ID.$configParamName, null, Constants::OXID_MODULE_ID);
}
}

View File

@ -1,37 +0,0 @@
<?php
declare(strict_types=1);
namespace D3\GoogleAnalytics4\Setup;
class Events
{
/**
* @return void
*/
public static function onActivate()
{
$oActions = oxNew(Actions::class);
$oActions->d3SaveDefaultSettings(
'str',
'_sServersidetagging_js',
'https://www.googletagmanager.com/gtm.js'
);
$oActions->d3SaveDefaultSettings(
'str',
'_sServersidetagging_nojs',
'https://www.googletagmanager.com/ns.html'
);
$oActions->d3SaveDefaultSettings(
'str',
'_sContainerID',
'GTM-'
);
}
/**
* @return void
*/
public static function onDeactivate(){}
}

View File

@ -37,16 +37,17 @@
"*.md",
"composer.json",
".php-cs-fixer.php",
"*.xml",
"*.neon"
],
"target-directory": "d3/googleanalytics4"
}
},
"require": {
"php": "7.1 - 8.2",
"oxid-esales/oxideshop-ce": "^6.5.3",
"google/apiclient":" ^2.0",
"phpstan/phpstan": "^1.10"
"php": ">=7.1",
"oxid-esales/oxideshop-ce": "v6.0 - v6.3",
"google/apiclient":"^2.0",
"phpstan/phpstan": "^1.8"
},
"autoload": {
"psr-4": {

View File

@ -1,8 +0,0 @@
<?xml version="1.0" encoding="ISO-8859-15"?>
<OX>
<OXMENU id="d3mxd3modules">
<MAINMENU id="d3mxgoogleanalytics4">
<SUBMENU id="d3mxgoogleanalytics4set" cl="d3googleanalytics4_main"/>
</MAINMENU>
</OXMENU>
</OX>

View File

@ -1,7 +1,5 @@
<?php
use D3\GoogleAnalytics4\Application\Controller\Admin\GA4AdminUserInterface_main as GA4AdminUserInterfaceMainController;
use D3\GoogleAnalytics4\Application\Model\Constants as Constants;
use D3\GoogleAnalytics4\Modules\Application\Component\d3GtmBasketComponentExtension;
use D3\GoogleAnalytics4\Modules\Application\Component\Widget\d3GtmWidgetArticleDetails as d3GtmWidgetArticleDetails;
use D3\GoogleAnalytics4\Modules\Application\Controller\ArticleDetailsController;
@ -16,7 +14,6 @@ use D3\GoogleAnalytics4\Modules\Application\Controller\d3GtmStartController;
use D3\GoogleAnalytics4\Modules\Application\Controller\ThankYouController;
use D3\GoogleAnalytics4\Modules\Application\Model\Basket as Basket;
use D3\GoogleAnalytics4\Modules\Application\Model\Category as Category;
use D3\GoogleAnalytics4\Modules\Application\Model\gtmPayment as gtmPayment;
use D3\GoogleAnalytics4\Modules\Application\Model\Manufacturer as Manufacturer;
use D3\GoogleAnalytics4\Modules\Core\ViewConfig;
use OxidEsales\Eshop\Application\Component\BasketComponent as OEBasketComponent;
@ -34,12 +31,11 @@ use OxidEsales\Eshop\Application\Controller\ThankYouController as OEThankYouCont
use OxidEsales\Eshop\Application\Model\Basket as OEBasket;
use OxidEsales\Eshop\Application\Model\Category as OECategory;
use OxidEsales\Eshop\Application\Model\Manufacturer as OEManufacturer;
use OxidEsales\Eshop\Application\Model\Payment as OEPayment;
use OxidEsales\Eshop\Core\ViewConfig as OEViewConfig;
$sMetadataVersion = '2.1';
$aModule = [
'id' => Constants::OXID_MODULE_ID,
'id' => 'd3googleanalytics4',
'title' => 'Google Analytics 4',
'description' => "Dieses Modul bietet die Möglichkeit in Ihrem OXID eShop (6.x) die neue 'Property'
Google Analytics 4 (GA4) von Google zu integrieren.<br>
@ -52,23 +48,18 @@ $aModule = [
Die Entwicklung basiert auf einem Fork von Marat Bedoev - <a href='https://github.com/vanilla-thunder/oxid-module-gtm'>Github-Link</a>
",
'thumbnail' => 'thumbnail.png',
'version' => '2.21.0',
'version' => '1.15.1',
'author' => 'Data Development (Inh.: Thomas Dartsch)',
'email' => 'support@shopmodule.com',
'url' => 'https://www.oxidmodule.com/',
'controllers' => [
'd3googleanalytics4_main' => GA4AdminUserInterfaceMainController::class
],
'extend' => [
// Core
OEViewConfig::class => ViewConfig::class,
\OxidEsales\Eshop\Core\WidgetControl::class => \D3\GoogleAnalytics4\Modules\Core\WidgetControl::class,
// Model
OECategory::class => Category::class,
OEBasket::class => Basket::class,
OEManufacturer::class => Manufacturer::class,
OEPayment::class => gtmPayment::class,
// Controller
OEBasketController::class => BasketController::class,
@ -90,9 +81,7 @@ $aModule = [
// Event files that store the GA4 Event-Information
'event/add_to_cart.tpl' => 'd3/googleanalytics4/Application/views/event/add_to_cart.tpl',
'event/view_item.tpl' => 'd3/googleanalytics4/Application/views/event/view_item.tpl',
'event/view_item.tpl' => 'd3/googleanalytics4/Application/views/event/view_item.tpl',
'event/begin_checkout.tpl' => 'd3/googleanalytics4/Application/views/event/begin_checkout.tpl',
'event/add_payment_info.tpl' => 'd3/googleanalytics4/Application/views/event/add_payment_info.tpl',
'event/view_cart.tpl' => 'd3/googleanalytics4/Application/views/event/view_cart.tpl',
'event/purchase.tpl' => 'd3/googleanalytics4/Application/views/event/purchase.tpl',
'event/view_item_list.tpl' => 'd3/googleanalytics4/Application/views/event/view_item_list.tpl',
'event/view_search_result.tpl' => 'd3/googleanalytics4/Application/views/event/view_search_result.tpl',
@ -103,10 +92,6 @@ $aModule = [
'page/account/d3gtmnoticelist.tpl' => 'd3/googleanalytics4/Application/views/tpl/page/account/d3gtmnoticelist.tpl',
'page/account/d3gtmrecommendationlist.tpl' => 'd3/googleanalytics4/Application/views/tpl/page/account/d3gtmrecommendationlist.tpl',
'page/account/d3gtmwishlist.tpl' => 'd3/googleanalytics4/Application/views/tpl/page/account/d3gtmwishlist.tpl',
// Admin Templates
'ga4/admin/d3ga4uimain.tpl' => 'd3/googleanalytics4/Application/views/admin/tpl/d3googleanalytics4_main.tpl',
'ga4/admin/d3ga4uiheaditem.tpl' => 'd3/googleanalytics4/Application/views/admin/tpl/d3googleanalytics4_headitem.tpl',
],
'blocks' => [
// tag manager js
@ -129,26 +114,12 @@ $aModule = [
'file' => '/Application/views/blocks/view_item.tpl',
'position' => 150
],
// View Cart
// checkout
[
'template' => 'page/checkout/basket.tpl',
'block' => 'checkout_basket_main',
'file' => '/Application/views/blocks/view_cart.tpl'
],
// add_to_cart
[
'template' => 'page/details/inc/productmain.tpl',
'block' => 'details_productmain_tobasket',
'file' => '/Application/views/blocks/details_productmain_tobasket.tpl',
'position' => 150
],
// remove_from_cart
[
'template' => 'page/checkout/basket.tpl',
'block' => 'checkout_basket_main',
'file' => '/Application/views/blocks/remove_from_cart.tpl',
'position' => 150
],
[
'template' => 'page/checkout/thankyou.tpl',
'block' => 'checkout_thankyou_main',
@ -169,6 +140,13 @@ $aModule = [
'file' => '/Application/views/blocks/view_search_result.tpl',
'position' => 150
],
// add_to_cart
[
'template' => 'page/details/inc/productmain.tpl',
'block' => 'details_productmain_tobasket',
'file' => '/Application/views/blocks/details_productmain_tobasket.tpl',
'position' => 150
],
[
'template' => 'page/list/list.tpl',
'block' => 'page_list_listbody',
@ -181,26 +159,56 @@ $aModule = [
'file' => '/Application/views/blocks/start_welcome_text.tpl',
'position' => 150
],
// Checkout process
// Begin CHeckout
// remove_from_cart
[
'template' => 'page/checkout/user.tpl',
'block' => 'checkout_user_main',
'file' => '/Application/views/blocks/begin_checkout.tpl',
'template' => 'page/checkout/basket.tpl',
'block' => 'checkout_basket_main',
'file' => '/Application/views/blocks/remove_from_cart.tpl',
'position' => 150
]
],
// Add payment info
// We add it into checkout_order_main ( checkout/order.tpl ) to make sure a payment is actually added;
// we'll also do it like that in the future for add_shipping_info ( not planed yet )
'settings' => [
[
'template' => 'page/checkout/order.tpl',
'block' => 'checkout_order_main',
'file' => '/Application/views/blocks/add_payment_info.tpl',
'position' => 150
'group' => 'd3_gtm_settings',
'name' => 'd3_gtm_sContainerID',
'type' => 'str',
'value' => 'GTM-',
'position' => 0
],
[
'group' => 'd3_gtm_settings',
'name' => 'd3_gtm_blGA4enab',
'type' => 'bool',
'value' => true,
'position' => 1
],
'events' => [
'onActivate' => '\D3\GoogleAnalytics4\Setup\Events::onActivate',
'onDeactivate' => '\D3\GoogleAnalytics4\Setup\Events::onDeactivate',
[
'group' => 'd3_gtm_settings',
'name' => 'd3_gtm_blEnableDebug',
'type' => 'bool',
'value' => false,
'position' => 999
],
[
'group' => 'd3_gtm_settings_cookiemanager',
'name' => 'd3_gtm_settings_hasOwnCookieManager',
'type' => 'bool',
'value' => false,
'position' => 999
],
[
'group' => 'd3_gtm_settings_cookiemanager',
'name' => 'd3_gtm_settings_controlParameter',
'type' => 'str',
'value' => '',
'position' => 999
],
[
'group' => 'd3_gtm_settings_cookiemanager',
'name' => 'd3_gtm_settings_HAS_STD_MANAGER',
'type' => 'select',
'value' => 'none',
'constraints' => 'NONE|CONSENTMANAGER|USERCENTRICS|COOKIEFIRST|COOKIEBOT',
],
]
];

View File

@ -1,15 +1,16 @@
parameters:
scanFiles:
- IntelliSenseHelper.php
- ../../oxid-esales/oxideshop-ce/source/bootstrap.php
- ../../oxid-esales/oxideshop-ce/source/oxfunctions.php
- ../../oxid-esales/oxideshop-ce/source/overridablefunctions.php
- ../../../../Shops/CE/6.1.x/616_/vendor/oxid-esales/oxideshop-ce/source/bootstrap.php
- ../../../../Shops/CE/6.1.x/616_/vendor/oxid-esales/oxideshop-ce/source/oxfunctions.php
- ../../../../Shops/CE/6.1.x/616_/vendor/oxid-esales/oxideshop-ce/source/overridablefunctions.php
scanDirectories:
- ../../oxid-esales
- ../../../../Shops/CE/6.1.x/616_/vendor/oxid-esales
ignoreErrors:
- '#.*is not subtype of Throwable.*#'
- '#\$sValue of method OxidEsales\\EshopCommunity\\Core\\Controller\\BaseController::addTplParam\(\) expects string,[ a-zA-Z\.]+#'
paths:
- ./
level: 5
phpVersion: 80100
phpVersion: 70200
checkMissingIterableValueType: false