Javascript gtag/谷歌标签管理器混乱

Javascript gtag/谷歌标签管理器混乱,javascript,reactjs,google-analytics,google-tag-manager,next.js,Javascript,Reactjs,Google Analytics,Google Tag Manager,Next.js,我正在使用Google Analytics跟踪我的react应用程序中的自定义事件。当我第一次推出代码时,我阅读了,建议使用gtag方法而不是ga方法来进行日志调用。这一直运作良好 我使用的是谷歌标签管理器,所以这些脚本都是通过GTM加载的(大概是这样) 现在我正在做一些更棘手的事情,服务器需要告诉客户端在特定情况下登录页面加载。因此,我修改了GTM初始化代码,以便在加载GTM后触发事件。我读过如何做到这一点 奇怪的是,当指示GTM库已加载的回调未定义且用于在Analytics中记录事件的代码失

我正在使用Google Analytics跟踪我的react应用程序中的自定义事件。当我第一次推出代码时,我阅读了,建议使用
gtag
方法而不是
ga
方法来进行日志调用。这一直运作良好

我使用的是谷歌标签管理器,所以这些脚本都是通过GTM加载的(大概是这样)

现在我正在做一些更棘手的事情,服务器需要告诉客户端在特定情况下登录页面加载。因此,我修改了GTM初始化代码,以便在加载GTM后触发事件。我读过如何做到这一点

奇怪的是,当指示GTM库已加载的回调未定义且用于在Analytics中记录事件的代码失败时,就会触发
gtag
。当我可以在浏览器控制台中键入
gtag
时,它已经被定义好了,所以GTM脚本可能是在第二次加载它

if (!!window.google_tag_manager) {
  // Google Tag Manager has already been loaded
  doSomethingWith(window.google_tag_manager);
} else {
  window.addEventListener('gtm_loaded', function() {
    //----------------------------------------
    // Google Tag Manager has been loaded, but
    // gtag object is not defined :(
    //----------------------------------------
  });
}
是否有其他方法使用
google\u tag\u manager
对象记录分析事件?或者,有没有办法知道
gtag
对象在缺少轮询的情况下何时可用(真的想避免这种情况)

这是我用来加载GTM的代码

class InitDataLayer extends Component {
    componentDidMount = () => {
        window.dataLayer = [{
            appName: 'promos',
        }];
    }
    render = () => (<script id="init-data-layer" />)
}

class LoadGtm extends Component {
    componentDidMount = () => {
        (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);

            j.addEventListener('load', () => {
                const _ge = new CustomEvent('gtm_loaded', { bubbles: true });
                d.dispatchEvent(_ge);
            });
        })(window,document,'script','dataLayer','GTM-XXXXXXX');
    }
    render = () => (<script id="load-gtm" />)
}
类InitDataLayer扩展组件{
componentDidMount=()=>{
window.dataLayer=[{
appName:“promos”,
}];
}
渲染=()=>()
}
类LoadGtm扩展组件{
componentDidMount=()=>{
(功能(w、d、s、l、i){
w[l]=w[l]| |[];
w[l]。推({
“gtm.start”:新日期().getTime(),
事件:'gtm.js'
});
var f=d.getElementsByTagName[0],
j=d.createElement,
dl=l!=“数据层”?“&l=”+l:“”;
j、 异步=真;
j、 src='1〕https://www.googletagmanager.com/gtm.js?id=“+i+dl;
f、 parentNode.insertBefore(j,f);
j、 addEventListener('load',()=>{
const_ge=new CustomEvent('gtm_-loaded',{bubbles:true});
d、 调度事件;
});
})(窗口、文档、'script'、'dataLayer'、'GTM-XXXXXXX');
}
渲染=()=>()
}

您可以在google tag manager界面中创建google analytics事件。这不需要额外的编码。参见参考

我意识到
gtag
是在GTM中定义的!然后,我使用问题中概述的方法调整标记,以触发一个定制事件,指示
gtag
何时可用:

<!-- Global site tag (gtag.js) - Google Analytics -->
<script async src="https://www.googletagmanager.com/gtag/js?id=UA-XXXXXXXXXX"></script>
<script>
  window.dataLayer = window.dataLayer || [];
  function gtag(){dataLayer.push(arguments);}
  gtag('js', new Date());
  gtag('config', 'UA-XXXXXXXXXX', {send_page_view: false});
  var _ge = new CustomEvent('gtag_loaded', { bubbles: true });
  document.dispatchEvent(_ge);
</script>

我不喜欢在GTM接口中实现几个事件中的一个。当然有一种方法可以通过编程实现这一点。
if(typeof gtag !== 'undefined') {
    gaSendEvent(event);
} else {
    window.addEventListener('gtag_loaded', () => {
        gaSendEvent(event);
    });
}