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
ts-loader breaking when it's used with TS Path mappings based module resolution #213
Comments
@DanielRosenwasser, it would be so nice if resolve get populated from tsconfig.json automatically. That way no need to update 2 configs (tsconfig.json & webpack.config.js) at build time. |
@jbrantly, @DanielRosenwasser any recommendation? Thanks! |
Edit: Don't do this, it won't work. See below.
declare module "foo" {
import m = require("../my_dependencies/foo");
export = m;
} |
Thanks for the suggestion @DanielRosenwasser I couldn't make it working. Can you please update my sample and show me how ambient module help? Thanks a lot again! |
Scratch that last suggestion. I've found a better fix. Fix up your resolve: {
// Add `.ts` and `.tsx` as a resolvable extension.
extensions: ['', '.webpack.js', '.web.js', '.ts', '.tsx', '.js'],
// Configure path resolution strategy
modulesDirectories: [
".",
"src/extension/",
"src/utility/"
]
}, That should keep it in sync with the path mappings in your "paths": {
"*": [
"*",
"src/extension/*",
"src/utility/*"
]
} Let me know how that works. |
Thanks a lot @DanielRosenwasser -- it works charmingly with your first config.
It doesn't work if I use the same mapping I've in tsconfig.
On the other hand, Typescript compiler working with the second way of mapping... it required '' at the end. Is there any way 'moduleDirectories' working with '' at the end? The reason I can't break TS compiler is I've a another build pipeline that required to build individual files using TSC. |
+1, would be nice if ts-loader would be able to automatically parse the paths/baseUrl properties from tsconfig.js. Took me a while to figure out that the problem was that I wasn't including the paths in |
Extending the modulesDirectory setting should work for simple mappings, but what about more complex mappings where "paths": {
"*": [
"*",
"components/*/src"
]
} If this is not possible, I would have to add a package.json with a typings field of "src/index.ts" to every component folder, but would rather prefer to have this working without dummy files. |
@tp @DanielRosenwasser @johnnyreilly @jbrantly I have whipped up an isolated webpack Resolver plugin (thanks to @s-panferov) that may apply the module resolution strategy over to webpack correctly with support for fallbacks etc. @bruk1977 @adambuczynski would you please try this out? If you don't use ts-node you can es5 it and implement. https://github.com/angular/angular-cli/blob/webpack/addon/ng2/utilities/ts-path-mappings-webpack-plugin.ts Usage is found here: |
@TheLarkInn I don't think having to add some paths to the resolve array weighs up against having to add an additional plugin/dependency. For me, the following now works and is quite simple to implement/manage once you know how to: tsconfig.json example (simplified): {
"compilerOptions": {
"target": "es5",
"moduleResolution": "node",
"baseUrl": ".",
"paths": {
"*": [
"app/components/*",
"app/*"
]
}
}
} And corresponding webpack config: //Resolve rules
resolve: {
extensions: [
'', '.js', '.ts', '.scss'
],
root: [
path.join(ROOT, 'app'),
path.join(ROOT, 'app/components'),
path.join(ROOT, 'node_modules')
]
}, But as I said, it would be great if webpack could detect this on it's own rather than having to do it by hand or with an extra plugin. |
How would handle something like this:
|
@TheLarkInn I don't know, I haven't had a use case for that. For now, it's fulfilling all my requirements and needs :) |
@TheLarkInn Love trying but when I'm trying to install wepback@2.1 or webpack@next I'm getting the below error.. .any idea? silly fetchPackageMetaData Error: No compatible version found: webpack@2.1 |
webpack@2.1.0-beta.15 give that a try |
Thanks @TheLarkInn -- 2.1.0-beta.15 install working. However, I'm getting the below error. I updated my sample and you can repro. Is there a bug in the plugin or do I miss anything? Error: |
Is it possible for At the moment I have to duplicate my config between
|
The Angular compiler solves this with a plugin. It's possible to use the plugin in any non-Angular webpack configuration. Just have to install {
apply(compiler) {
compiler.plugin('normal-module-factory', nmf => {
const PathsPlugin = require('@ngtools/webpack').PathsPlugin;
compiler.resolvers.normal.apply(new PathsPlugin({
nmf,
tsConfigPath: path.resolve(__dirname, 'tsconfig.json'),
}));
});
}
} |
@Merott - thanks for sharing! I don't suppose you'd fancy submitting a docs PR to aid discoverability of this solution? Also, I'm slightly curious about your usage example above. I'd anticipated usage that looked something like this in your
But this is different to what you have; I'm guessing there's a reason your setup is different but I wonder if you could elaborate? |
@johnnyreilly - the usage has to do with the constructor API for The constructor expects an options object, with the const PathsPlugin = require('@ngtools/webpack').PathsPlugin;
function TsConfigPathsPlugin(tsConfigPath) {
this._tsConfigPath = tsConfigPath;
}
TsConfigPathsPlugin.prototype.apply = function (compiler) {
compiler.plugin('normal-module-factory', normalModuleFactory => {
compiler.resolvers.normal.apply(new PathsPlugin({
nmf: normalModuleFactory,
tsConfigPath: this._tsConfigPath,
}));
});
};
module.exports = {
// ... webpack configuration
plugins: [
new TsConfigPathsPlugin(path.resolve(__dirname, 'tsconfig.json')),
]
} That's the best I can come up with, though I'm not a webpack expert, so tell me if there's a better way or an API that can help. As this seems a little bit tedious, I'm not sure if it would be good as an official solution to appear in the docs. |
Thanks for the clarification. Might be good to lift the existing plugin and create a standalone one. I think that's what |
I don't suppose you could try something for me could you? Would you be able to add
If that works I wonder if they'd be up for publishing this as a standalone package that could be used by ts-loader and awesome-typescript-loader alike? |
@johnnyreilly I can confirm that the solution from the post above works great for me: I have the following code:
const {TsConfigPathsPlugin} = require('awesome-typescript-loader');
resolve: {
plugins: [
new TsConfigPathsPlugin()
]
}
"baseUrl": ".",
"paths": {
"shared-services/*": ["./app/shared/services/*"]
} |
That's awesome @zuzusik! Would you be able to share a minimal that demonstrates this? I'd like to document this usage and also add a test to our testpack that uses the paths plugin. With a minimal repo I could probably do that. I don't use this functionality myself and so I don't have any example code of my own I could use. |
You could also use the tsconfig-paths-webpack-plugin package together with ts-loader in order to resolve |
Yeah - works for me. I still should really get round to creating an execution test for our test pack that covers using ts-loader with another plugin providing the path functionality. Haven't yet though. If anyone feels motivated to provide that I'd appreciate it. I'll close this though. |
tsconfig-paths-webpack-plugin is not working with Webpack 4 yet...
|
@cime Could you please report the problems you are experiencing with webpack 4 and tsconfig-paths-webpack-plugin in this issue. |
Maybe this tool I made for resolving paths might be handy (to someone)? |
I'm using Path Mapping based Module resolution feature of TypeScript 2.0 and ts-loader failing with 'can not resolve module' error.
To repro the issue, please follow the following steps:
You will get the following error:
It's working fine when I'm running the following command:
tsc -p tsconfig.json
The text was updated successfully, but these errors were encountered: