Создайте несколько APK для разных уровней API.

Если вы публикуете свое приложение в Google Play, вам необходимо создать и загрузить пакет Android App Bundle . Когда вы это сделаете, Google Play автоматически создаст и предоставит оптимизированные APK-файлы для конфигурации устройства каждого пользователя, поэтому они загружают только тот код и ресурсы, которые им необходимы для запуска вашего приложения. Публикация нескольких APK-файлов полезна, если вы не публикуете их в Google Play, но вам необходимо самостоятельно создавать, подписывать и управлять каждым APK-файлом.

При разработке приложения для Android с использованием нескольких APK-файлов в Google Play важно с самого начала принять некоторые передовые методы и избежать ненужных головных болей в дальнейшем процессе разработки. В этом уроке показано, как создать несколько APK-файлов вашего приложения, каждый из которых охватывает несколько отличающийся диапазон уровней API. Вы также получите некоторые инструменты, необходимые для того, чтобы максимально упростить поддержку нескольких кодовых баз APK.

Подтвердите, что вам нужно несколько APK

Пытаясь создать приложение, которое работает на нескольких поколениях платформы Android, естественно, вы хотите, чтобы ваше приложение использовало преимущества новых функций на новых устройствах, не жертвуя при этом обратной совместимостью. Поначалу может показаться, что поддержка нескольких APK — лучшее решение, но зачастую это не так. Раздел «Использование одного APK вместо» руководства для разработчиков нескольких APK содержит полезную информацию о том, как сделать это с помощью одного APK, включая использование нашей библиотеки поддержки. Из этой статьи вы также можете узнать, как писать код, который работает только на определенных уровнях API, в одном APK, не прибегая к дорогостоящим в вычислительном отношении методам, таким как отражение.

Если вы можете справиться с этим, ограничение вашего приложения одним APK-файлом имеет ряд преимуществ, в том числе:

  • Публикация и тестирование стали проще
  • Требуется поддерживать только одну кодовую базу
  • Ваше приложение может адаптироваться к изменениям конфигурации устройства.
  • Восстановление приложений на всех устройствах просто работает
  • Вам не нужно беспокоиться о рыночных предпочтениях, поведении при «обновлениях» с одного APK на другой или о том, какой APK подходит к какому классу устройств.

В оставшейся части этого урока предполагается, что вы изучили тему, тщательно усвоили материал из связанных ресурсов и определили, что несколько APK — это правильный путь для вашего приложения.

Напишите свои требования

Начните с создания простой диаграммы, чтобы быстро определить, сколько APK вам нужно и какой диапазон API охватывает каждый APK. Для удобства на странице «Версии платформы» веб-сайта разработчиков Android представлены данные об относительном количестве активных устройств, на которых установлена ​​данная версия платформы Android. Кроме того, хотя на первый взгляд это кажется простым, отслеживание того, на какой набор уровней API будет нацелен каждый APK, довольно быстро становится затруднительным, особенно если будет некоторое совпадение (а оно часто бывает). К счастью, ваши требования можно легко и быстро сформулировать и иметь под рукой справочную информацию на будущее.

Чтобы создать диаграмму из нескольких APK, начните с ряда ячеек, представляющих различные уровни API платформы Android. Добавьте в конце дополнительную ячейку, обозначающую будущие версии Android.

3 4 5 6 7 8 9 10 11 12 13 +

Теперь просто раскрасьте диаграмму так, чтобы каждый цвет представлял APK. Вот один из примеров того, как можно применить каждый APK к определенному диапазону уровней API.

3 4 5 6 7 8 9 10 11 12 13 +

Создав эту диаграмму, раздайте ее своей команде. Общение в команде по вашему проекту сразу стало проще, поскольку вместо вопросов «Как дела с APK для уровней API с 3 по 6, ну, вы знаете, для Android 1.x. Как продвигаются дела?» Вы можете просто сказать: «Как продвигается работа над Blue APK?»

Поместите весь общий код и ресурсы в проект библиотеки.

Изменяете ли вы существующее приложение Android или запускаете его с нуля, это первое, что вам следует сделать с базой кода, и, безусловно, самое важное. Все, что входит в проект библиотеки, необходимо обновить только один раз (например, строки, локализованные на языке, цветовые темы, исправленные ошибки в общем коде), что сокращает время разработки и снижает вероятность ошибок, которых можно было бы легко избежать.

Примечание. Подробности реализации создания и включения проектов библиотек выходят за рамки этого урока, но вы можете быстро освоиться, прочитав «Создание библиотеки Android» .

