【问题标题】:Migration from simple Module pattern to RequireJS AMD从简单的模块模式迁移到 RequireJS AMD
【发布时间】:2013-11-20 15:57:02
【问题描述】:

我在我的 Javascript 应用程序中使用模块模式,我想迁移到 RequireJS 和 AMD。

我目前的实现是这样的:

// Module main : Module.js
var myModule = (function(my, $, undefined) {
    'use strict';

    var m_privateMembers;
    var m_stuff = new my.Pear({color:"green"});

    //---------------------------------------

    function privateFunctions(args) {
    }

    //-----------------------------------

    my.publicFunctions = function(args) {
    };

    return my;
})(myModule || {}, jQuery);



// Module class Fruit : Module.Fruit.js
var myModule = (function(my, $, undefined) {
    'use strict';

    my.Fruit = Object.makeSubclass();

    my.Fruit.prototype._init = function() {

    };

    my.Fruit.prototype.someClassFunction = function() {
    };

    return my;
})(myModule || {}, jQuery);


// Module class Pear : Module.Pear.js
var myModule = (function(my, $, undefined) {
    'use strict';

    my.Pear = Fruit.makeSubclass();

    my.Pear.prototype._init = function(args) {
        this.m_someClassMember = args;
    };

    my.Pear.prototype.someClassFunction = function() {
    };

    return my;
})(myModule || {}, jQuery);

在我的 index.html 中,我使用脚本 html 标记来包含我的不同模块文件,并且一切正常。

我的问题是:

1/ 为什么RequireJS系统比这个多脚本标签系统更好?

使用我目前的 RequireJS 方法:

define(['jquery'], function($) {

    var myModule = (function(my, $, undefined) {
        'use strict';

        var m_privateMembers;
        var m_stuff = new my.Pear({color:"green"});

        //---------------------------------------

        function privateFunctions(args) {
        }

        //-----------------------------------

        my.publicFunctions = function(args) {
        };

        return my;
    })(myModule || {}, $);

    return myModule;
});

2/ 我如何迁移到 RequireJS 模块并保持我的实际模块通过嵌入式子类提供的类似单例的模式?

显然有几个问题:

2.1/ *m_stuff 无法实例化my.Pear,不知道怎么用require 将模块拆分成几个文件?*

2.2/ 如果我有两个其他模块都依赖于 myModule,那么 myModule 变量是否会是这些模块中的同一个实例(因为 myModule 不再位于全局范围内)? p>

编辑:这个快速模式说明了我需要在一个更复杂的框架中做些什么:

schema

【问题讨论】:

    标签: javascript requirejs js-amd


    【解决方案1】:

    为什么RequireJS系统比这个多脚本标签系统更好?

    我不会对此进行详细介绍,但只要查看您现有的模块设置,您就会发现 AMD 将不需要显式脚本排序和将内容分配给命名空间。 RequireJS 构建工具也会负责准备您的脚本以进行生产。

    你可以阅读更多

    我如何迁移到 RequireJS 模块并保持单例模式 我的实际模块提供嵌入式子类的模式?

    让我们以水果和梨为例来看看这个

    使用requiredefine 时,您已经创建了一个封装所有逻辑的闭包,因此无需在内部创建另一个闭包。保持简单。

    // Fruit.js
    define(['jquery'], function($) {
        'use strict';
    
        var Fruit = Object.makeSubclass();
    
        Fruit.prototype._init = function() {
    
        };
    
        Fruit.prototype.someClassFunction = function() {
    
        };
    
        return Fruit;
    });
    
    // Pear.js
    define(['jquery', 'path/to/Fruit'], function($, Fruit) {
        'use strict';
    
        var Pear = Fruit.makeSubclass();
    
        Pear.prototype._init = function(args) {
            this.m_someClassMember = args;
        };
    
        Pear.prototype.someClassFunction = function() {
    
        };
    
        return Pear;
    });
    

    我不知道如何用require将模块拆分成几个文件?

    基本上只是将您的“类”或模块分解为单独的 AMD 模块,并在需要时明确定义依赖关系。您可以从上面的示例中看到 Pear 如何使用 Fruit 模块。

    如果我有两个都依赖于 myModule 的其他模块,将 myModule var 在那些模块中是同一个实例(因为 myModule 不再在全局范围内)?

    一旦你需要一个模块并加载它,那么其他模块对它的任何其他引用都将获得相同的实例。因此,让您的模块返回构造函数并允许其他模块在必要时实例化它通常是最佳实践。

    【讨论】:

    • 我现在更清楚了,我还没有真正理解的最后一件事是我是否在我的模块中正确使用了相同的返回 var 将它们包装在一个公共命名空间中,但它接缝工作正常。
    • AMD 不需要使用命名空间。这个想法是将所有内容都包含在不引用全局范围的模块中
    • 如果我在一个包含多个大型应用程序的框架上工作,我倾向于拆分为模块的集合或库。我不能在同一个平面逻辑层次结构上拥有数百个模块(或者我应该?)。一组模块将处理 Fruit 逻辑,另一个将处理完全不同的任务,例如在应用程序外部发送消息等。我还需要在其他应用程序中重用部分模块,例如消息传递库。事实上,我需要的更像是一个 C++ 命名空间,在我的每个库中都有一个单例插件,当然还有我的库插件和/或其他库模块使用的所有库模块。
    • 您可以(并且应该)将模块分组到一个目录结构中。这将允许与命名空间相同的组织
    猜你喜欢
    • 2012-05-28
    • 1970-01-01
    • 2017-04-24
    • 2019-05-03
    • 2017-02-08
    • 2019-05-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多