This article mainly introduces the principle and implementation of webpack organization module packaging Library. Now I will share it with you and give you a reference.
The previous article analyzed the basic principles of Webpack packaging JS modules. The case introduced is the most common situation, that is, multiple JS modules and an entry module are packaged into a bundle file, which can be directly Executed by a browser or other JavaScript engine, it is equivalent to direct compilation to generate a complete executable file. However, there is another very common situation, that is, we need to build and publish a JavaScript library. For example, if you publish your own library in the npm community, then Webpack needs corresponding configuration, and the compiled code will be slightly different.
Like the previous article, this article mainly analyzes the generated code of Webpack, and combines it to explain the specific role of Webpack's library configuration options when compiling the library. The corresponding official documentation is here.
Library for writing JS
Let’s start with a simple case. We just write a simple library util.js:
import $ from 'jquery' function sayHello() { console.log("Hello"); } function hideImages() { $('img').hide(); } export default { sayHello: sayHello, hideImages: hideImages }
provides two functions. Of course, they have nothing to do with each other and are actually of no use. They are purely for teaching reference only. . .
Next write the configuration of Webpack:
// 入口文件 entry: { util: './util.js', } // 输出文件 output: { path: './dist', filename: '[name].dist.js' }
But this alone is not enough, the output file is a function that is executed immediately, Finally, the exports of util.js will be returned. Refer to the analysis in the previous article. The final generated bundle code structure is roughly like this:
(function(modules) { var installedModules = {}; function webpack_require(moduleId) { // ... } return webpack_require('./util.js'); }) ({ './util.js': generated_util, '/path/to/jquery.js': generated_jquery });
If it is executed That’s it. We just return the export part of util.js. What we need is to give this return value to module.export of the compiled file, so that the compiled file becomes a file that can be imported by others. library. So the compiled file we hope to get should be like this:
module.exports = (function(modules) { var installedModules = {}; function webpack_require(moduleId) { // ... } return webpack_require('./util.js'); }) ({ './util.js': generated_util, '/path/to/jquery.js': generated_jquery });
To get such a result, the library information needs to be added to the output part of the Webpack configuration:
// 入口文件 output: { path: './dist', filename: '[name].dist.js', library: 'util', libraryTarget: commonjs2 }
The most important thing here is the libraryTarget. If we now use the commonjs2 format, we will get the above compilation results, which means that Webpack will use the library to convert the final output to CommonJS. The form is exported, thus realizing the release of a library.
Other publishing formats
In addition to commonjs2, libraryTarget has other options:
var (默认值,发布为全局变量) commonjs commonjs2 amd umd
Use different options to compile The files can be used in different JavaScript execution environments. Here we directly see what the output of Wanjinbal umd format looks like:
(function webpackUniversalModuleDefinition(root, factory) { if(typeof exports === 'object' && typeof module === 'object') // commonjs2 module.exports = factory(); else if(typeof define === 'function' && define.amd) define("util", [], factory); // amd else if(typeof exports === 'object') exports["util"] = factory(); // commonjs else root["util"] = factory(); // var }) (window, function() { return (function(modules) { var installedModules = {}; function webpack_require(moduleId) { // ... } return webpack_require('./util.js'); }) ({ './util.js': generated_util, '/path/to/jquery.js': generated_jquery }); }
is much more complicated than the previous commonjs2 situation, because it needs to process various There are different cases, but in fact the following parts are the same. The most important ones are the first few lines. This is the standard way of writing the umd module. It runs the passed factory function, which is actually the function that loads the module, and then hands the returned result to the corresponding object according to different operating environments. For example, var will set the result as a global variable, which is used by the browser to directly import the JS file through the