2009-05-07 72 views
28

Me pregunto qué se utiliza la declaración del tipo de datos en bindParam() (o bindValue()) para ...PHP PDO :: bindParam() tipos de datos ... ¿cómo funciona?

quiero decir, pensé que si yo defino un argumento entero (PDO::PARAM_INT), el argumento debe ser convertido a un número entero, algo así como

$delete->bindParam(1, $kill, PDO::PARAM_INT); 
// should work like 
$delete->bindParam(1, (int)$kill); 

o al menos arrojar un error si el argumento no es del tipo declarado. Pero este no es el caso.

googlear alrededor, me encontré con que en el archivo php.net:

Hola a todos,

estoy trabajando actualmente en la DOP. Exactamente en la función bindParam(). El tercer parámetro data_type parece estar aquí para forzar el tipo del valor? Pero cuando intento :

$sql = "INSERT INTO produit (idproduit, nom, marque) VALUES (NULL, :nom, :marque)"; 
$stmt = $dbh->prepare($sql); 
$nom = 'Testarossa'; $marque = 'Ferrari' ; 
$stmt->BindValue(':marque',$marque) ; 
$stmt->BindParam(':nom',$nom,PDO::PARAM_INT) ; 

$stmt->execute(); $nom = '250 GTO' ; 
$stmt->execute(); ?> 

que estaba esperando a tener ya sea un error de PHP o un número entero en mi base de datos. Pero en mi base de datos que tengo:

22 Testarossa de Ferrari 250 GTO 23 Ferrari

Es decir que no cambiaría si tengo el tercer parámetro o no. O quizás echo de menos algo. ¿Puede alguien me tolera más? O simplemente puede alguien decirme dónde puedo encontrar información al respecto.

Saludos,

Cyruss

eso es exactamente mi situación. ¿Dónde están mis pensamientos que van mal?

+1

"Esperaba tener un error PHP o un interger en mi base de datos". yo también – VolkerK

Respuesta

30

En otros marcos de abstracción de base de datos en otros idiomas que se pueden utilizar para cosas como asegurarse de que está haciendo el escape adecuado para los valores de forro (para los conductores que no son compatibles con destino parámetros adecuada) y la mejora de la eficiencia de la red asegurándose de que los números se empaquetan binariamente de forma apropiada (se brinda soporte de protocolo). Parece que en PDO, no hace mucho.

if (PDO_PARAM_TYPE(param->param_type) == PDO_PARAM_STR && param->max_value_len <= 0 && ! ZVAL_IS_NULL(param->parameter)) { 
       if (Z_TYPE_P(param->parameter) == IS_DOUBLE) { 
         char *p; 
         int len = spprintf(&p, 0, "%F", Z_DVAL_P(param->parameter)); 
         ZVAL_STRINGL(param->parameter, p, len, 0); 
       } else { 
         convert_to_string(param->parameter); 
       } 
     } else if (PDO_PARAM_TYPE(param->param_type) == PDO_PARAM_INT && Z_TYPE_P(param->parameter) == IS_BOOL) { 
       convert_to_long(param->parameter); 
     } else if (PDO_PARAM_TYPE(param->param_type) == PDO_PARAM_BOOL && Z_TYPE_P(param->parameter) == IS_LONG) { 
       convert_to_boolean(param->parameter); 
     } 

lo tanto, si usted dice que es un RTS (o si usted dice nada en absoluto ya que es el valor por defecto) y el tipo interno de sus datos es un doble, entonces lo convertirá en una cadena mediante un método, si no es un doble, lo convertirá en una cadena utilizando un método diferente.

Si dices que es un int pero en realidad es un bool, entonces lo convertirá en un largo.

Si dices que es un bool pero en realidad es un número, lo convertirá en un booleano real.

Esto es realmente todo lo que vi (rápidamente) mirando la fuente stmt, imagino que una vez que pasa los parámetros en el controlador pueden hacer magia adicional. Entonces, supongo que todo lo que obtendrás es un poco de hacer lo correcto y una gran cantidad de ambigüedad de comportamiento y varianza entre los controladores.

+1

Doh, tengo un ninja publicado. Supongo que solo respondo lento ^^. – gradbot

+0

Maldición, pensé que se escapó./Corriendo a casa para arreglar el código. –

+0

Ah ok, encontré http://php.net/manual/en/pdo.prepared-statements.php no wories. –

5

Hay al menos un efecto PDO :: PARAM_INT ha de INSERT consultas: valores booleanos se convierten en 0 o 1. Al igual que en

$i = true; 
$stmt->bindParam(':i', $v, PDO::PARAM_INT);

pdo_stmt.c:

else if (PDO_PARAM_TYPE(param->param_type) == PDO_PARAM_INT && Z_TYPE_P(param->parameter) == IS_BOOL) { 
     convert_to_long(param->parameter); 
}

+1

Oh ... me pregunto si este efecto realmente es útil ... ¿qué pasa con otros data_typeS? cadena, etc. – Strae

+0

No he encontrado documentación confiable para estas características. Por lo tanto, podría revisar todo el código en/ext/pdo * ... o simplemente no confiar en ese parámetro para INSERT, UPDATE ... consultas. – VolkerK

+0

Bien, probaré las consultas SELECT para ver si el 'problema' también las afecta ... Triste, de todos modos, que la declaración data_type sea útil incluso para la limpieza/control de flujo en las consultas INSERTAR . – Strae

3

Probé la misma cosa con BindValue y obtuve el mismo resultado, por lo que el comportamiento que está viendo no está limitado a bindParam.

$stmt->BindValue(':marque', $marque) ; 
$stmt->BindValue(':nom', $nom, PDO::PARAM_INT) ; 

$stmt->execute(); 
$nom = '250 GTO'; 
$stmt->BindValue(':nom', $nom, PDO::PARAM_INT) ; 
$stmt->execute(); 
19

Así que decidí sumergirme en el código fuente de PHP y esto es lo que encontré.

static int really_register_bound_param en ext/PDO/pdo_stmt.c en la línea 329 de la versión 5.2.9

if (PDO_PARAM_TYPE(param->param_type) == PDO_PARAM_STR && param->max_value_len <= 0 && ! ZVAL_IS_NULL(param->parameter)) { 
    if (Z_TYPE_P(param->parameter) == IS_DOUBLE) { 
     char *p; 
     int len = spprintf(&p, 0, "%F", Z_DVAL_P(param->parameter)); 
     ZVAL_STRINGL(param->parameter, p, len, 0); 
    } else { 
     convert_to_string(param->parameter); 
    } 
} else if (PDO_PARAM_TYPE(param->param_type) == PDO_PARAM_INT && Z_TYPE_P(param->parameter) == IS_BOOL) { 
    convert_to_long(param->parameter); 
} else if (PDO_PARAM_TYPE(param->param_type) == PDO_PARAM_BOOL && Z_TYPE_P(param->parameter) == IS_LONG) { 
    convert_to_boolean(param->parameter); 
} 

Estas son las conversiones PDO hace durante la unión.

  • PDO :: PARAM_STR convierte lo que le dé a una cadena excepto nulo.
  • PDO :: PARAM_INT convierte en Bools anhela
  • PDO :: PARAM_BOOL convierte anhela en Bools

eso es todo. Nada más se convierte. PDO utiliza los indicadores PARAM para formatear SQL para no lanzar tipos de datos.

+0

"PDO :: PARAM_STR convierte todo lo que le das a una cadena", excepto NULL –