vue项目部分图片在windows下引用不到,linux下正常是怎么回事?

vue项目做了个皮肤切换之后,在windows系统打包后运行会出现某些图片引用不到,我看了路径是完全正常的,但是在linux系统打包后运行完全正常。

下面这两张图片存储在一个文件夹,一张可以加载,一张加载不出来,也没有任何报错。
正常加载的
image.png

不正常加载的
image.png

以下是配置文件代码

'use strict'
const path = require('path')
const defaultSettings = require('./src/settings.js')
const webpack = require('webpack')
var HardSourceWebpackPlugin = require('hard-source-webpack-plugin')
// const MiniCssExtractPlugin = require('mini-css-extract-plugin')
// 不要使用自己安装的mini-css-extract-plugin,会报错,使用vue内置的,可能是因为版本不一致的原因
const MiniCssExtractPlugin = require('./node_modules/@vue/cli-service/node_modules/mini-css-extract-plugin')
const htmlWebpackInjectAttributesPlugin = require('html-webpack-inject-attributes-plugin')
const HtmlWebpackExcludeAssetsPlugin = require('html-webpack-exclude-assets-plugin')

// npx vue-cli-service inspect --mode=production >> webpack.config.js  打印生产配置
// npx vue-cli-service inspect --mode=development >> webpack.config.dev.js  打印开发配置

function resolve(dir) {
  return path.join(__dirname, dir)
}

function setPublicPath() {
  return (process.env.ENV === 'production' ? './' : '/udap-web/')
}

function setOutPutDir() {
  if (process.env.ENV === 'staging' || process.env.ENV === 'development') {
    return 'udap-web'
  }
  return 'udap'
}

const themeReg = /^(.*)((red|blue)\..+\.css)$/
const themeRegJS = /^(.*)((red|blue).*\.js)$/
const themeLinkJudge = (tagName, attributes) => {
  return (
    tagName === 'link' && attributes.href && themeReg.test(attributes.href)
  )
}

const name = defaultSettings.title || '' // page title

// If your port is set to 80,
// use administrator privileges to execute the command line.
// For example, Mac: sudo npm run
// You can change the port by the following method:
// port = 9527 npm run dev OR npm run dev --port = 9527
const port = process.env.port || process.env.npm_config_port || 9527 // dev port

