This blog references the original blog from Medium, this version is just a different platform and has some updates.
Many Frontend engineers that use React commonly use templates like Create React App or Vite template for init a React project, because with that template we can easily use React without setup anything from scratch, like configuring Babel for javascript code can be transpile to javascript version that browser supported and setup Webpack to bundle all javascript files into one.
Setup React
Init project
- First, we should init node project, so we can install packages that we need.
npm init -y
Install react & react-dom
- React is a library that used for building user interfaces.
- React-dom is used to render components into DOM.
Create a component and render it into DOM
- Create file
index.jsx
containing a component calledApp
and componentApp
will be rendered into DOM using the methodrender
from functionreactDom.createRoot()
.
import React from 'react';
import reactDom from 'react-dom/client';
const App = () => {
return (
<div>
<h1>Hello world</h1>
</div>
);
};
const root = reactDom.createRoot(document.getElementById('root'));
root.render(<App />);
Bundle code using Webpack
What does bundle code mean? when we develop a website, we have many javascript files that should be inserted one by one into <script>
tags in HTML. So that will be troublesome for us because there may be some files that we forgot to add. With Webpack we just need to add the result of the bundling into HTML.
Install Webpack
We need two Webpack packages
webpack
webpack-cli
pnpm add -D webpack webpack-cli
Setup Webpack config
Create a file in the top-level directory called webpack.config.js
const path = require("path");
module.exports = {
mode: "development",
entry: path.resolve(__dirname, "./index.jsx"),
output: {
path: path.resolve(__dirname, "./build"),
filename: "index.js",
clean: true,
},
resolve: {
extensions: [".js", ".jsx"],
},
};
mode
determines should run in development or production mode.entry
determines the entry point file from the project, in this case, isindex.jsx
.output
determines where the results of the bundle.resolve
determines what file extension should bundle.
Transpile JSX becomes React.createElement
Why we should transpile JSX? Because JSX is not supported in the browser. We can use tools called Babel.
Install Babel
We need some Babel packages
@babel/core
@babel/cli
@babel/preset-env
allows you to use the latest JavaScript without needing to micromanage which syntax transforms (and optionally, browser polyfills) are needed by your target environment.@babel/preset-react
used to transpile JSX becomesReact.createElement
.
pnpm add -D @babel/core @babel/cli @babel/preset-env @babel/preset-react
Setup Babel Preset
After installing Babel preset, we should create a file in the top-level directory called .babelrc
to tell Babel what preset should we use.
{
"presets": ["@babel/preset-env", "@babel/preset-react"]
}
Run Babel while bundling
We should adjust Webpack config to run Babel, so that the result of the bundle does not contain JSX syntax, but should contain the result of the compile JSX that can be read by a browser.
pnpm install babel-loader
Then, we can adjust Webpack configuration like this
const path = require("path");
module.exports = {
mode: "development",
entry: path.resolve(__dirname, "./index.jsx"),
output: {
path: path.resolve(__dirname, "./build"),
filename: "index.js",
clean: true,
},
resolve: {
extensions: [".js", ".jsx"],
},
// new code :
module: {
rules: [
{
test: /\\.(js)x?$/,
exclude: /node_modules/,
use: [
{
loader: "babel-loader",
},
],
},
],
},
};
When Webpack finds files .js
or .jsx
, so will transpile JSX in that code to become React.createElement
.
Running a project with Webpack
Create HTML file
Create file index.html
with an empty div
that has attribute id=”root”
and will be used by react-dom
to render components inside that div
.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>React from scratch</title>
</head>
<body>
<div id="root"></div>
</body>
</html>
Setup Webpack so can run HTML file
We need two packages to run HTML files in Webpack
html-webpack-plugin
it will be used to insert the result of the bundle(javascript files) to<script>
tag in HTML.webpack-dev-server
used to run Webpack as a local server.
Then, we need to add plugins
in Webpack configuration
const path = require("path");
const htmlWebpackPlugin = require("html-webpack-plugin");
module.exports = {
mode: "development",
entry: path.resolve(__dirname, "./index.jsx"),
output: {
path: path.resolve(__dirname, "./build"),
filename: "index.js",
clean: true,
},
resolve: {
extensions: [".js", ".jsx"],
},
module: {
rules: [
{
test: /\\.(js)x?$/,
exclude: /node_modules/,
use: [
{
loader: "babel-loader",
},
],
},
],
},
// new code :
plugins: [
new htmlWebpackPlugin({
template: path.resolve(__dirname, "./index.html"),
}),
],
};
Adding npm script to run and build the project
"scripts": {
"build": "webpack --config webpack.config.js",
"start": "webpack serve --config webpack.config.js"
}
build
used to generate the result of the bundlestart
used to run the project
Conclusion
We already set up React project from scratch without using a template, and I think this is something good to know as an Engineer, we can easily use a template for creating a project, but we should understand how it works without a template or we should understand behind the scene of something.
You can access the code in this repository
In the next part, I will add adjustments for Webpack, so it can add styling and asset files