06 julio 2009

Una implementación de log en PHP

Particularmente durante el período de desarrollo y pruebas, es importante mantener un registro de lo que va ocurriendo a nivel de código, especialmente cuando las pruebas las realiza un tercero. En esos casos es difícil que el usuario de pruebas entregue una descripción concreta de lo que intentaba hacer y qué fue lo que realmente sucedió.

Especialmente en ambientes de producción, en donde se ocultan los errores en pantalla y a vista del usuario final todo funciona bien, es útil implementar algún método de registrar un log de las distintas acciones y/o errores que pudiesen ocurrir. ¿Cómo se puede controlar este tipo de situaciones?

A continuación una descripción detallada:

Es relativamente común mantener en un único archivo todas las especificaciones y configuraciones del sitio, y con la instrucción include() se le invoca cada vez que sea necesario. Por lo tanto, para implementar un log necesitamos pasar por dos etapas: 1. Definir el log, 2. Registrar acciones en el log.

Acá, los ejemplos de cada paso:

1. con la función ini_set() especifico cómo se visualizarán los errores por pantalla, establezco un archivo plano TXT como log y finalmente indico que iré agregando cualquier nivel de errores.

ini_set("display_errors","0");
ini_set("log_errors","1");
ini_set("error_log", ROOT_LOG."/error_log.txt");
error_reporting(E_ALL);


2. luego, para disparar una marca en el log ejecuto la linea que sigue. Ojo con los dos parámetros que recibe: la descripción del mensaje el nivel del error.

trigger_error("Inicio de Sesion de Usuario (".$variableNombreUser.").",E_USER_NOTICE);


¿Cómo queda esa marca en el log? A continuación un ejemplo....

[06-Jul-2009 00:13:17] PHP Notice: Inicio de Sesion de Usuario (VALOR_VARIABLE). in URL_ARCHIVO_QUE_GATILLA_LOG/inApp.php on line 13


(las dos cadenas en mayúsculas y con guión bajo serían reemplazadas con el valor pasado en la variable y la url específica del servidor en el que se implementa el log. Importante: no olvidar definir los permisos respectivos para el archivo de destino del log, para que se realice la escritura.)

Más referencias de interés:
* Envio de Error
* Constantes de Niveles de Errores

02 julio 2009

16 junio 2009

11 junio 2009

U2 - 360º

31 mayo 2009

Respaldos MySQL

Esta mañana retomé el trabajo en un proyecto que tenía olvidado, y para eso comencé rearmando el ambiente de desarrollo.

Básicamente, consistía en armar la base de datos y modificar algunos parámetros de configuración según correspondiese en el lado de la aplicación. El programa está hecho con PHP+MySQL, sobre Apache. Las modificaciones de parámetros resulta simple: consiste en chequear algunas rutas y valores de cuentas de acceso. Todo bien hasta acá.

Siguiente tarea: subir la base. Acá comenzaron los problemas, así es que como ya resolví todo, supongo es un buen momento para 1) explicar cuál era el lío, 2) mostrar cómo lo resolví y, finalmente, 3) repasar algunos conceptos básicos de respaldos de bases de datos y crear la base a partir del script previamente generado.

(Una aclaración: mi configuración es Apache 2.0.63, PHP 5.2.9 y MySQL 5.1.33, todo corriendo sobre Windows XP Professional)

1. El problema era el siguiente: tengo un script .SQL generado con mysqldump, en donde respaldé la estructura de la base y algunos (motor InnoDB) datos mínimos necesarios para comenzar a funcionar. El primer intento para subir la base a partir del respaldo fue ejecutar el script así, tal cual, sobre un cliente que se conecta a MySQL. Aunque he utilizado algunos programas para administrar MySQL, lo que estoy usando actualmente es MySQL Administrator y TOAD for MySQL. Entonces, el primer intento consistió en abrir el script en TOAD y ejecutar. Aquí el problema: errno 150. Buscando en la red, encuentro que el errno 150 ocurre al crear y/o alterar tablas InooDB, específicamente cuando se trabaja con claves foráneas. En general, el problema surge cuando los campos envueltos en la relación no son consistentes, esto es, son de distintos tipos o bien alguna restricción los hace inconsistentes. Otra situación que podría generar el error el un problema en la sintáxis del script.

2. La solución fue un tanto extraña, pero funciona..... y supongo que eso es lo más importante. Comencé revisando las indicaciones que resultaron más comunes en las descripciones del error en internet: el campo que será clave foránea debe tener previamente definido un índice. Eso estaba ok. La sintáxis, también se veía bien. Lo que me generaba más dudas era porqué el script daba errores, si lo había armado automáticamente con la funcionalidad mysqldump del servidor MySQL. Otra cosa que me daba vueltas era que había utilizado un script similar en una máquina distinta y había funcionado sin problemas. Entonces, para descartar, tomé otro script y lo ejecuté igual que el primero, y mandó el mismo error, aun cuando en otra máquina funcionó ok. Finalmente, buscando más en la red, encontré otros métodos para subir una base, y ahí recordé un método que he usado y creo es el mejor.... directamente desde la línea de comandos ejecuto la instrucción para armar la base.

Acá la sintáxis:
c:>mysql -h HOST -u USER -pPASSWORD NOMBRE_BASE < DIRECTORIO_DEL_SCRIPT_DE_LA_BASE
 
(lo que va con mayúsculas es lo que se debe completar de acuerdo a cada servidor)

Y está resuelto.

3. Conceptos básicos de respaldo de bases de datos.

La primera tarea es hacer un respaldo. Para eso, utilizo la funcionalidad mysqldump, propia del servidor MySQL.

La sintáxis generas es:
mysqldump -h HOST -u USER -pPASSWORD [OPCIONES]
(ojo con el valor del parámetro -p, debe ir sin espacios)

Ahora, algunas opciones que me parecen son las más importantes:

  • --add-drop-table: agrega un DROP TABLE antes de cada CREATE TABLE
  • --all-databases / -A: indica que se respaldarán todas las bases disponibles
  • --databases / -B: permite seleccionar una o más bases a respaldar
  • --no-create-db / -n: omite el comando CREATE DATABASE
  • --no-data / -d: respalda únicamente la estructura
  • --result-file / -r: especifica qué archivo se creará como script. Debe usarse en Windows
Por ejemplo, si quisiera respaldar la base BASE1 completa (estructura y datos) en el archivos respaldo_base1.sql en C:, la sentencia sería:

mysqldump -h HOST -u USER -pPASSWORD -B base1 -r C:\respaldo_base1.sql

Para un análisis detallado de las opciones disponibles, acá el link oficial.

Y luego, subir la base a partir del respaldo es fácil con la sintáxis que expliqué arriba, siempre desde la consola MySQL.

29 mayo 2009

15 marzo 2009

25 febrero 2009

LOST