Vue SFC styles not being extracted in webpack production build
Asked Answered
P

1

3

Trying to add vue (and SFCs) to my webpack app. The <template> and <script> blocks work fine, but for some reason the styles in the <style> block are not being extracted for production build.

In the dev build, it's extracting the .vue <style> block to a separate css file (named for the entrypoint). Which is OK but I'd prefer they went into my main stylesheet.

But no matter what I try, I can't get any .vue styles to show up (in any file) for the production build.

This is an abbreviated version of my webpack config:

const HtmlWebpackPlugin = require("html-webpack-plugin");
const MiniCssExtractPlugin = require("mini-css-extract-plugin");
const VueLoaderPlugin = require("vue-loader/lib/plugin");
...

module.exports = (env) => {
  return {
    entry: {
      app: ["./src/polyfills.js", "./src/scss/styles.scss", "./src/app.js"],
      ...
      testview: "./src/js/views/TestView.js"
    },
    output: {
      path: assets,
      filename: "[name].[hash].js",
      publicPath: "/static/"
    },
    resolve: {
      modules: ["node_modules", "src"],
      alias: {
        vue$: "vue/dist/vue.esm.js"
      },
      extensions: ["*", ".js", ".vue"]
    },
    module: {
      rules: [
        {
          test: /\.vue$/,
          loader: "vue-loader"
        },
        {
          test: /\.js?$/,
          exclude: /node_modules/,
          use: [
            {
              loader: "babel-loader",
              options: {
                presets: [
                  [
                    "@babel/preset-env",
                    {
                      targets: {
                        browsers: ["> 1%", "last 2 versions", "ie >= 11"]
                      }
                    }
                  ]
                ],

                plugins: ["@babel/plugin-proposal-class-properties"],
                code: true,
                comments: true,
                cacheDirectory: true,
                babelrc: false
              }
            }
          ]
        },
        {
          test: /\.s?[ac]ss$/,
          use: [
            "vue-style-loader",
            MiniCssExtractPlugin.loader,
            {
              loader: "css-loader",
              options: {
                sourceMap: ifNotProduction()
              }
            },
            {
              loader: "postcss-loader",
              options: {
                ident: "postcss",
                sourceMap: ifNotProduction(),
                plugins: () =>
                  ifProduction([
                    require("autoprefixer")({
                      preset: "default"
                    }),
                    require("cssnano"),
                    require("css-mqpacker")
                  ])
              }
            },
            {
              loader: "sass-loader",
              options: {
                sourceMap: ifNotProduction()
              }
            }
          ]
        }
      ]
    },
    optimization: {
      splitChunks: {
        cacheGroups: {
          commons: {
            name: "commons",
            chunks: "initial",
            minChunks: 2,
            minSize: 0
          },
          styles: {
            name: "styles",
            test: /\.css$/,
            chunks: "all",
            enforce: true
          }
        }
      },
      occurrenceOrder: true 
    },
    plugins: [
      new VueLoaderPlugin(),
      new MiniCssExtractPlugin({
        filename: "style.[hash].css"
      }),
      new HtmlWebpackPlugin({
        hash: true,
        inject: false,
        template: "./src/jinja-templates/base.html.j2",
        filename: `${templates}/base.html.j2`,
      })
    ]
  };
};

The .vue file I'm using is this demo one. I'm trying to import it into the entrypoint called 'testview' which contains simply:

import Vue from "vue";
import MainContent from "../components/main-content";
let MainComponent = Vue.extend(MainContent);
new MainComponent().$mount("#mainContent");
Patroclus answered 12/12, 2018 at 5:58 Comment(0)
P
3

Did figure it out. I had to remove sideEffects: false from my package.json. This issue explains it further.

Still would like to know how to extract the .vue styles to my main stylesheet As it is now, the .vue styles are extracting to a separate stylesheet (dev and production).

Patroclus answered 12/12, 2018 at 6:27 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.