Commit 697a88b1 authored by David 'Digit' Turner's avatar David 'Digit' Turner Committed by Commit Bot

android: Place English locale pak files into fallback directory.

This change ensures that all English locale pak files (i.e.
en-US.pak and en-GB.pak) are stored inside an app bundle into
a directory named:

  assets/fallback-locales/

This ensures that said .pak files are always stored in the base
module split APK, and thus available on all Chrome installs, after
any system locale change.

This prevents Chrome from crashing on startup under rare
circumstances (see related bug for details).

Testing was performed manually because we don't have a good regression
test suite that can change the device's system locale programmatically
(see http://crbug.com/904360 for this). Following these steps:

1) Set device's language to Spanish
2) Ensure Chrome is not installed, then install the bundle.
3) Start Chrome. It displays its UI in Spanish.
4) Change system language to Slovenčina, and *remove* Spanish from
   the list of system languages.
5) Start Chrome. It displays its UI in English (the fallback)
   instead of crashing.

English is chosen because it is the fallback language that the Android
framework actually choses when the application doesn't have any
resources compatible with the current system language.

BUG=905725
R=agrieve@chromium.org,estevenson@chromium.org,yfriedman@chromium.org,tiborg@chromium.org,tedchoc@chromium.org

Change-Id: I2c1f53a805122b6e48fb5105c1d9aa8c6262fa1d
Reviewed-on: https://chromium-review.googlesource.com/c/1340303Reviewed-by: default avatarTibor Goldschwendt <tiborg@chromium.org>
Reviewed-by: default avatarEric Stevenson <estevenson@chromium.org>
Reviewed-by: default avataragrieve <agrieve@chromium.org>
Reviewed-by: default avatarTed Choc <tedchoc@chromium.org>
Commit-Queue: David Turner <digit@chromium.org>
Cr-Commit-Position: refs/heads/master@{#609385}
parent b0e7619c
......@@ -172,8 +172,7 @@ def _RewriteLanguageAssetPath(src_path):
locales#<language>/<locale>.pak, where <language> is the language code
from the locale.
Returns a list of paths. The language split should be duplicated at all the
returned paths.
Returns new path.
"""
if not src_path.startswith(_LOCALES_SUBDIR) or not src_path.endswith('.pak'):
return [src_path]
......@@ -189,11 +188,16 @@ def _RewriteLanguageAssetPath(src_path):
else:
android_language = android_locale
result_paths = ['assets/locales#lang_%s/%s.pak' % (android_language, locale)]
if android_language == _FALLBACK_LANGUAGE:
result_paths.append('assets/locales/%s.pak' % locale)
# Fallback language .pak files must be placed in a different directory
# to ensure they are always stored in the base module.
result_path = 'assets/fallback-locales/%s.pak' % locale
else:
# Other language .pak files go into a language-specific asset directory
# that bundletool will store in separate split APKs.
result_path = 'assets/locales#lang_%s/%s.pak' % (android_language, locale)
return result_paths
return result_path
def _SplitModuleForAssetTargeting(src_module_zip, tmp_dir, split_dimensions):
......@@ -230,16 +234,15 @@ def _SplitModuleForAssetTargeting(src_module_zip, tmp_dir, split_dimensions):
src_path = info.filename
is_compressed = info.compress_type != zipfile.ZIP_STORED
dst_paths = [src_path]
dst_path = src_path
if src_path in language_files:
dst_paths = _RewriteLanguageAssetPath(src_path)
for dst_path in dst_paths:
build_utils.AddToZipHermetic(
dst_zip,
dst_path,
data=src_zip.read(src_path),
compress=is_compressed)
dst_path = _RewriteLanguageAssetPath(src_path)
build_utils.AddToZipHermetic(
dst_zip,
dst_path,
data=src_zip.read(src_path),
compress=is_compressed)
return tmp_zip
......
......@@ -39,6 +39,7 @@ public class ResourceExtractor {
private static final String V8_SNAPSHOT_DATA_FILENAME = "snapshot_blob.bin";
private static final String FALLBACK_LOCALE = "en-US";
private static final String COMPRESSED_LOCALES_DIR = "locales";
private static final String COMPRESSED_LOCALES_FALLBACK_DIR = "fallback-locales";
private static final int BUFFER_SIZE = 16 * 1024;
private class ExtractTask extends AsyncTask<Void> {
......@@ -173,6 +174,10 @@ public class ResourceExtractor {
//
// Where <lang> is an Android-specific ISO-639-1 language identifier.
//
// * With the exception of the fallback (English) pak files which are stored
// in the base module under:
// assets/locales-fallback/<locale>.pak
//
// Moreover, when the bundle uses APK splits, there is no guarantee that the split
// corresponding to the current device locale is installed yet, but the one matching
// uiLanguage should be there, since the value is determined by loading a resource string
......@@ -193,6 +198,10 @@ public class ResourceExtractor {
assetManager, COMPRESSED_LOCALES_DIR, activeLocales.get(0) + ".pak")) {
// This is a regular APK, and all pak files are available.
localesSrcDir = COMPRESSED_LOCALES_DIR;
} else if (assetPathHasFile(assetManager, COMPRESSED_LOCALES_FALLBACK_DIR,
activeLocales.get(0) + ".pak")) {
// This is a fallback language pak file.
localesSrcDir = COMPRESSED_LOCALES_FALLBACK_DIR;
} else {
// This is an app bundle, but the split containing the pak files for the current UI
// locale is *not* installed yet. This should never happen in theory, and there is
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment