i18n - Internationalization
aah provides internationalization and localization feature for aah application.
- i18n Message file format is 
forgeconfig syntax. Same asaah.confsyntax. - i18n Message filename format is 
message.<Language-ID>. Language ID is combination ofLanguage + RegionorLanguagevalue.- Language ID follows the two-letter 
ISO 639-1standard - Region ID follow the two-letter 
ISO 3166-1standard 
 - Language ID follows the two-letter 
 - Zero coding effect on localizing your application via URL Path Variable or URL Query String
 
Tip: aah supports sub-directories under <app-base-dir>/i18n/..., so aah user could organize message file(s) per use case in several sub-directories.
Supported message file extension formats are (in-casesensitive)
  1) Language + Region => en-us | en-US
  2) Language          => en
For Example:
  message.en-US or message.en-us
  message.en-GB or message.en-gb
  message.en-CA or message.en-ca
  message.en
  message.es
  message.zh
  message.nl
  etc.
Table of Contents
- Default Behavior
 - On-Demand Translation
 - i18n Methods
 - i18n Locale Param Processing Order
 - i18n Message Lookup strategy by key
 
Default Behavior
aah automatically does internationalization/localization based incoming Request Context i.e. HTTP header Accept-Language, parsed per RFC7231.
For example:
When user visits https://example.com/home; all the i18n keys in the view file is processed and presented based on request user locale.
On-Demand Translation
aah provides OOTB ways to override Request Context user locale. Refer to locale param processing order.
- Override via URL Query parameter, e.g. 
https://example.com/home?lang=de, example app - Override via URL Path parameter, e.g. 
https://example.com/de/home, example app- This involves the route path definition e.g. 
/:lang/home - On view file, to generate link URL using func rurl - 
<a href="{{ rurl . "home" "de" }}">Deutsch</a> 
 - This involves the route path definition e.g. 
 
Methods
At View file
{{ i18n . "message.key" }}{{ i18n . "message.key" arguments }}
At Controller
Msg(key)Msg(key, arguments)Msgl(locale, key)Msgl(locale, key, arguments)
Anywhere
aah.App().I18n().Lookup(locale, key)aah.App().I18n().Lookup(locale, key, arguments)
i18n Locale Param Processing Order
- First URL Query parameter if present
 - Next is URL Path parameter if present
 - Next is HTTP Header 
Accept-Languageparsed per RFC 7231 
Default key name is lang, if you would like to override the key name; refer app config: section i18n
i18n Message Lookup strategy by key
Scenario 1
Input Locale is en-US and message key is label.page.index.title.
- First it does looks up 
i18nstore by given localeLanguage + Regionvalue if found then returns it - Second if not found then it does looks up by 
Languageonly if found then return it. - Third if not found then it does looks up by 
i18n.defaultconfig value if found then return it. - Otherwise it returns 
emptystring and logs themsg keyas not found. 
Scenario 2
Input Locale is en and message key is label.page.index.title.
- First it does looks up 
i18nstore byLanguagevalue if found then return it. - Second if not found then it does looks up by 
i18n.defaultconfig value if found then return it. - Otherwise it returns 
emptystring and logs themessage keyas not found.