如何更改Meteor加载Javascript文件的顺序?

时间:2012-05-21 21:47:13

标签: javascript dependencies meteor require

当您使用Meteor框架创建项目时,它会将所有文件打包在一起,但似乎没有办法明确说出“我希望在该文件之前加载此文件”。

比方说,我有2个javascript文件:foo.jsbar.js

文件bar.js实际上包含的代码取决于foo.js内的代码,但Meteor在bar.js之前加载foo.js,打破了项目。

  • node.js 中,我只需在require('./bar')内使用foo.js
  • 浏览器中,我会将<script>标记指向foo.js,另一个指向bar.js,以便加载文件按照正确的顺序。

我们怎样才能在流星中做到这一点?

4 个答案:

答案 0 :(得分:62)

根据Meteor文档,文件当前按此顺序加载:

  1. 首先加载[project_root] / lib中的文件
  2. 文件按目录深度排序。首先加载更深的文件。
  3. 文件按字母顺序排序。
  4. main。*文件最后加载。
  5. 来源: http://docs.meteor.com/#structuringyourapp

答案 1 :(得分:2)

不是所有场景的解决方案,但我认为理想情况下,任何依赖于其他代码的内容都会放在Meteor.startup函数中,以确保所有内容都已加载。

答案 2 :(得分:-2)

您可以随时使用像yepnope.js这样的JS加载器,并将其添加到client.js文件中。这对我有用。

答案 3 :(得分:-2)

我有一组在公共名称空间(js global)下构建的实用程序函数。

// utils/utils.js
Utils = {};

然后在子文件夹中:

// utils/validation/validation.js
Utils.Validation = {};

// utils/validation/creditCard.js
Utils.Validation.creditCard = ... // validation logic etc

我也有大量使用Utils及其子对象的代码。

显然,这个结构首先不能作为Meteor加载子文件夹。

为了使它按预期工作,我不得不创建具有无意义名称的/ subfolder / subfolder / subfolder,然后在最深的子文件夹中推送根对象,并且子文件夹中的分支对象不那么深。

这对我的品味和容易出错非常违反直觉(假设你的组件在文件夹结构中更深)。

为了解决这个问题,我使用Q库来推迟和承诺。解决方案仍然不干净,因为它会使您进行常规代码重复和检查,但它可以让您完全控制加载顺序而不会弄乱目录结构(对于那些说您可以根据需要组织流星代码的人们问好)。

示例:

//utils.js
UtilsDefer = UtilsDefer || Q.defer();
UtilsDefer.resolve({
    // here some root utils stuff
});

//cards.js
// here we'll depend on Utils but don't want to care about directory structure
UtilsDefer = UtilsDefer || Q.defer(); // it will be a) already 
// resolved defer from utils.js, or b) new defer that will
// be resolved later in utils.js
UtilsDefer.then(function(Utils) {
    // do something with utils usage, or for instance add some fields here
    Utils.CreditCardDefer = Utils.CreditCardDefer || Q.defer();
    Utils.CreditCardDefer.resolve({
        // Credit card utils here
    })
});

//someOtherFile.js
// it will be pain to use sub-objects with this method though:
UtilsDefer = UtilsDefer || Q.defer();
UtilsDefer.then(function(Utils) {
    Utils.CreditCardDefer = Utils.CreditCardDefer || Q.defer();
    Utils.CreditCardDefer.then(function(CreditCard) {
        // do stuff with CreditCard _if_ you need to do it on startup stage   
    })
});

这是一个相当狭窄的用例的例子,因为大多数情况下你会很乐意在一些用户交互回调中处理这些全局变量,或Meteor.startup所有已经初始化的东西。否则,如果您希望在早期阶段对初始化顺序进行细粒度控制,那么这可能是一种解决方案。