Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to combine several plugins inside next.config.js file?

When I add "next-videos" loader to the next.config.js it works perfectly as long as module.exports goes the last one:

module.exports = withVideos()

On the other hand, it breaks another instance of module.exports that located above:

module.exports = {
   images: {
     domains: ['cdn.shopify.com'],
   },
};

Basically, it overwrites every previous module.exports. What are the rules for combining these exports? I guess I need to put them under one module but what are the rules to do it? I'm messing up with syntax and every try to relocate it under one module.exports ends with new errors

Just to sum up the questions:

  1. What are the rules of combining modules inside single export and how I can combine it with all my previous module.exports?

  2. Do I really need to leave "webpack(config)" part that duplicates the identical part above inside next.config? I gathered it from different sources and now trying to figure out how does it really work

webpack(config) { 
  config.module.rules.push(

Contents of the next.config.js:

const withPlugins = require('next-compose-plugins');
const withSass = require('@zeit/next-sass');
const withCSS = require('@zeit/next-css');
const withImages = require('next-images');
const withVideos = require('next-videos');
const withBundleAnalyzer = require('@next/bundle-analyzer')({
    enabled: process.env.ANALYZE === 'true',
});

// next.config.js
module.exports = withPlugins(
    [[withImages], [withSass], [withCSS], [withVideos]],
    {
        plugins: ['postcss-import', 'tailwindcss', 'autoprefixer'],
        serverRuntimeConfig: {
            mySecret: 'secret',
            secondSecret: process.env.SECOND_SECRET, // Pass through env variables
        },
        publicRuntimeConfig: {
            // Will be available on both server and client
            staticFolder: '/public',
        },
        module: {
            loaders: [
                {
                    test: /.jsx?$/,
                    loader: 'babel-loader',
                    exclude: /node_modules/,
                },
                {
                    test: /\.css$/,
                    loader: 'style-loader!css-loader',
                },
                {
                    test: /\.jsx?$/,
                    use: ['babel-loader', 'astroturf/loader'],
                },
                {
                    test: /\.(jpe?g|png|gif|woff|woff2|eot|ttf|svg)(\?[a-z0-9=.]+)?$/,
                    loader: 'url-loader?limit=100000',
                },
                {
                    test: /\.(eot|woff|woff2|otf|ttf|svg|png|jpg|gif|webm)$/,
                    use: {
                        loader: 'url-loader',
                        options: {
                            limit: 100000,
                            name: '[name].[ext]',
                        },
                    },
                },
                {
                    test: /\.mp4$/,
                    use: 'file-loader?name=videos/[name].[ext]',
                },
                {
                    test: /\.style.js$/,
                    use: [
                        'style-loader',
                        {
                            loader: 'css-loader',
                            options: { importLoaders: 1 },
                        },
                        {
                            loader: 'postcss-loader',
                            options: { parser: 'sugarss', exec: true },
                        },
                    ],
                },
            ],
        },
        webpack(config) {
            config.module.rules.push(
                {
                    test: /\.(eot|woff|woff2|otf|ttf|svg|png|jpg|gif)$/,
                    use: {
                        loader: 'url-loader',
                        options: {
                            limit: 100000,
                            name: '[name].[ext]',
                        },
                    },
                },
                {
                    test: /\.style.js$/,
                    use: [
                        'style-loader',
                        'css-loader',
                        {
                            loader: 'css-loader',
                            options: { importLoaders: 1 },
                        },
                        {
                            loader: 'postcss-loader',
                            options: { parser: 'sugarss', exec: true },
                        },
                    ],
                },
                {
                    test: /\.(js|jsx)$/,
                    exclude: /node_modules/,
                    use: ['babel-loader', 'eslint-loader'],
                },
            );
            withBundleAnalyzer({});
            return config;
        },
    },
    {
        images: {
            domains: ['cdn.shopify.com'],
        },
    },
    withVideos(),
);

module.exports = {
    extends: 'airbnb-base',
    rules: {
        'arrow-body-style': 0,
    },
};

module.exports = {
    images: {
        domains: ['cdn.shopify.com'],
    },
};

module.exports = withVideos();
like image 846
dima Avatar asked Oct 19 '25 13:10

dima


1 Answers

You seem to be mixing several configs incorrectly into your Next.js config file.

Without next-compose-plugins

There's no need to use next-compose-plugins. Next.js plugins are built to be chainable, you can nest each plugin call inside the next one, and pass the actual config object on the last call. Your next.config.js file should also only have a single module.exports.

// next.config.js

// Omitting requires for simplicity
 
module.exports = withImages(
    withSass(
        withCSS(
            withVideos(
                withBundleAnalyzer({
                    images: {
                        domains: ['cdn.shopify.com']
                    },
                    serverRuntimeConfig: {
                        mySecret: "secret",
                        secondSecret: process.env.SECOND_SECRET
                    },
                    publicRuntimeConfig: {
                        staticFolder: "/public"
                    },
                    // From here everything that's Webpack-related
                    webpack(config) {
                        // Add your custom Webpack configs
                        return config;
                    }
                })
            )
        )
    )
);

With next-compose-plugins

If you're using next-compose-plugins, it should roughly follow this structure:

// next.config.js

// Omitting requires for simplicity
 
module.exports = withPlugins(
    [withImages, withSass, withCSS, withVideos, withBundleAnalyzer], // All next plugins go here
    // Below is the main Next.js config object
    { 
        images: {
            domains: ['cdn.shopify.com']
        },
        serverRuntimeConfig: {
            mySecret: "secret",
            secondSecret: process.env.SECOND_SECRET
        },
        publicRuntimeConfig: {
          staticFolder: "/public"
        },
        // From here everything that's Webpack-related
        webpack(config) {
            // Add your custom Webpack configs
            return config;
        }
    }
);

Finally, the following config belongs to your ESlint config file, and not Next.js config.

// .eslintrc.js
module.exports = {
    extends: 'airbnb-base',
    rules: {
        'arrow-body-style': 0,
    },
};
like image 156
juliomalves Avatar answered Oct 22 '25 02:10

juliomalves



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!