Club Delphi  
    FTP   CCD     Buscar   Trucos   Trabajo   Foros

Retroceder   Foros Club Delphi > Otros entornos y lenguajes > PHP
Registrarse FAQ Miembros Calendario Guía de estilo Buscar Temas de Hoy Marcar Foros Como Leídos

Respuesta
 
Herramientas Buscar en Tema Desplegado
  #1  
Antiguo 04-09-2019
bucanero bucanero is offline
Miembro
 
Registrado: nov 2013
Ubicación: Almería, España
Posts: 208
Poder: 11
bucanero Va camino a la fama
imagecreatefromstring detiene el script

Hola buenas tardes,

Aquí vengo con un BUGS esta vez en PHP, que suerte todos los voy encontrando yo ...,
en particular se trata de un BUGS en la librería GD que lo que hace es elevar a error desconocido cualquier error que encuentra la propia librería y deteniendo totalmente el script que se esta ejecutando.

Aquí se comenta el BUGS que también tiene ya su tiempo
https://bugs.php.net/bug.php?id=70315

El problema en particular me afecta en PRESTASHOP que utiliza estas librerías para procesar las imágenes/miniaturas. Y en particular en el proceso de generación de miniaturas, donde siempre se detiene (debido al BUGS) en la misma imagen, sin llegar a finalizar ni a procesar el resto de las miniaturas que tiene la tienda, por lo que nunca avanza.

Intente solventarlo, antes de conocer que el problema es debido a este bug, creando un script alternativo que detecte y elimine las imágenes no validas para lo que cree una función que las chequea en el servidor para comprobar si son correctas, pero en cuanto llega a analizar la primera imagen con error en particular cuando llega al comando imagecreatefromstring() que es un comando de la librería GD el script se detiene y se acaba el proceso... no haciendo caso por mas que lo he intentado de los bloques try ... catch ... finally

Este es mi código:
Código PHP:
    function GetImageInfo($filename, &$errorMsg) {
        
        
/* Abrimos el archivo según su contenido */
        
$result false;
        try {
            
$finfo finfo_open(FILEINFO_MIME_TYPE);
            
$result finfo_file($finfo$filename);
        } catch (
Exception $e) {
            
$errorMsg .= $e->getMessage();              
        } 
finally {
            
finfo_close($finfo);        
        }         
        return 
$result;
    }
    
    function 
checkImage($filename, &$errorMsg) {
      
        
$result false;
        
$errorMsg '';
        try {    
            
$image false;    
            if (
$filename == "") {
                
$errorMsg .= "El nombre de fichero esta vacio";                                        
            } elseif ( !
file_exists($filename) ) {
                
$errorMsg .= "La ruta del fichero no es correcta";                                                    
            } elseif ( !
$infoFile GetImageInfo($filename$errorMsg) ) {
                
$errorMsg .= "{$filename}: No se ha podido obtener informacion del fichero";                            
            }elseif (( 
$infoFile != 'image/jpeg' ) && ( $infoFile != 'image/png' )) {
                
$errorMsg .= "{$filename}: Formato de imagen no soportado";            
            } elseif (!
$image_data file_get_contents($filename)) {
                
$errorMsg .= "{$filename}: Contenido no disponible";                        
            } elseif(!
$image imagecreatefromstring($image_data)) {
                
$errorMsg .= error_get_last()['message'];                  
            } else {
                unset(
$image);
                
$result true;
            } 
// if        
        
} catch (Exception $e) {
            
$errorMsg $e->getMessage();              
        } 
finally {            
            return 
$result;                    
        }  
    } 
// function 
- ¿Alguien mas que haya tenido este problema?
- ¿Alguna otra alternativa o solución para determinar si una imagen es correcta o no en PHP?

Gracias por su tiempo y colaboración
saludos
Responder Con Cita
  #2  
Antiguo 05-09-2019
Avatar de Ñuño Martínez
Ñuño Martínez Ñuño Martínez is offline
Moderador
 
Registrado: jul 2006
Ubicación: Ciudad Catedral, Españistán
Posts: 6.000
Poder: 25
Ñuño Martínez Tiene un aura espectacularÑuño Martínez Tiene un aura espectacular
Me parece muy raro que un error tan antiguo (2.015) no haya sido corregido todavía, y menos en una biblioteca tan usada como esta.

De todas formas, ¿seguro que para el programa sin más? ¿Estás ejecutando con todas las opciones de depuración activadas para que te muestre toda la información posible? [edit] ¿Qué versión de PHP estás usando? Porque dice que el error está arreglado y sólo afecta a un par de versiones viejas.
__________________
Proyectos actuales --> Allegro 5 Pascal ¡y Delphi!|MinGRo Game Engine

Última edición por Ñuño Martínez fecha: 05-09-2019 a las 12:37:27.
Responder Con Cita
  #3  
Antiguo 05-09-2019
bucanero bucanero is offline
Miembro
 
Registrado: nov 2013
Ubicación: Almería, España
Posts: 208
Poder: 11
bucanero Va camino a la fama
Cita:
Empezado por Ñuño Martínez Ver Mensaje
Me parece muy raro que un error tan antiguo (2.015) no haya sido corregido todavía, y menos en una biblioteca tan usada como esta.

