53

my directory structure is:

|
|__src
|    |_components
|                |
|                |_A
|                  |_index.tsx
|
|
tsconfig.json
package.json

I want to import A like this:

import { A } from 'src/components/A';

My tsconfig.json looks like this:

{
  "compilerOptions": {
    "baseUrl": "",
    "declaration": true,
    "downlevelIteration": true,
    "esModuleInterop": true,
    "jsx": "react",
    "lib": ["es5", "es2015", "es2016", "dom"],
    "module": "esnext",
    "moduleResolution": "node",
    "noImplicitAny": true,
    "noUnusedLocals": true,
    "noImplicitReturns": true,
    "outDir": "dist",
    "removeComments": false,
    "skipLibCheck": true,
    "strict": true,
    "strictFunctionTypes": false,
    "strictNullChecks": false,
    "suppressImplicitAnyIndexErrors": true,
    "target": "es5",
    "typeRoots": ["./node_modules/@types"],
    "types": ["node", "jest"],
    "paths": {
      "*": ["./node_modules/@types/*", "./types/*"]
    }
  },
  "include": ["src/**/*.ts", "src/**/*.tsx"],
  "exclude": ["./node_modules", "./dist", "src/**/*.test.ts", "src/**/*.test.tsx"]
}

But the import does not work and I get the error:

can't find module 'src/components/A';

dagda1
  • 26,856
  • 59
  • 237
  • 450

2 Answers2

77

In tsconfig.json define paths like this:

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

(and you have to import it with name of file as well)

import { A } from 'src/components/A/index'

based on the comments no need to import with file name as long as it is called index (With relative paths we can skip the /index)

NearHuscarl
  • 66,950
  • 18
  • 261
  • 230
Juraj Kocan
  • 2,648
  • 1
  • 15
  • 23
15

Imports with absolute paths work for me using this configuration in tsconfig.json:

{
  "compilerOptions": {
    "baseUrl": "src"
  }
}

This is the complete tsconfig.json that works for me in CRA app:

{
  "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",
    "baseUrl": "src"
  },
  "include": [
    "src"
  ]
}
Pinka
  • 201
  • 2
  • 6
  • 1
    For me, this breaks node_modules imports as it's trying to access from the src folder. – Conrad Kay Nov 22 '21 at 23:04
  • Could be that some other setting is affecting the node_modules imports. Added a complete tsconfig.json that works for me. – Pinka Dec 15 '21 at 14:45
  • For me, I had to set `"baseUrl": "./src"` – Drew Daniels May 10 '23 at 16:57
  • @ConradKay you need to leave out the src folder in your imports. For example `import { foo } from 'bar'` and not `import { foo } from 'src/bar'`. This actually annoys me as it makes it hard to read if my imports come from a library or a folder/code that I wrote. I'm currently trying to solve that problem here: https://stackoverflow.com/questions/76980414/absolute-path-typescript-react-works-in-ide-linting-but-not-in-cra-runtime – Fiddle Freak Aug 28 '23 at 02:38