Whenever I try to run npm build
on my code, I experience many errors along the lines of the following:
asset main.js 901 KiB [emitted] (name: main) 1 related asset
asset icon.png 795 bytes [compared for emit] [from: src/styles/icon.png] (auxiliary name: main)
orphan modules 51.1 KiB (javascript) 975 bytes (runtime) [orphan] 17 modules
runtime modules 2.15 KiB 7 modules
javascript modules 710 KiB
modules by path ./ 452 KiB
modules by path ./src/ 449 KiB 54 modules
./index.js 3.26 KiB [built] [code generated]
./index.scss 39 bytes [built] [code generated] [1 error]
modules by path ../ 258 KiB
modules by path ../../common/temp/node_modules/.pnpm/@babel+runtime@7.22.11/node_modules/@...(truncated) 22.4 KiB 31 modules
modules by path ../cursor-effects/ 13.2 KiB 5 modules
modules by path ../../backend/ 155 KiB
../../backend/common/dist/main.js 134 KiB [built] [code generated]
../../backend/event-emitter/dist/main.js 20.9 KiB [built] [code generated]
+ 7 modules
./src/styles/icon.png 42 bytes (javascript) 795 bytes (asset) [built] [code generated]
ERROR in ./src/styles/_iconview.scss (../../common/temp/node_modules/.pnpm/css-loader@6.8.1_webpack-cli@5.1.4/node_modules/css-loader/dist/cjs.js??ruleSet[1].rules[1].use[1]!./src/styles/_iconview.scss)
Module build failed (from ../../common/temp/node_modules/.pnpm/css-loader@6.8.1_webpack-cli@5.1.4/node_modules/css-loader/dist/cjs.js):
SyntaxError
(95:7) client\src\styles\_iconview.scss Unknown word
93 | overflow: visible;
94 |
> 95 | #{ $self }__icon {
| ^
96 | background-color: rgb(0 0 200 / 90%);
97 | }
@ ./index.scss.webpack[javascript/auto]!=!../../common/temp/node_modules/.pnpm/css-loader@6.8.1_webpack-cli@5.1.4/node_modules/css-loader/dist/cjs.js??ruleSet[1].rules[1].use[1]!../../common/temp/node_modules/.pnpm/sass-loader@13.3.2_sass@1.66.1_webpack@5.88.2/node_modules/sass-loader/dist/cjs.js??ruleSet[1].rules[1].use[2]!./index.scss 11:0-214 20:26-59
@ ./index.scss
@ ./index.js 32:0-22
I have the following Webpack configuration for the project:
const path = require("path");
const MiniCssExtractPlugin = require("mini-css-extract-plugin");
const CssMinimizerPlugin = require("css-minimizer-webpack-plugin");
const mode = process.env.NODE_ENV || "development";
const minimize = mode === "production";
const plugins = [];
if (mode === "production") {
plugins.push(new CssMinimizerPlugin());
}
module.exports = {
mode,
devtool: "source-map",
entry: [path.resolve(__dirname, "index.js")],
output: {
library: "MyClientName",
libraryTarget: "umd",
umdNamedDefine: true,
sourceMapFilename: "[file].map",
filename: "[name].js",
},
optimization: {
minimize,
},
plugins: [
new MiniCssExtractPlugin({
filename: "[name].css",
chunkFilename: "[id].css",
}),
...plugins,
],
module: {
rules: [
{
test: /\.(svg|png|jpe?g|gif|webp)$/,
type: "asset/resource",
exclude: /node_modules/,
generator: {
filename: "[name][ext]",
},
},
{
test: /\.(sa|sc|c)ss$/,
exclude: /node_modules/,
use: [
MiniCssExtractPlugin.loader,
{
loader: "css-loader",
options: {
sourceMap: true,
},
},
{
loader: "sass-loader",
options: {
sourceMap: true,
},
},
],
},
{
test: /\.html$/i,
loader: "html-loader",
},
{
test: /\.js$/,
exclude: /node_modules/,
use: {
loader: "babel-loader",
},
},
],
},
};
The code is valid SCSS and worked for me before, but I recently updated my dependency versions and this issue sprung up. Why am I encountering this problem, and how can I resolve it so the SCSS is parsed and compiled properly?
The problem turned out to be how the modules were imported in index.scss
. When I use the traditional method, it works:
@import "./src/styles/variables";
@import "./src/styles/core";
@import "./src/styles/window";
@import "./src/styles/notifications";
@import "./src/styles/login";
@import "./src/styles/loading";
@import "./src/styles/search";
@import "./src/styles/iconview";
But the reason the code had changed was because stylelint --fix
complained and automatically updated the code to the following:
@import url("./src/styles/variables");
@import url("./src/styles/core");
@import url("./src/styles/window");
@import url("./src/styles/notifications");
@import url("./src/styles/login");
@import url("./src/styles/loading");
@import url("./src/styles/search");
@import url("./src/styles/iconview");
And with that syntax, npm run build
gives the following errors, because the file path is different (i.e. ./src/styles/_iconview.scss
):
ERROR in ./index.scss
Module build failed (from ../../common/temp/node_modules/.pnpm/css-loader@6.8.1_webpack-cli@5.1.4/node_modules/css-loader/dist/cjs.js):
Error: Can't resolve './src/styles/variables' in 'frontend\client'
So I had changed the file paths to be correct to appease stylelint
, like so:
@import url("./src/styles/_variables.scss");
@import url("./src/styles/_core.scss");
@import url("./src/styles/_window.scss");
@import url("./src/styles/_notifications.scss");
@import url("./src/styles/_login.scss");
@import url("./src/styles/_loading.scss");
@import url("./src/styles/_search.scss");
@import url("./src/styles/_iconview.scss");
And that was when Webpack started giving all these errors. I was able to find a compromise by disabling stylelint
surrounding the imports:
/* stylelint-disable */
@import "./src/styles/variables";
@import "./src/styles/core";
@import "./src/styles/window";
@import "./src/styles/notifications";
@import "./src/styles/login";
@import "./src/styles/loading";
@import "./src/styles/search";
@import "./src/styles/iconview";
/* stylelint-enable */
This results in stylelint
still running as expected within the imported SCSS files, resolving all the issues. I believe the issue stems from the combination of url()
and @import
, because the code is processed by css-loader
twice, with once before the Sass has been transformed.