Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support for TypeScripts 'paths' option #4357

Closed
ChristoRibeiro opened this issue Mar 4, 2018 · 18 comments
Closed

Support for TypeScripts 'paths' option #4357

ChristoRibeiro opened this issue Mar 4, 2018 · 18 comments
Labels
help wanted Issue with a clear description that the community can help with.

Comments

@ChristoRibeiro
Copy link

ChristoRibeiro commented Mar 4, 2018

Description

I'm trying to implement alias for importing Typescript modules from root of my project. According to typescripts docs it can be done by adding following configuration to 'tsconfig.json' file

    "baseUrl": "./src",
    "paths": {
      "@components": ["/components"]

Then from anywhere ts/tsx file: import { MyComponent } from '@components/MyComponent'.

Environment

Gatsby version: 1.1.40
Node.js version: v8.9.4
Operating System: macOS 10.13.3

Actual result

Module @components/MyComponent not found. The Same behavior has been fixed with create-react-app: issue 203.

Expected behavior

Typescript should find my module.

Steps to reproduce

1. gatsby new website-gatsby-clean https://github.com/haysclark/gatsby-starter-typescript

2. add Typescript paths config to tsconfig.json

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

3. create src/components/MyComponent.tsx

const MyComponent = () => <h1>Hello</h1>
export default MyComponent

4. import MyComponent into src/pages/index.tsx

...
import MyComponent from '@components/MyComponent'
...
public render() {
    return <MyComponent />
}
...
@m-allanson
Copy link
Contributor

It looks like you'd need to use the tsconfig-paths-webpack-plugin to enable this setup? I think you could do this using Gatsby's webpack hooks - see the docs page on custom webpack configs.

Note that Gatsby v1 uses webpack version one. Gatsby v2 will upgrade to a newer release of webpack.

@ChristoRibeiro
Copy link
Author

@m-allanson thanks. Not sure how to make it work. I've tried that:

yarn add --dev tsconfig-paths-webpack-plugin

then

const TsconfigPathsPlugin = require('tsconfig-paths-webpack-plugin');

function TsconfigPathsContructor() {
  return new TsconfigPathsPlugin();
}

exports.modifyWebpackConfig = ({ config, stage }) => {
  if (stage == "develop" || stage == "build-javascript") {
    const opts = [{
      configFile: "./tsconfig.json"
    }];

    config.plugin("ts-config-paths-plugin", TsconfigPathsContructor, opts);
  }

  return config;
};

@tsriram
Copy link
Contributor

tsriram commented Mar 9, 2018

Not a complete solution, but I got rid of the TS error (in VS Code) with this in tsconfig.json:

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

Though gatsby/webpack still throws an error that the dependency is not found when I import a module using path defined in tsconfig.json. Not sure how to get this working!

@ChristoRibeiro
Copy link
Author

@m-allanson any idea how to make it work?

@t49tran
Copy link

t49tran commented May 8, 2018

I resolved the problem after having a look here #484. Basically, what I do is add an alias option to webpack.resolve in gatsby-node.js:

exports.modifyWebpackConfig = function({ config, env }) {
  config.merge({
    resolve: {
      alias: {
        `[ALIAS]`: [PATH_TO_ALIAS]
      }
    }
  });
  return config;
};

@m-allanson
Copy link
Contributor

Thanks @t49tran. It'd be nice for gatsby-plugin-typescript to support this automatically. It could read tsconfig.json and automatically apply the aliases to webpack.

@m-allanson m-allanson added help wanted Issue with a clear description that the community can help with. 🏷 type: feature labels May 8, 2018
@t49tran
Copy link

t49tran commented May 9, 2018

I think it makes complete sense @m-allanson, I will have a look into gatsby-plugin-typescript and see if I can do something.

@KyleAMathews
Copy link
Contributor

Due to the high volume of issues, we're closing out older ones without recent activity. Please open a new issue if you need help!

@0x80
Copy link
Contributor

0x80 commented Dec 8, 2018

I was struggling to make this work, not realizing the example by @t49tran was using the v1 gatsby config API. For the record, if anyone arrives here looking for a solution using v2, here's the summary:

You don't need the tsconfig-paths-webpack-plugin, and I'm not sure how it relates to be honest.

In tsconfig I have this:

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

So in code you can write things like import { widths } from '@src/styles/variables'

Then to make the build succeed, add to gatsby-node.js:

exports.onCreateWebpackConfig = function({ actions }) {
  actions.setWebpackConfig({
    resolve: {
      alias: {
        '@src': path.resolve(__dirname, 'src')
      }
    }
  })
}

I personally like the @ prefix, because it makes it very clear that you're not importing from node_modules.

@jbmusso
Copy link

jbmusso commented May 19, 2019

I personally like the @ prefix, because it makes it very clear that you're not importing from node_modules.

This could also indicate a @scoped package located in ./node_modules/, although I didn't check if @src scope is available there. In this context, maybe using # instead of @ could help better distinguish between scoped-packages and internal/local packages resolved via paths.

Thanks for the exports.onCreateWebpackConfig info :-).

