Adding Config file and Babel loader

branch-name:  
Click To Copy

Why adding Babel ?

Java Script is a language that evolves really fast, but unfortunately many people still use old browsers that doesn’t support the latest Java Script syntax.

Let’s say that we would like to be at the edge of the technology and use the latest ECMA Script 6 or (European Computer Manufacturers Association) or EC for shorter and we want to use the latest one EC6. The solution will be to `transpile` the new EC6 to older version, that is supported even with the old browsers.

But Webpack is just JS bundle creator and it doesn’t know how to translate the new EC6 syntax to the old one and here comes the Webpack loaders.

Webpack loaders simply pre-process the files which Webpack is going to bundle.

There are tons of loaders, you could check them here https://webpack.js.org/loaders/ but the one that we need for this particular task is called Babel

There are two ways of adding loaders: with a config file or from the package.json. Since doing it through a config file is more flexible we will explore this option.

Adding Babel loader and Webpack config file.

In order to use Babel loader, we have to tell Webpack about it.

Adding Webpack config file.

 Just creating webpack.config.js in the root folder of our project is enough to create Webpack config file, which Webpack will pick up automatically from this location.

But for our particular task we need to add Babel loader to our project. So first before we move any further, let’s do this:

Babel got split in a couple of sub-modules that we need to add:

  • babel-core
  • babel-loader
  • babel-preset-env – for compiling Javascript ES6 code down to ES5

yarn add @babel/core babel-loader @babel/preset-env

– create new file called webpack.config.js in the root of the project folder with these contents:

./webpack.config.js

module.exports = {
  mode: 'development',
  entry: [
    './src/app.js'
  ],
  output: {
    filename: '[name]-bundle.js',
  },  
  module: {
    rules: [
      {
        test: /\.js$/,
        exclude: /node_modules/,
        use: {
          loader: "babel-loader"
        }
      }
    ]
  }
};

What we just did:
– we created a brand new file called webpack.config.js in the root folder of our project and Webpack will look there and pick it up.
– we added mode: “development” insted of passing it through the build script (line 2)
– added entry point to to tell webpack where to look for the bundle files.
we could have skip this parameter if we name our bundle entry point was named ./src/index.js and Webpack was going to pick it automatically, but for the purpose of understanding Webpack config we customized it with ./src/app.js
– added output parameter to specify Where webpack should create the bundle.
By default if this parameter is not specified Webpack will create ./dist/main.js bundle.
– we added a Babel module config, that is going to transpile all JS files matching this RegExp pattern /\.js$/ and make them old fashioned JS that all browsers understand.
– we told Webpack to exclude node_modules “exclude: /node_modules/,” (line 13) since this folder is where npm installs packages and it doesn’t need to be transpiled.

Now we have to tell Babel how to transpile our files to JavaScript. Create .babelrc in the root of the project, with these contents:

./.babelrc

{
  "presets": [
    "@babel/preset-env"
  ]
}

Presets are like plug-ins. They describe which ES features we are going to use so Babel could transpile back to ES5 that all browsers will understand. In our case we added @babel/preset-env so we could use latest ES coding, and since we are going to add React we added @babel/preset-react which under the hood includes:

so Babel will know how to deal with react-jsx files.

Let’s give it a try:

yarn build-dev

and check the ./dist folder. Looks good right ?

But if you try to run in on old IE you will notice that the site break. We still need babel-polyfill to  emulate a full ES2015+ environment (no < Stage 4 proposals). This woks on the front end only.

Adding Babel-polyfill.

Let’s install the library first: yarn add @babel/polyfill

There are two different ways to add it: we could use require(“@babel/polyfill”); or import “@babel/polyfill”; or we could use Webpack to add it.

Let’s use Webpack:

./webpack.config.js

module.exports = {
  mode: 'development',
  entry: [
    '@babel/polyfill',
    './src/app.js'
  ],
  output: {
    filename: '[name]-bundle.js',
  },  
  module: {
    rules: [
      {
        test: /\.js$/,
        exclude: /node_modules/,
        use: {
          loader: "babel-loader"
        }
      }
    ]
  }
};

Now we added support for all old browsers.

Adding another pre-processor: Eslint.

Now we know how to add Webpack modules, let’s add another one, that will help us identify problems with our code even before we compile it.

yarn add eslint eslint-loader babel-eslint eslint-plugin-react --dev

what we just did:
– we installed:
eslint – the core JS linter
eslint-loader – tells webpack that we are going to use eslint in our build
babel-eslint – provides linting for ES6 code.
eslint-plugin-react – Since we are going to use React, we have to install the React plugin for
eslint.

The easiest way to configure eslint is through .eslintrc config file. Let’s create one in the root folder with these contents:

./.eslintrc

{
  "parser": "babel-eslint",
  "plugins": [
    "react"
  ],
  "rules": {
    "no-undef": 1
  }
}

what we just did:
– we set up the parser to be babel-eslint (line 1)
– we added react plugin
– we added one rule “no-undef” with a value ‘1’. The possible values are: 0 = off, 1 = warn, 2 = error

Now in the root folder execute:
./node_modules/eslint/bin/eslint.js .

the output probably will be similar to this:

~/babel-webpack-react-boilerplate/dist/main-bundle.js
45:48 warning ‘Symbol’ is not defined no-undef
46:44 warning ‘Symbol’ is not defined no-undef

~/babel-webpack-react-boilerplate/src/test.js
3:3 warning ‘console’ is not defined no-undef

✖ 3 problems (0 errors, 3 warnings)

….

Let’s add a script to execute linter through npm.

"scripts": {
  "clean": "rm -rf ./dist",
  "lint": "eslint .",
  "build-dev": "webpack --mode development ./src/app.js -o ./dist/main-bundle.js",
  "build-prod": "webpack --mode production ./src/app.js -o ./dist/main-bundle.js"
},

And give it a try:
yarn lint

 NPM always looks first in project’s node_modules folder, so if you have eslint (or any other module) installed globally and locally, it will always pick the local version.

Adding .eslintignore
And we could add the files that we don’t want to be checked into
./.eslintignore

dist
webpack.config.js

Let’s run the linter yarn lint

/Users/toninichev/Downloads/webpack-test/src/test.js
2:3 warning ‘console’ is not defined no-undef

✖ 1 problem (0 errors, 1 warning)

✨ Done in 1.38s.

Let’s say that we don’t want to `fix` this since this is not a real problem, but we want to tell Eslint to ignore it we could add /* eslint-disable no-undef */

./src/test.js

/* eslint-disable no-undef */

const test = (msg) => {
  console.log(msg);
}
export default test;

Run Eslint again and you sould not see any issues.

branch-name:  
Click To Copy

 

Leave a Reply