Inicialização do app Parte do Android Jetpack.
A biblioteca App Startup fornece uma maneira simples e eficiente de iniciar componentes na inicialização do aplicativo. Tanto os desenvolvedores de bibliotecas quanto os desenvolvedores de apps podem usar a inicialização para simplificar as sequências e definir explicitamente a ordem de inicialização.
Em vez de definir provedores de conteúdo separados para cada componente que você precisa inicializar, a inicialização do app permite definir inicializadores de componentes que compartilham um único provedor de conteúdo. Isso melhora significativamente o tempo de inicialização do app.
Configurar
Para usar o Jetpack Startup na sua biblioteca ou app, adicione o código abaixo ao arquivo Gradle:
Groovy
dependencies { implementation "androidx.startup:startup-runtime:1.1.1" }
Kotlin
dependencies { implementation("androidx.startup:startup-runtime:1.1.1") }
Inicializar componentes na inicialização do app
Apps e bibliotecas geralmente dependem da inicialização de componentes imediatamente quando o app é iniciado. É possível atender a essa necessidade usando provedores de conteúdo para inicializar cada dependência, mas eles são caros de instanciar e podem atrasar a sequência de inicialização desnecessariamente. Além disso, o Android inicializa provedores de conteúdo em uma ordem indeterminada. A inicialização do app oferece uma maneira mais eficiente de inicializar componentes na inicialização do app e definir explicitamente as dependências deles.
Para usar a inicialização do app para inicializar componentes automaticamente na inicialização, é necessário definir um inicializador de componente para cada componente que o app precisa inicializar.
Implementar inicializadores de componente
Para definir cada inicializador de componente, crie uma classe que implemente a
interface Initializer<T>
.
Essa interface define dois métodos importantes:
- O método
create()
, que contém todas as operações necessárias para inicializar o componente e retorna uma instância deT
. - O método
dependencies()
, que retorna uma lista dos outros objetosInitializer<T>
de que o inicializador depende. Você pode usar esse método para controlar a ordem em que o app executa os inicializadores na inicialização.
Por exemplo, suponha que seu app dependa de
WorkManager
e precise
inicializá-lo na inicialização. Defina uma classe WorkManagerInitializer
que
implemente Initializer<WorkManager>
:
Kotlin
// Initializes WorkManager. class WorkManagerInitializer : Initializer<WorkManager> { override fun create(context: Context): WorkManager { val configuration = Configuration.Builder().build() WorkManager.initialize(context, configuration) return WorkManager.getInstance(context) } override fun dependencies(): List<Class<out Initializer<*>>> { // No dependencies on other libraries. return emptyList() } }
Java
// Initializes WorkManager. class WorkManagerInitializer implements Initializer<WorkManager> { @Override public WorkManager create(Context context) { Configuration configuration = Configuration.Builder().build(); WorkManager.initialize(context, configuration); return WorkManager.getInstance(context); } @Override public List<Class<Initializer<?>>> dependencies() { // No dependencies on other libraries. return emptyList(); } }
O método dependencies()
retorna uma lista vazia porque WorkManager
não
depende de outras bibliotecas.
Suponha que seu app também dependa de uma biblioteca com o nome ExampleLogger
, que,
por sua vez, depende de WorkManager
. Essa dependência significa que você precisa garantir
que a inicialização do app inicialize WorkManager
primeiro. Defina uma
classe ExampleLoggerInitializer
que implemente Initializer<ExampleLogger>
:
Kotlin
// Initializes ExampleLogger. class ExampleLoggerInitializer : Initializer<ExampleLogger> { override fun create(context: Context): ExampleLogger { // WorkManager.getInstance() is non-null only after // WorkManager is initialized. return ExampleLogger(WorkManager.getInstance(context)) } override fun dependencies(): List<Class<out Initializer<*>>> { // Defines a dependency on WorkManagerInitializer so it can be // initialized after WorkManager is initialized. return listOf(WorkManagerInitializer::class.java) } }
Java
// Initializes ExampleLogger. class ExampleLoggerInitializer implements Initializer<ExampleLogger> { @Override public ExampleLogger create(Context context) { // WorkManager.getInstance() is non-null only after // WorkManager is initialized. return ExampleLogger(WorkManager.getInstance(context)); } @Override public List<Class<Initializer<?>>> dependencies() { // Defines a dependency on WorkManagerInitializer so it can be // initialized after WorkManager is initialized. return Arrays.asList(WorkManagerInitializer.class); } }
Como você inclui WorkManagerInitializer
no método dependencies()
, a
inicialização do app inicializa o WorkManager
antes de ExampleLogger
.
Configurar entradas de manifesto
A inicialização do app inclui um provedor de conteúdo especial chamado InitializationProvider
,
que ele usa para descobrir e chamar os inicializadores de componentes. A inicialização
do app descobre inicializadores de componentes ao verificar primeiro se há uma entrada <meta-data>
na entrada de manifesto InitializationProvider
. Em seguida, a inicialização do app chama os
métodos dependencies()
para qualquer inicializador que já tenha sido descoberto.
Isso significa que, para que um inicializador de componente seja detectável pela inicialização do app, uma das seguintes condições precisa ser atendida:
- O inicializador do componente tem uma entrada
<meta-data>
correspondente na entrada do manifestoInitializationProvider
. - O inicializador de componente é listado no método
dependencies()
de um inicializador que já é detectável.
Considere novamente o exemplo com WorkManagerInitializer
e
ExampleLoggerInitializer
. Para garantir que a inicialização do app possa detectar esses
inicializadores, adicione o seguinte ao arquivo de manifesto:
<provider
android:name="androidx.startup.InitializationProvider"
android:authorities="${applicationId}.androidx-startup"
android:exported="false"
tools:node="merge">
<!-- This entry makes ExampleLoggerInitializer discoverable. -->
<meta-data android:name="com.example.ExampleLoggerInitializer"
android:value="androidx.startup" />
</provider>
Não é necessário adicionar uma entrada <meta-data>
para WorkManagerInitializer
,
porque WorkManagerInitializer
é uma dependência de ExampleLoggerInitializer
.
Isso significa que, se ExampleLoggerInitializer
for detectável, WorkManagerInitializer
também será.
O atributo tools:node="merge"
garante que a ferramenta de combinação
de manifestos resolva corretamente todas as entradas conflitantes.
Executar verificações de lint
A biblioteca App Startup inclui um conjunto de regras de lint que podem ser usadas para verificar
se você definiu os inicializadores de componentes corretamente. Você pode realizar
essas verificações de lint executando ./gradlew :app:lintDebug
na linha de comando.
Inicializar componentes manualmente
Normalmente, ao usar a inicialização do app, o objeto InitializationProvider
usa uma
entidade chamada
AppInitializer
para
descobrir e executar automaticamente inicializadores de componentes na inicialização do aplicativo.
No entanto, você também pode usar AppInitializer
diretamente para inicializar
manualmente componentes que não são necessários para o app na inicialização. Isso é chamado de
inicialização lenta e pode ajudar a minimizar os custos de inicialização.
Primeiro, desative a inicialização automática de todos os componentes que você quiser inicializar manualmente.
Desativar a inicialização automática de um componente individual
Para desativar a inicialização automática de um único componente, remova do manifesto a entrada
<meta-data>
do inicializador desse componente.
Por exemplo, adicionar o código abaixo ao arquivo de manifesto desativa a inicialização
automática de ExampleLogger
:
<provider
android:name="androidx.startup.InitializationProvider"
android:authorities="${applicationId}.androidx-startup"
android:exported="false"
tools:node="merge">
<meta-data android:name="com.example.ExampleLoggerInitializer"
tools:node="remove" />
</provider>
Use tools:node="remove"
na entrada em vez de simplesmente remover a entrada
para garantir que a ferramenta de combinação também remova a entrada de todos os outros
arquivos de manifesto integrados.
Desativar a inicialização automática para todos os componentes
Para desativar toda a inicialização automática, remova toda a entrada de
InitializationProvider
do manifesto:
<provider
android:name="androidx.startup.InitializationProvider"
android:authorities="${applicationId}.androidx-startup"
tools:node="remove" />
Chamar inicializadores de componente manualmente
Se a inicialização automática estiver desativada para um componente, será possível usar
AppInitializer
para inicializar manualmente esse componente e as dependências dele.
Por exemplo, o código a seguir chama AppInitializer
e inicializa manualmente
ExampleLogger
:
Kotlin
AppInitializer.getInstance(context) .initializeComponent(ExampleLoggerInitializer::class.java)
Java
AppInitializer.getInstance(context) .initializeComponent(ExampleLoggerInitializer.class);
Como resultado, a Inicialização do app também inicializa WorkManager
porque WorkManager
é
uma dependência de ExampleLogger
.
Enviar feedback
Envie comentários e ideias usando os recursos abaixo:
- Issue tracker
- Informe os problemas para que possamos corrigir os bugs.
Recomendados para você
- Observação: o texto do link aparece quando o JavaScript está desativado.
- Arquitetura do app: camada de dados – Agendar tarefas com o WorkManager – Desenvolvedores Android
- Arquitetura do app: camada de dados – DataStore – Desenvolvedores Android