Webpack ProvidePlugin vs externals?

[[4]}zgłębiam ideę używania Webpacka z szkieletem.js .

Śledziłem przewodnik szybkiego startu i mam ogólne pojęcie o tym, jak działa Webpack, ale nie wiem, jak załadować bibliotekę zależności, taką jak jquery / backbone / underscore.

Powinny być ładowane zewnętrznie <script> czy to jest coś, co Webpack może obsłużyć jak Shim Wymagajs?

Zgodnie z webpack doc: shimming modules, ProvidePlugin i externals wydają się być związane z tym (podobnie jak gdzieś jest bundle! loader), ale nie wiem, kiedy użyć którego.

Thanks

Author: Henry, 2014-04-26

3 answers

Jest to możliwe: możesz dołączać biblioteki z <script> (tzn. używać biblioteki z CDN) lub dołączać je do wygenerowanego pakietu.

Jeśli załadujesz go za pomocą znacznika <script>, możesz użyć opcji externals, Aby zezwolić na zapis require(...) w swoich modułach.

Przykład z biblioteką z CDN:

<script src="https://code.jquery.com/jquery-git2.min.js"></script>

// the artifial module "jquery" exports the global var "jQuery"
externals: { jquery: "jQuery" }

// inside any module
var $ = require("jquery");

Przykład z biblioteką zawartą w pakiecie:

copy `jquery-git2.min.js` to your local filesystem

// make "jquery" resolve to your local copy of the library
// i. e. through the resolve.alias option
resolve: { alias: { jquery: "/path/to/jquery-git2.min.js" } }

// inside any module
var $ = require("jquery");

ProvidePlugin może mapować moduły do (wolnych) zmiennych. Można więc zdefiniować: "za każdym razem, gdy używam (wolnej) zmiennej xyz wewnątrz modułu należy (webpack) ustawić xyz na require("abc")."

Przykład Bez ProvidePlugin:

// You need to require underscore before you can use it
var _ = require("underscore");
_.size(...);

Przykład z ProvidePlugin:

plugins: [
  new webpack.ProvidePlugin({
    "_": "underscore"
  }) 
]

// If you use "_", underscore is automatically required
_.size(...)

Podsumowanie:

  • Biblioteka z CDN: użyj znacznika <script> i opcji externals
  • Biblioteka z systemu plików: Dołącz bibliotekę do pakietu. (Może zmodyfikować opcje resolve, aby znaleźć bibliotekę)
  • externals: udostępnienie zmiennych globalnych jako modułu
  • ProvidePlugin: udostępnienie modułów jako wolnych zmiennych wewnątrz Moduły
 139
Author: Tobias K.,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-10-01 11:27:50

Warto zauważyć, że jeśli użyjesz ProvidePlugin w połączeniu z właściwością externals, pozwoli to na przekazanie jQuery do zamknięcia modułu webpack bez konieczności jawnego require. Może to być przydatne do refaktoryzacji kodu źródłowego z wieloma różnymi plikami odwołującymi się do $.

//webpack.config.js
module.exports = {
  entry: './index.js',
  output: { 
    filename: '[name].js' 
  },
  externals: {
    jquery: 'jQuery'
  },
  plugins: [
    new webpack.ProvidePlugin({
      $: 'jquery',
    })
  ]
};

Teraz w indeksie.js

console.log(typeof $ === 'function');

Będzie miał skompilowane wyjście z czymś takim jak poniżej przekazane do webpackBootstrap zamknięcia:

/******/ ([
/* 0 */
/***/ function(module, exports, __webpack_require__) {

    /* WEBPACK VAR INJECTION */(function($) {
        console.log(typeof $ === 'function');

    /* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(1)))

/***/ },
/* 1 */
/***/ function(module, exports, __webpack_require__) {

    module.exports = jQuery;

/***/ }
/******/ ])

Dlatego widać, że $ odwołuje się do global / window jQuery z CDN, ale jest przekazywany do zamknięcia. Nie jestem pewien, czy jest to zamierzona funkcjonalność lub szczęśliwy hack, ale wydaje się działać dobrze dla mojego przypadku użycia.

 21
Author: dtothefp,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-06-02 04:18:33

Wiem, że to stary post, ale pomyślałem, że warto wspomnieć, że Webpack script loader może być przydatny również w tym przypadku. Z webpack docs:

" script: wykonuje plik JavaScript raz w kontekście globalnym( jak w znaczniku script), wymagania nie są przetwarzane."

Http://webpack.github.io/docs/list-of-loaders.html

Https://github.com/webpack/script-loader

Znalazłem to szczególnie przydatne podczas migracji starszych kompilacji procesy, które łączą pliki dostawcy JS i pliki aplikacji razem. Słowo ostrzeżenia jest takie, że script loader zdaje się działać tylko przez przeciążenie require() i nie działa, o ile mogę powiedzieć, będąc określonym w webpacku.plik konfiguracyjny. Chociaż wielu twierdzi, że przeciążenie require jest złą praktyką, może być całkiem przydatne do łączenia dostawcy i skryptu aplikacji w jednym pakiecie, a jednocześnie ujawniania JS Globals, które nie muszą być shimmed w dodatkowe pakiety webpack. Na przykład:

require('script!jquery-cookie/jquery.cookie');
require('script!history.js/scripts/bundled-uncompressed/html4+html5/jquery.history');
require('script!momentjs');

require('./scripts/main.js');

To by $.pliki cookie, Historia i moment dostępne na całym świecie wewnątrz i na zewnątrz tego pakietu, a także dołącz te biblioteki dostawców z głównym.skrypt js i wszystkie pliki require d.

Również, przydatne w tej technice jest:

resolve: {
  extensions: ["", ".js"],
  modulesDirectories: ['node_modules', 'bower_components']
},
plugins: [
  new webpack.ResolverPlugin(
    new webpack.ResolverPlugin.DirectoryDescriptionFilePlugin("bower.json", ["main"])
   )
]

, który używa Bowera, spojrzy na plik main w każdym pakiecie bibliotek required.json. W powyższym przykładzie Historia.js nie ma określonego pliku main, więc ścieżka do pliku jest konieczna.

 11
Author: dtothefp,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-01-25 22:14:24