Webpack有幾個和模塊化相關的loader,imports-loader,exports-loader,expose-loader,比較容易混淆。今天,我們來理一理。
imports-loaders
文檔介紹的是:用於向一個模塊的作用域內注入變量(Can be used to inject variables into the scope of a module.),官方的文檔總是言簡意賅但是不太好懂。我們來舉個例子。
例子完整的代碼可以點這里jqGreen.js文件里僅一行代碼
//沒有模塊化 $('#box').css('color','green');
index.js文件也只有一行代碼
require('./jqGreen');
我們的配置文件中,是把index.js作為入口文件的。
{ entry:{ index:'./src/js/index.js' } }
注意,我們並沒有引入jquery。所以運行的結果是$ is not defined。
但是如果我們稍微修改一下jqGreen的引入方式,就能很輕松的解決這個問題。index.js文件
require('imports?$=jquery!./jqGreen');
當然,這個能運行之前,我們要npm install imports-loader一下。上面代碼,把變量$注入進模塊jqGreen.js。同時,我們指定了變量$=jquery。等於是在jqGreen.js文件的最頂上,加上了var $=require('jquery')。這樣,程序就不會報$ is not defined的錯誤了。
exports-loader
exports有導出的意思,這讓我們猜測它有從模塊中導出變量的功能。實際情況大致如此。我們來看個小例子。
例子的完整代碼在 這里Hello.js文件中僅有一個方法,直接綁定在全局變量window上面。
window.Hello = function(){ console.log('say hello.'); }
然后我們在index.js文件里去引用這個Hello.js:var hello = require('./Hello.js');。這樣引用的結果是變量hello是undefined。因為我們在Hello.js文件里沒有寫module.exports=window.Hello,所以index.js里我們require的結果就是undefined。這個時候,exports-loader就派上用場了。我們只用把index.js的代碼稍微改動一下:var hello = require('exports?window.Hello!./Hello.js');,這個時候,代碼就能正確的運行了。變量hello就是我們定義的window.hello啦。var hello = require('exports?window.Hello!./Hello.js');這行代碼,等於在Hello.js里加上一句module.exports=window.Hello,所以我們才能正確的導入。
expose-loader
把一個模塊導出並付給一個全局變量。文檔里給了一個例子:
require("expose?libraryName!./file.js"); // Exposes the exports for file.js to the global context on property "libraryName". // In web browsers, window.libraryName is then available.
例子中的注釋是說把file.js中exports出來的變量付給全局變量"libraryName"。假如file.js中有代碼module.exports=1,那么require("expose?libraryName!./file.js")后window.libraryName的值就為1(我們這里只討論瀏覽器環境)。
我這里還有一個稍稍復雜點的從一個umd模塊的文件里導出到全局變量的例子,有興趣的同學點擊這里。