Если вы конвертируете существующее приложение для использования поддержки нескольких APK, просмотрите свою кодовую базу на предмет каждого локализованного строкового файла, списка значений, цветов темы, значков меню и макета, которые не будут меняться в разных APK, и поместите все это в файл APK. проект библиотеки. Код, который не будет сильно меняться, также должен быть включен в проект библиотеки. Скорее всего, вы расширите эти классы, добавив один или два метода из APK в APK.

С другой стороны, если вы создаете приложение с нуля, постарайтесь сначала как можно больше написать код в проекте библиотеки, а затем при необходимости переместите его в отдельный APK. В долгосрочной перспективе с этим гораздо проще справиться, чем добавлять его в один, затем в другой, затем в третий, а затем месяцами позже пытаться выяснить, можно ли переместить этот большой объект в раздел библиотеки, не испортив ничего.

Создавайте новые проекты APK

Для каждого APK, который вы собираетесь выпустить, должен быть отдельный проект Android. Для упрощения организации поместите проект библиотеки и все связанные проекты APK в одну родительскую папку. Также помните, что каждый APK должен иметь одно и то же имя пакета, хотя им не обязательно передавать имя пакета вместе с библиотекой. Если бы у вас было 3 APK-файла по схеме, описанной ранее, ваш корневой каталог мог бы выглядеть следующим образом:

alexlucas:~/code/multi-apks-root$ ls
foo-blue
foo-green
foo-lib
foo-red

После создания проектов добавьте проект библиотеки в качестве ссылки на каждый проект APK. Если возможно, определите начальное действие в проекте библиотеки и расширьте это действие в проекте APK. Наличие стартового действия, определенного в проекте библиотеки, дает вам возможность разместить всю инициализацию вашего приложения в одном месте, так что каждому отдельному APK не придется повторно реализовывать «универсальные» задачи, такие как инициализация Analytics, запуск проверок лицензии и т. д. другие процедуры инициализации, которые не сильно меняются от APK к APK.

Настройте манифесты

Когда пользователь загружает приложение, использующее несколько APK-файлов, через Google Play, правильный APK-файл выбирается с использованием двух простых правил:

  • В манифесте должно быть указано, что конкретный APK соответствует требованиям.
  • Из подходящих APK-файлов побеждает наивысший номер версии.

В качестве примера возьмем описанный ранее набор из нескольких APK и предположим, что мы не установили максимальный уровень API ни для одного из APK. В отдельности возможный диапазон каждого APK будет выглядеть следующим образом:

3 4 5 6 7 8 9 10 11 12 13 +
3 4 5 6 7 8 9 10 11 12 13 +
3 4 5 6 7 8 9 10 11 12 13 +

Поскольку требуется, чтобы APK с более высоким значением minSdkVersion также имел более высокий код версии, мы знаем, что с точки зрения значений versionCode красный ≥ зеленый ≥ синий. Поэтому мы можем эффективно свернуть диаграмму, чтобы она выглядела так:

3 4 5 6 7 8 9 10 11 12 13 +

Теперь давайте предположим, что у Red APK есть некоторые требования, которых нет у двух других. Фильтры на странице Google Play руководства для разработчиков Android содержат целый список возможных виновников. Для примера предположим, что для красного цвета требуется фронтальная камера. Фактически, весь смысл красного APK-файла состоит в том, чтобы объединить фронтальную камеру с новыми приятными функциями, которые были добавлены в API 11. Но оказывается, что не все устройства, поддерживающие API 11, даже ЕСТЬ фронтальные камеры! Ужас!

К счастью, если пользователь просматривает Google Play с одного из таких устройств, Google Play просмотрит манифест, увидит, что Red указывает наличие фронтальной камеры в качестве требования, и спокойно проигнорирует это, определив, что Red и это устройство не являются обязательными. матч, созданный на цифровом раю. Затем он увидит, что Green не только совместим с устройствами с API 11 (поскольку maxSdkVersion не был определен), но также не заботится о том, есть ли фронтальная камера! Пользователь по-прежнему может загрузить приложение из Google Play, потому что, несмотря на всю неудачу с фронтальной камерой, все еще существовал APK, который поддерживал этот конкретный уровень API.

Чтобы все ваши APK-файлы находились на отдельных «дорожках», важно иметь хорошую схему кода версии. Рекомендуемый вариант можно найти в разделе «Коды версий» нашего руководства для разработчиков. Поскольку примерный набор APK имеет дело только с одним из трех возможных измерений, было бы достаточно разделить каждый APK на 1000, установить первые пару цифр в minSdkVersion для этого конкретного APK и увеличить его. Это может выглядеть так:

