Shorten your imports in Visual Studio Code in React App with this trick

Shorten your imports in Visual Studio Code in React App with this trick

You're a web developer and working with ReactJS, have you ever gone through a situation when your project gets bigger and bigger with a lot of components, folders, and importing things become a nightmare? Like this

jsx
import { useUser } from '../../../../talons/useUser'
import { useUser } from '../../../../talons/useUser'

I can feel your pain, I've been through it before too. I am not sure about other IDE/ Text editors, but VS Code is still smart enough to suggest to us where our component/function is, then it will auto-import it into that file for us, it's great, but the trouble comes when you decide to modify your project structure, and sometimes you move a lot of files from here to there or vice versa and at that time, there might be some cases when VS Code doesn't keep track of directories of file for us (like it usually does) and at that time, we will be people who have to do that. And it would be a nightmare, .. and .. and .. and .. again. After having been in that scenario multiple times, I wondered myself, there must be a way to get rid of this, I decided to ask "Google-sama" who knows everything on Earth and got what I want. The research and config took me a while so today I want to share with you guys the way to do it. Maybe there are some tutorials out there talking about this trick too, but you know, I just want to share my own experience with this configuration. Hope this would help you.

Okay, I don't want to waste your time anymore, let's dive into it.

Note that in this post, I'll guide you guys to create config with create-react-app and typescript, it would be a little bit more complicated because we have to override webpack which is configured beforehand by create-react-app.

Okay, let's go.

First, let's create a new react app:

bash
yarn create react-app sample --template typescript
yarn create react-app sample --template typescript

This is our project

Shorten your imports in Visual Studio Code in React App with this trick — figure 1

Now, create a new folder called components in src

In components, create a very simple Text component

We will create 2 files:

jsx
// index.ts
export { default } from './Text'

// Text.tsx
import React from "react";

const Text = () => {
    return <div>This is from Text</div>;
};

export default Text;
// index.ts
export { default } from './Text'

// Text.tsx
import React from "react";

const Text = () => {
    return <div>This is from Text</div>;
};

export default Text;

Our project now will be like this:

Shorten your imports in Visual Studio Code in React App with this trick

Before going to the next step, I want to give you a brief about what we're going to do. To avoid using relative paths, we will create aliases for our folders. To create aliases for our folder, we have to configure the webpack alias. But things get harder since webpack is configured under the hood by create-react-app, it will not let us (users) configure webpack on our own unless you decide to eject configurations by create-react-app. But ejecting is a bad idea because by doing that you will get rid of all benefits that come with Create-react-app. Luckily, we still have some tools which help us deal with that issue. One of those tools is craco, and we will use it to override webpack configuration, after that, creating an alias will be easy as a piece of cake!

First, let's install craco:

bash
npm install @craco/craco
or
yarn add @craco/craco
npm install @craco/craco
or
yarn add @craco/craco

Once we have craco installed, we have to change our scrips in package.json:

bash
"scripts": {
  - "start": "react-scripts start",
  - "build": "react-scripts build",
  - "test": "react-scripts test",
	+ "start": "craco start",
  + "build": "craco build",
  + "test": "craco test",
  },
"scripts": {
  - "start": "react-scripts start",
  - "build": "react-scripts build",
  - "test": "react-scripts test",
	+ "start": "craco start",
  + "build": "craco build",
  + "test": "craco test",
  },

Now, in the root directory of our app, create a new file: craco.config.js

We will write all our new webpack configurations in this file.

jsx
const path = require("path");

module.exports = {
    webpack: {
        alias: {
            "@components": path.resolve(__dirname, "src/components"),
        },
    },
};
const path = require("path");

module.exports = {
    webpack: {
        alias: {
            "@components": path.resolve(__dirname, "src/components"),
        },
    },
};

Now react bundler will understand our new configuration, but we haven't done it yet. Go to our App.tsx component and change it to:

jsx
import React from "react";
import "./App.css";
import Text from "@components/Text";

