ignore_macros |
---|
true |
ILC comes with built in internationalization support, so you can easily run micro frontends on the websites which require support of the multiple languages.
However, you need to keep in mind that ILC does only part of the job for you. Support of the i18n capabilities from the micro frontends side is required.
ILC uses 2-tier routing model. It means that:
- ILC itself handles only global routing (says which set of apps should be loaded at particular URL)
- Micro Frontend has own routing in place which determines component to be rendered.
While having i18n feature enabled - ILC allows you to handle localized URLs at global level. Currently, we support two routing schemes:
- Prefixing all routes with the locale except those of the default locale
- Prefixing all routes with the locale
In Registry, you continue to specify all routes in Registry w/o locale information.
When dealing with internationalization - we obviously don't want to hardcode localized links in the source code of every micro frontend that we run with ILC. Instead, it's better to separate concerns.
Such approach allows to be flexible in the selection of the localization pattern for your URLs, and you can manage this behaviour from central place.
The other thing that we need to consider - is the fact that process & business logic of actual location.href
un-localization before use
in the app's router & localization of the URLs before rendering into the DOM should be synchronized across all applications
and ILC itself.
To achieve that ILC provides IlcIntl
class
via App SDK that can be used at CSR & SSR.
Examples:
When customer wants to change locale or currency on the website - it's often impossible to immediately render an updated content as loading of the localization files or updated prices is necessary.
If we would only emit locale/currency change event and allow every micro frontend to deal with it on its own - customer would likely see "blinking" of the UI as various parts of it will be re-rendered in different moments of time. To prevent this from happening - ILC uses prepare/execute pattern to synchronize re-rendering of all micro frontends.
Example:
class Root extends React.Component {
constructor(props) {
super(props);
this.state = { links: [] };
// This is a root React component, so it receives appSdk as property from ILC.
const lang = this.props.appSdk.intl.get().locale;
import(`./links/${lang}.json`).then(v => {
this.setState({links: v.default});
});
}
componentDidMount() {
this.props.appSdk.intl.onChange(
(e) => import(`./links/${e.locale}.json`), // Prepare all necessary data
(e, langModule) => { // Perform language change
this.setState({links: langModule.default});
}
);
}
changeLocale(locale, e) {
e.preventDefault();
this.props.appSdk.intl.set({ locale });
}
render() {
return (
<div className='navbar-app'>
{
this.state.links.map((link) => {
return (
<NavLink key={link.href}
to={this.props.appSdk.intl.localizeUrl(link.href)}>
{link.name}
</NavLink>
)
})
}
<div className='lang-selector'>
<NativeListener onClick={this.changeLocale.bind(this, 'en-US')}>
<a href="#" style={{color: 'white'}}>EN</a>
</NativeListener>
/
<NativeListener onClick={this.changeLocale.bind(this, 'ua-UA')}>
<a href="#" style={{color: 'white'}}>UA</a>
</NativeListener>
</div>
</div>
);
}
}