944 063 154

Blog

Un vistazo al driver php_sqlsrv para trabajar con bases de datos SQL Server 2005 o superior en PHP

Publicado enDesarrollo y Programación

Desde hace algunos años el driver que se facilita en los paquetes de PHP por defecto está considerado deprecated y no se aconseja su uso. Sobre todo desde que fue publicada la última versión: SQL Server 2005. En su lugar, por suerte, disponemos del driver php_sqlsrv. Una extensión creada desde Microsoft con la que podemos aprovechar de una forma mucho más avanzada este expléndido motor de bases de datos.

Traducción nativa de los datos a utf-8

Una de las características que más me han gustado en la versión 1.1 del driver php_sqlsrv, es la traducción nativa y transparente de la codificación de los datos desde UTF-8 a UCS-2 y viceversa. Para quien haya tenido un mínimo de experiencia desarrollando aplicaciones en internet, la importancia de usar codificación UTF-8 es clave. Nos puede evitar pasar varias noches sin dormir al encontrarnos multitud de problemas al integrar aplicaciones, consumir datos de fuentes externas o migrar a otras plataformas. Es un detalle que los desarrolladores de esta librería le hayan dado prioridad a esta característica vital para desarrolladores de aplicaciones PHP.

Para activar esta característica, que os recomiendo que lo hagáis, basta con especificar el enconding en el array de conexión:

$params = array(

"UID" => "usuario",
"PWD"  =>"password",
"Database" => "base_de_datos"

);

$params["CharacterSet"] = "utf-8";
$conexion = sqlsrv_connect( "nombre_de_la_instancia", $params);

Campos de tipo fecha recuperables como cadenas

Por defecto el driver nos permite recuperar los datos de tipo datetime, Date, Time, DateTime2 y DateTimeOffset como datos DateTime. Normalmente nos puede interesar más tratarlos como si fuesen cadenas desde PHP y para ellos, el driver nos provee de una forma de hacerlo.

Basta con inidicarlo en el array de conexión:

$params = array(

"UID"=> "usuario",
"PWD" = > "password",
"Database" => "base_de_datos",
"CharacterSet" => "utf-8"

);

$params["ReturnDatesAsStrings"] = true;

$conexion = sqlsrv_connect( "nombre_de_la_instancia", $params);

Autenticación de sistema o de usuario de SQL Server 2005

A la hora de conectarnos a una instancia, podemos hacerlo mediante autenticación de sistema o de usuario de SQL Server según esté establecido en la configuración de la instancia.

Aunque para una aplicación web, especialmente una aplicación que tenga como destino dar servicio en internet, nos interese aplicar una autenticación de usuario de SQL Server, el driver dispone de soporte nativo para reconocer el usuario con el cual estamos ejecutando la aplicación web y usar sus credenciales para realizar la autenticación.

Para realizar una autenticación de sistema no necesitamos indicar usuario ni contraseña, tan sólo la base de datos:

$params =  array("Database" => "base_de_datos");

$conexion = = sqlsrv_connect( "nombre_de_la_instancia", $params);

Limpieza de parámetros en las consultas

Uno de los puntos más vulnerables en una aplicación web siempre ha sido la forma en la que realizamos las consultas a la base de datos.

Para ayudarnos a securizar los datos que interoducimos en las consultas, disponemos de un mecanismo muy sencillo de limpieza.

$sql = "INSERT INTO usuarios (email, password) VALUES (?,?);";

//creamos el array de parámetros
$params = array(strtolower($email),md5($pass));

//realizamos la consulta, pasándole los parámetros a blindar
$stmt = sqlsrv_query( $conexion, $sql, $params);

Instanciación de objectos específicos en los resultados de una consulta

Otra opción muy útil que nos provee el driver es la posibilidad de especificar un objeto que será instanciado como resultado de una query.

class User{
 public $object_id= null;
 public $user_id = null;
 public $email = null;
 public $password = null;

 public function __construct($id){
   $this->object_id = $id;
 }

}

$sql = "SELECT TOP 1 user_id,email FROM users WHERE user_id = ? ";

$stmt = sqlsrv_query( $conexion, $sql, array($user_id));

if($stmt!==false){

 $i=0; $items = array();

 //cada variable $object será una instancia del objeto User
 while( $object = sqlsrv_fetch_object( $stmt, "User", array($i)))
 {
  $items[] = $object;
  $i++;
 }

 sqlsrv_free_stmt($stmt);
 $stmt=null;
}

Constantes para la conversión de tipos PHP a tipos nativos de SQL Server

En algunos casos necesitamos convertir el parámetro al tipo de dato nativo de SQL Server que necesitemos evaluar en la consulta. Como puede ser el caso de los tipos DateTime.

Para ello, el driver php_sqlsrv dispone de una serie de constantes que nos ayudan a hacerlo.

$sql = "SELECT user_id FROM usuarios WHERE created_at >= ? AND user_id < ?;";

//creamos el array de parámetros, cada elemento será un array en el que especifiquemos la constante del tipo que necesitamos
$params = array(array($date, null, null, SQLSRV_SQLTYPE_DATETIME), array($user_id,null));

//realizamos la consulta, pasándole los parámetros a blindar
$stmt = sqlsrv_query( $conexion, $sql, $params);

Opciones que echamos en falta en el driver php_sqlsrv

PDO es una capa de abstracción cuyo objetivo principal es aislarnos de las particularidades de cada driver disponible. Todo ello con el objetivo de atacar los diferentes motores de bases de datos que existen. Muchos ORMs como doctrine y Propel lo usan. No disponer de soporte para PDO supone una barrera para algunso de los CMS o frameworks más usados. Además de un trabajo adicional para los desarrolladores a la hora de necesitar utilizar SQL Server en sus proyectos. Irónicamente, el antiguo driver a pesar de estar obsoleto soporta PDO.

Se agradece ir abandonando poco a poco el paradigma estructurado en PHP y algunas librerías como MySQLi; que nos permiten usarlas como si se tratase de un objeto. Sería una muy buena característica para este driver.