De todas formas, ¿seguro que para el programa sin más? ¿Estás ejecutando con todas las opciones de depuración activadas para que te muestre toda la información posible? [edit] ¿Qué versión de PHP estás usando? Porque dice que el error está arreglado y sólo afecta a un par de versiones viejas.
Gracias Ñuño Martínez por responder!!

La versión de PHP de mi servidor es la 5.6.32 de fecha 26/10/2017, es verdad que no es la ultima, pero se supone que dicho BUGS esta ya solventado en esa versión, pues según la documentación se aplico a partir de la versión 5.6.25 de fecha 18/08/2016. De todas formas ya he abierto tickets para que actualicen la versión del hosting.

En cualquier caso ejecuto con todas las opciones de depuración, y se sigue deteniendo.
La solución que he aplicado momentáneamente es capturar cuando finaliza el script y analizar si se ha producido una excepción de tipo E_ERROR y en tal caso borrar el fichero. Este es el método:

Código PHP:
    register_shutdown_function('fatalErrorShutdownHandler');
    
    function 
fatalErrorShutdownHandler() {
        
        global 
$filename;
        
        
$last_error error_get_last();
        if (
$last_error['type'] === E_ERROR && ($filename != '') ) {
            if ( !
unlink $filename ) ) {
                echo 
"{$filename} no se ha podido eliminar";
            } else {
                echo 
"{$filename} eliminado";                
            }
        }
    } 
No es la solución mas optima, pero al menos para la siguiente vez que se ejecute el script ya no se volverá a detenerse en el mismo fichero.
Responder Con Cita
  #4  
Antiguo 06-09-2019
Avatar de dec
dec dec is offline
Moderador
 
Registrado: dic 2004
Ubicación: Alcobendas, Madrid, España
Posts: 13.107
Poder: 34
dec Tiene un aura espectaculardec Tiene un aura espectacular
Hola a todos,

Supongo que sí... pero... ¿estás mostrando los posibles errores de PHP? Esto es, al comienzo del script, prueba a añadir las siguientes líneas de código:

Código PHP:

error_reporting
(E_ALL);

ini_set('display_errors'1); 
__________________
David Esperalta
www.decsoftutils.com
Responder Con Cita
  #5  
Antiguo 06-09-2019
bucanero bucanero is offline
Miembro
 
Registrado: nov 2013
Ubicación: Almería, España
Posts: 208
Poder: 11
bucanero Va camino a la fama
Cita:
Empezado por dec Ver Mensaje
Hola a todos,

Supongo que sí... pero... ¿estás mostrando los posibles errores de PHP? Esto es, al comienzo del script, prueba a añadir las siguientes líneas de código:

Código PHP:

error_reporting
(E_ALL);

ini_set('display_errors'1); 
David gracias por responder!!!

Si, esta activo el modo de depuración. De echo la librería GD devuelve exactamente el error que encuentra. El error en particular es:

Código:
Fatal error: imagecreatefromstring(): gd-jpeg: JPEG library reports unrecoverable error: Bogus marker length in itest.php on line 53
El error es correcto es de la propia imagen por estar corrupta (parece ser que el tamaño de los datos contenidos en la imagen es distinto al definido por las dimensiones de la imagen). Y ese mismo error también lo obtengo al intentar leer esa imagen con cualquier programa externo de imagenes en windows.
El problema es de la libreria GD y de PHP que detiene la ejecución ...

Este es mi código completo que utilizo para hacer la prueba de comprobación y en donde ya se da el fallo:
Código PHP:
<?php
  
// https://bugs.php.net/bug.php?id=73986
  
  
error_reporting(E_ALL);  
  
ini_set('display_errors'1);
  
ini_set('display_startup_errors'1);
  
  
ini_set ('gd.jpeg_ignore_warning'1);
  
  
register_shutdown_function('fatalErrorShutdownHandler');
    
    function 
fatalErrorShutdownHandler() {
        
        global 
$filename;
        
        
$last_error error_get_last();
        if (
$last_error['type'] === E_ERROR && ($filename != '') ) {
            echo 
"<BR/>\r\r(" __LINE__ ") ERROR: {$filename}. Ejecución detenida."
        }
    }
    
    function 
GetImageInfo($filename, &$errorMsg) {
        
        
/* Abrimos el archivo según su contenido */
        
$result false;
        try {
            
$finfo finfo_open(FILEINFO_MIME_TYPE);
            
$result finfo_file($finfo$filename);
        } catch (
Exception $e) {
            
$errorMsg .= $e->getMessage();              
        } 
finally {
            
finfo_close($finfo);        
        }         
        return 
$result;
    }
    
    function 
