lisan-plugin-loader
TypeScript icon, indicating that this package has built-in type declarations

0.1.1 • Public • Published

Lisan.js
i18n, Reimagined!

A blazing fast and super small i18n library for Javascript


Website

Installation · API · Guides & Tips · Examples


Lisan Plugin Loader

Lisan Loader allows you dynamically load your dictionaries and locale configurations.

However, dictionaries must be created compatible with the loader. For that, you can set module option to lisan in Lisan Compiler or provide --module=lisan flag to the Lisan CLI compile command;

Installation

You can install lisan from the sources below, as you see fit.

from npm

npm install lisan-plugin-loader

from CDN

<script src="https://unpkg.com/lisan-plugin-loader/dist/index.umd.js" type="text/javascript"></script>

After adding the script tag above, all public variables will be accessible via window.lisanPluginLoader variables.

Usage

const { lisan } = require('lisan');
const { Loader } = require('lisan-plugin-loader');
 
lisan.use(
  Loader({
    dictionaryUrlFn: (dictionaryName, localeName) =>
      `https://cdn.mydomain.com/static/${localeName}/dictionaries/${dictionaryName}.js`,
  }),
);
 
lisan.setLocaleName('tr');
 
lisan.load('main').then(() => {
  // Loaded https://cdn.mydomain.com/static/tr/dictionaries/main.js
  const translated = lisan.t('hello.person', {
    name: 'John Doe',
  });
  console.log(translated); // Merhaba John Doe
});

Type Signature

type Loader = (urlResolverFunctions: {
  dictionaryUrlFn: string;
  localeUrlFn: string;
}) => TSLisan.Plugin;

Options

dictionaryUrlFn

Type: DictionaryURLResolverFunction
Default: undefined

Type Signature

type DictionaryURLResolverFunction = (
  dictionaryNamestring;
  localeNamestring;
) => string;

localeUrlFn

Type: LocaleURLResolverFunction
Default: ({ localeName }) => `https://unpkg.com/lisan-locales/dist/${localeName}.lisan.js`

Warning

localeUrlFn only works if lisan-plugin-l10n is used.

Type Signature

type LocaleURLResolverFunction = (localeName: string) => string;

Methods

For the full list of methods, see Lisan Loader API.

Compatibility

Platform IE Edge Firefox Chrome Nodejs
Version 9+ All All All 8+

Guide

Why might you need a dynamic loader?

Lisan takes advantage of doing interpolation on runtime with pure functions. To achieve that it uses Javascript files. However, there is a very important difference loading javascript files dynamically vs synchronously.

Popular Javascript modules (Eg. commonjs, esm, umd) loads modules synchronously. That's why module bundlers like webpack, rollup can statically analyze your code and bundle your source code.

Since i18n preferences are gathered from client-side, it would be a good practice to load dictionaries and/or locales dynamically as chunks (a.k.a lazy loading) especially for Single Page Applications since it would decrease the main bundle size.

Hint

You can also create a separate bundle for each locale and/or dictionaries and include locale/dictionary files to reduce latency. You are completely free to choose how to design your application.

Luckily, Lisan Loader Plugin is here to save you from some pain.

You can use lisan.loadLocale() method to load locales and lisan.load() method to load dictionaries.

Info

lisan compile --module=lisan command will generate dictionaries
which are compatible with Lisan Loader.

To learn more about compile command, see: lisan compile.

Loading on Node Environment

When doing server side rendering, Lisan Loader will use require function to load desired file.

It is important to know that the file paths will be added to current working directory path. See: process.cwd()

Example:

Let's assume you are working on a project located in /Users/me/workspace/myproject folder.

// src/index.js
const { lisan } = require('lisan');
const { Loader } = require('lisan-plugin-loader');
 
lisan.use(
  Loader({
    dictionaryUrlFn: (dictionaryName, localeName) =>
      `/static/${localeName}/dictionaries/${dictionaryName}.js`,
  }),
);
 
