【问题标题】:Vue 3 - Vite app missing some CSS rules after buildVue 3 - Vite 应用程序在构建后缺少一些 CSS 规则
【发布时间】:2021-12-12 09:38:17
【问题描述】:

所以,我一直在努力解决这个问题,为我的应用程序进行大更新工作了很长时间,一切都运行顺利并且在开发中非常好,但是一旦我为生产构建了一些 CSS 规则,有些元素不正常,颜色没有按应有的方式显示,而且 flexbox 似乎关闭了......

所以让我从头开始:

环境:

  • Vite 2.6.11
  • Vue 3.2.20
  • 参考糖
  • Firebase 托管

这是我的依赖项

  "dependencies": {
    "@ckeditor/ckeditor5-build-classic": "30.0.0",
    "@ckeditor/ckeditor5-vue": "2.0.1",
    "@hennge/vue3-pagination": "^1.0.17",
    "@iconify/iconify": "2.0.4",
    "@mapbox/mapbox-gl-geocoder": "4.7.4",
    "@popperjs/core": "2.10.2",
    "@vueform/multiselect": "2.2.0",
    "@vueform/slider": "2.0.5",
    "@vuelidate/core": "^2.0.0-alpha.21",
    "@vuelidate/validators": "^2.0.0-alpha.18",
    "@vueuse/core": "6.7.3",
    "@vueuse/head": "0.6.0",
    "animate.css": "^4.1.1",
    "ant-design-vue": "^2.2.8",
    "apexcharts": "3.28.3",
    "axios": "0.22.0",
    "billboard.js": "3.1.5",
    "bulma": "0.9.3",
    "bulma-css-vars": "0.7.0",
    "dayjs": "1.10.7",
    "dragula": "3.7.3",
    "dropzone": "5.9.3",
    "filepond": "4.30.3",
    "filepond-plugin-file-validate-size": "2.2.5",
    "filepond-plugin-file-validate-type": "1.2.6",
    "filepond-plugin-image-crop": "2.0.6",
    "filepond-plugin-image-edit": "1.6.3",
    "filepond-plugin-image-exif-orientation": "1.0.11",
    "filepond-plugin-image-preview": "4.6.10",
    "filepond-plugin-image-resize": "2.0.10",
    "filepond-plugin-image-transform": "3.8.7",
    "firebase": "9.1.3",
    "flag-icon-css": "^3.5.0",
    "imask": "6.2.2",
    "mapbox-gl": "2.5.0",
    "markdown-it-emoji": "2.0.0",
    "notyf": "3.10.0",
    "nprogress": "0.2.0",
    "photoswipe": "4.1.3",
    "pinia": "^2.0.0-rc.15",
    "pinia-plugin-persist": "^0.0.92",
    "qrcode-vue3": "^1.4.17",
    "simple-datatables": "3.1.2",
    "simplebar": "6.0.0-beta.10",
    "simplebar-vue": "2.0.0-beta.10",
    "stylelint-csstree-validator": "^1.9.0",
    "sweetalert2": "^10.16.7",
    "tiny-slider": "2.9.3",
    "tippy.js": "6.3.2",
    "tslib": "2.3.1",
    "v-calendar": "3.0.0-alpha.5",
    "v-offline": "^3.0.0",
    "vant": "^3.2.6",
    "vee-validate": "4.5.4",
    "vivus": "0.4.6",
    "vue": "3.2.20",
    "vue-accessible-color-picker": "3.0.0",
    "vue-currency-input": "^2.0.1",
    "vue-i18n": "9.2.0-beta.15",
    "vue-router": "4.0.12",
    "vue-scrollto": "2.20.0",
    "vue-stripe-menu": "^2.1.1",
    "vue-tippy": "6.0.0-alpha.33",
    "vue-toastification": "^2.0.0-rc.1",
    "vue3-apexcharts": "1.4.1",
    "vue3-burger-menu": "^1.1.1",
    "vue3-carousel": "^0.1.28",
    "vue3-clipboard": "^1.0.0",
    "vueperslides": "^3.3.2",
    "xlsx": "^0.17.3",
    "yup": "0.32.9"
  },
  "devDependencies": {
    "@commitlint/cli": "13.2.0",
    "@commitlint/config-conventional": "13.2.0",
    "@commitlint/prompt-cli": "13.2.0",
    "@iconify/json": "1.1.410",
    "@intlify/vite-plugin-vue-i18n": "2.4.0",
    "@types/dragula": "3.7.1",
    "@types/luxon": "^1.27.1",
    "@types/mapbox-gl": "2.4.2",
    "@types/mapbox__mapbox-gl-geocoder": "4.7.1",
    "@types/markdown-it": "12.2.1",
    "@types/node": "16.10.2",
    "@types/nprogress": "0.2.0",
    "@types/photoswipe": "4.1.2",
    "@types/prismjs": "1.16.6",
    "@types/simplebar": "5.3.3",
    "@types/vivus": "0.4.4",
    "@typescript-eslint/eslint-plugin": "4.33.0",
    "@typescript-eslint/parser": "4.33.0",
    "@vitejs/plugin-vue": "1.9.3",
    "@vue/compiler-sfc": "3.2.20",
    "autoprefixer": "9.8.6",
    "commitlint": "13.2.0",
    "cross-env": "7.0.3",
    "cypress": "8.5.0",
    "eslint": "7.32.0",
    "eslint-config-prettier": "8.3.0",
    "eslint-plugin-md": "1.0.19",
    "eslint-plugin-vue": "7.19.0",
    "eslint-plugin-vuejs-accessibility": "^0.7.1",
    "gray-matter": "4.0.3",
    "lint-staged": "11.2.0",
    "markdown-it": "12.2.0",
    "markdown-it-anchor": "8.3.1",
    "npm-run-all": "4.1.5",
    "path": "^0.12.7",
    "plyr": "3.6.8",
    "postcss-nested": "4.2.3",
    "prettier": "2.4.1",
    "prismjs": "1.25.0",
    "rimraf": "3.0.2",
    "rollup": "2.58.3",
    "rollup-plugin-purgecss": "^4.0.3",
    "sass": "1.32.13",
    "standard-version": "9.3.2",
    "stylelint": "13.13.1",
    "stylelint-config-prettier": "8.0.2",
    "stylelint-config-standard": "22.0.0",
    "stylelint-scss": "3.21.0",
    "typescript": "4.4.3",
    "unplugin-vue-components": "0.16.0",
    "vfonts": "^0.1.0",
    "vite": "2.6.11",
    "vite-imagetools": "3.6.8",
    "vite-plugin-fonts": "0.2.2",
    "vite-plugin-imagemin": "0.4.6",
    "vite-plugin-pages": "0.18.1",
    "vite-plugin-purge-icons": "0.7.0",
    "vite-plugin-pwa": "0.11.3",
    "vite-plugin-radar": "0.2.0",
    "vite-svg-loader": "^2.2.0",
    "vue-tsc": "0.3.0",
    "yorkie": "2.0.0"
  }

