Join FlipAndroid.COM Telegram Group: https://t.me/joinchat/F_aqThGkhwcLzmI49vKAiw


Reino que causa un montón de ANR

En mis propias pruebas no encontré este problema, pero una vez que se publicó mi aplicación, las ANR comenzaron a inundarse. Mi aplicación tiene actualmente 22 ANR, y algunas se reportan como 100 veces. Todas las trazas parecen ser de intentar crear una nueva instancia de Realm en el subproceso de interfaz de usuario.

"main" prio=5 tid=1 MONITOR | group="main" sCount=1 dsCount=0 obj=0x4183ede0 self=0x417548b8 | sysTid=19680 nice=0 sched=0/0 cgrp=apps handle=1073975684 | state=S schedstat=( 2816413167 710323137 3658 ) utm=215 stm=66 core=1 at io.realm.Realm.createAndValidate(Realm.java:~495) - waiting to lock <0x41df9c98> held by tid=12 (IntentService[UASyncService]) at io.realm.Realm.create(Realm.java:486) at io.realm.Realm.getInstance(Realm.java:404) at io.realm.Realm.getInstance(Realm.java:366) at io.realm.Realm.getInstance(Realm.java:347) 

Creo que la raíz de este problema es, como mencionó Beeender, que tengo una transacción de Realm abierta en un subproceso de trabajo que está bloqueando mis intentos de obtener una instancia de Realm en el subproceso de interfaz de usuario que produce ANR.

Actualizaré más tarde después de que tenga una solución.

* Editar: Añadido información actualizada.

  • Cómo configurar el incremento automático de clave principal en el reino de Android
  • Realm java sort con varios campos
  • Cómo cerrar el reino abierto por Realm.getDefaultInstance?
  • Borrar la base de datos predeterminada de Android Realm
  • RealmDb: Arquitectura limpia en Android
  • Realm Auto Incremento campo ejemplo
  • Realm.io - ¿Cómo actualizar el objeto?
  • Resultados de Limit Realm
  • 2 Solutions collect form web for “Reino que causa un montón de ANR”

    Realm ya no tiene este problema.

    Para referencia mi solución en el momento era:

    Gracias a beeender por señalarme en la dirección correcta y vincular esta PR https://github.com/realm/realm-java/pull/1297

    Problema

    Cuando hay una transacción de Realm pendiente, cualquier llamada a Realm.getInstance en un subproceso diferente se bloqueará hasta que se haya confirmado o cancelado la transacción pendiente.

    En mi caso tengo un IntentService que rellena mi Realm con datos de usuario existentes, mientras tanto intento mostrar cualquier información actual consultando Realm en el subproceso de UI. Aunque las consultas son simples y no causan ningún problema con normalidad, si hay una transacción pendiente en IntentService, se bloqueará Bloqueando el Realm.getInstance interfaz de usuario, llamando a Realm.getInstance , causando potencialmente una ANR.

    Mi primera tentativa en una solución era tirar de la rama del PR del beeender y crear un tarro. Creo que este arreglo me hizo un paso más allá, permitiendo que la instancia de Realm se creara sin bloquear, pero el subproceso de interfaz de usuario todavía estaba bloqueado por pequeñas transacciones que estaba intentando realizar en el subproceso de interfaz de usuario.

    Solución

    La solución que implementé implica varios pasos:

    • Crear objetos duplicados para todos mis modelos. Los duplicados no extienden RealmObject (ya que RealmObjects no se puede utilizar en todos los subprocesos).
    • Mueva todos los accesos a Realm en subprocesos de fondo. Básicamente, envolvió mis consultas en AsyncTasks y agregó a los oyentes que devuelven la versión no RealmObject del modelo.
    • Realizar transacciones más pequeñas en vez de menos transacciones grandes. Cuando anteriormente comencé y cometí transacciones a ambos lados de un bucle que creó muchos nuevos RealmObjects, ahora empiezo y comprometo la transacción por objeto. El propósito de esto es reducir el tiempo total ininterrumpido que Realm puede estar en un estado de transacción abierta para que mis consultas que proporcionan datos para la interfaz de usuario puedan completarse sin tener que esperar tanto tiempo.

    Conclusión

    Inicialmente estaba dudando en usar Realm debido a que todavía está en beta, así como la advertencia de que RealmObjects no se puede utilizar a través de hilos. Después de algunas pruebas me sentí seguro de que podría realizar consultas simples en el hilo de la interfaz de usuario sin problema (todavía con una sensación de culpabilidad en mi intestino sin embargo.)

    Overall Realm es un gran proyecto para vigilar, pero siento que no está listo para proyectos comerciales a gran escala. El uso de Realm en este proyecto puede haber ahorrado algo de tiempo por adelantado, pero le costó a muchos clientes disgustados y un problema difícil de diagnosticar.

    * Editar: Edición aclarada.

    El ejemplo de introducción de Realm les muestra usando un AsyncTask para hacer sus lecturas y escrituras.

    Cualquier E / S costosa, ya sea de la red, una base de datos, o un archivo de gran tamaño por lo general se mantendrá fuera del hilo principal, ya que causará una lenta interfaz de usuario. Sin ver su código, me imagino que si usted está recibiendo un ANR probablemente está haciendo algo demasiado complejo para el hilo principal.

    FlipAndroid es un fan de Google para Android, Todo sobre Android Phones, Android Wear, Android Dev y Aplicaciones para Android Aplicaciones.