Ejercicios de Gestión de errores y depuración de PHP

Crea un proyecto sesion05 e introduce en él los diferentes ficheros que vayas creando.

Depuración de un script PHP con NetBeans

Este ejercicio tiene como objetivo realizar un ejemplo de debug con NetBeans.

Para la entrega de este ejercicio tienes que seguir los siguientes pasos y entregar el fichero **index.php** el cual se irá modificando e introduciendo nuevos cambios para ir cogiendo práctica con la depuración de scripts PHP junto con NetBeans.

Para poder realizar un debug con NetBeans y XDebug necesitas activar dicha librería en el fichero **php.ini**.

Sigue los siguientes pasos:

  1. Activar esa línea desde WAMP: Pincha con el botón derecho en W del barra de tareas y accede a la parte de PHP.Posteriormente accede a la parte de PHP -> PHP Settings y activa/selecciona (XDebug): Remote Debug.
  2. Por último, para poder "conectar" XDebug junto con NetBeans nos falta añadir tres parámetros de configuración de XDebug. Al activar dicha librería, se habrán descomentado una serie de líneas en el fichero php.ini. Esas líneas suelen estar al final de dicho fichero, en la zona ; XDEBUG Extension .
    Añade las siguientes líneas:
xdebug.remote_handler=dbgp
xdebug.remote_host=localhost
xdebug.remote_port=9000


Y después recuerda que hay que reiniciar Apache (dado que hemos modificado el fichero php.ini)

A continuación:

  • Crea un nuevo proyecto PHP para esta sesión.
  • Justo después de crear el proyecto y para activar el uso de teclas de acceso rápido, pulsa con el botón derecho en el nombre del proyecto y selecciona "Set as Main Project" (establece como proyecto principal el proyecto recién creado).
  • Crea un nuevo fichero PHP llamado index.php e introduce el siguiente código:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
   <head>
      <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
      <title>Ejemplo de Debug con NetBeans</title>
   </head>
   <body>
      <?php
         $m=5;
         $n=10;
         $suma_de_factoriales = calcular_suma_de_factoriales ($m, $n);

         echo "fact($m) + fact($n) = " . $suma_de_factoriales;

         function calcular_suma_de_factoriales ($param1, $param2) {
            $factorial1 = factorial ($param1);
            $factorial2 = factorial ($param2);
            $result = sumar ($factorial1, $factorial2);
            return $result;
         }
         function factorial ($param) {
            $resultado = 1;
            for ($i=1; $i<=$param; $i++) {
               $resultado = $resultado * $i;
            }
            return $resultado;
         }
         function sumar ($param1, $param2) {
            return $param1 + $param2;
         }
      ?>
   </body>
</html>
  • Establece un breakpoint (Ctrl-F8) al principio del bloque de código PHP como vemos en la imagen siguiente Colocamos un punto de parada en la etiqueta de inicio del código PHP
  • Arranca la sesión de depuración pinchando en el botón. El debugger parará en el breakpoint.
  • Presiona tres veces F7. El debugger parará justo antes de ser invocada la función calcular_suma_de_factoriales(). La ventana de variables locales nos muestra las variables $m y $n y sus valores: Momento previo a la ejecución de la función calcular_suma_de_factoriales()
  • Entra dentro de la ejecución de la función calcular_suma_de_factoriales() presionando F7. El debugger empieza a ejecutar el código de la función y parará justo en la llamada a la función factorial(). Ejecutando el código de la función calcular_suma_de_factoriales()
  • Como vemos en la imagen la ventana Variables muestra el valor de las variables locales $param1 y $param2 de la función calcular_suma_de_factoriales().Por supuesto también podemos acceder al valor de las variables superglobales: $_GET, $_POST,... Valor de las variables locales $param1 y $param2 dentro de la función calcular_suma_de_factoriales()
  • Presiona otra vez la tecla F7. El debugger empezará con la ejecución del código de la función factorial(). La ventana Call Stack mostrará la pila de llamadas de las funciones en orden inverso con la llamada a la última función en primer lugar de la lista: Ventana justo en la ejecución de la función factorial
  • Presiona otra vez F7 para entrar al bucle. Podemos ver el valor de las variables en la ventana de variables locales (Local Variables). Valor de las variables al iniciar la ejecución del bucle que calcula el factorial
  • Ejecuta un par de iteraciones para comprobar que el código funciona correctamente. Posteriormente presiona la combinación de teclas Ctrl-F7 para cancelar la ejecución de la función y volver a la próxima línea después de la llamada a la funciónfactorial().

    Alternativamente podríamos presionar F7 hasta que acabe la ejecución de la función factorial() . El programa volverá a la línea siguiente después de la llamada a la función.

  • Como ya sabemos que la función factorial() funciona correctamente, podemos pasar la ejecución de la misma ("step over"). Para saltar la ejecución de una función, presiona F8. El programa parará en la llamada a la función sumar(). Después de calcular los factoriales de 5 y 1
  • Presiona F8 para no entrar en la ejecución de la función sumar(). En cualquier caso, el debugger parará en la última línea de la función calcular_suma_de_factoriales().Después de ejecutar la función sumar()
  • Presiona F7 y el debugger ejecutará la siguiente línea: echo "fact...."
  • Presiona F7 hasta que el debugger termine de ejecutar todo el fichero. La ventana del navegador mostrará el resultado final:

