Lawrence Whiteside
 

Webpack 4 Upgrade Guide

Webpack 4 was just released promising speed improvements, config defaults and some deprecations and a new plugin API that's no longer based on Tappable. I'm going to walk you through all of it and talk about the changes that need to be made to move your project from 3 to 4.

The ecosystem is definately in transition. There's not much honestly to do on the Webpack side, but I've noticed that loader and plugin authors are using this major version change to somewhat shift some options around, require new dependencies and otherwise break things.

This lesson specifically hopes to give you the tools to diagnose and properly upgrade both the packages and the configuration syntax.

As Webpack 4 was officially released on February 25th, Some stuff is still in transition and some deprecation warnings will still be there. But as things smooth out, this course will keep pace.

TLDR

I've done much of the work on the course materials here. The last few oddball packages (discussed below) will be sorted out soon this repo will change but I wanted to provide working code branches with explicit versions on the packages that need them, to hopefully ease the transition.

Upgraded repo

git clone https://github.com/lawwantsin/webpack-4-upgraded

So without further ado, let's upgrade. We can upgrade Webpack to 4 with one command.

npm update webpack

Webpack CLI

We see that webpack-cli has been removed from the webpack package.

Missing Image

This is simply the matter of installing it separately.

npm install webpack-cli

Mode Warning

First thing you'll notice is webpack kind of requires a new option in the config.

Missing Image

In our webpack config, next to entry and output, we can put mode: "development" or mode: "production".

This is supposed to give webpack sensible defaults for that environment and allow developers to use only 1 config file for both environments if they wish. I don't see a reason to do this unless you're building a toy app and want to get up and running even quicker.

Upgrading Our Package Versions

When upgrading your loaders, it's important to specify exactly the versions you're using, since most of these have all been updated in the last month to work with Webpack 4.

To find our what we need to upgrade make sure your package.json specifies the latest version of Webpack. (4.0.0) right now.

In terminal:

npm outdated

Missing Image

You get a nice list. From this you can run:

npm update

And most packages will be updated automatically. The exception is when there's no clear path to the right version. Like with the url-loader above. Since it's on 1.0.0-beta.0 and the latest is 0.6.2 we may have to try both to see. In this case, either works with Webpack 4.

When you've specified all the right version numbers, it's best to delete the package-lock.json and reinstall.

rm package-lock.json
npm install -S

Extract and HTML Loaders

The HTML and Extract loaders changed their options a bit. We need to remove the options in html-loader and add a publicPath in the extract-loader, so the final rule in the webpack.dev.js will look like this:

{
  test: /\.html$/,
  use: [
    {
      loader: "file-loader",
      options: {
        name: "[name].[ext]"
      }
    },
    {
      loader: "extract-loader",
      options: {
        publicPath: "../"
      }
    },
    {
      loader: "html-loader"
    }
  ]
}

Plugins

The plugin system got a rewrite under the hood. "The .plugin method on tapable objects is theoretically backward-compatible, but it causes a deprecation warning in HTMLWebpackPlugin, so plugin's still have some upgrades to do before these are gone, but it does work. Because of this, we may see warnings about tappable.

HTMLWebpackPlugin

For the time being, the upgrade here is coming from a new repo under webpack-contrib. This plugin has a deprecation warning that they're working on

npm i -S git+ssh://git@github.com/webpack-contrib/html-webpack-plugin

Missing Image

It's now going to require extract-text-webpack-plugin even if we're not using it specifically yet.

npm i extract-text-webpack-plugin@next

Also your project may lose track of html-webpack-plugin because it's coming from a git repo for the time being, not npm, even though you definately already installed it, it'll error like this.

HTMLWebpackPlugin missing

To fix this simply use:

npm i -S

Named Modules Plugin

No longer needed. You can take it out of your plugins array.

Choose Your Own Adventure Section

Typescript

There is a version of the awesome-typescript-loader package in Pre-release, so to get it, you'll want to put in @next after that to get it.

In package.json:

"awesome-typescript-loader": "^4.0.0-0",
"typescript": "^2.7.2",

Turn off warnings about packages being too big. In webpack.dev.js:

devServer: {
  contentBase: "dist",
  overlay: true,
  stats: {
    warning: false,  // Add this
    colors: true
  }
},

Awesome Typescript Loader is still adding Webpack 4 support (as of Feb 2018)

Gives you errors like this. I hear ts-loader works though. Let's check it out.

In terminal:

npm install ts-loader

In webpack.dev.js:

{
  test: /\.ts$/,
  loader: "ts-loader",
  exclude: /node_modules/,
  // options: {
  //   configFile: path.join(__dirname, "./config/tsconfig.json")
  // }
},

I comment out the configFile option, because it's giving me this error right now. But soon, it will be worked out. Until then just mv your tsconfig.json to the root of your project.

mv config/tsconfig.json

It does work. Cool.

Angular

Angular is pretty slow. But it works with ts-loader for now. The polyfill does need to go before the angular entry.

entry: {
  main: ["./src/main.js"],
  polyfills: "./src/angular-polyfills.ts",
  angular: "./src/angular.ts"
},

Production

Babel Minify Webpack Plugin

Babel Minify Webpack Plugin does through a warning, but it's only used until it's replaced with Uglify, which is working. Are they working on a update?

Babel Minify webpack Plugin needs an upgrade

Common Chunks

Common Chunks plugin is no longer needed as it's been made automatic by Webpack core.

Common Chunks obsolute

We can remove it from our Plugins array in both webpack.dev.js and webpack.prod.js. It just happens if it's worth it and you have 2 entry points that use similar stuff.

Server-side Rendering & Dynamic Imports

Extract CSS Chunks

This package still needs to be made Webpack 4 compatible. There is a branch and it does work. You can install it by putting this in your package.json.

"extract-css-chunks-webpack-plugin": "github:izaakschroeder/extract-css-chunks-webpack-plugin#webpack-4",

It feels buggy on reload and the Nav is definately buggy and Hot Module reloading isn't showing up even though we do include it.

So I'm going to say this episode is 3.x only for now.

Further Updates

Things are moving fast. Since I began this document 3 days ago, things have changed already. I need to go back and edit this.

Anyway, let me know if you encounter any snags along the way. This is what living on the cutting edge feels like.

Animation, Film, Web & Design Craftsman

All I want to do is help artists and small business entrepreneurs succeed.

My rates are surprisingly fair, because money does not motivate me. Freedom does.

Communicating is always free. For more info before you do: check out theF.A.Q.read moreabout meand read whatmy clients have to say.

Printable Resume

Let's get started!

Phone: 971-770-1661

Email:

Contact Me.

Add Payment

Stay in Touch!