2010-01-12 10 views
32

Ok, este es un problema extraño, así que por favor ten paciencia conmigo como te explico.Pasa por problema de referencia con PHP 5.3.1

Actualizamos nuestros servidores de desarrollo de PHP 5.2.5 a 5.3.1.

Cargando nuestro código después del cambio, que comienza a recibir errores como:

Warning: Parameter 2 to mysqli_stmt::bind_param() expected to be a reference, value given in /home/spot/trunk/system/core/Database.class.php on line 105

la mencionada línea (105) es el siguiente:

call_user_func_array(Array($stmt, 'bind_param'), $passArray); 

cambiamos la línea a la siguiente:

call_user_func_array(Array($stmt, 'bind_param'), &$passArray); 

en este punto (porque allow_call_time_pass_reference) está apagado, php lanza esto:

Deprecated: Call-time pass-by-reference has been deprecated in /home/spot/trunk/system/core/Database.class.php on line 105

Después de tratar de solucionar este problema desde hace algún tiempo, que se rompió y me puse a allow_call_time_pass_reference sucesivamente.

que se libró de la advertencia Deprecated, pero ahora la advertencia Warning: Parameter 2 to mysqli_stmt::bind_param() expected to be a reference está lanzando cada vez, con o sin la referenciación.

No tengo ni idea de cómo solucionarlo. Si el método de destino fuera mío, simplemente haría referencia a los vars entrantes en la declaración de func, pero es un método (relativamente) nativo (mysqli).

¿Alguien ha experimentado esto? ¿Cómo puedo evitarlo?

Gracias.

+0

Además, en el código anterior $ stmt es un objeto devuelto por mysqli :: prepare – Spot

+1

También tuve este problema y encontró [esto] (https://sixohthree.com/1486/migrating-to-php-5-3-call_user_func_array) publicación de blog que me ayudó mucho. – cb0

Respuesta

16

Estás pasando una matriz de elementos ($ passArray). El segundo elemento dentro de el conjunto pasado debe ser una referencia, ya que esa es realmente la lista de elementos que está pasando a la función.

+0

En realidad, tienes razón. Sin embargo, hacer referencia a esa var tampoco ayuda. Hmmmm – Spot

+4

Ok, solucionado esto creando una matriz ficticia, haciendo referencia a los valores de la principal. Es bastante triste que se requiera esto para ser honesto. :) Gracias! – Spot

+0

Estimado Spot Tengo un problema similar. tienes alguna sugerencia. http://stackoverflow.com/questions/23290490/mysqli-prepared-statements-error?noredirect=1#comment35651490_23290490 –

0

Creo que las funciones mysqli_bind_param() y mysqli_bind_result() son muy difíciles de usar. He encontrado la misma dificultad que describe al usarlos en combinación con call_user_func_array()

Mi solución fue dejar de usar mysqli y en su lugar usar PDO_mysql. Tiene un uso mucho más fácil:

$pdoStmt->execute($passArray); 
+0

¿Creí que PDO_mysql estaba en desuso? – Spot

+0

No, en absoluto. ¿Qué demonios te dio esa idea? –

+0

@Spot: 'php_mysql.so' no se recomienda (no está en desuso),' pdo_mysql.so' es muy recomendable. –

-1

El segundo paramer Debe ser una matriz. aparentemente esto solo se aplicó en 5.3

+0

Es es una matriz. – Spot

+0

¿Qué hay en esa matriz? – DeveloperChris

2

Creo que lo que está en desuso es pasar una referencia a través de una función. En la definición de función haces algo como:

function(&$arg) { 

} 

Esto no le ayuda mucho, pero es probable que no es necesario pasar la referencia de todos modos. Supongo que podrías probar una función de envoltura.

function wrapper($stmt, &$passArray) { 
    call_user_func_array($stmt, $passArray); 
} 
45

acabo experimentado este mismo problema, llamando a través de bind_param call_user_func_array y pasando una matriz de parámetros. La solución es modificar los valores en la matriz a la que se hará referencia. No es elegante, pero funciona.

call_user_func_array(array($stmt, 'bind_param'), makeValuesReferenced($passArray)); 

function makeValuesReferenced($arr){ 
    $refs = array(); 
    foreach($arr as $key => $value) 
     $refs[$key] = &$arr[$key]; 
    return $refs; 

} 
+2

tu salvaste mi vida – KennyPowers

6

En realidad, tenga en cuenta que hay un error con PHP 5.3.1 relativos a las referencias y todos call familia de funciones:

PHP Bugs #50394: Reference argument converted to value in __call

El comportamiento que está viendo podría ser un resultado de este error y cualquier intento de corregirlo en cuanto al código puede causar problemas a largo plazo.

El problema ha sido reparado en la versión SVN de PHP. Hasta que se publique 5.3.2, puede compilar una nueva versión para usarla o degradarla a una versión anterior.

3

Estábamos experimentando este mismo problema con este código:

call_user_func(array($strCartHandler, 'CartPurchaseEvent'), $strCartEvent, $objToUser, null, $this); 

Mi solución fue omitida call_user_func por completo y hacer esto:

$strCartHandler::CartPurchaseEvent($strCartEvent, $objToUser, null, $this); 
0

Esto le ayuda:

<?php 
call_user_func_array(Array($stmt, 'bind_param'), array(&$passArray)); 

function bind_param ($val) 
{ 
    $val = (is_array($val)) ? $val[0] : $val; 

    // operations... 
} 

?> 
0

Tengo un problema similar, el código actual no funcionó:

$query="Select id,name FROM mytable LIMIT ?,?"; 
$params=Array('ii'); 
array_push($params,$from_var); 
array_push($params,$to_var); 
... 
$stmt=$link->prepare("$query"); 
$ref=new ReflectionClass('mysqli_stmt'); 
$method=$ref->getMethod("bind_param"); 
$method->invokeArgs($stmt,$params); 
... 

Se dice que "Parámetro 2 a mysqli_stmt :: bind_param() espera que sea una referencia, el valor dado"

Y luego, en la desesperación, he tratado de tomar $ from_var y $ to_var entre comillas ¡Y funcionó!

$params=Array('ii'); 
array_push($params,"$from_var"); 
array_push($params,"$to_var"); 

Esperanza, que le ayudará a alguien, buena suerte :)

Cuestiones relacionadas