Contenido del curso
Arquitectura y Almacenamiento de Datos
Repositorios y Gestión de Datos
Capa de Presentación y Navegación
- 12

HomeScreen con ViewModel, StateFlow y Coil
26:24 min - 13

Primera app Android con Hilt, Retrofit y Room
Viendo ahora - 14

Implementación de Barra de Navegación Inferior en Android Compose
13:05 min - 15

Creación de un Detail Screen en Jetpack Compose para Android
25:49 min - 16

Formulario de preórdenes con SharedFlow en Compose
20:02 min - 17

Lista y sincroniza preórdenes con StateFlow
23:58 min
Optimización y Flexibilidad
Primera app Android con Hilt, Retrofit y Room
Resumen
Poner a correr por primera vez una aplicación Android que integra inyección de dependencias con Hilt, llamadas remotas con Retrofit y caché local con Room suele revelar errores de imports, anotaciones mal puestas y configuraciones incompletas. Aquí aprenderás a depurar paso a paso ese flujo, conectar el home screen con el MainActivity y validar que la app funcione tanto online como offline.
Por qué fallan los imports de Singleton en Hilt
Cuando integras Hilt en un proyecto Android, el primer tropiezo común aparece al importar la anotación equivocada de Singleton. El compilador marca el error porque existen dos paquetes distintos con el mismo nombre y solo uno es válido para el grafo de dependencias.
En la clase, al compilar por primera vez, aparece el mensaje de que el scope Singleton hace referencia a un scope diferente, específicamente Jakarta Inject Singleton. La solución es reemplazar ese import por javax.inject.Singleton, que es el que Hilt reconoce.
Este mismo ajuste se repite en varios módulos del proyecto:
- El módulo Royal o de aplicación general.
- El Mapping Module que define los mapeos entre capas.
- El módulo de Retrofit para la configuración de red.
- El módulo de repositorio que conecta data con dominio.
¿Cuál es la diferencia entre Jakarta Inject Singleton y javax.inject.Singleton? Ambos definen un scope de instancia única, pero Hilt en Android usa
javax.inject.Singleton. Si importas el de Jakarta, Hilt no lo reconoce y rompe el grafo de dependencias.
Cómo agregar Provide y Singleton al módulo de Room
Una vez corregidos los imports, aparece un nuevo error relacionado con OrderDao. La causa es que el DAO no está siendo agregado al grafo de Hilt porque le faltan las anotaciones correspondientes en el módulo de database.
La regla es simple: cada función dentro del módulo que devuelve una dependencia necesita la anotación @Provides y, si quieres que la instancia se reutilice, también @Singleton. En el módulo de database hay que aplicar este patrón a las tres funciones que exponen los DAO.
Cuándo no debes usar suspend en un módulo de Hilt
Después de agregar las anotaciones, surge otro error con Preorder. La inyección como Singleton está correcta, pero la función está marcada como suspend, y eso no aplica para módulos de Hilt.
Los módulos de inyección de dependencias solo proveen instancias, no ejecutan código asíncrono. Por eso debes quitar el modificador suspend de las funciones @Provides. Las corrutinas se manejan en las capas de repositorio o ViewModel, no en el grafo de Hilt.
Cómo conectar el home screen al MainActivity
Con la aplicación compilando sin errores, el siguiente paso es reemplazar el contenido por defecto del MainActivity. En lugar del composable HelloAndroid que viene de la plantilla, se llama directamente al HomeScreen y se le pasa el Modifier con el padding.
Este cambio es el que finalmente hace visible el listado de órdenes en pantalla.
Por qué Retrofit no devuelve datos remotos
Al correr la app, el home screen aparece vacío. Para entender qué pasa, conviene ejecutar la aplicación en modo debug y recorrer el flujo desde el ViewModel hasta la implementación del repositorio.
El recorrido revela tres pistas:
- El almacén local devuelve tamaño cero porque no hay órdenes cacheadas todavía.
- La emisión de valores vacíos se ejecuta correctamente.
- La llamada remota se dispara, pero no devuelve información.
Revisando la consola, no hay tráfico HTTP saliendo del emulador. El problema está en el módulo de Retrofit: el OkHttpClient con el interceptor del logger está definido, pero nunca se le pasa a la instancia de Retrofit.
¿Qué hace el interceptor en Retrofit? Captura cada petición y respuesta HTTP para mostrarla en consola. Si no se conecta al cliente y este no se le pasa al builder de Retrofit, las llamadas se hacen pero no se loguean ni se configuran correctamente.
Cómo agregar Moshi y el cliente al builder de Retrofit
La corrección tiene dos partes. Primero, pasar el OkHttpClient configurado al builder de Retrofit. Segundo, agregar la instancia de Moshi con su factory dentro del addConverterFactory.
Un detalle importante es importar la factory correcta de Moshi, ya que existen variantes y elegir la equivocada vuelve a romper la deserialización.
Con ambos ajustes, la app conecta al servicio remoto, devuelve un código 200 y renderiza las órdenes con un estado de loading mientras carga las imágenes.
Cómo probar la app en modo offline con caché de Room
La prueba final valida que la arquitectura de capas funcione cuando no hay red. Activando el modo avión en el emulador y reabriendo la aplicación, los ítems deben renderizarse igual porque ya quedaron almacenados en la base de datos local.
Esto confirma que la estrategia de cache-first con Room responde correctamente: si hay datos locales, se muestran sin depender del servicio remoto.
¿Te ha pasado algún error similar al integrar Hilt con Retrofit y Room? Cuéntame en los comentarios cómo lo resolviste.