I18n.json legacy build handler very slow

I have a large project with translation files that add up to around 7,000 lines of English text which means that 46 of the 48 seconds of rebuild (as per below) is all down to the “legacy handler (.i18n.json)”:

Rebuild App..................................................48,159 ms (1)
| └─ bundler.bundle............................................48,159 ms (1)
|    ├─ compiler.compile(the app)..............................46,328 ms (1)
|    │  └─ compileUnibuild (the app)...........................46,327 ms (4)
|    │     ├─ legacy handler (.i18n.json)                      45,804 ms (4)
|    │     └─ other compileUnibuild (the app)                     371 ms
|    ├─ bundler.bundle..makeClientTarget........................1,555 ms (2)
|    │  └─ Target#make..........................................1,555 ms (2)
|    │     ├─ Target#_runCompilerPlugins..........................241 ms (2)
|    │     │  └─ plugin templating-compiler.......................166 ms (2)
|    │     │     └─ files.readFile                                132 ms (56)
|    │     ├─ Target#_emitResources.............................1,068 ms (2)
|    │     │  └─ PackageSourceBatch.computeJsOutputFilesMap.......971 ms (2)
|    │     │     └─ ImportScanner#scanImports for the app.........648 ms (2)
|    │     │        ├─ Babel.compile                              102 ms (1802)
|    │     │        ├─ ImportScanner#resolve                      122 ms (13812)
|    │     │        └─ other ImportScanner#scanImports for the app 262 ms
|    │     └─ Target#minifyJs.....................................114 ms (2)
|    │        └─ sha512                                           106 ms (339)
|    └─ bundler writeTargetToPath.................................266 ms (2)
|       └─ ClientTarget#write                                     263 ms (2)

I am using this meteor package:

tap:i18n

I would love my builds to be 2 seconds! Does anyone know how I can stop the i18n rebuild each time and only have it build when I change my language file(s)?

I have solved this by creating a package that is built separately. This is actually described in the their docs, but I could not get it to work until now… so:

In packages create a new folder called, say, translations and in this:

  1. Create a i18n folder in which you put your language translation files (e.g. en.i18n.json)
  2. Create a minimalist package.js file:
Package.describe({
    name: 'dthwaite:translations',
    version: '0.0.1'
});

Package.onUse(function(api) {
    api.use(['tap:i18n'], ['server', 'client']);
    api.use(['templating'], 'client');
    api.add_files('package-tap.i18n',['server', 'client']);
    api.add_files('index.html', 'client');
    api.add_files(['i18n/en.i18n.json'],['server', 'client']);
});

The trick that took me a while to get was that a dummy template file is mandatory, so:

  1. Add a dummy index.html file:
<template name="i18n_dummy_package_template">
</template>
  1. Add a package-tap.i18n file that tells the package to apply the translations at the “project” level:
{
  "namespace": "project"
}

Finally, we need to tell Meteor about this new package:

meteor add dthwaite:translations

And job’s a good’un. My project now builds in 3 seconds (and with HMR it’s even better). I still have to wait for 45 seconds if I want to add translations, but as far as I am concerned I’ve moved 100 steps forward and 1 step backward.