@0x80
Copy link
Contributor

0x80 commented May 27, 2019

@jbmusso You're right, a different character would probably be better. I realized that shortly after :) But I haven't ran into any problems yet. The prefixes I'm using are so generic they are not very likely to clash with a library namespace (src, components, modules, utils, config, ...)

@martinmckenna
Copy link

martinmckenna commented Jun 2, 2019

@0x80 Forgetting this line at the top of the gatsby-node.js file

var path = require('path');

Here's a quick starter project for anyone interested:

https://github.com/martinmckenna/gatsby-typescript-starter

@thetrevorharmon
Copy link
Contributor

Has anybody been successful at getting this working while also using TSLint? I have followed what @0x08's recommendedation but I keep running into a "not found" error:

Cannot find module '@src/UI-Kit'.

I'll also run in to other lint errors (like no-submodule-imports) but those are easily fixed by explicitly allowing @src in my tslint.json.

@kirbycool
Copy link

If anyone's still struggling with this issue, I was able to get it working pretty easily using tsconfig-paths-webpack-plugin.

tsconfig.json

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

gatsby-node.js

const TsconfigPathsPlugin = require('tsconfig-paths-webpack-plugin')

exports.onCreateWebpackConfig = ({ actions }) => {
  actions.setWebpackConfig({
    resolve: {
      plugins: [new TsconfigPathsPlugin()],
    },
  })
}

And then you can import like this

import Foo from '@components/foo'

@anxious-coder-lhs
Copy link

If anyone's still struggling with this issue, I was able to get it working pretty easily using tsconfig-paths-webpack-plugin.

tsconfig.json

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

gatsby-node.js

const TsconfigPathsPlugin = require('tsconfig-paths-webpack-plugin')

exports.onCreateWebpackConfig = ({ actions }) => {
  actions.setWebpackConfig({
    resolve: {
      plugins: [new TsconfigPathsPlugin()],
    },
  })
}

And then you can import like this

import Foo from '@components/foo'

This certainly works for Gatsby v2.

@kaluabentes
Copy link

How to remove the warning from VSCode? Did anyone found a solution to this?

@d0t15t
Copy link

d0t15t commented Aug 16, 2021

I'm also struggling with this in Gatsby v3. i've tried variations of with/without tsconfig-paths-webpack-plugin, and onCreateWebpackConfig as suggested here, but no luck. Does anyone have a definitive solution for this in Gatsby v3?

@aaronadamsCA
Copy link
Contributor

aaronadamsCA commented Oct 12, 2021

Deleted my prior comment.

This Gatsby plugin is working for me: https://www.gatsbyjs.com/plugins/gatsby-plugin-tsconfig-paths/

Its key limitation is that it doesn't work for require statements in gatsby-config.js. Once I worked around that, it's all good.

Shirokuiu added a commit to Shirokuiu/ssg-template--gatsby- that referenced this issue May 13, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
help wanted Issue with a clear description that the community can help with.
Projects
None yet
Development

No branches or pull requests