io.appium.settings
Version:
App for dealing with Android settings
96 lines • 4.62 kB
JavaScript
;
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.setDeviceLocale = setDeviceLocale;
exports.listSupportedLocales = listSupportedLocales;
const lodash_1 = __importDefault(require("lodash"));
const logger_1 = require("../logger");
const constants_1 = require("../constants");
/**
* Set the locale name of the device under test.
* Don't need to reboot the device after changing the locale.
* This method sets an arbitrary locale following:
* https://developer.android.com/reference/java/util/Locale.html
* https://developer.android.com/reference/java/util/Locale.html#Locale(java.lang.String,%20java.lang.String)
*
* @param language - Language. The language field is case insensitive, but Locale always canonicalizes to lower case.
* format: [a-zA-Z]{2,8}. e.g. en, ja : https://developer.android.com/reference/java/util/Locale.html
* @param country - Country. The country (region) field is case insensitive, but Locale always canonicalizes to upper case.
* format: [a-zA-Z]{2} | [0-9]{3}. e.g. US, JP : https://developer.android.com/reference/java/util/Locale.html
* @param script - Script. The script field is case insensitive but Locale always canonicalizes to title case.
* format: [a-zA-Z]{4}. e.g. Hans in zh-Hans-CN : https://developer.android.com/reference/java/util/Locale.html
* @throws {Error} If language or country name is not provided
*/
async function setDeviceLocale(language, country, script = null) {
if (lodash_1.default.isEmpty(language)) {
throw new Error('Language name must be provided');
}
if (lodash_1.default.isEmpty(country)) {
throw new Error('Country name must be provided');
}
const lcLanguage = language.toLowerCase();
const ucCountry = country.toUpperCase();
const curLocale = await this.adb.getDeviceLocale();
// zh-Hans-CN : zh-CN
const localeCode = script ? `${lcLanguage}-${script}-${ucCountry}` : `${lcLanguage}-${ucCountry}`;
this.log.debug(logger_1.LOG_PREFIX, `Current locale: '${curLocale}'; requested locale: '${localeCode}'`);
if (localeCode.toLowerCase() !== curLocale.toLowerCase()) {
await setDeviceLocaleInternal.bind(this)(lcLanguage, ucCountry, script);
}
}
/**
* Retrieves the list of supported device locales
*
* @returns List of supported locales
* @throws {Error} If the list cannot be retrieved
*/
async function listSupportedLocales() {
const params = [
'-a', constants_1.LOCALES_LIST_SETTING_ACTION,
'-n', constants_1.LOCALES_LIST_SETTING_RECEIVER,
];
const output = await this.checkBroadcast(params, 'list supported locales');
const match = /result=-1, data="([^"]+)/.exec(output);
if (!match) {
throw new Error('Cannot retrieve the list of supported device locales. Check the logcat output for more details');
}
return JSON.parse(Buffer.from(match[1], 'base64').toString()).items;
}
/**
* Change the locale on the device under test. Don't need to reboot the device after changing the locale.
* This method sets an arbitrary locale following:
* https://developer.android.com/reference/java/util/Locale.html
* https://developer.android.com/reference/java/util/Locale.html#Locale(java.lang.String,%20java.lang.String)
*
* @param language - Language. e.g. en, ja
* @param country - Country. e.g. US, JP
* @param script - Script. e.g. Hans in `zh-Hans-CN`
*/
async function setDeviceLocaleInternal(language, country, script = null) {
const params = [
'-a', constants_1.LOCALE_SETTING_ACTION,
'-n', constants_1.LOCALE_SETTING_RECEIVER,
'--es', 'lang', language.toLowerCase(),
'--es', 'country', country.toUpperCase()
];
if (script) {
params.push('--es', 'script', script);
}
for (let retry = 0; retry < 2; retry++) {
try {
await this.checkBroadcast(params, 'set device locale');
}
catch (err) {
if (retry === 0 && lodash_1.default.has(err, 'output') && err.output.includes('NoSuchMethodException')) {
// The above exception may be thrown if hidden API policies have not been picked up by
// Settings app yet. Restart might fix this issue.
await this.requireRunning({ shouldRestoreCurrentApp: true, forceRestart: true });
continue;
}
throw err;
}
}
}
//# sourceMappingURL=locale.js.map