lisan.setLocaleName('en-US');
lisan.load('main').then(() => {
  /*
   * 1. On Node Environment, dictionary will be REQUIRED from:
   * - "/Users/me/workspace/myproject/static/en-US/dictionaries/main.js"
   * 2. On Browser environment,  dictionary will be LOADED from:
   * - "http://<HOSTNAME>/static/en-US/dictionaries/main.js"
   */
  lisan.t('hello.world');
});

Loading on Browser Environment

Lisan Loader will load dictionaries and locales by appending <script> elements before closing body tag </body>.

// src/index.js
const { lisan } = require('lisan');
const { Loader } = require('lisan-plugin-loader');
const { Localization } = require('lisan-plugin-l10n');
const renderHome = require('./pages/home.js');
 
// Localization is needed to use loadLocale function.
lisan.use(Localization);
 
lisan.use(
  Loader({
    localeUrlFn: localeName =>
      `https://cdn.mydomain.com/static/locales/${localeName}.js`,
    dictionaryUrlFn: (dictionaryName, localeName) =>
      `https://cdn.mydomain.com/static/${localeName}/dictionaries/${dictionaryName}.js`,
  }),
);
 
(async () => {
  await lisan.loadLocale('en-US');
  // Loaded https://cdn.mydomain.com/static/locales/en-US.js
 
  await lisan.load('main');
  // Loaded https://cdn.mydomain.com/static/en-US/dictionaries/main.js
 
  renderHome();
})().then(() => console.log('rendered'));

Please note that,

lisan.loadLocale("en-US") method will append the script element below:

<script id="Lisan_Locale__en-US" src="https://cdn.mydomain.com/static/locales/en-US.js"></script>

lisan.load("main") method will append the script element below:

<script id="Lisan_Dictionary__en-US__main" src=" https://cdn.mydomain.com/static/en-US/dictionaries/main.js"></script>

Using another dynamic import strategy

There are plenty of ways to dynamically import javascript files like using import() expression,
ES Modules in Browsers or a third-party library like requireJS etc.

You are free to use any of them. All you need to do is to provide --module option to lisan compile tool while building your dictionaries.

You can check Dynamic Import Strategies page for more details.

Caching

When you start using javascript files to serve dictionaries, you need to be aware of caching.

Browsers will cache the webpage assets. Thus, if you make a change in your dictionary, clients may not see it.

There are plenty of different strategies to invalidate the cache for javascript files like
setting Cache-Control header, or using manifest files, or redirecting static assets' URLs to hashed URLs etc.

However, depending on your use case, one of the simplest solutions could be adding a version tag at the end of your dictionary URLs.

const MY_APP_VERSION = require('package.json').version;
 
lisan.use(
  Loader({
    localeUrlFn: localeName =>
      `https://cdn.mydomain.com/static/locales/${localeName}.js?v=${MY_APP_VERSION}`,
    dictionaryUrlFn: (dictionaryName, localeName) =>
      `https://cdn.mydomain.com/static/${localeName}/dictionaries/${dictionaryName}.js?v=${MY_APP_VERSION}`,
  }),
);

Or if you'd like to version dictionaries separately, you can add the version name to your dictionary files.

lisan.use(
  Loader({
    dictionaryUrlFn: dictionaryName =>
      `https://cdn.mydomain.com/static/dictionaries/${dictionaryName}.js`,
  }),
);
 
lisan.load('main-v1.2.3').then(() => {
  // Loaded https://cdn.mydomain.com/static/dictionaries/main-v1.2.3.js
  // All entries can be used by `lisan.t()` and `lisan.c()` methods
});
 
lisan.load('about-v1.0.0').then(() => {
  // Loaded https://cdn.mydomain.com/static/dictionaries/about-v1.0.0.js
  // All entries can be used by `lisan.t()` and `lisan.c()` methods
});

License

This package is MIT licensed.

Package Sidebar

Install

npm i lisan-plugin-loader

Weekly Downloads

11

Version

0.1.1

License

MIT

Unpacked Size

33.6 kB

Total Files

11

Last publish

Collaborators

  • yatki