checkImage($filename, &$errorMsg) {
      
        
$result false;
        
$errorMsg '';
        try {    
            
$image false;    
            if (
$filename == "") {
                
$errorMsg .= "El nombre de fichero esta vacio";                                        
            } elseif ( !
file_exists($filename) ) {
                
$errorMsg .= "La ruta del fichero no es correcta";                                                    
            } elseif ( !
$infoFile GetImageInfo($filename$errorMsg) ) {
                
$errorMsg .= "{$filename}: No se ha podido obtener informacion del fichero";                            
            }elseif (( 
$infoFile != 'image/jpeg' ) && ( $infoFile != 'image/png' )) {
                
$errorMsg .= "{$filename}: Formato de imagen no soportado";            
            } elseif (!
$image_data file_get_contents($filename)) {
                
$errorMsg .= "{$filename}: Contenido no disponible";                        
            } elseif(!
$image imagecreatefromstring($image_data)) {
                
$errorMsg .= error_get_last()['message'];                  
            } else {
                unset(
$image);
                
$result true;
            } 
// if        
        
} catch (Exception $e) {
            
$errorMsg .= $e->getMessage();              
        } 
finally {        
            return 
$result;                    
        }  
    } 
// function

  
$errorMsg ''
  
$filename '3612272.jpg';      
  if ( !
checkImage($filename$errorMsg) ) {
    echo 
"<BR/>\r\r(" __LINE__ ") ERROR: {$filename} {$errorMsg}";
  } else {
    echo 
"{$filename} OK";
  }
?>
y dejo enlace a la imagen corrupta por si alguien quiere hacer pruebas en su propio equipo
Imágenes Adjuntas
Tipo de Archivo: jpg 3612272.jpg (10,5 KB, 3 visitas)
Responder Con Cita
  #6  
Antiguo 06-09-2019
Avatar de dec
dec dec is offline
Moderador
 
Registrado: dic 2004
Ubicación: Alcobendas, Madrid, España
Posts: 13.107
Poder: 34
dec Tiene un aura espectaculardec Tiene un aura espectacular
Hola a todos,

¿Se detiene la ejecución incluso con el "try...catch"? Sea como sea... claro, lo primero que se le ocurre a uno es, ¿por qué no se usa una imagen "incorrupta"? ¿Es obligatorio usar esa imagen? Pero siempre podría convertirse, ¿no? ... porque el error pinta malamente así a bote pronto...
__________________
David Esperalta
www.decsoftutils.com
Responder Con Cita
  #7  
Antiguo 06-09-2019
bucanero bucanero is offline
Miembro
 
Registrado: nov 2013
Ubicación: Almería, España
Posts: 208
Poder: 11
bucanero Va camino a la fama
Cita:
Empezado por dec Ver Mensaje
Hola a todos,

¿Se detiene la ejecución incluso con el "try...catch"? Sea como sea...
Si, se detiene sin mas y finaliza, el try ... catch hace caso omiso, cosa que también a mi me ha sorprendido mucho....

Cita:
Empezado por dec Ver Mensaje
Hola a todos,
claro, lo primero que se le ocurre a uno es, ¿por qué no se usa una imagen "incorrupta"? ¿Es obligatorio usar esa imagen? Pero siempre podría convertirse, ¿no? ...
Esta imagen procede de un proceso automático donde las recoge de diversos catálogos de precios de varios proveedores y en distintos servidores y monta un catalogo propio de productos (dropshipping). La imagen puede venir ya corrupta incluso desde el propio servidor web del proveedor, o corromperse a lo largo del proceso de descarga, o simplemente no ser un formato de imagen valido... por tanto el objetivo de este código es simplemente detectar las imágenes problemáticas y eliminarlas, por lo menos para que no interfieran en el resto de procesos.

Hasta ahora con la medio solución de register_shutdown_function(); he conseguido a base de ejecutar muchas veces el script, ir eliminando de una en una cada imagen problemática. Pero esta solución es como matar moscas a cañonazos...

Cita:
Empezado por dec Ver Mensaje
porque el error pinta malamente así a bote pronto...
Pues parece que si...
Responder Con Cita
Respuesta


Herramientas Buscar en Tema
Buscar en Tema:

Búsqueda Avanzada
Desplegado

Normas de Publicación
no Puedes crear nuevos temas
no Puedes responder a temas
no Puedes adjuntar archivos
no Puedes editar tus mensajes

El código vB está habilitado
Las caritas están habilitado
Código [IMG] está habilitado
Código HTML está deshabilitado
Saltar a Foro

Temas Similares
Tema Autor Foro Respuestas Último mensaje
Firebird se detiene en Ubuntu. subzero Firebird e Interbase 25 30-07-2014 22:49:39
Impresión directa al puerto COM se detiene en linea 30... krlosrp C++ Builder 5 28-08-2007 23:40:39
La policía detiene 15 personas ArdiIIa La Taberna 16 09-03-2007 22:56:54
Cuantos <Script></Script> deben haber en un <Body>? Deiv HTML, Javascript y otros 9 07-12-2006 02:27:50
El Motor Detiene Su Servicio DANY Firebird e Interbase 6 08-12-2003 18:48:03


La franja horaria es GMT +2. Ahora son las 18:08:56.


Powered by vBulletin® Version 3.6.8
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Traducción al castellano por el equipo de moderadores del Club Delphi
Copyright 1996-2007 Club Delphi