• Run Multiple Webpack Configs Sequentially


    https://www.viget.com/articles/run-multiple-webpack-configs-sequentially/

    const path = require('path');
    const serverConfig = {
        entry: './src/b.ts'
    }
    
    const config2 = {
        entry: './src/index.ts',
        devtool: 'inline-source-map',
        module: {
            rules: [
                {
                    test: /.tsx?$/,
                    use: 'ts-loader',
                    exclude: /node_modules/
                }
            ]
        },
        "devServer": {
            "port": 8083
        },
        resolve: {
            extensions: ['.tsx', '.ts', '.js']
        },
        output: {
            filename: 'bundle.js',
            path: path.resolve(__dirname, 'dist')
        }
    };
    module.exports = [config2, serverConfig]
    

      

    ---------------------------------------------

    When one webpack config depends on the outcome of another, running the configurations sequentially can save the day.

    I have a webpack build process, and it is has two isolated configurations (one for my server-side build, and another for my client-side build). Here's an incredibly simplified example:

    // webpack.config.js
    
    const clientConfig = {
      entry: './src/client/index.js',
    }
    
    const serverConfig = {
      entry: './src/server/index.js'
    }
    
    module.exports = [clientConfig, serverConfig]

    Everything clicked together quickly and easily, webpack is able to run these two builds and export different bundles for each environment. But then, of course, the joyous innocence of the early days faded as we added more functionality.

    The Rub

    We pulled in a library called React Loadable (side note: fantastic library), which comes with a webpack plugin, which can generate a file during the build. This file generation is defined in the client config, but application code within the server depends on that file. Because the file itself is a build artifact, we're not checking it into our source control, and thus the build must succeed without the up-front existence of this file.

    // webpack.config.js
    const { ReactLoadablePlugin } = require('react-loadable/webpack')
    
    const clientConfig = {
      entry: './src/client/index.js',
      plugins: [
        // This plugin creates the react-loadable.json file
        new ReactLoadablePlugin({
          filename: path.resolve(__dirname, 'react-loadable.json')
        }),
      ]
    }
    
    const serverConfig = {
      // This entry point makes use of the built react-loadable.json file
      entry: './src/server/index.js'
    }
    
    module.exports = [clientConfig, serverConfig]

    This is where things stop working. I've deduced that the configurations are being built in parallel, because even though the client configuration successfully creates the new file (I can see it in the build logs, and I can see those logs before I see any mention of the server build), the server build fails with a "I can't find that file!" error. If the file exists before the build runs, then everything flows smoothly, so the question became how to make it work without the pre-existence of that artifact.

    The Solution

    The internet had a few things to say about this. One option is to break apart the build and manually build each configuration in isolation. This requires some fiddling with your CLI usage, but does ensure that one config completely finishes before starting the new one. I was tempted to find a more streamlined solution, one that would allow me to run webpack the way that you'd expect.

    What I ended up with was an extension of WebpackBeforeBuildPlugin which simply polled for the existence of the required file.

    // WaitPlugin.js
    const WebpackBeforeBuildPlugin = require('before-build-webpack')
    const fs = require('fs')
    
    class WaitPlugin extends WebpackBeforeBuildPlugin {
      constructor(file, interval = 100, timeout = 10000) {
        super(function(stats, callback) {
          let start = Date.now()
    
          function poll() {
            if (fs.existsSync(file)) {
              callback()
            } else if (Date.now() - start > timeout) {
              throw Error("Maybe it just wasn't meant to be.")
            } else {
              setTimeout(poll, interval)
            }
          }
    
          poll()
        })
      }
    }
    
    module.exports = WaitPlugin
    // webpack.config.js
    const { ReactLoadablePlugin } = require('react-loadable/webpack')
    const WaitPlugin = require('./WaitPlugin')
    
    const clientConfig = {
      entry: './src/client/index.js',
      plugins: [
        new ReactLoadablePlugin({
          filename: path.resolve(__dirname, 'react-loadable.json')
        }),
      ]
    }
    
    const serverConfig = {
      entry: './src/server/index.js',
      plugins: [
        new WaitPlugin('react-loadable.json')
      ]
    }
    
    module.exports = [clientConfig, serverConfig]

    Now, the server config will hang while the client config wraps up. Checking every 100 milliseconds (for a maximum of 10 seconds), the build will only proceed when the file in question exists.

    I admit that I was hoping to be able to more definably run the multiple configuration builds in sequence, but this has certainly done the trick. If you've found another solution to this problem, we'd love to hear about it in the comments below!

  • 相关阅读:
    Java spring自查笔记
    C#设置IP地址 用WMI
    idea换成护眼色
    WPF布局的6种面板
    spring注解
    c# 播放mp3
    Python 提示 “No matching distribution found for MySQLdb”
    Python3链接数据库报错:Connection.__init__() takes 1 positional argument but 5 positional arguments (and 1 keywordonly argument) were given
    安装Mysql数据库及配置相关环境变量
    Python中文件命名的注意事项
  • 原文地址:https://www.cnblogs.com/oxspirt/p/11812173.html
Copyright © 2020-2023  润新知