Webpack打包图片路径问题

Webpack使用file-loader处理图片

在页面中引入图片有两种方式

  • img标签引入
  • css引入

file-loader

配置

          {
                test: /\.jpg|\.png|\.jpeg|\.svg|\.ttf|\.woff$/,
                use: [{
                    loader: 'file-loader',
                    options: {
                        name: '[name].[ext]',
                        outputPath: './img',
                        publicPath: '/img'
                    }
                }]
            }

其中

outputPath负责输出目录, 即打包后的写在磁盘的位置.

publicPath则是对页面引入资源的补充,比如img标签引入或者css引入等.

问题

按上面路径配置时, 打包后文件都在build/img

开发环境下可以正确引入文件,引入路径为localhost:8080/img

生产环境下引入路径为f:///img导致找不到图片

file-loader的官方说明

  • outputPath
    Specify a filesystem path where the target file(s) will be placed

  • publicPath
    Specifies a custom public path for the target file(s)

output : 指定将放置目标文件的文件系统路径. 这跟我们遇到的文件没多大关系.那问题就是在publicPath

publicPath: 指定目标文件的自定义公共路径,它是定义公共路径,所以我们在开发模式下能正确引入文件,因为都在同一个路径下,即localhost:8080.

生产模式下如何解决该问题呢?

别忘了我们引进图片有两种方式,img标签或者css引入.

当我将file-loader路径配置修改为

outputPath: './img',
publicPath: '../img'

因为打包后目录结构是

image.png

结果通过css引入的图片打包后还可以正确引入,路径是../img
但是通过img标签引入的图片则报错,引入路径是项目根目录/img,正确的应该是项目根目录/build/img

我们看看打包后的js中的引入路径

image.png

看起来好像是正确的,但是有一点,CSSJS引入图片的机制是不一样,详细可以看 css和js引用图片的路径问题

当我们要引用一个图片时,在js文件中要以引用它的html的路径为准;而在css文件中,要以该css的路径为准,而与引用该CSS文件的页面所在的位置无关

我们已经找到问题所在了, 那么该如何解决呢?

解决方法

不设置file-loaderoutputPathpublicPath,默认跟随webpack的打包目录, 这还不够,我们还得将css文件也打包到跟图片文件同级.

打包后目录为

image.png

这样不管是生产环境还是开发环境下都能正确引入图片.

但是当图片多了之后build目录下会有很多的文件,我们还是希望图片文件打包后在img文件夹.让我们再来看看这该怎么解决.

我们已经知道了设置了file-loader下的publicPath就是css文件与js文件引入图片的路径,因为cssjs引入的机制不同,我们只需要将css文件打包之后与html同级即可.

修改webpack配置

       {
                test: /\.jpg|\.png|\.jpeg|\.svg|\.ttf|\.woff$/,
                use: [{
                    loader: 'file-loader',
                    options: {
                        name: '[name].[ext]',
                        outputPath: './img',
                        publicPath: './img'
                    }
                }]
            }

修改前

new ExtractTextPlugin('css/[name].css')

修改后

new ExtractTextPlugin('[name].css')

打包后目录结构

image.png

完美解决.

更新 --- 将CSS单独打包,并且图片路径能正常引用

修改extract-text-webpack-plugin的options以及file-loaderpublicPath

打包后的目录

css/
img/
...

根据两个文件夹的位置关系, 我们设置extract-text-webpack-plugin


use: ExtractTextPlugin.extract({
          fallback: ...,
          use: loaders,
          publicPath: '../'  // 注意,这个是重点,根据目录结构不同值也不同
        })

移除file-loader的干扰

...
                    loader: 'file-loader',
                    options: {
                        name: '[name].[ext]',
                        outputPath: './img',  // 运行在服务器时发布路径
                        // publicPath: './img'  // 注销掉这一行,不设置.
                    }
...

你可能感兴趣的:(Webpack打包图片路径问题)