function App() {
    return (
        <div className="App">
            <Text />
        </div>
    );
}

export default App;
import React from "react";
import "./App.css";
import Text from "@components/Text";

function App() {
    return (
        <div className="App">
            <Text />
        </div>
    );
}

export default App;

Now, if you're using VS Code, it will complain that "Cannot find module '@components/Text' or its corresponding type declarations", we need one more step to make VSC Intellisense work.

Create a new file called: tsconfig.paths.json:

Note that you can name this file everything you want.

json
{
    "compilerOptions": {
        "baseUrl": "./src",
        "paths":{
            "@components/*": ["components/*"]
        }
    }
}
{
    "compilerOptions": {
        "baseUrl": "./src",
        "paths":{
            "@components/*": ["components/*"]
        }
    }
}

Small note: Notice the "/*" or you'll get in trouble when VS Code Intellisense doesn't work as expected.

And import it to our tsconfig.json file:

json
{
  "compilerOptions": {
    "target": "es5",
    "lib": [
      "dom",
      "dom.iterable",
      "esnext"
    ],
    "allowJs": true,
    "skipLibCheck": true,
    "esModuleInterop": true,
    "allowSyntheticDefaultImports": true,
    "strict": true,
    "forceConsistentCasingInFileNames": true,
    "noFallthroughCasesInSwitch": true,
    "module": "esnext",
    "moduleResolution": "node",
    "resolveJsonModule": true,
    "isolatedModules": true,
    "noEmit": true,
    "jsx": "react-jsx",
    "baseUrl": "./src"
  },
  "include": [
    "src"
  ],
  + "extends": "./tsconfig.paths.json"
}
{
  "compilerOptions": {
    "target": "es5",
    "lib": [
      "dom",
      "dom.iterable",
      "esnext"
    ],
    "allowJs": true,
    "skipLibCheck": true,
    "esModuleInterop": true,
    "allowSyntheticDefaultImports": true,
    "strict": true,
    "forceConsistentCasingInFileNames": true,
    "noFallthroughCasesInSwitch": true,
    "module": "esnext",
    "moduleResolution": "node",
    "resolveJsonModule": true,
    "isolatedModules": true,
    "noEmit": true,
    "jsx": "react-jsx",
    "baseUrl": "./src"
  },
  "include": [
    "src"
  ],
  + "extends": "./tsconfig.paths.json"
}

No, if you go back to App.tsx file, you won't see any complaints from Visual Studio Code anymore.

Let's restart our app:

Tadaa, it worked!

Shorten your imports in Visual Studio Code in React App with this trick (2)

So from now on, every time you have a new folder and want to add an alias for it, just go to tsconfig.paths.json, add it to paths object and craco.config.js as well.

For example: this is from my project:

json
// tsconfig.paths.json
{
    "compilerOptions": {
        "baseUrl": "./src",
        "paths": {
            "@type/*": ["types/*"],
            "@pages/*": ["pages/*"],
            "@hooks/*": ["hooks/*"],
            "@utils/*": ["utils/*"],
            "@talons/*": ["talons/*"],
            "@shared/*": ["shared/*"],
            "@config/*": ["config/*"],
            "@layout/*": ["layout/*"],
            "@context/*": ["context/*"],
            "@images/*": ["assets/images/*"],
            "@components/*": ["components/*"]
        }
    }
}
// tsconfig.paths.json
{
    "compilerOptions": {
        "baseUrl": "./src",
        "paths": {
            "@type/*": ["types/*"],
            "@pages/*": ["pages/*"],
            "@hooks/*": ["hooks/*"],
            "@utils/*": ["utils/*"],
            "@talons/*": ["talons/*"],
            "@shared/*": ["shared/*"],
            "@config/*": ["config/*"],
            "@layout/*": ["layout/*"],
            "@context/*": ["context/*"],
            "@images/*": ["assets/images/*"],
            "@components/*": ["components/*"]
        }
    }
}

The full repo can be found at Link

Tagged:#Front-end#Web Development
0