// All configuration item explanations can be find in https://cli.vuejs.org/config/
module.exports = {
  /**
   * You will need to set publicPath if you plan to deploy your site under a sub path,
   * for example GitHub Pages. If you plan to deploy your site to https://foo.github.io/bar/,
   * then publicPath should be set to "/bar/".
   * In most cases please use '/' !!!
   * Detail: https://cli.vuejs.org/config/#publicpath
   */
  publicPath: setPublicPath(),
  outputDir: setOutPutDir(),
  assetsDir: 'udap-web-assets',
  lintOnSave: process.env.NODE_ENV === 'development',
  productionSourceMap: false,
  devServer: {
    port: port,
    disableHostCheck: true,
    proxy: {
      '/mock-api': {
        target: '/',
        changeOrigin: true
      },
      '/api/udap_web/websocket': {
        target: 'ws://192.168.31.xxxx:3210',
        changeOrigin: true,
        pathRewrite: {
          '^/api': ''
        }
      },
      '/api': {
        target: 'http://192.168.31.xxxx:3210', // 公司服务器
        changeOrigin: true
        // pathRewrite: {
        //  '^/api': ''
        // }
      },
      '/cogones-api': {
        target: 'http://192.168.31.xxxx:9300',
        changeOrigin: true,
        pathRewrite: {
          '^/cogones-api': ''
        }
      }
    }
  },
  configureWebpack: {
    devtool: 'source-map',
    // provide the app's title in webpack's name field, so that
    // it can be accessed in index.html to inject the correct title.
    name: name,
    resolve: {
      alias: {
        '@': resolve('src')
      }
    },
    plugins: [
      new HardSourceWebpackPlugin(),
      new webpack.ProvidePlugin({ _: 'lodash' })
    ],
    performance: {
      hints: false
    },
    entry: {
      app: path.resolve(__dirname, 'src/main.js'),
      blue: path.resolve(__dirname, 'src/theme/blue/index.js'),
      red: path.resolve(__dirname, 'src/theme/red/index.js')
    }
  },
  chainWebpack(config) {
    // it can improve the speed of the first screen, it is recommended to turn on preload
    // it can improve the speed of the first screen, it is recommended to turn on preload
    config.plugin('preload').tap(() => [
      {
        rel: 'preload',
        // to ignore runtime.js
        // https://github.com/vuejs/vue-cli/blob/dev/packages/@vue/cli-service/lib/config/app.js#L171
        fileBlacklist: [/\.map$/, /hot-update\.js$/, /runtime\..*\.js$/],
        include: 'initial'
      }
    ])

    // when there are many pages, it will cause too many meaningless requests
    config.plugins.delete('prefetch')

    // set svg-sprite-loader
    config.module
      .rule('svg')
      .exclude.add(resolve('src/icons'))
      .end()
    config.module
      .rule('icons')
      .test(/\.svg$/)
      .include.add(resolve('src/icons'))
      .end()
      .use('svg-sprite-loader')
      .loader('svg-sprite-loader')
      .options({
        symbolId: 'icon-[name]'
      })
      .end()

    config
      .when(process.env.NODE_ENV !== 'development',
        config => {
          config
            .plugin('ScriptExtHtmlWebpackPlugin')
            .after('html')
            .use('script-ext-html-webpack-plugin', [{
              // `runtime` must same as runtimeChunk name. default is `runtime`
              inline: /runtime\..*\.js$/
            }])
            .end()

          config
            .optimization.splitChunks({
              chunks: 'all',
              cacheGroups: {
                libs: {
                  name: 'chunk-libs',
                  test: /[\\/]node_modules[\\/]/,
                  priority: 10,
                  chunks: 'initial' // only package third parties that are initially dependent
                },
                elementUI: {
                  name: 'chunk-elementUI', // split elementUI into a single package
                  priority: 20, // the weight needs to be larger than libs and app or it will be packaged into libs or app
                  test: /[\\/]node_modules[\\/]_?element-ui(.*)/ // in order to adapt to cnpm
                },
                commons: {
                  name: 'chunk-commons',
                  test: resolve('src/components'), // can customize your rules
                  minChunks: 3, //  minimum common number
                  priority: 5,
                  reuseExistingChunk: true
                }
              }
            })
          // https:// webpack.js.org/configuration/optimization/#optimizationruntimechunk
          config.optimization.runtimeChunk('single')
        }
      )

    /** 皮肤配置  start */
    // MiniCssExtractPlugin可以给不同入口的独立打包css文件
    // dev环境下vue使用的不是MiniCssExtractPlugin来提取css生成css文件,而是使用vue-style-loader来生成style标签,
    // 因为我们需要生成文件,所以这里即使dev环境下也使用MiniCssExtractPlugin

    config.when(process.env.NODE_ENV === 'development', config => {
      config
        .plugin('extract-css')
        .use(MiniCssExtractPlugin, [
          {
            filename: '[name].[contenthash:8].css',
            chunkFilename: '[name].[contenthash:8].css'
          }
        ])
        .end()
    })

    // 让normal这个module不去匹配我们的主题文件  /^((?!light\.scss|default\.scss).)*$/
    config.module
      .rule('scss')
      .oneOf('normal')
      .test((p1) => {
        const pat = /^(?!.*\\theme\\).*\.scss$/
        const result = pat.test(p1)
        return result
      })
      .end()

    // 定义自己的module来使用我们自己的loader .*(light|default)\.scss$
    const theme = config.module
      .rule('scss')
      .oneOf('ownTheme')
      .test(/^(?=.*\\theme\\).*\.scss$/)
    // 清除vue-cli写好的loader,改用自己写的
    theme.uses.clear()

    theme
      .use(MiniCssExtractPlugin.loader)
      .loader(MiniCssExtractPlugin.loader)
      .end()
      .use('css-loader')
      .loader('css-loader')
      .end()
      .use('postcss-loader')
      .loader('postcss-loader')
      .end()
      .use('sass-loader')
      .loader('sass-loader')
      .end()

    // 增加自定义标签属性
    config
      .plugin('html')
      .tap((args) => {
        args[0].attributes = {
          'data-theme': function(tag) {
            const { attributes, tagName } = tag
            if (themeLinkJudge(tagName, attributes)) {
              return 'true'
            }
            return false
          },
          rel: function(tag) {
            const { attributes, tagName } = tag
            if (themeLinkJudge(tagName, attributes)) {
              if (attributes.href.indexOf('blue') > -1) {
                return 'stylesheet'
              }
              return 'alternate stylesheet'
            } else if (tagName === 'link') {
              return 'stylesheet'
            }
            return false
          },
          title: function(tag) {
            const { attributes, tagName } = tag
            if (themeLinkJudge(tagName, attributes)) {
              if (attributes.href.indexOf('red') > -1) {
                return 'red'
              } else if (attributes.href.indexOf('blue') > -1) {
                return 'blue'
              }
              return false
            }
            return false
          }
        }

        args[0].excludeAssets = [themeRegJS]
        return args
      })
      .end()

    // HtmlWebpackPlugin生成HTML文件时,这个插件能给生成的标签注入自己需要的属性
    config
      .plugin('htmlInjectAttribute')
      .after('html')
      .use(htmlWebpackInjectAttributesPlugin)
      .end()

    // 移除多入口生成的无用script标签和JS文件
    config
      .plugin('ExcludeAssets')
      .after('htmlInjectAttribute')
      .use(HtmlWebpackExcludeAssetsPlugin)
      .end()

    /** 皮肤配置 end */
  }
}

阅读 653
avatarAI BotBETA

问题解答

这个问题可能是由于Windows和Linux对大小写敏感性的不同所导致的。Windows系统对文件路径大小写不敏感,而Linux系统则是敏感的。

当你在Windows下引用图片时,可能由于路径大小写的不一致(例如:bVddhjIbVddhjZ),但实际上文件系统中只有一个正确的大小写文件名存在,Windows系统能够正确加载是因为它不区分大小写。然而,在Linux系统中,由于它区分大小写,所以如果你的引用路径的大小写与文件系统中的实际文件名大小写不匹配,那么图片将无法被正确加载。

解决方案

  1. 检查文件名的大小写:确保你在Vue项目中引用图片的路径与文件系统中实际文件名的大小写完全一致。
  2. 避免大小写不一致:在编写代码和命名文件时,尽量保持大小写的一致性,以避免跨平台时出现此类问题。
  3. 使用工具:你可以使用文本编辑器或IDE的搜索和替换功能,在项目中查找并替换所有可能的大小写不一致的路径引用。
  4. 检查构建脚本:确保你的构建脚本(如Webpack配置)没有在处理文件路径时引入大小写不一致的情况。
  5. 测试:在更改后,分别在Windows和Linux系统上进行测试,以确保问题已得到解决。

注意:在Vue项目中,通常建议将资源(如图片)放在public目录下,并通过绝对路径(以/开头)来引用它们,这样可以避免在构建时由于路径处理导致的问题。如果你将资源放在src/assets或其他由Webpack处理的目录中,那么你需要确保路径的大小写与文件系统中的实际文件名一致。

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题
宣传栏