【问题标题】:How to add momentjs to a minified bundle file?如何将 momentjs 添加到缩小的捆绑文件中?
【发布时间】:2015-04-13 07:28:59
【问题描述】:

我将在项目中添加momentjs 库(及其moment-timezone 插件)。在这个项目中,我使用dojo 及其 AMD 加载程序(与requirejs 非常相似)在调试模式下工作。但是对于生产环境,我创建了三个压缩包:一个包含所有外部库(如jquerybootstrap 和其他插件),另一个包含私有 js 框架,第三个包含应用程序的特定代码。

好吧,在开发模式下momentjs 没有问题,因为在配置文件中定义了它的路径后,它会正确加载,但我想将它添加到外部捆绑文件中。这就是我遇到问题的地方,因为虽然捆绑文​​件包含 momentjs 代码,但文件 moment.jsmoment-timezone-with-data.js 也被加载了,因为它们在模块的开头是必需的。

为了解决类似文件的这个问题,我使用了文件的条件加载。例如,这适用于jquery:如果我正在调试该库,则会显式加载。如果我不调试,我假设它是通过捆绑文件加载的,并且它可以工作,因为$ 是作为全局变量加载的。

我的问题的根源来了:momentjs 在开头进行检查,以查看是否定义了 define 函数:

(function (global, factory) {
    typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() :
    typeof define === 'function' && define.amd ? define(factory) :
    global.moment = factory()
}(this, function () { 
    'use strict';
    [...] 
});

显然,define 函数是由dojo 定义的,这会导致momentjs 必须始终作为 amd 模块加载,这会导致即使在生产环境中也可以加载其文件。那么如何在不修改原始源代码的情况下避免这个问题呢?我认为如果将它作为全局变量加载,它应该可以工作,但是还有其他方法可以解决这个问题吗?

对这篇大文章感到抱歉,但我已尽力解释得更好。

【问题讨论】:

    标签: javascript dojo requirejs bundle momentjs


    【解决方案1】:

    如果您有一个库检测到 AMD 加载器并仅在加载器存在时才将自己声明为 AMD 模块,并且想要加载此库以便它不会将自己声明为 AMD 模块,那么您需要加载这个库在script 元素中你加载 AMD 加载器之前。

    或者,必须在加载您的 AMD 加载程序之后加载您的库,您可以暂时取消定义 define 并在之后再次定义它:

    <script>
        my_variable_for_saving_define = define;
        window.define = undefined;
    </script>
    <script [that loads your module]></script>
    <script>
        define = my_variable_for_saving_define;
    </script>
    

    my_variable_for_saving_define 用于说明目的。选择合理可能不会引起冲突的东西。

    【讨论】:

    • 我已经测试了您的方法并且它有效(我必须查看我的捆绑文件以解决任何其他问题,但发布问题已解决)。但是我想知道是否有任何更优雅的解决方案,因为这似乎有点棘手,不是吗?
    • 如果我知道一个更优雅的解决方案,它会在我的答案中。 :) 我可以看到有人为 RequireJS 实现了一个可以形式化它的插件,但我不知道这样的插件。 (而且我不确定创建此类插件是否存在不可逾越的障碍。)
    猜你喜欢
    • 1970-01-01
    • 2012-08-09
    • 2012-08-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多