这是我的 vite.config.ts

import { defineConfig } from 'vite'
// @ts-ignore
import path from 'path'
import Vue from '@vitejs/plugin-vue'
import Pages from 'vite-plugin-pages'
import Components from 'unplugin-vue-components/vite'
import ViteFonts from 'vite-plugin-fonts'
import ViteRadar from 'vite-plugin-radar'
import PurgeIcons from 'vite-plugin-purge-icons'
import { imagetools } from 'vite-imagetools'
import ImageMin from 'vite-plugin-imagemin'
import { vueI18n } from '@intlify/vite-plugin-vue-i18n'
import { VitePWA } from 'vite-plugin-pwa'
import purgecss from 'rollup-plugin-purgecss'
import ViteComponents, {
  AntDesignVueResolver,
  VantResolver
} from 'unplugin-vue-components/resolvers'

const SILENT = Boolean(process.env.SILENT) ?? false
const SOURCE_MAP = Boolean(process.env.SOURCE_MAP) ?? false

/**
 * This is the main configuration file for vitejs
 *
 * @see https://vitejs.dev/config
 */
export default defineConfig({
  // Project root directory (where index.html is located).
  root: process.cwd(),
  // Base public path when served in development or production.
  // You also need to add this base like `history: createWebHistory('my-subdirectory')`
  // in ./src/router.ts
  // base: '/my-subdirectory/',
  base: '/',
  // Directory to serve as plain static assets.
  publicDir: 'public',
  // Adjust console output verbosity.
  logLevel: SILENT ? 'error' : 'info',
  /**
   * By default, Vite will crawl your index.html to detect dependencies that
   * need to be pre-bundled. If build.rollupOptions.input is specified,
   * Vite will crawl those entry points instead.
   *
   * @see https://vitejs.dev/config/#optimizedeps-entries
   */
  optimizeDeps: {
    include: [
      '@ckeditor/ckeditor5-vue',
      '@ckeditor/ckeditor5-build-classic',
      '@iconify/iconify',
      '@mapbox/mapbox-gl-geocoder/dist/mapbox-gl-geocoder.min.js',
      '@vueuse/core',
      '@vueuse/head',
      '@vueform/multiselect',
      '@vueform/slider',
      'axios',
      'billboard.js',
      'dayjs',
      'dropzone',
      'dragula',
      'filepond',
      'filepond-plugin-file-validate-size',
      'filepond-plugin-file-validate-type',
      'filepond-plugin-image-exif-orientation',
      'filepond-plugin-image-crop',
      'filepond-plugin-image-edit',
      'filepond-plugin-image-preview',
      'filepond-plugin-image-resize',
      'filepond-plugin-image-transform',
      'imask',
      'nprogress',
      'notyf',
      'mapbox-gl',
      'photoswipe/dist/photoswipe',
      'photoswipe/dist/photoswipe-ui-default',
      'plyr',
      'v-calendar',
      'vee-validate',
      'vue',
      'vue-scrollto',
      'vue3-apexcharts',
      'vue-tippy',
      'simplebar',
      'simple-datatables',
      'tiny-slider/src/tiny-slider',
      'vue-accessible-color-picker',
      'yup',
      'ant-design-vue',
      'vant'
    ],
  },
  // Will be passed to @rollup/plugin-alias as its entries option.
  resolve: {
    alias: [
      {
        find: '/~/',
        replacement: `/src/assets/`,
      },
      {
        find: '/@src/',
        replacement: `/src/`,
      },
    ],
  },

  build: {
    sourcemap: SOURCE_MAP,
    // Turning off brotliSize display can slightly reduce packaging time
    brotliSize: !SILENT,
    chunkSizeWarningLimit: 2000,
    minify: 'esbuild',
    cssCodeSplit: true,
  },
  plugins: [
    /**
     * plugin-vue plugin inject vue library and allow sfc files to work (*.vue)
     *
     * @see https://github.com/vitejs/vite/tree/main/packages/plugin-vue
     */
    Vue({
      include: [/\.vue$/],
    }),

    /**
     * vite-plugin-vue-i18n plugin does i18n resources pre-compilation / optimizations
     *
     * @see https://github.com/intlify/bundle-tools/tree/main/packages/vite-plugin-vue-i18n
     */
    vueI18n({
      include: path.resolve(__dirname, './src/locales/**'),
    }),

    /**
     * unplugin-vue-components plugin is responsible of autoloading components
     * documentation and md file are loaded for elements and components sections
     *
     * @see https://github.com/antfu/unplugin-vue-components
     */
    Components({
      dirs: ['src/components', 'src/layouts', 'src/views'],
      extensions: ['vue', 'md'],
      dts: true,
      include: [/\.vue$/, /\.vue\?vue/, /\.md$/],
      resolvers: [
        AntDesignVueResolver(),
        VantResolver()
      ]
    }),

    /**
     * vite-plugin-purge-icons plugin is responsible of autoloading icones from multiples providers
     *
     * @see https://icones.netlify.app/
     * @see https://github.com/antfu/purge-icons/tree/main/packages/vite-plugin-purge-icons
     */
    PurgeIcons(),

    /**
     * vite-plugin-fonts plugin inject webfonts from differents providers
     *
     * @see https://github.com/stafyniaksacha/vite-plugin-fonts
     */
    ViteFonts({
      google: {
        families: [
          {
            name: 'Fira Code',
            styles: 'wght@400;600',
          },
          {
            name: 'Montserrat',
            styles: 'wght@500;600;700;800;900',
          },
          {
            name: 'Roboto',
            styles: 'wght@300;400;500;600;700',
          },
        ],
      },
    }),

    /**
     * vite-plugin-radar plugin inject snippets from analytics providers
     *
     * @see https://github.com/stafyniaksacha/vite-plugin-radar
     */
    ViteRadar({
      analytics: {
        id: '',
      },
    }),

    /**
     * vite-plugin-pwa generate manifest.json and register services worker to enable PWA
     *
     * @see https://github.com/antfu/vite-plugin-pwa
     */
    VitePWA({
      registerType: 'autoUpdate',
      base: '/',
      includeAssets: [
        'favicon.svg',
        'favicon.ico',
        'robots.txt',
        'apple-touch-icon.png',
      ],
      manifest: {
        name: 'Treebū Admin',
        short_name: 'Treebū Admin',
        start_url: '/?utm_source=pwa',
        display: 'standalone',
        theme_color: '#ffffff',
        background_color: '#ffffff',
        icons: [
          {
            src: 'pwa-192x192.png',
            sizes: '192x192',
            type: 'image/png',
          },
          {
            src: 'pwa-512x512.png',
            sizes: '512x512',
            type: 'image/png',
          },
          {
            src: 'pwa-512x512.png',
            sizes: '512x512',
            type: 'image/png',
            purpose: 'any maskable',
          },
        ],
      },
    }),

    /**
     * rollup-plugin-purgecss plugin is responsible of purging css rules
     * that are not used in the bundle
     *
     * @see https://github.com/FullHuman/purgecss/tree/main/packages/rollup-plugin-purgecss
     */
    purgecss({
      content: [`./src/**/*.vue`],
      variables: false,
      safelist: {
        standard: [
          /(autv|lnil|lnir|fas?)/,
          /-(leave|enter|appear)(|-(to|from|active))$/,
          /^(?!(|.*?:)cursor-move).+-move$/,
          /^router-link(|-exact)-active$/,
          /data-v-.*/,
        ],
      },
      defaultExtractor(content) {
        const contentWithoutStyleBlocks = content.replace(
          /<style[^]+?<\/style>/gi,
          ''
        )
        return (
          contentWithoutStyleBlocks.match(/[A-Za-z0-9-_/:]*[A-Za-z0-9-_/]+/g) ||
          []
        )
      },
    }),

    /**
     * vite-imagetools plugin allow to perform transformation (blur, resize, crop, etc)
     * on images at build time
     *
     * @see https://github.com/JonasKruckenberg/vite-imagetools
     */
    imagetools({
      silent: SILENT,
    }),

    /**
     * vite-plugin-imagemin optimize all images sizes from public or asset folder
     *
     * @see https://github.com/anncwb/vite-plugin-imagemin
     */
    ImageMin({
      verbose: !SILENT,
      gifsicle: {
        optimizationLevel: 7,
        interlaced: false,
      },
      optipng: {
        optimizationLevel: 7,
      },
      mozjpeg: {
        quality: 60,
      },
      pngquant: {
        quality: [0.8, 0.9],
        speed: 4,
      },
      svgo: {
        plugins: [
          {
            name: 'removeViewBox',
            active: false,
          },
          {
            name: 'removeEmptyAttrs',
            active: false,
          },
        ],
      },
    }),
  ],
})

