Getting started with webpack - Part 10: Webpack and React.js from scratch
You will need Node 6.11.5+ installed on your machine.
Introduction
In this final tutorial, we will consider how to configure another popular JavaScript library from scratch. As with Vue, React, comes with its own CLI tool that can help you get started pretty quickly. However, the React CLI tool abstracts all the logic and does all the magic in the background. So let’s attempt to set up React from scratch without using the CLI tool.
In the previous post we learned how we can configure the popular JavaScript library Vue.js from scratch. We configured things we are already used to having from the vue-cli tool like hot reloading, stylesheet support, loading .vue
files, and more.
A quick reminder
Before we get started, please note that we are not recommending any way of setting up the libraries. This article is designed to show you in examples how you can use webpack. You should decide to use CLI tools or manual depending on the project and the level of customization you want to have.
Now, that that’s out of the way, let’s get started.
Source code of the application is available on GitHub.
Prerequisites
To follow along in this series, you need the following requirements:
- Completed all previous parts of the series.
- Basic knowledge of JavaScript.
- Basic knowledge of the CLI.
- A text editor. VS Code is recommended.
- Node.js (>= 6.11.5) and npm installed locally.
Let’s continue with the series.
Starting from scratch
The recommended way to start a React project is using the create-react-app tool. This tool will help us generate new React applications that are already complete with hot reloading, asset compilation and more all with one command:
$ npx create-react-app my-app
However, the aim of this tutorial is to create a React application from scratch without using the CLI tool.
Getting started
To get started we have to create a new project directory. This will be the directory where all our code will reside. Create a new directory and cd
to the directory on your terminal application and run the following command:
$ npm init -y
The above command will initialize the project and add a new package.json
file in the root of the directory.
When the command has finished executing, run the next command to install webpack
and webpack-cli
:
$ npm install --save-dev webpack webpack-cli
When both packages have been installed successfully, open the package.json
file and add the following script
as seen below:
// File: ./package.json
{
// [...]
"scripts": {
"build": "webpack --mode development"
},
// [...]
}
Next, let’s install the required Babel packages. To do this, run the following command below:
$ npm i @babel/core babel-loader @babel/preset-env @babel/preset-react --save-dev
This command will install the Babel packages we will use to bundle our React application. The babel-react
package will help us compile the .jsx
files if we have any in the project.
Before we continue, we need to configure our Babel installation. We can do this by creating a new .babelrc
file in the root of the project and paste the following contents into it:
// File: ./.babelrc
{
"presets": ["@babel/preset-env", "@babel/preset-react"]
}
Next, let’s create a new webpack configuration file and paste the following code into the file:
// File: ./webpack.config.js
const env = process.env.NODE_ENV;
module.exports = {
mode: env == 'production' || env == 'none' ? env : 'development',
entry: ['./src/app.js'],
module: {
rules: [
{
test: /\.(js|jsx)$/,
exclude: /node_modules/,
loader: 'babel-loader'
}
]
}
};
This is actually the barest minimum we need to compile our React application. The main thing we added is the babel-loader
which will help us bundle the JS and JSX files. Now let’s start writing some sample components.
To get started, we need to install the React package. In your terminal, run the following command to install React as a dependency:
$ npm i react react-dom --save-dev
When the installation is complete, we can start creating some React specific files. In the root of the project, create a new src
directory and inside the directory, create a new file app.js
and paste the following code into the file:
// File: ./src/app.js
import React from 'react';
import ReactDOM from 'react-dom';
const App = () => <div>Hello React!</div>;
ReactDOM.render(<App />, document.getElementById('app'));
Next, we need to create a new HTML file as our entry point. Create a new index.html
file in the root of the project and paste the following code into it:
<!-- File: ./index.html -->
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<meta http-equiv="X-UA-Compatible" content="ie=edge" />
<title>React and Webpack</title>
</head>
<body>
<div id="app"></div>
</body>
</html>
To make sure webpack adds the bundled JavaScript to the HTML file, let’s install the html-webpack-plugin
and add it to our webpack configuration file. Run the following command in your terminal to install the plugin:
$ npm i html-webpack-plugin -D
When the installation is complete, open the webpack configuration file and update it as seen below:
// File: ./webpack.config.js
// [...]
const HtmlWebPackPlugin = require('html-webpack-plugin');
module.exports = {
// [...]
plugins: [
new HtmlWebPackPlugin({
template: 'index.html',
filename: 'index.html',
inject: true
})
]
};
Next, run the following command below to build the application:
$ npm run build
This will build the application to the dist
directory in the project directory. Open the dist/index.html
file in your browser to see the bundled application:
Improving our webpack bundling
Although our build above works, we can definitely do better. Let’s do some additional configuration that will get us closer to an actual development environment. First, we will install the webpack dev server. This will remove the need for us to manually launch the index.html
file.
In your terminal, run the following command:
$ npm i webpack-dev-server -D
Next, in your package.json
file, add the following build script:
// File: ./package.json
{
// [...]
"scripts": {
// [...]
"dev": "webpack-dev-server --open"
}
// [...]
}
Now when we run the dev
script and visit http://localhost:8080, we should see the same output as above. However, when we change the contents of the App.vue
the changes are not reflected immediately.
To add hot reload, let’s make a few changes. In the webpack configuration file, update as seen below:
// File: ./webpack.config.js
// [...]
const webpack = require('webpack');
module.exports = {
// [...]
devServer: {
hot: true,
watchOptions: {
poll: true
}
},
// [...]
plugins: [
new webpack.HotModuleReplacementPlugin(),
// [...]
]
};
Now we can re-run the dev
script and we will see true hot reloading whenever we change our source files.
Adding styles and other components
Right now, we have a single component and an unstyled HTML page. Let’s add some styling and an additional component.
In the src
directory create a new components
directory and in the directory create a new file HelloWorld.js
and paste the following code:
// File: ./src/components/HelloWorld.js
import React from 'react';
const HelloWorld = () => <h1>Hello World!</h1>;
export default HelloWorld;
Next, create a new styles
directory in the src
directory and in this directory, create a new app.css
file. Paste the following code inside the file:
/* File: ./src/styles/app.css */
#app .container {
width: 100%;
margin: 0 auto;
max-width: 1200px;
}
#app .container h1 {
color: #232b2b;
text-align: center;
}
Next, open the src/app.js
file and replace the contents with the following:
// File: ./src/app.js
import React from 'react';
import ReactDOM from 'react-dom';
import HelloWorld from './components/HelloWorld';
import './styles/app.css';
const App = () => (
<div className="container">
<HelloWorld />
</div>
);
ReactDOM.render(<App />, document.getElementById('app'));
Before we run the server again, let’s add a loader to handle the CSS we imported above. In your terminal, run the following command:
$ npm i css-loader style-loader -D
When the installation is complete, open the webpack configuration file and update as seen below:
// File: ./webpack.config.js
// [...]
module.exports = {
// [...]
module: {
rules: [
// [...]
{
test: /\.css$/,
use: ['style-loader', 'css-loader']
}
]
}
// [...]
};
Above, we just added the style-loader
and css-loader
to handle the CSS in the application.
Now, run the command to build and start the server once again (if it was previously running, you need to kill it with ctrl+c
and restart it):
$ npm run dev
Now you should see the styled application when you visit http://localhost:8080
That’s all. We have successfully created a React web application from scratch using webpack.
Conclusion
In this final tutorial of the series, we learned how to set up a new React application from scratch using the power of webpack.
Throughout the series, we have touched on various aspects of webpack as a whole and though there is still a lot more, you should know your way around webpack now. If you need more information, you can always visit the documentation.
The source code to the applications built in the series is available on GitHub.
5 March 2019
by Neo Ighodaro