Solución final mostrada en el navegador

Entrega el fichero index.php y una captura de pantalla justo cuando se está depurando el función factorial (ten en cuenta que el objetivo de los ejercicios de este tema es que conozcas y configures cómo debuggear en NetBeans)

(OPTATIVO) Usando visualizaciones adicionales (Watches)

Los "watches" nos permiten definir la visualización de expresiones adicionales para realizar un seguimiento dentro de la ejecución de un programa. Esto nos podría ayudar a capturar un error.

Esta opción está deshabilitada por defecto, ya que, puede provocar algún error de comunicación entre XDebug y NetBeans y puede hacer que el editor tenga que cerrarse (depende del nivel de profundidad de la visualización).
Para activar los watches en un sesión de depuración, ve a la sección de **Herramientas** del menú principal y selecciona **opciones**.
Dentro de opciones selecciona **PHP** y la pestaña **Debugging**.
Tendrás que activar la opción de "Watches and Balloon Evaluation" (NetBeans te mostrará un mensaje de advertencia). En la siguiente imagen puedes ver la opción que hay que activar:

Pestaña de debugging de NetBeans

Realiza las siguientes pasos:

*. Actualiza el código de la función sumar() del anterior ejercicio por lo siguiente (sustituir un más por un menos):

function sumar ($argument1, $argument2) {
   return $argument1 - argument2;
}

*. Elige Debug > New Watch o pulsando la combinación Ctrl-shift-F7. La ventana de visualizaciones se abrirá.

  1. Introduce la siguiente expresión y pinchar en OK.
$factorial1 + $factorial2

La nueva expresión aparecerá en la ventana de visualización (Watches).

4. Ejecuta otra vez la sesión de debug y cuando el debugger se pare en esta línea: ```php return $result; ```

compara el valor de la expresión en la ventana de visualizaciones (Watches) y el valor de la variable **$result** en la ventana de variables locales. Deberían tener una valor similar pero con distinto signo. En la imagen siguiente podemos ver el resultado:

Ejemplo de uso de visualizaciones adicionales

Entrega el fichero index.php y una captura de pantalla donde quede se muestre la visualización

Depurar scripts PHP junto a HTML

Podemos depurar código que contenga bloques de código PHP y HTML. En el anterior ejercicio de depuración los valores estaban codificados a un valor prefijado. Vamos a mejorar el ejemplo de la suma de dos factoriales introduciendo un formulario HTML para que el usuario pueda introducir los valores.

Realizaremos los siguientes pasos:

  1. Añade el siguiente código HTML antes del bloque de PHP <?php ?>:
<form action="index.php" method="POST">
   Introduzca el primer entero:
   <input type="text" name="primer_entero"/><br/>
   Introduzca el siguiente entero:
   <input type="text" name="segundo_entero"/><br/>
   <input type="submit" name="submit" value="Enviar"/>
</form>
  1. Sustituye las líneas siguientes:
$m=5;
$n=10;
$suma_de_factoriales = calcular_suma_de_factoriales ($m, $n);
echo "fact($m) + fact($n) = " . $suma_de_factoriales;
  1. Por este otro código:
