Samuel Ogundipe
· 8 min read

Configuring Webpack from scratch for Tailwind CSS with React

In this tutorial, we will work through configuring Webpack for use with react and tailwind CSS.

Configuring Webpack from scratch for Tailwind CSS with React

In this tutorial, we will work through configuring Webpack for use with react and tailwind CSS. Before we dive into the configurations, let us first look at an overview of the technologies involved.

Webpack
Webpack is a wonderful tool for bundling and optimizing front-end assets (JS, CSS, and Images). Webpack uses a configuration file to determine how specific things are loaded into your application. You write commands in your configuration file of where your assets are and how to load them. Then, when you run it, it goes into your application entry point(the base file your app loads from) reads it and figures out exactly what it needs, and the order it needs it, and what each piece depends on.

It will then create few bundles, optimize them, and include as the scripts in your application. It does not run during your page load, it runs during your development. It also allows you to easily consume other packages from NPM (Node Package Manager).

React

As you're likely already aware, React is a simple, modern front-end library for building elegant user interfaces. It reduces the amount of effort building a versatile UI takes by efficiently handling DOM manipulation and event handling, producing a more predictable and easier to debug code.

Before React, other libraries like JQuery were used to manipulate the DOM. But as the web grew, exponentially more frameworks like Angular, Vue, and React came to light. What differentiates React from the rest of the pack is that it allows you to create your own HTML elements (typically wrapped within components) with customized functionality.

Tailwind CSS
Tailwind is a utility-first CSS framework for rapidly building custom user interfaces. One thing I love about tailwind CSS is that it doesn’t come with any predefined components, but rather it offers highly composable, low-level utility classes.

It leaves all the magic in your hands and doesn’t help you make any decision as to how your website should look. This makes your website look and feels unique with every new design.

Since it is utility first all you need do is to apply those utility classes to your HTML tags. It is possible to build a fully functional website with only tailwind CSS or with just minor CSS additions.

Assumptions and Prerequisites

This tutorial assumes that you have the following pre-installed:
Package manager: Npm or Yarn.

You can use yarn if you wish, although the commands will vary slightly.

Before we start, here’s the full list of features we will set up together in this tutorial:

  • Webpack 4
  • Webpack Bundle Analyzer
  • Webpack Dev Server
  • React 16
  • React Dom
  • Tailwind CSS
  • autoprefixer (required for tailwind CSS)
  • postcss-cli (required for tailwind CSS)
  • css-loader (to compile CSS files)
  • postcss-loader (to compile the tailwind CSS files)
  • babel-loader (required for react)
  • @babel/core (required for react)
  • @babel/preset-env (required for react)
  • @babel/preset-react (required for react)
  • @babel/cli (required for react)

At this point, we clearly understand each of the technologies involved, let’s configure them to work together.

Install Webpack

Let’s start by creating a new directory to work with. In your terminal, type:

mkdir rect_test

First, we change into the new directory, then initialize a package.json file:

cd rect_test
npm init

Answer the prompt or type npm init -y if you want to skip the prompt.
Inside the **package.json** add this if it doesn’t already exist.

{
  "name": "rect_test"
  "version": "1.0.0",
  "main": "index.js",
  "license": "MIT"
}

Now we need to install Webpack on our machine. You can install it locally (project only) or globally. For our purposes, we'll install it as a dev dependency and webpack-cli so we can use it in the terminal. In your terminal, type this command:

npm i webpack webpack-cli -D

Now we need to create an entry point for our app (page loaded when the app starts up). To do that:

  • Create a src folder and create an index.js file inside it.
  • Update your package.json ‘s script section to look like this:
"scripts": {
    "start": "webpack --mode development",
    "build": "webpack --mode production"
}

To test our progress so far, in your terminal type:

npm run start

You should see the following output:

terminal_output

If you see that, then Webpack is up and running properly.

Add React

Now we are set to install React. But for react to work, we need to install Babel alongside (to transpile the code from es5 to es6) because some browsers do not yet support ES6.

So, we will install React as a dependency and install babel as a dev dependency. In your terminal type:

npm i react react-dom -S

Then install babel-core, babel-loader, babel-preset-env and babel-preset-react as dev dependencies:

npm i babel-loader @babel/core @babel/preset-env @babel/preset-react @babel/cli -D

Now we need to create and configure our **webpack.config.js**. In your project root, create this file and add the following to it:

module.exports = {
  module: {
    rules: [
      {
        test: /\.js$/,
        exclude: /node_modules/,
        use: {
          loader: "babel-loader"
        }
      }
    ]
  }
};

We now need to make a separate file called .babelrc to provide configuration options for babel-loader. When you state you’re using babel-loader in your Webpack config, it will look for .babelrc file if there is one. In your terminal type:

touch .babelrc

Now add the following code to it:

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

At this point, we will also need to create an index.html file in the src folder where we can add our section element with id index.

This is where we render our main react component:
Under the src folder create an index.html file and add the following lines to it:

<!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, Webpack and TailwindCSS</title>
</head>
<body>
  <section id="index"></section>
</body>
</html>

