【问题标题】:Loading Scripts Sequentially按顺序加载脚本
【发布时间】:2016-11-03 11:46:55
【问题描述】:

我有一个网页,我按顺序加载我的脚本,因为每个加载的脚本都需要在它之前加载脚本。例如js/global.jsjs/menu.jsjs/loan.jsjs/contribution.js按顺序需要彼此,contributions.js需要loan.jsloan,js需要menu.js,等等。我已经设法通过下面的代码实现了这一点。

$(document).ready(function () {

LoadScriptscontri();
});

function LoadScriptscontri(async) {
    if (async === undefined) {
        async = false;
    }
    var scripts = [];
    var _scripts = [  'js/global.js', 'js/menu.js', 'js/loan.js', 'js/contributions.js'];

    if (async) {
        LoadScriptsAsync(_scripts, scripts)
    } else {
        LoadScriptsSync(_scripts, scripts)
    }
}

    // what you are looking for :
   function LoadScriptsSync(_scripts, scripts) {

    var x = 0;
    var loopArray = function (_scripts, scripts) {
        // call itself
        loadScript(_scripts[x], scripts[x], function () {
            // set x to next item
            x++;
            // any more items in array?
            if (x < _scripts.length) {
                loopArray(_scripts, scripts);
            }
        });
    }
    loopArray(_scripts, scripts);
}

// async load as in your code
function LoadScriptsAsync(_scripts, scripts) {
    for (var i = 0; i < _scripts.length; i++) {
        loadScript(_scripts[i], scripts[i], function () { });
    }
}

// load script function with callback to handle synchronicity 
function loadScript(src, script, callback) {

    script = document.createElement('script');
    script.onerror = function () {
        // handling error when loading script
        alert('Error to handle')
    }
    script.onload = function () {
        console.log(src + ' loaded ')
        callback();
    }
    script.src = src;
    document.getElementsByTagName('head')[0].appendChild(script);
}

但他的问题是,当我使用window.location = "http://cooperative-izumedia.rhcloud.com/contributions.html"; 将页面从这个更改为window.location = "http://cooperative-izumedia.rhcloud.com/dashboard.html"; 并返回时,它不再按所需的顺序加载,而是首先加载contributions.js。到底发生了什么,我该如何摆脱它。我在 firefox 和 chrome 中都对其进行了测试,但仍然得到相同的结果。

我的调试信息

dashboardjsloader.js:54 js/global.js 已加载

dashboardjsloader.js:54 js/menu.js 加载

dashboardjsloader.js:54 js/loan.js 加载

dashboardjsloader.js:54 js/dashboard.js 加载

menu.js:113 id in menu.js = d2b2aecb0197b6f439056 /*here am spitting out the id got from menu.js*/

dashboard.js:119 0 /*here dashboard.js is able to determine that the section it will work on is of index 0 thanks to menu.js*/

导航到http://cooperative-izumedia.rhcloud.com/contributions.html/*here I change page*/

contributionsjsloader.js:54 js/global.js 加载

contributionsjsloader.js:54 js/menu.js 加载

contributionsjsloader.js:54 js/loan.js 加载

contributions.js:71 Contri 某事/*For some reason menu.js isnt't called to spit out its value before contribution.js tell us something even before contibution.js is loaded which loaded below*/

contributionsjsloader.js:54 js/contributions.js 加载

menu.js:183 can't make index TypeError: Cannot read property 'removeAttribute' of undefined /*Now menu.js decides to show its face and this exception is allowed, its expected.*/

menu.js:113 id in menu.js = d2b2aecb0197b6f439056 /* and then it finally spits out its value*/

导航到http://cooperative-izumedia.rhcloud.com/dashboard.html

dashboardjsloader.js:54 js/global.js 已加载

dashboardjsloader.js:54 js/menu.js 加载

dashboardjsloader.js:54 js/loan.js 加载

dashboardjsloader.js:54 js/dashboard.js 加载

/* I go back to dashboard and because menu is not called first my dashboard.js goes to complete shits */

dashboard.js:119 NaN

dashboard.js:132 TypeError: 无法设置未定义的属性“innerHTML”

dashboard.js:75 in dashboard TypeError: Cannot set property 'innerHTML' of 未定义

/*Now menu.js rears its ugly head*/

menu.js:113 id in menu.js = d2b2aecb0197b6f439056

【问题讨论】:

  • 脚本注入脚本默认是异步的。尝试在您的 loadScript 函数中添加 script.async = false
  • @SalmanA:看上面的代码,OP显然是在等待上一个脚本完成加载,然后再加载下一个。
  • Alex - “到底发生了什么,我该如何摆脱它。我在 firefox 和 chrome 中都对其进行了测试,但仍然得到相同的结果。”当您使用浏览器内置的全功能调试器时,您看到了吗?你做过哪些调试?这个问题现在归结为“请为我调试此代码”。这确实是您要做的事情,如果您仍有问题,请发布有关您找到的详细信息的问题。
  • @T.J.Crowder 他只是在头部添加了几个&lt;script&gt; 元素。据我记得,它们默认是异步的。
  • 另外:您正在使用 jQuery 的 ready 事件来异步加载系列脚本。为什么?复制浏览器为您所做的工作需要大量:只需将您的脚本放在文档末尾的标准脚本标记中,就在结束&lt;/body&gt; 标记as is the usual recommendation 之前。它们将按顺序在幕后加载,不会阻止您页面的显示,也不会阻止ready 的触发,并且可以完全访问您页面上的所有元素。

标签: javascript jquery html


【解决方案1】:

您应该考虑使用 RequireJS 之类的东西 - 它允许您明确定义依赖于其他模块的模块,这样您就可以始终确定性地以正确的顺序要求您的所有代码。

【讨论】:

  • 这是一个评论(可能有用),而不是答案。 “为什么我的代码不起作用?”的答案不是“使用这个库”。
  • 感谢@T.J.Crowder 的提示 :-)
  • Requirejs.js 是一个很棒的库,易于直接学习,并为我提供所需的控制。谢啦!不是一个解决方案,而是一个解决方案,如果你知道我的意思胸罩!
猜你喜欢
  • 1970-01-01
  • 2012-03-29
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-04-09
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多