if (array_key_exists ("primer_entero", $_POST)
   && array_key_exists ("segun- do_entero", $_POST))
{
   $primerEntero = $_POST["primer_entero"];
   $segundoEntero = $_POST["segundo_entero"];
   $result = calcular_suma_de_factoriales ($primerEntero, $segundoEntero);
   echo "fact($primerEntero) + fact($segundoEntero) = " . $result;
}
  1. La función array_key_exists ($indice, $array) comprueba si un índice (suele ser una cadena) o clave dada existe en el array. Para más información accede a esta url: http://php.net/manual/es/function.array-key-exists.php

  2. Establece un breakpoint al principio del bloque <?php y vuelve a ejecutar la sesión de debug.

  3. Presiona F7 y entra al programa. Si accedes al navegador, todavía no se habrá mostrado el formulario en el mismo. Este comportamiento es correcto porque hasta que pasemos por todo el código fuente de la página web, éste no será mostrado. Prácticamente, lo que significa es que el debugger pasará dos veces por la página. La primera vez procesa el código a mostrar por el formulario HTML. La segunda vez el debugger ejecutará el código paso a paso.

  4. Presiona F7 hasta que el debugger llegue al final del programa y comprueba que finalmente el formulario se visualiza en el navegador. Debe mostrar lo siguiente:

Formulario de ejemplo para realizar un debug con NetBeans

  1. Introduce los valores 5 y 10 respectivamente en los campos del formulario y pulsa el botón de Enviar(submit). Vuelves a NetBeans y comprueba que la sesión de debug está parada en el breakpoint.

Visualización de los valores del array superglobal _POST justo después de comprobar que se han introducido valores en los dos campos del formulario.

En la imagen se muestra desplegado los índices y sus valores del array superglobal **$_POST.** El índice "primer_entero" vale 5, "segundo_entero" vale 10 y "submit" vale "Enviar". Destacar también que, como vemos en la imagen, al desplegar el conjunto de variables "Superglobals" vemos que están otros arrays superglobales $_GET, $_REQUEST, $_SERVER, etcétera.

Si continuamos con la ejecución comprobaremos que el resultado es el correcto.

Solución final después de introducir los valores 5 y 1 en los campos del formulario.

(OPTATIVO) Función factorial en modo recursivo

En los ejercicios anteriores, la función factorial se ha ejecutado en modo iterativo.Añade en el formulario un **select html** para seleccionar en qué modo ejecutar el factorial: recursivo o iterativo. Modifica el script PHP para obtener el valor del select y calcular el factorial en un modo u otro.

(OPTATIVO) Cálculo de tiempo

Vamos a usar el siguiente script para obtener el tiempo de ejecución entre dos puntos. Al fichero lo llamaremos **benchmark.php** y el código es el siguiente:

<?php
   /**
   * microtime http://docs.php.net/manual/es/function.microtime.php
   * round http://docs.php.net/manual/es/function.round.php *
   */
   function time_start () {
      global $starttime;
      $mtime = microtime(true);
      $starttime = $mtime;
   }
   function time_end () {
      global $starttime;
      $mtime = microtime(true);
      echo "<hr><b>Tiempo: " . round($mtime - $starttime, 4) .
         "</b><hr>";
   }
?>

Este fichero incluye dos funciones:

  • time_start(): inicia el temporizador o cronómetro

  • time_end(): termina el temporizador y devuelve el tiempo transcurrido desde la llamada a la función time_start().

Además usa una variable global **$starttime** que servirá para restar el tiempo de inicio y fin.

Para medir el tiempo de ejecución de un script, colocaremos la llamada a la función time_start() al principio del mismo (incluir la definición del fichero benchmark.php antes de la llamada) y time_end() al final del código. Para el fichero anterior quedaría algo así:

<?php
   include("benchmark.php");
   time_start();
   if (array_key_exists ("primer_entero", $_POST)
      && array_key_exists ("segundo_entero", $_POST))
      ....
   time_end();
?>
</body>
</html>

Realiza varias pruebas realizando con debug y sin él para comprobar lostiempos de ejecución.

Si has realizado el ejercicio optativo donde se convierte la función factorial a una función recursiva, realiza un factorial de 50 (o más) y muestra por pantalla lo que tarda cada una de ellas verificando que la función recursiva es mucho más lenta que la iterativa.

Cuidado porque PHP tiene limitada la memoria RAM que puede utilizar en un script PHP (suele ser a 128Mb). La puedes modificar cambiando la directiva memory_limit de php.ini http://www.php.net/manual/en/ini.core.php#ini.memory-limit

results matching ""

    No results matching ""