这是我的 index.html

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <!--iOS configuration-->
    <meta name="apple-mobile-web-app-capable" content="yes">

    <meta name="google" content="notranslate">

    <!--ICONS-->
    <link rel="apple-touch-icon" href="/images/mobile-icons/ios/apple-icon.png">
    <link rel="apple-touch-icon" sizes="57x57" href="/images/mobile-icons/ios/apple-icon-57x57.png">
    <link rel="apple-touch-icon" sizes="60x60" href="/images/mobile-icons/ios/apple-icon-60x60.png">
    <link rel="apple-touch-icon" sizes="72x72" href="/images/mobile-icons/ios/apple-icon-72x72.png">
    <link rel="apple-touch-icon" sizes="76x76" href="/images/mobile-icons/ios/apple-icon-76x76.png">
    <link rel="apple-touch-icon" sizes="114x114" href="/images/mobile-icons/ios/apple-icon-114x114.png">
    <link rel="apple-touch-icon" sizes="120x120" href="/images/mobile-icons/ios/apple-icon-120x120.png">
    <link rel="apple-touch-icon" sizes="144x144" href="/images/mobile-icons/ios/apple-icon-144x144.png">
    <link rel="apple-touch-icon" sizes="152x152" href="/images/mobile-icons/ios/apple-icon-152x152.png">
    <link rel="apple-touch-icon" sizes="180x180" href="/images/mobile-icons/ios/apple-icon-180x180.png">

    <!--    Splashscreen-->
    <link href="/images/splashscreens/iphone5_splash.png" media="(device-width: 320px) and (device-height: 568px) and (-webkit-device-pixel-ratio: 2)" rel="apple-touch-startup-image" />
    <link href="/images/splashscreens/iphone6_splash.png" media="(device-width: 375px) and (device-height: 667px) and (-webkit-device-pixel-ratio: 2)" rel="apple-touch-startup-image" />
    <link href="/images/splashscreens/iphoneplus_splash.png" media="(device-width: 621px) and (device-height: 1104px) and (-webkit-device-pixel-ratio: 3)" rel="apple-touch-startup-image" />
    <link href="/images/splashscreens/iphonex_splash.png" media="(device-width: 375px) and (device-height: 812px) and (-webkit-device-pixel-ratio: 3)" rel="apple-touch-startup-image" />
    <link href="/images/splashscreens/iphonexr_splash.png" media="(device-width: 414px) and (device-height: 896px) and (-webkit-device-pixel-ratio: 2)" rel="apple-touch-startup-image" />
    <link href="/images/splashscreens/iphonexsmax_splash.png" media="(device-width: 414px) and (device-height: 896px) and (-webkit-device-pixel-ratio: 3)" rel="apple-touch-startup-image" />
    <link href="/images/splashscreens/ipad_splash.png" media="(device-width: 768px) and (device-height: 1024px) and (-webkit-device-pixel-ratio: 2)" rel="apple-touch-startup-image" />
    <link href="/images/splashscreens/ipadpro1_splash.png" media="(device-width: 834px) and (device-height: 1112px) and (-webkit-device-pixel-ratio: 2)" rel="apple-touch-startup-image" />
    <link href="/images/splashscreens/ipadpro3_splash.png" media="(device-width: 834px) and (device-height: 1194px) and (-webkit-device-pixel-ratio: 2)" rel="apple-touch-startup-image" />
    <link href="/images/splashscreens/ipadpro2_splash.png" media="(device-width: 1024px) and (device-height: 1366px) and (-webkit-device-pixel-ratio: 2)" rel="apple-touch-startup-image" />

    <!--Status Bar-->
    <meta name="apple-mobile-web-app-status-bar-style" content="black-translucent">
    <meta name="theme-color" content="#2f3048">
    <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" />
    <meta content="initial-scale=1.0, maximum-scale=1.0, width=device-width, user-scalable=no, shrink-to-fit=no" name="viewport">
    <link
      rel="apple-toucv-icon"
      sizes="180x180"
      href="/icons/apple-touch-icon.png"
    />
    <link
      rel="icon"
      type="image/png"
      sizes="32x32"
      href="/icons/favicon-32x32.png"
    />
    <link
      rel="icon"
      type="image/png"
      sizes="16x16"
      href="/icons/favicon-16x16.png"
    />
    <link rel="mask-icon" href="/icons/safari-pinned-tab.svg" color="#5bbad5" />
    <meta name="msapplication-TileColor" content="#232326" />
    <!--    <meta name="theme-color" content="#ffffff" />-->
    <title>Treebū Hotels</title>
    <script>
      /**
       * this is a hack for dragula used on KanbanApp
       *
       * @see src/components/pages/apps/KanbanApp.vue
       */
      var global = global || window
    </script>
    <link
      rel="preload"
      as="style"
      onload="this.rel='stylesheet'"
      href="/vendors/font-awesome-v5.css"
    />
    <link
      rel="preload"
      as="style"
      onload="this.rel='stylesheet'"
      href="/vendors/line-icons-pro.css"
    />
    <link
      rel="preload"
      as="style"
      onload="this.rel='stylesheet'"
      href="/vendors/prism-coldark-cold.css"
    />
  </head>
  <body>
    <div data-teleport-bg></div>
    <div id="app" class="app-wrapper"></div>
    <script type="module" src="/src/styles.ts"></script>
    <script type="module" src="/src/main.ts"></script>
  </body>
