Let's say I have 2 strings files:
Strings_en.properties
Strings_fr.properties
Let's say English is the default language, and all the strings are present, while French lags behind and some strings are missing.
I want to fall back to English in both of these cases:
ResourceBundle.getBundle("path/to/Strings", Locale.GERMAN);
ResourceBundle.getBundle("path/to/Strings", Locale.FRENCH).getString("only.in.english");
The first fallback is simple enough: as per the documentation, it's enough to have English as the default locale, for example by setting Locale.setDefault(Locale.ENGLISH);
.
My problem is with the second fallback. If the string is not found in Strings_fr
, the lookup continues to the "parent bundle": getObject() documentation. However, Strings_en
is not the parent of Strings_fr
and a MissingResourceException
is thrown.
A simple fix is to rename Strings_en.properties
to Strings.properties
. This makes it the parent bundle for Strings_fr
(and for any other Strings_
, for that matter) and looking up missing strings returns the default English versions.
Problem: the system now has a default localization, but it no longer understands that there is an English localization.
When fetching a string, check if it's present in the bundle - if not, fetch it from the English one instead.
ResourceBundle bundle = ResourceBundle.getBundle("path/to/Strings", Locale.FRENCH);
if (bundle.containsKey(key)) { return bundle.getString(key); }
return ResourceBundle.getBundle("path/to/Strings", DEFAULT_WHICH_IS_ENGLISH).getString(key);
Problem: this is just a hack, I believe there is an "intended" way to do it.
Is there a simple way to make Strings_en
the parent of Strings_fr
? If not, is it reasonable to for example hardlink Strings_en
to Strings
, so that I can keep English as an explicit localization and at the same time as the default one?
You can rename Strings_en.properties
to Strings.properties
(making English the default localization) and add a new empty Strings_en.properties
.
Then
ResourceBundle.getBundle("path/to/Strings", Locale.ENGLISH).getLocale()
also returns Locale.ENGLISH
.
Old thread, another solution:
You can use ResourceBundle.Control
and getCandidateLocales
to add custom language candidates (file suffix)
ResourceBundle.getBundle(baseName, locale, new ResourceBundle.Control() {
@Override
public List<Locale> getCandidateLocales(String baseName, Locale locale) {
List<Locale> list = super.getCandidateLocales(baseName, locale);
list.add(new Locale("en"));
return list;
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With