Search code examples
reactjswebpacksassbabeljswebpack-hmr

Webpack watch compiles my scss sass but not webpack-dev-server


I am able to compile my sass successfully with webpack using the webpack --watch command, but it does not perform hot module replacement.

I am able to do HMR successfully with the webpack-dev-server --hot --progress --colors --inline command, and it reloads with my .js changes, but not my .scss/.css ones.

I've noticed that when I change a sass file the server refreshes, but the styles aren't updated. I want to make sure I'm doing it with just one command.

Here's the scripts from my package.json

"scripts": {
    "build": "webpack -p",
    "watch": "webpack --watch",
    "start": "webpack-dev-server --hot --progress --colors --inline"
  },

and here's my entire webpack config:

const ExtractTextPlugin = require("extract-text-webpack-plugin");
const webpack = require('webpack');
const path = require("path");

module.exports = {
  entry: {
    master: "./src/index.jsx"
  },
  output: {
    path: path.resolve(__dirname, "dist"),
    filename: "[name].js"
  },
  module: {
    rules: [
      {
        test: /\.scss$/,
        use: ExtractTextPlugin.extract({
          fallback: "style-loader",
          use: ["css-loader", "sass-loader"],
          publicPath: "dist"
        })
      },
      {
        test: /\.jsx?$/,
        exclude: /node_modules/,
        use: "babel-loader"
      },
    ]
  },
  resolve: {
    extensions: [".js", ".jsx"]
  },
  plugins: [
    new ExtractTextPlugin({
      filename: "master.css",
      allChunks: true
    }),
    new webpack.HotModuleReplacementPlugin()
  ],
  devServer: {
    contentBase: './dist',
    hot: true,
    port: 3000,
    host: '0.0.0.0',
    inline: true,
    disableHostCheck: true,
  }
};

and, in case it's necessary, here's my .babelrc (I'm using React):

{
  "presets": [
    "@babel/preset-env",
    "@babel/preset-react"
  ],
  "plugins": [
    "@babel/plugin-transform-runtime",
    "react-hot-loader/babel"
  ]
}

How do I get my webpack dev server to reload with my compiled sass changes as I change them?


Solution

  • I eventually figured this out with the following setup. I think the issue was related to the fact that both watch and webpack dev server were in the webpack config - and I realized that watch mode is not needed in my setup if I'm running webpack dev server:

    const ExtractTextPlugin = require("extract-text-webpack-plugin");
    const webpack = require('webpack');
    const path = require("path");
    
    module.exports = {
      entry: {
        master: "./src/index.jsx"
      },
      watch: true,
      output: {
        path: path.resolve(__dirname, "dist"),
        filename: "[name].js"
      },
      module: {
        rules: [
          {
            test: /\.jsx?$/,
            exclude: /node_modules/,
            use: ["babel-loader"]
          },
          {
            test: /\.scss$/,
            use: ExtractTextPlugin.extract({
              fallback: "style-loader",
              use: ["css-loader", "sass-loader"],
              publicPath: "dist"
            })
          },
    
        ]
      },
      resolve: {
        extensions: [".js", ".jsx"]
      },
      plugins: [
        new ExtractTextPlugin({
          filename: "master.css",
          allChunks: true
        }),
        new webpack.HotModuleReplacementPlugin()
      ],
      devServer: {
        contentBase: './dist',
        hot: true,
        port: 3000,
        host: '0.0.0.0',
        inline: true,
        disableHostCheck: true,
        watchOptions: {
          ignored: [
            path.resolve(__dirname, 'node_modules')
          ]
        }
      }
    };
    
    

    and package.json:

    "scripts": {
        "start": "webpack-dev-server",
        "dist": ""
      },