</html>

请注意以下图片中开发版和生产版的区别:

开发版本:

产品版本:

如您所见,样式不匹配...让我们继续:

Dev 版本,flexbox 正常工作:

prod 版本中没有 flexbox

构建版本的控制台上没有警告或错误,

我已经尝试删除 antd、vant 和其他自定义 css 样式,以防万一有冲突,但我得到了相同的结果,也尝试了

minify: 'esbuild', // 或 false

cssCodeSplit: true, //or false

在 vite.config 中

一切都在开发中完美运行,但在构建时却一团糟。

有什么提示吗?想法?可能性?机会?

提前致谢!

【问题讨论】:

  • 你有没有想过这个问题?我现在正在努力解决同样的问题。如果您有解决方案,我将不胜感激。谢谢

标签: css vue.js sass build vite


【解决方案1】:

我也遇到了和你一样的问题,所以我搜索了一下,找到了解决办法。

我刚刚运行了npm run hot这个命令,通过这样做,问题已经解决了

【讨论】:

  • 我的 packages.js 中没有该命令,那应该做什么?你能分享一下脚本是什么吗?
  • 您能告诉我您是如何将 CSS 文件附加到主 app.css 文件的吗?
  • 它是从一个名为 styles.ts 的主文件中添加到 index.html 中的,我确实在其中导入了所有 SASS 和 CSS 样式......事情是......这就像这样工作以前,但现在不...我不认为npm run hot 这是解决方案,我正在使用VITE,只是为了记录。
  • npm run hot 正在为 laravel mix 工作,但是正如你所说的你正在使用 VITE,我很难给出正确的答案,很抱歉
  • 在任何情况下,错误发生在构建应用程序而不是在 dev 上,所以......热重载与构建本身无关。
猜你喜欢
  • 2019-11-26
  • 2022-07-06
  • 1970-01-01
  • 2019-12-24
  • 2023-01-30
  • 2020-04-13
  • 1970-01-01
  • 2021-06-24
  • 2014-10-31
相关资源
最近更新 更多