之前的一个问题揭示了如何使用本机JavaScript加载jQuery.我已经成功地使用了那里答案的回调代码,在这里复制:
// Anonymous "self-invoking" function (function() { // Load the script var script = document.createElement("SCRIPT"); script.src = 'https://ajax.googleapis.com/ajax/libs/jquery/1.7.1/jquery.min.js'; script.type = 'text/javascript'; document.getElementsByTagName("head")[0].appendChild(script); // Poll for jQuery to come into existance var checkReady = function(callback) { if (window.jQuery) { callback(jQuery); } else { window.setTimeout(function() { checkReady(callback); }, 100); } }; // Start polling... checkReady(function($) { // Use $ here... }); })();
如何使用本机JavaScript Promises完成同样的事情?
我问的原因是因为我突然需要链接早期的回调,这是一个混乱的问题.我希望Promise是一种更好的方式,我对使用加载器框架没有兴趣.
这是我到目前为止所得到的,但承诺总是被拒绝:
// This code doesn't work quite right. // Poll for jQuery to come into existance using a Promise var jQueryReady = new Promise( function(resolve, reject) { // Load jQuery var script = document.createElement('SCRIPT'); script.type = 'text/javascript'; script.src = 'https://ajax.googleapis.com/ajax/libs/jquery/2.1.4/jquery.min.js'; document.getElementsByTagName('head')[0].appendChild(script); if (window.jQuery) { resolve("YAY"); } else { reject("UGH"); } }); jQueryReady.then( function(success) { console.log(success); }, function(error) { console.error("Really helpful error:", error); });
(我很抱歉提前完全无知.)
这是一个版本,它创建一个loadScript()
返回promise 的简单函数,然后提供一个包装器来检测jQuery是否已经加载:
function loadScript(url) { return new Promise(function(resolve reject) { var script = document.createElement("script"); script.onload = resolve; script.onerror = reject; script.src = url; document.getElementsByTagName("head")[0].appendChild(script); }); } function loadjQuery() { if (window.jQuery) { // already loaded and ready to go return Promise.resolve(); } else { return loadScript('https://ajax.googleapis.com/ajax/libs/jquery/2.1.4/jquery.min.js'); } } // Usage: loadjQuery().then(function() { // code here that uses jQuery }, function() { // error loading jQuery });
您的代码注释:
在您的第一个代码块中,设置一个计时器并假设在该计时器触发时将加载脚本就像玩轮盘赌一样.它大部分时间都可以工作,但它不是一种纯粹可靠的做事方法.此外,为了安全起见,您必须将计时器设置为比通常所需的更长的时间段.相反,您应该根据onload
脚本的回调触发.然后,您将确切知道脚本何时准备就绪,具有100%的可靠性.
在您的第二个代码块中,您的promise版本成功处理了已加载jQuery的情况,但是rejects()
当jQuery必须自定义加载时.正如您在我的示例中所看到的,您需要resolve()
在新加载的脚本标记完成加载后,您的承诺将按预期工作.