0

我有一个包含多个组件的 AEM 页面,这些组件有一个 .js 文件,其中包含一个包含所有客户端逻辑的函数。然后我们在组件的 HTML 中调用该函数:

<script>
    window.bootstrap_component(function() {
        init_component_name();
    });
</script>

如前所述,init_component_name 是包含我们需要的所有逻辑的函数的名称:

function init_component_name() {
    //DO STUFF
}

包装器 bootstrap_component 功能在我们所有页面的共享 head.html 中定义为:

<script>
    window.bootstrap_component = function (handler) {
        if (typeof handler === 'function') {
            if (document.readyState === "complete" || document.readyState === "loaded" || document.readyState === "interactive") {
                handler();
            } else {
                document.addEventListener("DOMContentLoaded", function() {
                    handler();
                });
            }
        }
    }
</script>

这工作正常,我们没有任何实际问题,但我们最近开始使用 Bugsnag 进行错误监控和报告,并且我们收到几乎每个组件的报告,在页面上都说 ReferenceError 所以/和/所以 init_component_name() 没有定义。

我认为发生这种情况的原因是因为 init_component_name() 函数未在脚本标记中声明,并且因为这个函数(init_component_name)已附加到它正在执行的窗口对象,并且您没有看到任何控制台错误。

如果我是正确的,是否会将这些脚本标签修改为这样的工作?

<script>
    window.bootstrap_component(function() {
        window.init_component_name();
    })
</script>

我的一位同事想为 init_component_name 函数添加一个超时时间,比如 1ms,但它让我感觉不对劲。有没有更明智的做法?

4

1 回答 1

2

如果我是正确的,是否会将这些脚本标签修改为这样的工作?

window.bootstrap_component(function() {
    window.init_component_name();
})

是的,但是您会遇到将多个数据写入全局命名空间的问题window,这并不理想。如果另一个第三方脚本决定覆盖它怎么办?

理想情况下,您应该有一个命名空间并将所有内容都放在那里,并且只将该命名空间写入window.

window.something = {};
something.bootstrap_component = { //...

something.init_component_name = () => {
    //DO STUFF
}

或者更好的是,使用模块(尽管这需要一些简单的代码重构)。

不要做超时黑客。真的,真的太可怕了;如果由于某种原因脚本加载时间超过一秒怎么办?您还迫使您的 UI 等待一秒钟,这通常是不必要的。这种 hack 往往会出现在没有正确考虑年表和范围的地方。

于 2021-01-13T18:25:52.617 回答