Absolute path not working in Vite project React TS

Viewed 17852

I'm struggling to get absolute path to work in a Vite react-ts project.

Here's how I created the project

npm init @vitejs/app
npx: installed 6 in 1.883s
√ Project name: ... test-vite
√ Select a framework: » react
√ Select a variant: » react-ts

Then I added baseUrl to tsconfig.json based on the TS official doc:

{
  "compilerOptions": {
    "baseUrl": "./src",
    ...

followed by adding a simple component (T:\test-vite\src\components\Test.tsx)

import React from "react";

const Test = () => <h1>This is a Test.</h1>;

export default Test;

Finally I import the Test component in App.tsx
but it won't let me use absolute path:

import Test from "components/Test";

I get this error enter image description here

whereas if I use relative path, the app works in dev & build mode without any error:

import Test from "./components/Test";

How can I make absolute path work in the project?

4 Answers

There are two problems here:

  • Tell typescript how to resolve import path
  • Tell vite how to build import path

You only tell typescript how to resolve, but vite don't konw how to build. So refer to the official document resolve.alias, maybe this is what you want:

// vite.config.ts
{
  resolve: {
    alias: [
      { find: '@', replacement: path.resolve(__dirname, 'src') },
    ],
  },
  // ...
}

You can import path like this (or any module under ./src):

import Test from "@/components/Test";
import bar from "@/foo/bar"

Moreover, you can use vite plugin vite-tsconfig-paths directly, it makes you don't have to manually configure resolve.alias

@Yuns solutions works, but it shows error in vscode. And it was breaking auto-import in vs code.

To make it work in vscode and vite both, I added alias in both tsconfig and vite.config.

// tsconfig.json
{
  "paths": {
      "@/*": ["src/*"]
    }
  // ...
}


// vite.config.ts
{
  resolve: {
   alias: [{ find: '@', replacement: '/src' }],
  },
  // ...
}

Then, I could import like below (svelte app is in src directory)

import Header from '@/components/Header.svelte

I came here through search results, I was looking for something different, namely, how to do a simple absolute import like import { foo } from 'src/lib/foo.ts'

So if you have a /src directory that contains all code and want to use an absolute import path.

vite.config.ts

export default defineConfig({
  ...
  resolve: {
    alias: {
      src: path.resolve('src/'),
    },
  }
})

tsconfig.json

{
  "compilerOptions": {
    ...
    "baseUrl": "./"
  }
}

Note that this is a trick: src is an alias, so it appears like the path is absolute in Vite. If you have another directory in the root dir, adjacent to /src, you will need to add another alias for that directory.

Looking for import {...} from "src/foo/bar";?

I also came here through search results like user Maciej Krawczyk, but the @ part also wasn't what I was interested in. That user's answer helped me, but I had trouble with the path.resolve part (ReferenceError because path wasn't defined), so I used a slightly different approach:

vite.config.ts
export default defineConfig({
  ...
  resolve: {
    alias: {
      src: "/src",
    },
  },
  ...
})

Vite's resolver considers the absolute path /src to be from where the server is serving (see GH issue). So if you're running/building from the root of your project with src as a top level directory -- which is pretty common -- this alias points Vite in the right direction.

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

This is basically blindly following this StackOverflow answer. TypeScript needs to know that we have special resolving going on as well, otherwise TS will be freaked out about your non-existent src package and not know where it should go looking. (Note: After I changed my TS config, VSCode didn't immediately pick up the change, so I was still getting warnings. I quit, re-opened, and had to wait ~15sec for the warnings to go away.)

Related