Xcode y depuración avanzada en LLDB: Parte 1

Buenas tardes, hoy le sugiero que se familiarice con la traducción de un artículo sobre depuración de aplicaciones iOS usando LLDB.

Los ingenieros de Apple introdujeron una de las partes más interesantes de la presentación de WWDC 2018, Xcode y depuración avanzada en LLDB . Brindaron algunos consejos útiles sobre cómo usar los puntos de interrupción en Xcode y el depurador de bajo nivel (LLDB) para optimizar el proceso de depuración de errores, donde sea que el desarrollador los detectara.

El artículo consta de tres partes, repasaremos los puntos principales que se han dicho en la WWDC. Creé un proyecto de demostración específicamente para comprender mejor cómo usar varios tipos de puntos de interrupción (puntos de interrupción) junto con LLDB para capturar y depurar errores en su aplicación.

Proyecto de demostración

Creé un proyecto de tarea de plantilla que todos los desarrolladores de iOS se han reunido de una forma u otra. Es muy importante entender cómo funciona antes de profundizar en la lectura del artículo. Estas son las principales funciones del proyecto de demostración:

  • Cuando se abre, vemos un controlador de vista de tabla que carga una lista de publicaciones.
  • Al desplazarse hacia abajo, el controlador de vista de tabla carga nuevas publicaciones.
  • En total, puedes cargar publicaciones 7 veces .
  • Puede actualizar la lista de publicaciones desplegando usando el controlador de actualización (desplegar para actualizar).
  • En la barra de navegación en la parte superior hay 2 etiquetas (etiquetas) que muestran cuántas publicaciones se han descargado (etiqueta derecha) y cuántas veces el usuario ya ha subido publicaciones (etiqueta izquierda).

Puede descargar el proyecto de demostración desde aquí si prefiere Objective-C.

Si prefieres Swift, entonces desde aquí .

¡Lanza Xcode y vámonos!

Errores para arreglar!

Entonces, se familiarizó con el proyecto y probablemente notó los siguientes errores:

  • Al tirar de la tabla hacia abajo, la actualización no actualiza las publicaciones.
  • El usuario no recibe ninguna notificación (utilizando el controlador de alerta) de que la solicitud HTTP no se ha completado debido a problemas de conexión.
  • Puedes cargar publicaciones más de 7 veces.
  • El indicador izquierdo (etiqueta) en la barra de navegación, que es responsable de contar el número de descargas, no funciona.

Una regla importante: hasta el final de este artículo, no detiene el compilador y no reinicia la aplicación después del primer lanzamiento. Corrige errores durante la ejecución del programa.

El poder de los equipos de instrucción.

Vayamos al primer error.

1. Cuando baja la tabla, las publicaciones no se actualizan.

Cómo reproducir el error:

  • Inicie la aplicación, las primeras 10 publicaciones ya están cargadas.
  • Desplácese hacia abajo para cargar más publicaciones.
  • Desplácese hasta el comienzo de la tabla y arrástrelo hacia abajo para actualizar.
  • Las publicaciones nuevas no se cargan, las antiguas no desaparecen y el contador de publicaciones no se restablece.

El enfoque estándar para corregir tales errores implica examinar lo que sucede dentro del selector de métodos responsable del control UIRefresh de nuestra tabla. Vaya a PostsTableViewController en la sección pragma mark Refresh control support support . Desde la función setupRefreshControl, podemos concluir que el selector responsable de actualizar las publicaciones es la función reloadNewPosts . Agreguemos un punto de interrupción a la primera línea de esta función y descubramos qué está sucediendo exactamente aquí. Ahora desplácese hasta el comienzo de la tabla y arrastre la pantalla para actualizar.

imagen
Objetivo-c

imagen
Veloz

El depurador se detuvo en el punto de interrupción que estableció. Para más estudio, haga clic en el botón "omitir bloque" del depurador.

imagen
Objetivo-c

imagen
Veloz

¡Ahora tenemos una comprensión de lo que va mal!

La condición if no se cumple (es decir, la variable booleana isPullDownToRefreshEnabled se establece en NO) y, como resultado, se omite el código para actualizar las publicaciones.

El enfoque estándar implica detener el compilador, luego debe establecer isPullDownToRefreshEnabled como YES / true y esto resolvería el problema. Pero sería mucho más conveniente probar primero nuestra hipótesis antes de realizar cambios en el código y sin tener que detener el compilador. Aquí es donde los comandos de instrucciones del depurador resultan ser muy útiles.

Haga doble clic en el punto de interrupción instalado o haga clic con el botón derecho en "Editar punto de interrupción" y haga clic en el botón "Agregar acción". Seleccione también el tipo de acción "Comando del depurador".

imagen

Ahora necesitamos establecer la propiedad isPullDownToRefreshEnabled como YES / true. Agregue el siguiente comando al depurador.

Objetivo-c

expression self.isPullDownToRefreshEnabled = YES 


imagen

Veloz

 expression self.isPullDownToRefreshEnabled = true 

imagen

Luego, verifique que la casilla de verificación "Continuar automáticamente después de evaluar acciones" esté seleccionada. Es responsable de garantizar que el depurador no se detenga en el punto de interrupción cada vez y automáticamente continúe trabajando con el comando recién agregado. Ahora desplácese hacia arriba hasta el comienzo de la tabla y arrastre hacia abajo para actualizar.

Voila, las nuevas publicaciones se cargaron y reemplazaron las antiguas y, en consecuencia, se actualizó el contador de publicaciones.

Resolvimos el primer problema, obtenga su arma anti-error, procedemos al segundo.

2. El usuario no recibe ninguna notificación (utilizando el controlador de alertas) de que la solicitud HTTP no se ha completado debido a problemas de conexión.

Cómo reproducir el error:

  • Desconecte la conexión a Internet en su iPhone / simulador.
  • Desplácese hacia arriba hasta el comienzo de la tabla y arrastre hacia abajo para actualizar.
  • Las nuevas publicaciones no se descargarán debido a un error de conexión a Internet.
  • Al usuario no se le muestra ninguna notificación de error.

Vaya a PostsTableViewController en la sección Networking de la marca pragma . Tiene exactamente una función loadPosts . Utiliza una instancia genérica de administrador de red para ejecutar una solicitud GET HTTP, que devuelve una serie de publicaciones a través de un controlador de finalización "exitoso" o NSError a través de un controlador de finalización "fallido".

Necesitamos agregar el código al cierre "fallido" para mostrar un controlador de alerta. Si va a la sección Soporte de la marca pragma, verá que ya existe una función presentNetworkFailureAlertController que es responsable de mostrar el controlador de alerta deseado. Todo lo que necesitamos hacer es llamar a esta función dentro de un cierre "fallido" en loadPosts .
La forma tradicional es detener el simulador y agregar el código deseado. ¡Vamos por el otro lado!

Agregue un punto de interrupción dentro del cierre "sin éxito" después de la línea

Objetivo-c

 [self updateUIForNetworkCallEnd]; 

Veloz

 self.updateUIForNetworkCallEnd() 

Haga doble clic en el punto de interrupción instalado o haga clic con el botón derecho en "Editar punto de interrupción" y haga clic en el botón "Agregar acción". Seleccione también el tipo de acción "Comando del depurador".

Agregue el siguiente comando al depurador.

Objetivo-c

 expression [self presentNetworkFailureAlertController] 

imagen

Veloz

 expression self.presentNetworkFailureAlertController() 

imagen

Verifique que la casilla de verificación "Continuar automáticamente después de evaluar acciones" esté seleccionada.
Con Internet apagado, desplácese hacia arriba hasta el comienzo de la tabla y arrastre hacia abajo para actualizar, o puede desplazarse hacia abajo hasta el final de la tabla e intentar cargar nuevas publicaciones. Esto es lo que verás:

imagen

Lo que acabamos de hacer se llama " inyectar " el código usando un comando agregado al depurador en un punto de interrupción específico.

Un pequeño resumen

Vamos a enumerar una vez más lo que podemos hacer con los comandos del depurador agregados al punto de interrupción:

  • Operar con un valor de propiedad existente.
  • Agregue una nueva línea de código.

Ambas tareas se realizaron durante la ejecución del programa. Esencialmente no necesitamos detener el compilador para corregir errores y reiniciar la aplicación.

Que sigue

Además, traigo a su atención la segunda parte del artículo , donde corregiremos más errores y descubriremos otro tipo de punto de interrupción (punto de interrupción): el punto de observación (punto de observación).

Source: https://habr.com/ru/post/es431506/


All Articles