Generalidades

Cómo redujimos el tiempo de construcción de Gradle en más del 80% | Autor: Adam Ahmed | Noviembre de 2021

Adam Ahmed
Fuente de la imagen: Gradle

Cuando me uní a mi empresa actual hace unos meses, me tomó un promedio de 14 minutos construir nuestra aplicación de Android en mi máquina. Puedes imaginar lo ineficiente que me hace sentir esto, así que comencé el viaje de acelerarlo.

Ahora está reducido a aproximadamente 2 minutos, por lo que compartiré algunas de las cosas que aprendí en el proceso, pero no aplique ciegamente estos cambios a su proyecto, use el generador de perfiles de Gradle para asegurarse de que se apliquen a su configuración existente. Diferentes cosas se aplican a diferentes proyectos.

  1. Use la última versión de las herramientas y complementos que usa en su proyecto

Solíamos Al usar AGP 4.2 y actualizar a AGP 7, pudimos aprovechar las mejoras de rendimiento prometidas en Gradle 7, lo que nos lleva al siguiente punto.

2. Habilite la supervisión del sistema de archivos

Si ya está usando AGP 7, omita esta sección, pero si insiste en usar una versión entre esta versión y AGP 4.1, debe habilitar manualmente la supervisión del sistema de archivos. Le permite a Gradle almacenar información sobre las entradas y salidas de las tareas que han cambiado entre compilaciones, para que pueda determinar qué tareas volver a ejecutar. Sin él, no puede saber si se han producido cambios entre compilaciones y tiene que realizar un trabajo de E / S innecesario para resolverlo nuevamente.

Puedes agregarlo a tu gradle.properties texto

org.gradle.vfs.watch=true

3. Habilite la configuración bajo demanda

Esto es útil para proyectos de varios módulos porque intenta configurar solo los módulos relacionados con las tareas que está ejecutando, en lugar de configurar todo el proyecto para cada tarea. Sin embargo, actualmente sigue siendo una función de incubación, por lo que puede que no sea adecuada para su proyecto.Puedes leer más sobre esto aquí

Puedes agregarlo a tu gradle.properties texto

org.gradle.configureondemand=true

4. Habilite la ejecución paralela

Si está trabajando en un proyecto de varios módulos, obligar a Gradle a ejecutar tareas en paralelo también es una simple mejora del rendimiento. Debe tenerse en cuenta que sus tareas en diferentes módulos deben ser independientes y no puede acceder al estado compartido, no debe hacerlo en ningún caso.

Puedes agregarlo a tu gradle.properties texto

org.gradle.parallel=true

5. Habilite la creación de caché

Si la entrada no ha cambiado, esto funciona almacenando y reutilizando la salida producida por otras compilaciones. Una de las funciones es el almacenamiento en caché de resultados de tareas.Utiliza el existente de Gradle UP_TO_DATE Verifique, pero no solo reutilice la salida de la compilación más reciente en la misma máquina, le permite a Gradle reutilizar la salida de cualquier compilación anterior en cualquier lugar de la máquina. Cuando se utiliza una memoria caché de compilación compartida para el almacenamiento en caché de salida de tareas, esto puede funcionar incluso en máquinas de desarrollo y agentes de compilación, por lo que puede compartir la misma caché con sus colegas y CI. Nelson Ozaki Escribió una gran serie sobre los beneficios y precauciones de usar el almacenamiento en caché de compilación remota aquí

Puedes agregarlo a tu gradle.properties texto

org.gradle.caching=true

Antes de continuar con la siguiente parte, aquí hay un inicio rápido del ciclo de vida de la compilación de Gradle. Esto es importante, por lo que comprendemos los ahorros que obtendremos de los siguientes puntos.

Cada compilación de Gradle tiene 3 etapas:

  • inicialización: Aquí es donde Gradle decide qué módulos participarán en la compilación y crea un project Ejemplos de cada uno de ellos.
  • Configuración: Esto es cuando se configura el objeto del proyecto y se ejecutan todos los scripts de compilación de todos los proyectos que forman parte de la compilación. Esta etapa es donde debe prestar más atención, porque se ejecutará cada vez que compile, por lo que si inicia una solicitud de red aquí por alguna razón, no lo haga.
  • implementar: Como sugiere el nombre, aquí es donde Gradle ejecuta las tareas creadas y configuradas previamente.

Ahora comience con algunas sugerencias aleatorias, ¡sin importancia especial!

6. Piense detenidamente en los complementos que agrega a su proyecto.

Cada complemento que agrega al proyecto agrega tiempo a la fase de configuración, incluso si no hace nada. Por lo tanto, explore los complementos y elimine los complementos que no utilice.

7. Si usa complementos de monitoreo de rendimiento de Crashlytics o Firebase, desactívelos para depurar compilaciones.

Nosotros vimos Un montón de Mejore haciendo estos cambios.

android 
……
buildTypes
debug
ext.enableCrashlytics = false
FirebasePerformance
instrumentationEnabled false



También debe deshabilitar Crashlytics para la versión de depuración en tiempo de ejecución, de la siguiente manera:

FirebaseCrashlytics.getInstance().setCrashlyticsCollectionEnabled(!BuildConfig.DEBUG)

8. Convierta la lógica de compilación en una tarea estática.

Si tienes mucha lógica build.gradle Scripts, considere convertirlos en tareas estáticas de Gradle para que Gradle pueda almacenar en caché sus resultados y reducir su impacto en el tiempo de la fase de configuración del proyecto.Por ejemplo, si tiene el código para determinar versionName Basado en la rama actual de Github, esta es una buena opción.Mientras discutimos este tema, siempre verifique y asegúrese de que su build.gradle El guión es lo más conciso posible. De esta manera, eliminamos algunas tareas heredadas / fragmentos de código que ya no tienen sentido dentro del alcance de nuestro proyecto.

9. Mueva las secuencias de comandos y las tareas a su directorio buildSrc

Como mencionamos anteriormente, esto puede limpiar su build.gradle Scripts, pero también le permite reutilizar fácilmente estas tareas en diferentes módulos. Puede leer el directorio buildSrc aquí, escribir scripts aquí y escribir tareas aquí.

10. Utilice la configuración para evitar

Ahora que está escribiendo su propia secuencia de comandos de Gradle, debe comprender cómo evitar la configuración. Cuando estas tareas no se ejecutarán, le permite a Gradle evitar la creación / configuración de tareas durante la fase de configuración. Por ejemplo, cuando se ejecuta una tarea de compilación, no se ejecutarán otras tareas no relacionadas, como la calidad del código, las pruebas y las tareas de publicación, por lo que el tiempo dedicado a crear y configurar estas tareas es innecesario. Puede registrar sus tareas primero en lugar de crearlas con entusiasmo, pero al leer el documento vinculado anteriormente, puede aprender más sobre la creación efectiva de tareas. Las tareas registradas son conocidas por la compilación, pero solo se configuran cuando es necesario ejecutarlas. Mira estas dos tareas:

task mySlowTask 
sleep 2000
doLast
println "This task will add 2 seconds to your configuration phase every time you run any task"

tasks.register("mySlowTask")
sleep 2000
doLast
println "This task won't add much time to your build unless you specifically execute it or any tasks that depend on it"

11. Si está utilizando JDK 9+, habilite el recolector de basura paralelo

Es posible que desee analizar este cambio antes de habilitarlo para su proyecto, pero puede habilitarlo agregando una cadena -XX:+UseParallelGC Para ti org.gradle.jvmargs= dentro gradle.properties Script, o si no ha personalizado estas configuraciones antes, simplemente agregue la siguiente línea allí.

org.gradle.jvmargs=-XX:+UseParallelGC

12. Utilice doctor-gradle insertar

Sé que acabo de decir que realmente debería pensarlo antes de agregar un complemento a su proyecto, pero el único propósito es mejorar su compilación advirtiéndole sobre los problemas que encuentra en el proyecto, y puede eliminarlo cuando haya terminado.

13. Habilite la clase R no transitiva

Hacerlo ayuda a prevenir la duplicación de recursos y asegura que la clase R de cada módulo solo contenga referencias a sus propios recursos y no extraiga referencias de sus dependencias.Esto conduce a más UP_TO_DATE Los correspondientes beneficios de construir y evitar la compilación.

Esta es una excelente publicación de blog sobre esto. Brundle

14. Habilite la caché de configuración

Esta es una función experimental, así que proceda con precaución, pero puedo confirmar que es absolutamente mágica para nosotros. ¿Recuerda la fase de configuración de la que hablamos anteriormente? Bueno, esta función almacena en caché sus resultados y los reutiliza para compilaciones posteriores, de manera similar a la forma de crear una caché y reutilizar la salida de la tarea.Puede agregar la siguiente línea a su gradle.properties Script, pero léalo aquí primero.

org.gradle.unsafe.configuration-cache=true

15. Desactivar Jetifier

La herramienta jetifier básicamente reemplazada android.support Bibliotecas y sus equivalentes androidx Versión, pero también agregará mucho tiempo a su fase de configuración. Si no lo necesita, este es un simple impulso de rendimiento.

Esta excelente publicación de blog proviene de Adam Bennett Le ayudará a determinar si Jetifier se puede eliminar del proyecto y describirá las mejoras que su equipo ha visto al hacerlo.

16. Inhabilita las variantes de compilación que no usas.

Gradle crea una variante de compilación para cada combinación posible de estilo de producto y tipo de compilación que configure, pero puede haber algunas variantes que no necesite o que no tengan ningún significado en el contexto de su proyecto.Puede eliminar estas configuraciones de variantes de compilación creando filtros de variantes a nivel de módulo build.gradle Este es un ejemplo de cómo deshabilitar la variante mockRelease en caso de que no desee construirla.

android 
………
buildTypes
debug …
release …

productFlavors
mock …
full …

variantFilter variant ->
def names = variant.flavors*.name
def isReleaseBuildType = variant.buildType.name == "release"
if(names.contains("mock") && isReleaseBuildType)
setIgnore(true)


17. Si usa Github Actions en CI, considere Gradle Build Action

Al usar la operación de compilación de Gradle, pudimos reducir a la mitad el tiempo total de ejecución de CI de todos los empujes consecutivos a la misma rama, porque puede almacenar en caché correctamente los resultados de las ejecuciones anteriores, que es completamente diferente de la operación de almacenamiento en caché de Github para nosotros fuera de la caja.

Muchísimas gracias Adam Bennett con Vladimir Jovanovic ¡Gracias por su ayuda en la revisión de esta publicación de blog!

¡Eso es todo!Comparta esta publicación de blog para difundir conocimientos

Agrégame LinkedIn con Gorjeo ¡Habla sobre Gradle y Android! 🙂

LEER  Dead Target MOD APK Medio

Publicaciones relacionadas

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *

Botón volver arriba