3 minute read

In this video I’ll show you how to make your React application more reliable. Your components and class names will always be consistent. And the next time, when you remove the class name so that it no longer exists, you will get a compilation error.

Used commands:

  • npx create-react-app my-app --template typescript
  • npm run start
  • npm install -D dts-css-modules-loader
  • git add . && git commit -m "Initial commit"
  • npm run eject
  • npm run build

First, let’s create a react app with typescript components. For this, in the command line we need to execute: npx create-react-app my-app --template typescript

Next, we go to the app folder and execute npm run start, to make sure the application works.

Now, if we open the App.tsx component, we see import './App.css';. This line imports styles from the CSS file, and we can use them as class names like <header className="App-header">.

But what if we change the name of this class or remove it. Let’s do that and save the CSS file. In this case, the application is still running, and we don’t get any errors or warnings by default. This means that sometimes we may not even notice such inconsistency in our application. This is even more frustrating as we don’t get any benefits from using the TypeScript type system.

So let me show you how to improve this situation (and for now I want to return the removed class name). Ok.

First of all, we need to install the dts-css-modules-loader package. This is a simple loader that generates typescript declaration files based on the CSS files it found.

Next, we need to include this style loader in our pipeline. For this, I’m going to update the webpack configuration file. Let’s stage our changes by executing git add . && git commit -m "Initial commit" command.

Now, we can run the npm run eject command, which allows us to update the configuration files.

In the webpack.config.js we find a configuration section that defines the list of style loaders for CSS files. Let’s change it:

{
  test: cssRegex,
  exclude: cssModuleRegex,
  use: [
    {
      loader: require.resolve('style-loader'),
      options: {
        esModule: false,
      },
    },
    {
      loader: require.resolve('dts-css-modules-loader'),
      options: {
        namedExport: true
      }
    },
    {
      loader: require.resolve('css-loader'),
      options: {
        modules: {
          exportLocalsConvention: 'camelCaseOnly',
          localIdentName: "[hash:base64:5]",
        }
      }
    }
  ]
}

We’ve defined our own list of styles loaders that we want to apply to the CSS files in our project. And the dts-css-modules-loader is now one of them.

Let’s save it and build the application with the npm run build command.

When the build is complete, you can notice the new App.css.d.ts file generated by our loader. If we open it, we can see that the file now contains the declaration of our class names.

Let’s open the App.tsx file and finally import our class names. All we have to do is update the import line to import classes from './App.css';.

Now, we can reference to our class names using the classes object.

For example, we change:

  • className="App" to className={classes.app}
  • className="App-header" to className={classes.appHeader}
  • classes.appLogo and classes.appLink appropriately

If we start the application, we will see that it works as before.

But what if we change a class name or remove it.

Let’s save the file.

And from now on, in case of any inconsistency with our styles, we will receive an error message in the VSCode and also a compilation error in the application. In my opinion, this approach is extremely helpful and absolutely a must for any large react application.

And that’s all for today. I hope this approach will make your react applications more solid and save you a lot of time.

The link to the source code is in the description of this video. And I hope to see you next time.

References: