haul icon indicating copy to clipboard operation
haul copied to clipboard

Build times are too slow

Open SuhairZain opened this issue 6 years ago • 8 comments

We have our source code written in TS and we use [email protected] along with awesome-typescript-loader and babel-loader for our RN app. The build is too slow for both the first build and when changes are made to a single component. The initial build time is okay, but the incremental changes are too slow for normal use.

First build      2m13s71
Change component 0m14s10
Revert change    0m13s12

Current Behavior

The initial build and incremental changes take too long.

Expected Behavior

The initial build should preferably be fast. Incremental changes need to be considerably faster.

Haul Configuration (webpack.haul.js)

const path = require('path');

const appDir = path.resolve(__dirname, '..');

const paths = {
    appSrc: path.resolve(appDir, 'src'),
    nodeModules: path.resolve(appDir, 'node_modules'),
};

module.exports = ({ platform }, { module, resolve }) => {
    return {
        entry: path.resolve(paths.appSrc, 'index.native.tsx'),

        devtool: 'inline-source-map',

        module: {
            ...module,
            rules: [
                {
                    test: /\.tsx?$/,
                    loader: 'awesome-typescript-loader',
                    options: {
                        transpileOnly: true,
                    },
                },
                {
                    test: /\.(js|jsx|mjs)$/,
                    include: [
                        paths.nodeModules,
                    ],
                    loader: 'babel-loader',
                    options: {
                        compact: true,
                    },
                },
                ...module.rules,
            ],
        },

        resolve: {
            ...resolve,
            extensions: [
                `.${platform}.ts`, `.${platform}.tsx`,
                '.native.ts', '.native.tsx',
                '.ts', '.tsx',
                ...resolve.extensions,
            ],
        },

    };
};

Your Environment

software version
Haul 1.0.0-rc.7
react-native 0.53.0
node 8.4.0
npm or yarn 0.27.5

I tried using cache with awesome-typescript-loader via happypack and cacheloader, but it didn't make any noticeable changes. I also verified that babel-loader is writing to the disk cache.

Is the build times to be expected or can they be made faster? Any help would be greatly helpful.

SuhairZain avatar Sep 24 '18 14:09 SuhairZain

How many components are there in your project? Maybe you're compiling you're files twice, once with babel, second time with TS, can you check that?

thymikee avatar Sep 24 '18 14:09 thymikee

I'd say about 150 components. About 50 of these are large (>200 lines).

I don't think it's possible that the files are being compiled twice. The config is to compile the TS files with awesome-typescript-loader and JS files with babel-loader. Also, babel-loader is set to compile only the files inside node_modules.

How would I check if it is actually being compiled twice? Also, I saw how we could profile a webpack build. Is there a similar profiling tool that I can use with haul?

SuhairZain avatar Sep 24 '18 15:09 SuhairZain

We don't have a profiler. Maybe you're trying to compile all files in node_modules? 150 components is not much, so that's definitely weird. @jukben do you have some clever thoughts on that?

thymikee avatar Sep 24 '18 15:09 thymikee

We are using typescript with similar number of files (I believe even more, can't check now, sorry) and it takes about 1 minute to compile on first build and the subsequent changes take 3-4 seconds. For me that's fast enough, but it would be nice if it was faster.

Also, we are using ts-loader not awesome-typescript-loader.

meznaric avatar Sep 25 '18 15:09 meznaric

@meznaric 3-4 seconds for incremental updates sounds good. Would it be possible for you to share your haul config file?

SuhairZain avatar Sep 25 '18 15:09 SuhairZain

Can't really share it in its entirety, but here are relevant bits I believe:

  const tsRule = {
    test: /\.tsx?$/,
    exclude: /node_modules/,
    use: [
      {
        loader: 'babel-loader'
      },
      {
        loader: 'ts-loader'
      }
    ]
  };

  const extensions = defaults.resolve.extensions.reduce(
    (acc, ext) =>
      acc.concat([
        ext,
        ext.replace('.js', '.jsx'),
        ext.replace('.js', '.ts'),
      ]),
    []
  );


// Later on:
  const finalConf = {
    ...defaults,
    module: {
      ...defaults.module,
      rules: [
        ...haulRules,
        tsRule
      ]
    },
    resolve: Object.assign({}, resolve, {
      extensions,
      modules: [node_modules']
    }),
    plugins
  };

Nothing about typescript in .babelrc.

meznaric avatar Sep 25 '18 16:09 meznaric

Note: We had it a bit misconfigured and once I reconfigured it and babel was doing everything as expected our build times increased by a bit. From 4 seconds for incremental builds to ~10 if not more.

Anyways; we've upgraded to rc.8 and upgraded to babel 7 and now we are back at previous speeds if not even faster.

meznaric avatar Oct 16 '18 14:10 meznaric

I'm also facing this. 4-8 seconds after making a minor fix.

@haul-bundler/cli: 0.17.0 RN: 0.61.5 System: Mac mid 15 Processor 2.5 GHz intel core i7

config:

const removeRuleByTest = (moduleConfig, test) => {
    const index = moduleConfig.findIndex((rule) => {
        if (rule.test) {
            return rule.test.toString() === test.toString();
        }
        return false;
    });
    moduleConfig.splice(index, 1);
};

function transform({ config }) {
    // Remove babel-loader, as it handles both .ts(x) and .js(x) files
    removeRuleByTest(config.module.rules, /\.[jt]sx?$/);

    config.module.rules = [
        ...config.module.rules,

        {
            test: /\.[tj]sx?$/,
            loader: require.resolve('babel-loader'),
            options: {
                plugins: [
                    require.resolve(
                        '@haul-bundler/core/build/utils/fixRequireIssues',
                    ),
                ],
            },
        },
    ];

    console.log(`[BUNDLE]: ROLE = ${ROLE}`);
    console.log(`[BUNDLE]: PROJECT = ${PROJECT}`);

    config.resolve.alias = {
        ...config.resolve.alias,
        '@shared': path.join(__dirname, 'shared'),
        '@app': path.join(__dirname, `./pkg/${ROLE}/src`),
    };

    config.resolve.mainFiles = [
        PROJECT && `index.${PROJECT}`,
        'index',
    ].filter(Boolean);
}

export default makeConfig({
    bundles: {
        index: {
            entry: withPolyfills(`./pkg/${ROLE}`),
            transform,
        },
    },
});

Natteke avatar Mar 03 '20 09:03 Natteke