1

I have a couple of config files in my application that a want in a separate bundle or not bundled at all but copied to the output folder and read by the main bundle somehow.

I've managed to get my files into a separate config bundle, but the problem is that these files are also still bundled into the main bundle, in effect rendering my config bundle useless.

I've managed to get the config bundle working with the help of @Chase, but I'm not happy yet. Next I want to know how to have these files not bundled at all, but still available to the main bundle after deployment.

ANY SUGGESTIONS?

My project folder/file structure (the essential bits):

- app
  - js
    - components
      - [all of my components]
    - config
      - [my config files that I want to isolate]
    - App.jsx
    - index.jsx
    - ...
  - ...

My webpack config:

const path = require('path')
const webpack = require('webpack')
const HtmlWebpackPlugin = require('html-webpack-plugin')
const cwd = process.cwd()
const mode = 'production'
const CleanWebpackPlugin = require('clean-webpack-plugin');

module.exports = {
  context: path.join(cwd, 'app'),
  mode,

  optimization: {
    runtimeChunk: 'single',
    minimize: false,
    splitChunks: {
      chunks: 'all',
      maxInitialRequests: Infinity,
      minSize: 0,
      cacheGroups: {
        config: {
          test: /[\\/]app[\\/]js[\\/]config[\\/]/,
          minSize: 0
        },
        vendors: {
          test: /[\\/]node_modules[\\/]/,
          name(module) {
            // get the name. E.g. node_modules/packageName/not/this/part.js
            // or node_modules/packageName
            const packageName = module.context.match(/[\\/]node_modules[\\/](.*?)([\\/]|$)/)[1];

            // npm package names are URL-safe, but some servers don't like @ symbols
            return `npm.${packageName.replace('@', '')}`;
          },
        }
      },
    },
  },

  entry: {
    app: ["babel-polyfill", './js/index.jsx'],
    silentRenew: ["./silent_renew/silent_renew.js"],
  },

  output: {
    path: path.resolve('dist'),
    filename: 'bundle_[name].js'
  },

  module: {
    rules: [{
      test: /\.jsx?$/,
      use: ['babel-loader'],
      exclude: /node_modules/
    },
    {
      test: /\.json$/,
      use: ['json-loader'],
      exclude: /node_modules/
    },
    {
      test: /\.css$/,
      use: [
        'style-loader',
        'css-loader'
      ]
    },
    {
      test: /\.less$/,
      use: [
        'style-loader',
        'css-loader',
        'less-loader'
      ]
    },
    {
      test: /\.scss$/,
      use: [
        'style-loader',
        'css-loader',
        'scss-loader'
      ]
    },
    {
      test: /\.(png|jpg|jpeg|svg|gif)$/,
      use: [
        'file-loader'
      ]
    },
    {
      test: /\.(woff|woff2|eot|ttf|otf)$/,
      use: [
        'file-loader'
      ]
    },
    {
      test: /\.(pptx|zip)$/,
      loader: "file-loader",
      options: {
        name: '[name].[ext]'
      }
    }]
  },

  plugins: [
    new CleanWebpackPlugin(['dist']),
    new HtmlWebpackPlugin({
      template: './index.ejs',
      excludeChunks: ["silentRenew"],
    }),
    new HtmlWebpackPlugin({
      template: "./silent_renew/silent_renew.html",
      chunks: ["silentRenew",],
      filename: "silent_renew.html"
    }),
    new webpack.DefinePlugin({
      CONSTANTS: {
        PROD: false,
        TEST: true,
        DEV: false
      }
    }),
    new webpack.IgnorePlugin(/^(fs|ipc|ignore)$/)
  ]
}

I want my config files to go into the config bundle, this is already working. But then I also need them to not be included in the main bundle.

Even better would be if I could have the config files not bundled at all and just copied to the output folder and read from there by the main (app) bundle. But an isolated config bundle is second option.

  • copy-webpack-plugin – PlayMa256 Jan 18 '19 at 15:36
  • I tried that too, and got the files to copy over, but because the config files are being imported all over the place in my components they still end up in the main bundle and are used/read from there. Thus my copied files were also useless. – André Engelbrecht Jan 18 '19 at 15:45
  • I found this related question: https://stackoverflow.com/questions/38272128/how-to-load-an-external-config-file-in-a-webpack-react-application-without-bundl?rq=1. But it does not explain how the file can be read by the main bundle after deployment. – André Engelbrecht Jan 18 '19 at 16:02
  • So I managed to get the config bundle working, but it's not ideal, there's some content in there that I didn't have in my original files, added by Webpack. So now the next step is to figure out how to not bundle these files at all and yet have them available/readable to the main bundle after deployment. ANY SUGGESTIONS? – André Engelbrecht Feb 01 '19 at 10:47

1 Answers1

1

You need to chunk out your bundle based on conditions. This is an example of splitting out node_modules into a "common" bundle, but you can rewrite the test property to match your directory conditions.

    optimization: {
    splitChunks: {
      cacheGroups: {
        commons: {
          test: /[\\/]node_modules[\\/]/,
          name: "common",
          chunks: "all"
        }
      }
    }
Chase
  • 2,206
  • 1
  • 13
  • 17
  • Thanks @Chase, I'll try this on Monday. Can you perhaps point me to where I can find details on how that test condition works (i.e the syntax)? Thanks again. – André Engelbrecht Jan 19 '19 at 19:32
  • Hi @chase, I've tried everything I could think of for that test condition and I just can't get it to work. I'm no good with regex so I'm not sure what to change that to. I also tried setting it to the 'absolute' path (./App/JS/Config) but this does not work either. Your example seems to work in that it created a bundle, but the moment I change it no bundle is created. Please help, how can I set that test condition to bundle the files in my ./App/JS/Config folder? – André Engelbrecht Jan 21 '19 at 10:37
  • 1
    Try /[\\/]App[\\/]JS[\\/]Config[\\/]/ – Chase Jan 21 '19 at 14:54
  • Thanks @chase I tried this but it does not generate the 'config' bundle. I'm starting to think there's something else wrong here (with my setup), but what? I've updated my webpack config to relect it's current state. Any additional help you can provide will be greatly appreciated! – André Engelbrecht Jan 21 '19 at 16:25
  • 1
    Finally got this working. Thanks again @Chase, your answer was 99% correct. I had to make two small adjustments to make it work. First I had to make the regex all lower-case, even though my folder names start with upper-case letters. Secondly, because my config files are very tiny, I had to override the default minSize value to '0'. – André Engelbrecht Jan 31 '19 at 17:51