Novedad en PHP: MySQLi
¿Dejará PHP de ofrecer soporte técnico para MySQL pronto?: esta era la pregunta que se hacía la comunidad PHP cuando, al conectarse con un servidor MySQL mediante la antigua extensión mysql, aparecía una aviso de error y la recomendación de cambiarse a ext/mysqli. Este mensaje empezó a mostrarse con la versión PHP 5.5, pero la extensión mysqli ya se había lanzado con PHP 5.0, es decir, en 2004.
Y ¿por qué tanto nerviosismo? Entre otras cosas, porque el equipo encargado de PHP en Oracle se percató de que aún eran muchos los que usaban ext/mysql, entre ellos pesos pesados del sector, como WordPress. Oracle decidió entonces iniciar un lento proceso de deprecation, es decir, una transición para dejar atrás ext/mysql y reemplazarla por la nueva extensión. No obstante, la antigua extensión no duró mucho más: dejó de existir con la versión PHP7. En este artículo te describimos en detalle a su sucesora, MySQLi, mostrando ejemplos y explicando las diferencias concretas entre ambas extensiones.
Bajo la división Arsys Cloud Solutions, diseñamos Soluciones a tu medida.
¿Qué es MySQLi de PHP?
MySQLi es una extensión mejorada (la i final es de improved) de PHP para acceder a bases de datos MySQL. MySQL es, junto con Oracle y Microsoft SQL Server, uno de los sistemas de gestión de bases de datos (es decir, un Database Management System o DBMS) relacionales más populares a nivel mundial. Las bases de datos relacionales son un elemento central de Internet, ya que permiten procesar grandes cantidades de datos y guardarlos de forma permanente. Para hacerlo, dividen los complejos conjuntos de datos en partes y establecen luego las relaciones necesarias entre ellos.
Este software, desarrollado en 1994 por la compañía sueca MySQL AB, es distribuido en la actualidad por Oracle Corporation mediante un sistema dual de licencias: además de la licencia propietaria para empresas, Oracle ofrece también una versión con licencia GPL y de código abierto. Este doble sistema de licencias da a las empresas la oportunidad de desarrollar aplicaciones propias basadas en MySQL sin necesidad de recurrir a una licencia open source.
¿Qué abarca la extensión mysqli?
En PHP existen tres maneras de acceder a una base de datos MySQL. La más antigua es utilizar la extensión MySQL, la cual, sin embargo, está considerada desfasada o deprecated desde la versión PHP 5.5 y fue eliminada completamente con PHP 7. En esta última versión, la función mysql ya no funciona y ha sido reemplazada por mysqli.
Además de la anticuada extensión mysql, para acceder a una base de datos MySQL, PHP también ofrece los PHP Data Objects (PDO), cuya aplicación es particularmente flexible. La tercera opción es usar la MySQL Improved Extension, es decir, la extensión mysqli, que ya desde PHP 5 permite acceder a bases de datos MySQL. El siguiente snippet o fragmento de código puede ayudarte a hacerte una idea de cómo funciona la extensión MySQLi de PHP.
Snippet: enviar una consulta SQL a la base de datos
Para enviar queries o consultas a la base de datos, se utiliza la orden query($sql) :
<?php
$mysqli = new mysqli("localhost", "user", "password", "database");
if ($mysqli->connect_errno) {
die("error de conexión: " . $mysqli->connect_error);
}
$sql = "UPDATE tabla SET columna = 'Valor' WHERE id = 1";
$mysqli->query($sql);
?>
¿Qué ventajas tiene MySQLi?
Al contrario que su predecesora, la extensión mysqli no solo puede usarse de forma procedural, sino también de forma orientada a objetos. Una ventaja de la programación orientada a objetos es que el código escrito puede corregirse y adaptarse fácilmente a posteriori. Esto puede ser útil, por ejemplo, para crear nuevas clases que puedan heredar el comportamiento y las propiedades de otras clases ya existentes. Así, se acorta considerablemente el tiempo de desarrollo y se facilita la adaptación del programa ante un entorno cambiante o nuevos requisitos.
Otra ventaja importante de MySQLi son los prepared statements o consultas preparadas. Se trata, por así decirlo, de instrucciones ya preparadas para el sistema de la base de datos. Mientras que los statements convencionales contienen valores de parámetros, los prepared statements contienen en su lugar los llamados marcadores de posición o caracteres comodín. Cuando se ejecuta en el sistema de la base de datos un statement con distintos parámetros varias veces (en un bucle, por ejemplo), los prepared statements permiten aumentar la velocidad, puesto que las órdenes en sí ya se encuentran compiladas en la base de datos y simplemente han de ser ejecutadas con los nuevos parámetros. Además, los prepared statements son una medida efectiva de prevención contra las inyecciones SQL, ya que el sistema de la base de datos ha de comprobar la validez de los parámetros antes de procesarlos.
Snippet: prepared statements en MySQLi
En MySQLi, un ejemplo de prepared statements podría tener la siguiente forma:
<?php
$mysqli = new mysqli("localhost", "user", "Password", "database");
if ($mysqli->connect_errno) {
die("error de conexión: " . $mysqli->connect_error);
}
$sql = "UPDATE user SET email = ?, contraseña = ? WHERE id = ?";
$statement = $mysqli->prepare($sql);
$statement->bind_param('ssi', $email, $contraseña, $id);
//Asignar valores a las variables
$id= 1;
$email = "un@ejemplo.es";
$contraseña = "nueva contraseña";
$statement->execute();
?>
La orden bind_param() relaciona los parámetros de la consulta SQL con las variables. En el ejemplo de arriba, el primer argumento de bind_param(), que tiene el valor ssi, describe los tipos de parámetro. En este caso, ssi indica que hay tres parámetros en la consulta: el primero es de tipo string, el segundo también y el tercero es de tipo integer. Para cifras de coma flotante existe, además, el valor d.
Una vez las variables han sido relacionadas con los parámetros, a estos últimos se les asignan los valores correspondientes y, mediante $statement→execute(), se envía el prepared statement a la base de datos. En comparación con la extensión PDO, sin embargo, este proceso es claramente más complicado.
mysqli() versus mysql(): ¿por qué se modificó la extensión de PHP?
No quedaba más remedio que cambiar a MySQLi, ya que la antigua extensión mysql había quedado anticuada. Además, al desarrollar la extensión antigua, se había intentado que fuera compatible con las versiones anteriores, de forma que el código resultaba difícil de actualizar, puesto que databa de los inicios de PHP y MySQL y, en parte, no había sido desarrollado de la mejor manera.
Si, por ejemplo, no se indicaba ningún recurso de conexión explícitamente, todas las funciones intentaban utilizar la última conexión que se había producido. En el peor de los casos, mysql_query() podía incluso acceder a una base de datos totalmente distinta. El identificador de conexión era opcional en la extensión antigua, mientras que en la nueva sí debe indicarse. También se han añadido, además, prepared statements, que hacen que la lectura de los datos de la base de datos sea más rápida y más segura.
Por suerte, muchas funciones pueden modificarse simplemente añadiendo una i a la función mysql(). No obstante, existen algunas diferencias ambas extensiones.
Snippet: identificador de conexión en MySQL y MySQLi
Algunas funciones de mysqli() requieren un identificador de conexión, es decir, una variable PHP generada al realizar la conexión con la base de datos. En el siguiente ejemplo, será $link.
<?php
// mysql() establecer conexión:
mysql_connect("localhost", "root", "", "test");
// mysqli() establecer conexión:
$link = mysqli_connect("localhost", "root", "", "test");
?>
Snippet: leer datos de la tabla de la base de datos
La función mysqli_query() necesita un identificador de conexión; la función mysqli_fetch_array(), en cambio, no.
<?php
$link = mysqli_connect("localhost", "root", "", "test");
// Leer registros:
$registros = mysqli_query($link,
"SELECT `nombre`, `texto`, `fecha` FROM `mensajes`");
// Mostrar registros:
while (list($nombre, $texto, $fecha) = mysqli_fetch_array($registros)) {
echo "<p>$nombre - $titel - $texto - $fecha</p>";
}
?>
Además de la función mencionada, las siguientes funciones, entre otras, también requieren un identificador de conexión:
En resumen: MySQLi es más seguro y más rápido
El cambio a MySQLi era necesario para aumentar la velocidad de acceso a las bases de datos. A la nueva extensión se le añadieron prepared statements o consultas preparadas que, además, mejoran la seguridad de la conexión al prevenir inyecciones SQL. Logran prevenirlas porque obligan al sistema de la base de datos a comprobar si los parámetros son válidos antes de procesarlos. Por si eso fuera poco, el nuevo código puede actualizarse de forma mucho más fácil gracias a la programación orientada a objetos.