Now we need to install html-webpack-plugin and use this in our Webpack config file. It will generate an HTML file for your application, or you can provide a template, it also minifies the file.

To install html-webpack-plugin as a dev dependency in your terminal type:

npm i html-webpack-plugin -D

Now update your Webpack config file to look like this:

const HtmlWebPackPlugin = require("html-webpack-plugin");

module.exports = {
  module: {
    rules: [
      {
        test: /\.js$/,
        exclude: /node_modules/,
        use: {
          loader: "babel-loader"
        }
      }
    ]
  },
  plugins: [
    new HtmlWebPackPlugin({
    template: "./src/index.html",
    filename: "./index.html"
  });
]
};

Now React is successfully setup we need to set up a dev server so anytime we start our app it comes up in the browser and automatically updates whenever we change our files.

In your terminal type:

npm i webpack-dev-server -D

Now update your scripts object inside your package.json file to look like this:

  "scripts": {
    "start": "webpack-dev-server --mode development",
    "build": "webpack --mode production"
  },

Add Tailwind CSS

At this point, we need install tailwind CSS and it's dependencies then configure it for usage. In your terminal, type:

npm install tailwindcss autoprefixer postcss-cli mini-css-extract-plugin postcss-loader --save-dev

Next, we generate a tailwind config file, In your terminal type:

./node_modules/.bin/tailwind init tailwind.config.js

This command will generate a **tailwind.config.js** file in the root of your project.

Now let's configure PostCSS so we can use it to transform the Tailwind directives into pure CSS, in the root of your project, create a file called postcss.config.js and add this code:

const tailwindcss = require('tailwindcss');
module.exports = {
    plugins: [
        tailwindcss('./tailwind.config.js'),
        require('autoprefixer'),
    ],
};

Now we need to tell Webpack what CSS file to watch and rebuild on every change.
Inside your src/ directory create a **styles.css** and add the following lines of code to it:

This is also where you can add your custom CSS files
@tailwind preflight;

@tailwind components;

@tailwind utilities;

/* Custom css */

Since we will import the CSS files into our React components we need to install css-loader module to resolve them. Once that’s resolved, we also need a style-loader to inject this into our DOM by adding a style tag into the head element of our HTML. In your terminal type:

npm i css-loader style-loader -D

Now update your Webpack config file to look like this:

const HtmlWebPackPlugin = require("html-webpack-plugin");
const MiniCssExtractPlugin = require("mini-css-extract-plugin");

module.exports = {
  module: {
    rules: [
      {
        test: /\.js$/,
        exclude: /node_modules/,
        use: {
          loader: "babel-loader"
        }
      },
       {
        test: /\.css$/,
        use: [
          MiniCssExtractPlugin.loader,
          "css-loader", "postcss-loader",
          ],
      },
    ]
  },
  plugins: [
    new MiniCssExtractPlugin({
      filename: "styles.css",
      chunkFilename: "styles.css"
    }),
    new HtmlWebPackPlugin({
    template: "./src/index.html",
    filename: "./index.html"
  }),
]
};

Testing

It's time to see what we have done so far. Open your index.js and add the following lines copied straight from the tailwind website:

import React from "react";
import ReactDOM from "react-dom";
import './styles.css';

const Index = () => {
  return <div className="bg-white mx-auto max-w-sm shadow-lg rounded-lg overflow-hidden">
  <div className="sm:flex sm:items-center px-6 py-4">
    <img className="block h-16 sm:h-24 rounded-full mx-auto mb-4 sm:mb-0 sm:mr-4 sm:ml-0" src="https://avatars2.githubusercontent.com/u/4323180?s=400&u=4962a4441fae9fba5f0f86456c6c506a21ffca4f&v=4" alt=""/>
    <div className="text-center sm:text-left sm:flex-grow">
      <div className="mb-4">
        <p className="text-xl leading-tight">Adam Wathan</p>
        <p className="text-sm leading-tight text-grey-dark">Developer at NothingWorks Inc.</p>
      </div>
      <div>
        <button className="text-xs font-semibold rounded-full px-4 py-1 leading-normal bg-white border border-purple text-purple hover:bg-purple hover:text-white">Message</button>
      </div>
    </div>
  </div>
</div>;
};

ReactDOM.render(<Index />, document.getElementById("index"));

In your terminal run npm start and you should see this in your browser.

Conclusion

In this post, we’ve learnt how to install and configure Webpack for use with tailwind CSS and react. There are a lot of more awesome things that can be achieved if you leverage on this new knowledge. Hack on!


Plug: LogRocket, a DVR for web apps

LogRocket is a frontend logging tool that lets you replay problems as if they happened in your own browser. Instead of guessing why errors happen, or asking users for screenshots and log dumps, LogRocket lets you replay the session to quickly understand what went wrong. It works perfectly with any app, regardless of framework, and has plugins to log additional context from Redux, Vuex, and @ngrx/store.

In addition to logging Redux actions and state, LogRocket records console logs, JavaScript errors, stacktraces, network requests/responses with headers + bodies, browser metadata, and custom logs. It also instruments the DOM to record the HTML and CSS on the page, recreating pixel-perfect videos of even the most complex single page apps.

Try it for free.