首页 > 解决方案 > Webpack4 如何直接从 HTML 文件加载图像和自定义 javascript?

问题描述

我想使用 Webpack 4 直接从 HTML 加载图像,并将自定义 Javascript 文件添加到我的 HTML 文件中,但两个文件都在控制台显示检查Not found 404

如何使用 Webpack 4 正确加载图像和 Javascipt 文件?

我的 Webpack 4 配置文件:

const path = require("path");
const HtmlWebpackPlugin = require("html-webpack-plugin");
const { CleanWebpackPlugin } = require("clean-webpack-plugin");

module.exports = {
  entry: {
    main: "./src/index.js"
  },
  output: {
    path: path.join(__dirname, "../build"),
    filename: "[name].bundle.js"
  },
  mode: "development",
  devServer: {
    contentBase: path.join(__dirname, "../build"),
    compress: true,
    port: 3000,
    overlay: true
  },
  devtool: "cheap-module-eval-source-map",
  module: {
    rules: [
      {
        test: /\.js$/,
        exclude: /node_modules/,
        use: {
          loader: "babel-loader" // transpiling our JavaScript files using Babel and webpack
        }
      },
      {
        test: /\.(sa|sc|c)ss$/,
        use: [
          "style-loader", // creates style nodes from JS strings
          "css-loader", // translates CSS into CommonJS
          "postcss-loader", // Loader for webpack to process CSS with PostCSS
          "sass-loader" // compiles Sass to CSS, using Node Sass by default
        ]
      },
      {
        test: /\.(png|svg|jpe?g|gif)$/,
        use: [
          {
            loader: "file-loader", // This will resolves import/require() on a file into a url and emits the file into the output directory.
            options: {
              name: "[name].[ext]",
              outputPath: "assets",
            }
          },
        ]
      },
      {
        test: /\.html$/,
        use: {
          loader: "html-loader",
          options: {
            attrs: ["img:src", ":data-src"],
            minimize: true
          }
        }
      }
    ]
  },
  plugins: [
    // CleanWebpackPlugin will do some clean up/remove folder before build
    // In this case, this plugin will remove 'dist' and 'build' folder before re-build again
    new CleanWebpackPlugin(),
    // The plugin will generate an HTML5 file for you that includes all your webpack bundles in the body using script tags
    new HtmlWebpackPlugin({
      template: "./src/index.html",
      filename: "index.html"
    }),
  ]

我的 webpack.prod.js 文件:

const path = require("path");
const MiniCssExtractPlugin = require("mini-css-extract-plugin");
const HtmlWebpackPlugin = require("html-webpack-plugin");
const { CleanWebpackPlugin } = require("clean-webpack-plugin");
const CompressionPlugin = require("compression-webpack-plugin");
const TerserJSPlugin = require("terser-webpack-plugin");
const OptimizeCSSAssetsPlugin = require("optimize-css-assets-webpack- 
plugin");
const BrotliPlugin = require("brotli-webpack-plugin");
const PurgecssPlugin = require('purgecss-webpack-plugin');
const glob = require("glob");

module.exports = {
entry: {
main: "./src/index.js"
},
output: {
path: path.join(__dirname, "../build"),
filename: "[name].[chunkhash:8].bundle.js",
chunkFilename: "[name].[chunkhash:8].chunk.js"
},
mode: "production",
module: {
rules: [
  {
    test: /\.js$/,
    exclude: /node_modules/,
    use: {
      loader: "babel-loader" // transpiling our JavaScript files using 
Babel and webpack
    }
  },
  {
    test: /\.(sa|sc|c)ss$/,
    use: [
      MiniCssExtractPlugin.loader,
      "css-loader", // translates CSS into CommonJS
      "postcss-loader", // Loader for webpack to process CSS with 
PostCSS
      "sass-loader" // compiles Sass to CSS, using Node Sass by 
default
    ]
  },
  {
    test: /\.(png|svg|jpe?g|gif)$/,
    use: [
      {
         loader: "file-loader", // This will resolves import/require() 
 on a file into a url and emits the file into the output directory.
        options: {
          name: "[name].[ext]",
          outputPath: "assets/"
        }
      },
    ]
  },
  {
    test: /\.html$/,
    use: {
      loader: "html-loader",
      options: {
        attrs: ["img:src", ":data-src"],
        minimize: true
      }
    }
  }
]
},
optimization: {
minimizer: [new TerserJSPlugin(), new OptimizeCSSAssetsPlugin()],
splitChunks: {
  cacheGroups: {
    commons: {
      test: /[\\/]node_modules[\\/]/,
      name: "vendors",
      chunks: "all"
    }
  },
  chunks: "all"
},
runtimeChunk: {
  name: "runtime"
}
},
plugins: [
// CleanWebpackPlugin will do some clean up/remove folder before build
// In this case, this plugin will remove 'dist' and 'build' folder 
before re-build again
new CleanWebpackPlugin(),
// PurgecssPlugin will remove unused CSS
new PurgecssPlugin({
  paths: glob.sync(path.resolve(__dirname, '../src/**/*'), { nodir: 
true })
}),
// This plugin will extract all css to one file
new MiniCssExtractPlugin({
  filename: "[name].[chunkhash:8].bundle.css",
  chunkFilename: "[name].[chunkhash:8].chunk.css",
}),
// The plugin will generate an HTML5 file for you that includes all 
 your webpack bundles in the body using script tags
new HtmlWebpackPlugin({
  template: "./src/index.html",
  filename: "index.html"
}),

我的项目嵌套:

--Build
--src
----html
----js
----styles
----assets
------images

我希望这些文件可以简单地加载:

<img src="assets/images/myimage.jpg">
<srcipt src="js/custom.js"></script>

任何帮助,将不胜感激。

具有讽刺意味的是,这是我使用 Webpack 4 的第二个项目,这次我无法解决这个问题,第一次没有问题。

标签: javascripthtmlwebpackwebpack-4

解决方案


这是img在 Webpack 中的工作方式:

<img src=require("./assets/images/myimage.jpg")>

如果您将“require”与文件加载器一起使用,则需要添加默认值。

 <img src=require("./assets/images/myimage.jpg").default>

对于 script 标签, src 应该是你的输出bundle.js文件;bundle.js因为 Webpack在 Babel 的帮助下将所有代码写入. 因此,当浏览器请求 html 时,浏览器将只有一个 Javascript 文件,该文件是要下载的捆绑包。这就是捆绑的全部意义,越小bundle.js越好。

// According to your Webpack config, it is main.bundle.js
<srcipt src="main.bundle.js"></script>

但为了让浏览器使用它main.bundle.js,它必须是公开的。因此,您需要明确定义公用文件夹,当浏览器查找时main.bundle.js,您的应用程序将查看公用文件夹,如果该文件存在,它将发送到浏览器。

const express = require("express");
const server = express();

const staticMiddleware = express.static("build");
server.use(staticMiddleware);

推荐阅读