我在Webpack中遇到有关相对路径的问题。 让我试着解释一下这个场景:
我在工作区目录:
中有2个单独的项目由于两个项目都使用相同的样式,所以我想将 项目A的SCSS文件[由标准变量,预定义布局,模态,类等组成]重用到项目B中
现在,如果我尝试在Project-B index.scss中导入Project-A index.scss作为另一部分[注释掉背景图像URL依赖性],webpack能够生成必需的CSS输出文件。
// Import Project A SCSS [Common Varibles, Classes, Styling etc]
@import "../../../../Project_A/assets/stylesheets/index";
但是,由于Project-A的index.scss进一步引用了来自相应Relative-Path的背景图像,因此webpack构建引发错误
'在XYZ / Project-B / Source / Stylesheets'中找不到文件/目录。
确切的错误阻止:
> ./src/assets/stylesheets/index.scss中的错误 模块构建失败:ModuleNotFoundError:找不到模块:错误:无法解析'file'或'diWorkSpace \ Project_B \ src \ assets \ stylesheets截图:
我无法理解,为什么Webpack无法解决Project-A内部资产的相对路径,仍然在“项目B”内部查看。
以下是模拟问题的Code-Repo网址: https://github.com/raviroshan/webpack-build-issue/tree/master/WorkSpace
重现的步骤。
答案 0 :(得分:8)
所以,经过这么多的努力,得到了一个合适的解决方案。
结果是CSS加载器出现了问题,即它无法解析与当前文件相对应的URL。
使用 resolve-url-loader 解决了这个问题。 https://www.npmjs.com/package/resolve-url-loader
// Old Loader Config in Webpack-entry
loader: ExtractTextPlugin.extract('style-loader', 'css-loader?sourceMap!sass-loader?sourceMap')
// New [Fixed] Loader Config in Webpack-entry
loader: ExtractTextPlugin.extract('style-loader', 'css-loader?sourceMap!resolve-url-loader!sass-loader?sourceMap')
此处更新了Code-Repo解决方案:https://github.com/raviroshan/webpack-build-issue
注意:不要省略-loader 您的Webpack.config.js应始终使用加载器名称的长格式(即-loader后缀)。
还有另一个名为resolve-url的包,Webpack可以将其与resolve-url-loader混淆。
答案 1 :(得分:3)
似乎是 css-loader 错误及其在@import
和url()
中解析路径的方式。它尝试解析所有路径 - 甚至是导入样式表中的路径 - 相对于主CSS文件 - 在您的情况下为/Project_B/src/assets/stylesheets/index.scss
。
也许它并不完美,但它是我迄今为止最好的一个。
创建一个全局变量$assetsPath
,其中包含相对于当前样式表的资源的路径。然后将此变量添加到您的所有url()
值。
在你的/Project_A/assets/stylesheets/index.scss
中写道:
/*/ Using !default we can override this variable even before the following line: /*/
$assetsPath: '../' !default;
.container {
/*/ ... /*/
.content-wrapper {
/*/ ... /*/
background-image: url($assetsPath + "images/content-bg.jpg");
}
}
在你的/Project_B/src/assets/stylesheets/index.scss
中写道:
/*/ The following variable will override $assetsPath defined in the imported file: /*/
$assetsPath: '../../../../Project_A/assets/';
/*/ Import Project A SCSS [Common Varibles, Classes, Styling etc] /*/
@import "../../../../Project_A/assets/stylesheets/index";
如果您将Project-A与Gulp捆绑在一起,它会将Project-A的代码视为:
/*/ ... /*/
background-image: url("../images/content-bg.jpg");
虽然,当您将Project-B与Webpack捆绑在一起时,它会将Project-A的代码视为:
/*/ ... /*/
background-image: url("../../../../Project_A/assets/images/content-bg.jpg");
因此, 已保存。
我肯定会仔细研究这个问题。如果url-loader
尊重@import
语句中的路径并相应地将其应用于引用的资产,则可以避免所有这些。要么我错过了某些东西,要么将它视为一个错误。
我希望你度过美好的一天! 〜Wiktor的
答案 2 :(得分:2)
您需要将publicPath设置为获取文件加载器中相对路径的相对路径。