如何使用 webpack-4 解析 sass 文件中的背景图片 URL?

ded*_*bie 9 javascript webpack webpack-style-loader webpack-4

这是我第一次在这里写信,所以请记住这一点。我是第一次在项目中使用 webpack,我遇到了一个问题,我试图在我的 sass 文件中使用背景 url() 函数设置背景图像,如下所示:

.img-container {
  background: url('../../img/homepage-login-prog.jpg') no-repeat center center fixed;
  background-size: cover;
}
Run Code Online (Sandbox Code Playgroud)

我的文件夹结构是:

- css
  | app.css
- dist (this folder is created after building for production)
- img
  | some-image.jpg
- js
  | app.js (entry point for webpack output, 
            this is where I import main.scss file)
- js-vendor
  | vendor.js (third-party libraries like bootstrap, jquery)
- sass  (this is where I keep all my sass files which get compiled using 
         webpack loaders)
  | components
    | greetings-section.scss
    | navbar.scss
  | main.scss
  | variables.scss
- template.html
- webpack.common.js
- webpack.dev.js
- webpack.prod.js
Run Code Online (Sandbox Code Playgroud)

因为我为开发和生产都配置了 webpack,所以我为它们都有单独的文件,它们都扩展了通用(通用)配置文件。那个看起来像这样:

const path = require("path");

module.exports = {
  entry:{
    main: "./js/app.js",
    vendor: "./js-vendor/vendor.js"
  },
  module: {
    rules: [
      {
        test: /\.html$/,
        use: ["html-loader"]
      },
      {
        test: /\.(svg|png|jp(e*)g|gif)$/,
        use: [{
          loader: "file-loader",
          options: {
            name: "[name].[hash].[ext]",
            outputPath: "img",
          }
        }]
      }
    ]
  }
};
Run Code Online (Sandbox Code Playgroud)

我的 webpack 开发配置如下所示:

const common = require("./webpack.common");
const merge = require("webpack-merge");
const path = require("path");
var HtmlWebpackPlugin = require("html-webpack-plugin");
const MiniCssExtractPlugin = require("mini-css-extract-plugin");

module.exports = merge(common, {
  mode: "development",
  output: {
    filename: "[name].bundle.js",
    path: path.resolve(__dirname, "dist")
  },
  plugins: [
    new HtmlWebpackPlugin({
      template: "./template.html"
    }),
    new MiniCssExtractPlugin({
      filename: "[name].[contentHash].min.css"
    }),
  ],
  module: {
    rules: [
      {
        test: /\.scss$/,
        use: [
          {
            loader: MiniCssExtractPlugin.loader,
            options: {
              publicPath: "../../"
            }
          },
          "css-loader",
          "sass-loader"
        ]
      }
    ]
  }
});
Run Code Online (Sandbox Code Playgroud)

所以,在 webpack-dev-server 启动后,会弹出一个错误:

ERROR in ./sass/main.scss (./node_modules/css-loader/dist/cjs.js!./node_modules/sass-loader/lib/loader.js!./sass/main.scss)
Module not found: Error: Can't resolve '../../img/homepage-login-prog.jpg' in 'C:\Users\...\...\...\sass'
Run Code Online (Sandbox Code Playgroud)

如您所见,我尝试在 mini-css-extract-plugin 中使用 publicPath 选项设置相对路径,但它并没有为我解决。我也一直在读其他人也有类似的问题,但他们的解决方案都没有对我有用,所以我想问的是,有谁知道我如何配置 webpack 来识别我的 sass 中图像的 url文件,并正确绑定它?

很抱歉这篇很长的帖子,任何帮助将不胜感激。

小智 5

遇到了类似的问题,对我有用的是将我的 main.scss 文件移动到我的 sass 文件夹中。之前,它位于 src 文件夹中。main.scss 文件导入我所有的其他 .scss 文件。在作为入口点的 index.js 中,我导入了 main.scss 文件。

但是,我的文件结构与您的不同。

文件结构

我有一个用于输出的 dist 文件夹和用于输入的 src 文件夹。

索引.js:

import "./sass/main.scss";
Run Code Online (Sandbox Code Playgroud)

主文件:

@import "./footer";
@import "./header";
@import "./home";
@import "./navigation";
@import "./reset";
@import "./typography";
@import "./variables";
Run Code Online (Sandbox Code Playgroud)

_header.scss:

  #hero {
  background-image: url("../assets/heroImage.jpg");
  background-size: cover;
  height: 100vh;
  width: 100vw;
  display: flex;
  justify-content: center;
  align-items: center;
}
Run Code Online (Sandbox Code Playgroud)

由于我的 scss 代码中的 background-image: url() 问题,我遇到了同样的错误。这个导入结构为我解决了这个问题。

对于我的 webpack,我有一个非常相似的配置,分为 3 个,common、dev 和 prod。我添加的唯一插件是 webpack.dev 中的“resolve-url-loader”。我已经在 miniCssExtractPlugin 中尝试了 publicpath 无济于事。

除了入口点之外,我的共同点几乎与您的完全相同。我的是 src 文件夹中的 index.js 而不是 app.js。

webpack.dev.js

const path = require("path");
const common = require("./webpack.common");
const merge = require("webpack-merge");
var HtmlWebpackPlugin = require("html-webpack-plugin");

module.exports = merge(common, {
  mode: "development",
  output: {
    filename: "[name].bundle.js",
    path: path.resolve(__dirname, "dist")
  },
  plugins: [
    new HtmlWebpackPlugin({
      template: "./src/template.html"
    })
  ],
  module: {
    rules: [
      {
        test: /\.scss$/,
        use: [
          {
            loader: "style-loader"
          },
          {
            loader: "css-loader"
          },
          {
            loader: "resolve-url-loader"
          },
          {
            loader: "sass-loader"
          }
        ]
      }
    ]
  }
});
Run Code Online (Sandbox Code Playgroud)

无数个小时后,这为我解决了这个问题。如果您有任何帮助,请告诉我。干杯。


Tan*_*ame 5

问题不在 webpack 中。您的问题出在后台 url 路径中。由于您已将所有 css 导入到单个 main.scss 中,因此您需要在背景 url 中执行以下操作 -

.img-container {
      background: url('./../img/homepage-login-prog.jpg') no-repeat center center fixed;
      background-size: cover;
 }
Run Code Online (Sandbox Code Playgroud)


Vib*_*shu -1

这种图片是webpack的静态资源。这样就可以使用url-loader来加载了。

要安装它:

npm install url-loader --save-dev
Run Code Online (Sandbox Code Playgroud)

在你的 webpack 配置文件中使用 url-loader 加载器

{
  test: /\.(png|jpg)$/,
  loader: 'url-loader'
}
Run Code Online (Sandbox Code Playgroud)