5 ms·
This isn't fixed properly The linked code is: String languageCode = Locale.getDefault().getDisplayLanguage(); Locale locale = new Locale(langu
by david_allison 2y ago
This isn't fixed properly
The linked code is:
String languageCode = Locale.getDefault().getDisplayLanguage();
Locale locale = new Locale(languageCode);
Locale.setDefault(locale);
But `getDisplayLanguage()` is defined as returning the display name, not the language code:
> if the locale is en_US and the default DISPLAY locale is fr_FR, getDisplayLanguage() will return "anglais"
https://developer.android.com/reference/java/util/Locale#getDisplayLanguage https://developer.android.com/reference/java/util/Locale#get...()
----
This then proceeds to create a locale with a corrupt language code. The language parameter of `Locale` is not validated (besides a null check), and using a corrupt Locale in `Locale.setDefault()` will cause a number of bugs
- canucker2016 2y agoI agree. Locale.getLanguage() returns the language code. The specific Locale() constructor used in the code is documented as taking a parameter: "An ISO 639 alpha-2 or alpha-3 language code, or a language subtag up to 8 characters in length. See the Locale class description about valid language values." I'd guess the app code lucked out on the string returned from getDisplayLanguage() getting mapped to the appropriate language in all the other cases that the app supports. Now if getLanguage() had been renamed to getLanguageCode() then maybe a dev might have had the light bulb turn on, but random string returned from an API passed to another API passes the compile test and the app doesn't blow up, so we're good to go... Searching for the offending incorrect code on the web doesn't return any matching "sample" code, so I'm not sure where the app got the bug from.
- marcellus23 2y agoFor me the light bulb here is the word `display`. The method is called `getDisplayLanguage` because it's returning the language name for display to the user. Even if I didn't already know that, I'd be asking myself as I was typing the code: "wait, what does 'display' mean here? Why would they name it that? I'd better check the docs..."
- ryandrake 2y agoWould stronger typing help here? If I were to design those APIs, I'd maybe suggest a more opaque type called "LanguageCode" that is NOT a String and could not be returned from or passed as a String. Then getLanguage() could return a LanguageCode type, and the Locale() constructor could take the LanguageCode type as its parameter, and then tooling could enforce that you can't mix LanguageCode with String. Then, calling Locale's constructor with the return value from getDisplayLanguage() would produce an easy-to-find error.
- amne 2y agoThe API is the problem here. The method names in this case: getLanguageCode() and getLanguageName(), or getLanguageDisplayName() even, are much better names.
- xandrius 2y agoYep, having proper types instead of passing around strings would have prevented this.
- sonicanatidae 2y ago>Would stronger typing help here? While we're not programmers, we can say with certainty that hitting the keys harder, does NOT change the behavior. -Ops Team.