Rollup
The next generation of packaging tools, this is how Rollup sees itself. In today’s front-end world, there is no shortage of build tools, and every front-end engineer has used or heard of WebPack. You can see that build tools for frameworks like React and Vue use rollup. So why do these frameworks choose rollup? What are its characteristics? How do we choose build tools for different scenarios? This article will show you one by one.
Tree Shaking
Tree shaking is a very important rollup feature. When building code, in ES6 modularity, your code is analyzed statically and only the code that you use is packaged. This has the advantage of reducing the size of the code.
You can see that its implementation relies on static analysis, so why use ES6 Modules? Let’s review a few features of ES6 Modules:
import
Can only be string constants- Import binding is immutable, similarly
const
- Can only appear as a statement at the top level of a module, not in
function
Inside orif
Inside the block-level scope - Import hoisted, regardless
import
Where does the statement appear when the module is initializedimport
All must have been imported.
This makes ES6 Modules less flexible, but allows all dependencies to be fixed and code to be statically analyzed. There is no need to rely on the runtime to determine dependencies. One example: maths.js
// maths.js
export function square ( x ) {
return x * x;
}
export function cube ( x ) {
return x * x * x;
}
Copy the code
main.js
import { cube } from './maths.js';
console.log( cube( 5));Copy the code
Run the following command
$ rollup main.js --o bundle.js --f iife
Copy the code
Output bundles. Js
(function () {
'use strict';
// maths.js
function cube(x) {
return x * x * x;
}
console.log(cube(5)); } ());Copy the code
As you can see, the square method in maths.js is not used and is not packaged into the build result. At build time, a parameter f is added with the value of the iIFE option, and the organization of the post-build code is wrapped in a function that executes immediately.
Output format after code is built
Rollup supports the following output formats: rollup (iIFE) rollup (iIFE) rollup (iIFE) rollup (iIFE)
- amd – AMD
- cjs -CommonJS
- es – ES6 modules
- umd – UMD
- system – SystemJS loader
When building code, you can choose different output formats depending on the environment in which your code is running. CJS is fine if your code is running in Node, iIFE is fine if your code is running in a browser, and UMD is fine if both. In webpack compile & Build, there are actually three types of code that refer to webPack build output.
- Your business logic code
- Runtime – Bootstrap for code execution
- Manifest – A record of module dependencies
If we execute the following command on main.js after build
webpack main.js dist.js
Copy the code
Output dist. Js
/ * * * * * * / (function(modules) { // webpackBootstrap
/ * * * * * * / // The module cache
/ * * * * * * / var installedModules = {};
/ * * * * * * /
/ * * * * * * / // The require function
/ * * * * * * / function __webpack_require__(moduleId) {
/ * * * * * * /
/ * * * * * * / // Check if module is in cache
/ * * * * * * / if(installedModules[moduleId]) {
/ * * * * * * / return installedModules[moduleId].exports;
/ * * * * * * / }
/ * * * * * * / // Create a new module (and put it into the cache)
/ * * * * * * / var module = installedModules[moduleId] = {
/ * * * * * * / i: moduleId,
/ * * * * * * / l: false./ * * * * * * / exports: {}
/ * * * * * * / };
/ * * * * * * /
/ * * * * * * / // Execute the module function
/ * * * * * * / modules[moduleId].call(module.exports, module.module.exports, __webpack_require__);
/ * * * * * * /
/ * * * * * * / // Flag the module as loaded
/ * * * * * * / module.l = true;
/ * * * * * * /
/ * * * * * * / // Return the exports of the module
/ * * * * * * / return module.exports;
/ * * * * * * / }
/ * * * * * * /
/ * * * * * * /
/ * * * * * * / // expose the modules object (__webpack_modules__)
/ * * * * * * / __webpack_require__.m = modules;
/ * * * * * * /
/ * * * * * * / // expose the module cache
/ * * * * * * / __webpack_require__.c = installedModules;
/ * * * * * * /
/ * * * * * * / // define getter function for harmony exports
/ * * * * * * / __webpack_require__.d = function(exports, name, getter) {
/ * * * * * * / if(! __webpack_require__.o(exports, name)) {/ * * * * * * / Object.defineProperty(exports, name, {
/ * * * * * * / configurable: false./ * * * * * * / enumerable: true./ * * * * * * / get: getter
/ * * * * * * / });
/ * * * * * * / }
/ * * * * * * / };
/ * * * * * * /
/ * * * * * * / // getDefaultExport function for compatibility with non-harmony modules
/ * * * * * * / __webpack_require__.n = function(module) {
/ * * * * * * / var getter = module && module.__esModule ?
/ * * * * * * / function getDefault() { return module['default']; } :
/ * * * * * * / function getModuleExports() { return module; };
/ * * * * * * / __webpack_require__.d(getter, 'a', getter);
/ * * * * * * / return getter;
/ * * * * * * / };
/ * * * * * * /
/ * * * * * * / // Object.prototype.hasOwnProperty.call
/ * * * * * * / __webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };
/ * * * * * * /
/ * * * * * * / // __webpack_public_path__
/ * * * * * * / __webpack_require__.p = "";
/ * * * * * * /
/ * * * * * * / // Load entry module and return exports
/ * * * * * * / return __webpack_require__(__webpack_require__.s = 0);
/ * * * * * * / })
/ * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * /
/ * * * * * * / ([
/* 0 */
/ * * * / (function(module, __webpack_exports__, __webpack_require__) {
"use strict";
Object.defineProperty(__webpack_exports__, "__esModule", { value: true });
/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0__maths_js__ = __webpack_require__(1);
console.log(Object(__WEBPACK_IMPORTED_MODULE_0__maths_js__["a" /* cube */]) (5));
/ * * * / }),
/ * 1 * /
/ * * * / (function(module, __webpack_exports__, __webpack_require__) {
"use strict";
/* unused harmony export square */
/* harmony export (immutable) */ __webpack_exports__["a"] = cube;
// maths.js
function square(x) {
return x * x;
}
function cube(x) {
return x * x * x;
}
/ * * * / })
/ * * * * * * / ]);
Copy the code
- You can see the business logic code, Runtime and Manifest in the build result
- Log dependencies in Manifest, through
__webpack_require__
loading - The build results contain unused ones
square
- Build volume is significantly greater than in rollup
iife
Large format - Rollup when the code executes
iife
Output format, faster code execution, Webpack built out of the dependency search, and each module through a function wrapped form, when executing, it forms a closure, occupying memory, of course, can be used in Webpack 3ConcatenationPlugin
The plug-in optimizes this output format and packages it into a dependency
The cost-of-small-modules performance has done a good evaluation, you can understand.
There is no silver bullet
Code-splitting was implemented in order to solve the construction of static files such as CSS and pictures and make codes load on demand. In our daily online business code development, more or less static resources need to be packed, so rollup was not suitable. So we can see that we can choose rollup for building some libs and WebPack for building some applications.
IVWEB Technology Weekly shocked online, pay attention to the public number: IVWEB community, weekly timing push quality articles.
- Collection of weekly articles: weekly
- Team open source project: Feflow