vue-i18n-loader

vue-i18n-loader - another webpack loader i18n solution for Vue (Nuxt) with auto generated keys.

Currently under development, pull requests and suggestions are welcome.

Why?

  • We need auto generated keys for texts to be translated

    There are only two hard things in Computer Science: cache invalidation and naming things. -- Phil Karlton

    Most i18n solutions ask developers to name each text with a unique key, like $t("message.hello"), naming is so annoying, it's not reasonable to waste time doing this job

  • Text translations should be put just beside source codes

    Some solutions extract all texts to a single json file, it's not conform to modularization

How it works?

  1. Find automatically texts to translate by two means: regex string or 'delimiter'(Refer to usage below).
  2. Keep first 8 characters of every matched text as key (and append 4 characters md5 hash to the key if the text is longer than 8)
  3. Replace texts by translator markups using regex
  4. Create or update filename.messages.json to store translations, import this file in filename.vue

!!! Attentions !!!

  • Since this at the top level of es6 module bind to undefined, but not the vue instance.

    All target texts in script part should be put in functions(not fat arrow functions refer to this doc)

Usage

Config webpack

Config example based on Nuxt.js.

Given regString, the loader will match all texts/attributes/string templates by new RegExp(regString)

Given delimiter, the loader will ignore regString, The loader will match all texts between delimiter, for example ##text##.

    {
        test: /\.vue$/,
        exclude: [/node_modules/],
        loader: 'vue-i18n-loader',
        enforce: 'pre',
        options: {
          updateMessagesFile: ctx.isClient && ctx.isDev, // only update messages file when it's dev and client(when using ssr)
          cacheTime: 3000,
          // regString to match simplified chinese characters
          regString: '[\u4e00-\u9fa5\u3002\uff1b\uff0c\uff1a\u2018\u2019\u201c\u201d\uff08\uff09\u3001\uff1f\uff01\ufe15\u300a\u300b]+',
          // delimiter: '##', // match texts surrounded by '##', like '##text##'
          // Loader will use existing translations, if there is not, will use text generated by translator
          languages: [{
            key: 'zh_Hans_CN',
            translator: (matched) => {
              // Delete repeat mark R, sometimes we need a text to be translated differentlyz`
              return matched.replace(/^\[R\]+/, '')
            }
          }, {
            key: 'zh_Hant_HK',
            translator: (matched) => {
              // example to auto translate simplified chinese to traditional
              return chineseS2T.s2t(matched.replace(/^\[R\]+/, ''))
            }
          }, {
            key: 'en_US',
            // if translator is not given, the loader will use the default translator(translator of the first language, zh_Hans_CN here)
          }],
        }
      }

Add a global plugin to tell our helper which language to show

An example of plugin can be:

    import Vue from 'vue';
    import {mapGetters} from 'vuex';

    // !!! the key must be $lang, which will be referenced by the helper !!!
    Vue.mixin({
      computed: {
        ...mapGetters({'$lang': 'currentLang'}),
      }
    });

The helper will insert code automatically to refer this $lang variable like this:

    methods:{
        $t(key){
              if(!this.$lang && !messages["${defaultLang}"]) return key;
              const trans = messages[this.$lang]||messages["${defaultLang}"]||{};
              return trans[key];
        },
    }

defaultLang is the first language key set in config, zh_Hans_CN here in the example.

Demo

check the example directory:

  1. This example is based on Nuxt.js
  2. Download this example and start by npm install then npm run dev
  3. Try changing texts and add some translations

Cli tool

We provide a cli tool to group all *.messages.json and serve a web page for human translators Please refer to the github repo of viai18n-cli

Roadmap

  • Support JSX
  • Add tests

GitHub

https://github.com/bitapp/vue-i18n-loader