Error: Can't resolve '/path/to/image.jpg' in '/app/path/to/module/module'
The issue is with images used for css backgrounds where the files aren't stored in the repository, and are not available at build-time. (Why it's this way is a story for another time.)
In my scss file:
background-image: url(/path/to/image.jpg);
In Webpack-4, it was left as-is, and just worked.
Webpack-5 tries processing the image and fails with the error above.
Adding quotes to the path...
background-image: url("/path/to/image.jpg");
I've tried Webpacks magic comments...
/* webpackIgnore: true */
background-image: url(/path/to/image.jpg)
... but it didn't work (maybe they were getting stripped too early? - This seems to be the case as is evidenced by the dev build working in my create-react-app example)
webpack.IgnorePlugin 👎
I also tried some of the edge-case tips from here. But i think that comes in too late because Webpack already assumes that the file exists.
What does work, is including the absolute path to the asset:
background-image: url(https://www.example.com/path/to/image.jpg);
But that creates it's own set of problems.
The Webpack magic comments work for the development build, but not for the production build.
~/webpack-test$ npm run build
> webpack-test@0.1.0 build
> node scripts/build.js
Creating an optimized production build...
Failed to compile.
Module not found: Error: Can't resolve '/mypics/pom.jpg' in '/home/nodejs/webpack-test/src'
It turns out that the css-loader has configuration options just for this under options.url
!
Thank you Alexander Akait from the Webpack team for answering my question here.
It has the option to pass an object that contains a filter()
predicate function that should determine whether a path should be processed:
module.exports = {
module: {
rules: [
{
test: /\.css$/i,
loader: "css-loader",
options: {
url: {
filter: (url, _resourcePath) => {
// Disable processing for root-relative urls under /images
return !/^\/images\//.test(url)
// This would disable processing for all root-relative urls:
// return !/^\//.test(url);
},
},
},
},
],
},
};
Here is the commit I used to fix this issue in the repo mentioned in the question: https://github.com/dovidweisz/webpack-test/commit/a9e4cfc4ae0a5a8475ddd2cc114a8650846db421
You can also disable ALL url-handling by simply passing false
to options.url
:
module.exports = {
module: {
rules: [
{
test: /\.css$/i,
loader: "css-loader",
options: {
url: false,
},
},
],
},
};