Синий: 03001, 03002, 03003, 03004...
Зеленый: 07001, 07002, 07003, 07004...
Красный: 11001, 11002, 11003, 11004...

Если сложить все это вместе, ваши манифесты Android, скорее всего, будут выглядеть примерно так:

Синий:

<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    android:versionCode="03001" android:versionName="1.0" package="com.example.foo">
    <uses-sdk android:minSdkVersion="3" />
    ...

Зеленый:

<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    android:versionCode="07001" android:versionName="1.0" package="com.example.foo">
    <uses-sdk android:minSdkVersion="7" />
    ...

Красный:

<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    android:versionCode="11001" android:versionName="1.0" package="com.example.foo">
    <uses-sdk android:minSdkVersion="11" />
    ...

Просмотрите контрольный список перед запуском

Перед загрузкой в ​​Google Play дважды проверьте следующие пункты. Помните, что они относятся конкретно к нескольким APK-файлам и никоим образом не представляют собой полный контрольный список для всех приложений, загружаемых в Google Play.

  • Все APK-файлы должны иметь одинаковое имя пакета.
  • Все APK должны быть подписаны одним и тем же сертификатом.
  • Если APK-файлы перекрываются по версии платформы, файл с более высоким minSdkVersion должен иметь более высокий код версии.
  • Дважды проверьте фильтры манифеста на предмет противоречивой информации (APK, который поддерживает только кексы на экранах XLARGE, никто не увидит).
  • Манифест каждого APK должен быть уникальным хотя бы для одной поддерживаемой версии экрана, текстуры OpenGL или версии платформы.
  • Попробуйте протестировать каждый APK хотя бы на одном устройстве. За исключением этого, на вашей машине разработки находится один из самых настраиваемых эмуляторов устройств в отрасли. С ума сойти!

Также стоит проверить скомпилированный APK перед выпуском на рынок, чтобы убедиться в отсутствии каких-либо сюрпризов, которые могут скрыть ваше приложение в Google Play. На самом деле это довольно просто с помощью инструмента «aapt». Aapt (инструмент упаковки ресурсов Android) — это часть процесса сборки для создания и упаковки приложений Android, а также очень удобный инструмент для их проверки.

>aapt dump badging
package: name='com.example.hello' versionCode='1' versionName='1.0'
sdkVersion:'11'
uses-permission:'android.permission.SEND_SMS'
application-label:'Hello'
application-icon-120:'res/drawable-ldpi/icon.png'
application-icon-160:'res/drawable-mdpi/icon.png'
application-icon-240:'res/drawable-hdpi/icon.png'
application: label='Hello' icon='res/drawable-mdpi/icon.png'
launchable-activity: name='com.example.hello.HelloActivity'  label='Hello' icon=''
uses-feature:'android.hardware.telephony'
uses-feature:'android.hardware.touchscreen'
main
supports-screens: 'small' 'normal' 'large' 'xlarge'
supports-any-density: 'true'
locales: '--_--'
densities: '120' '160' '240'

Когда вы проверяете выходные данные aapt, обязательно убедитесь, что у вас нет конфликтующих значений для support-screens и совместимых-screens, а также что у вас нет непреднамеренных значений «uses-feature», которые были добавлены в результате разрешений, которые вы установлен в манифесте. В приведенном выше примере APK не будет виден многим устройствам.

Почему? Добавление необходимого разрешения SEND_SMS неявно добавило требование к функции android.hardware.telephony. Поскольку API 11 — это Honeycomb (версия Android, оптимизированная специально для планшетов), и ни одно из устройств Honeycomb не имеет телефонного оборудования, Google Play будет отфильтровывать этот APK во всех случаях, пока не появятся будущие устройства с более высоким уровнем API И обладающие телефонное оборудование.

К счастью, это легко исправить, добавив в манифест следующее:

<uses-feature android:name="android.hardware.telephony" android:required="false" />

Требование android.hardware.touchscreen также добавляется неявно. Если вы хотите, чтобы ваш APK был виден на телевизорах без сенсорного экрана, вам следует добавить в свой манифест следующее:

<uses-feature android:name="android.hardware.touchscreen" android:required="false" />

Заполнив контрольный список перед запуском, загрузите APK-файлы в Google Play. Приложению может потребоваться некоторое время, чтобы оно появилось при просмотре Google Play, но когда это произойдет, выполните последнюю проверку. Загрузите приложение на любые имеющиеся у вас тестовые устройства, чтобы убедиться, что APK-файлы предназначены для нужных устройств. Поздравляем, все готово!