Home > OS >  Replace file-loader with asset module when chaining other loaders
Replace file-loader with asset module when chaining other loaders

Time:04-16

I have the following webpack v4 module:

{
  test: /atffonts\.scss$/,
  use: [
        {
          loader: 'file-loader',
          options: {
            name: 'style/[name].css',
          },
        },
        'extract-loader',
        'css-loader',
        'sass-loader',
  ],
}

The intent of this code is to take an SCSS file and output a new file which is valid CSS.

I am attempting to migrate to Webpack v5 and make use of asset modules. I understand that it is possible to continue using the deprecated file-loader syntax, but I am attempting to not remain dependent on this deprecated feature.

I've rewritten the above code as:

 {
  test: /atffonts\.scss$/,
  type: 'asset/resource',
  generator: {
    filename: 'style/[name].css',
  },

  use: [
    'extract-loader',
    'css-loader',
    'sass-loader',
  ],
}

This code does output a file, but the contents of the file are not valid CSS. Instead, the file's content is:


var content = require("!!../../node_modules/css-loader/dist/cjs.js!../../node_modules/sass-loader/dist/cjs.js!../../node_modules/style-loader/index.js!../../node_modules/css-loader/dist/cjs.js!../../node_modules/sass-loader/dist/cjs.js!./atffonts.scss");

if(typeof content === 'string') content = [[module.id, content, '']];

var transform;
var insertInto;



var options = {"hmr":true}

options.transform = transform
options.insertInto = undefined;

var update = require("!../../node_modules/style-loader/lib/addStyles.js")(content, options);

if(content.locals) module.exports = content.locals;

if(module.hot) {
    module.hot.accept("!!../../node_modules/css-loader/dist/cjs.js!../../node_modules/sass-loader/dist/cjs.js!../../node_modules/style-loader/index.js!../../node_modules/css-loader/dist/cjs.js!../../node_modules/sass-loader/dist/cjs.js!./atffonts.scss", function() {
        var newContent = require("!!../../node_modules/css-loader/dist/cjs.js!../../node_modules/sass-loader/dist/cjs.js!../../node_modules/style-loader/index.js!../../node_modules/css-loader/dist/cjs.js!../../node_modules/sass-loader/dist/cjs.js!./atffonts.scss");

        if(typeof newContent === 'string') newContent = [[module.id, newContent, '']];

        var locals = (function(a, b) {
            var key, idx = 0;

            for(key in a) {
                if(!b || a[key] !== b[key]) return false;
                idx  ;
            }

            for(key in b) idx--;

            return idx === 0;
        }(content.locals, newContent.locals));

        if(!locals) throw new Error('Aborting CSS HMR due to changed css-modules locals.');

        update(newContent);
    });

    module.hot.dispose(function() { update(); });
}

It's not clear to me if what I'm attempting to do is compatible with the asset module paradigm.

Am I on the right path but overlooking something? Or should I keep using the deprecated file-loader for this purpose for now?

CodePudding user response:

I have done something similar using MiniCssExtractPlugin

const MiniCssExtractPlugin = require('mini-css-extract-plugin');
use : [
  MiniCssExtractPlugin.loader,
  "css-loader",
  "sass-loader",
],

Reminder: you have to install the loader via npm/yarn

Hopefully that works for you, works for me

  • Related