Quantcast
Channel: Tordek
Viewing all articles
Browse latest Browse all 10

PDO, ó, por qué todos los tutoriales de PHP llevan a las malas prácticas

$
0
0

PDO es una panacea. Es mágico. Hace todo lo que queremos, y más. Y lo hace más fácil, rápido, y seguro que lo que podemos hacerlo nosotros.

O, bueno, no tanto. Pero es mucho mejor que manejar conexiones con pg_ o mysql_ o mysqli_ o cualquiera sea el prefijo particular del motor de base de datos que usemos.

PDO (PHP Data Objects) es una capa de abstracción sobre las llamadas a bajo nivel de consultas a DB. Se compone de 3 clases: PDO, que se encarga de las conexiones, PDOStatement, que envuelve consultas y resultados y PDOException, su tipo nativo de excepciones.

En su forma más básica, usar PDO puede ser exactamente igual que usar cualquiera de los otros drivers a mano: Simplemente iniciamos una conexion, ejecutamos la consulta y usamos los resultados.

$connection = pg_connect("host=example.com user=tordek password=42");
$result = pg_query($connection, "SELECT * FROM foo");
 
while ($row = pg_fetch_row($result)) {
        echo $row['bar'], ' ', $row['baz'];
}

cf.

$connection = new PDO("pgsql:host=example.com user=tordek password=42");
$result = PDO->query("SELECT * FROM foo");
 
foreach ($result as $row) {
        echo $row['bar'], ' ', $row['baz'];
}

La conexión se crea pasando un “DSN”, Data Source Name ó Nombre de Fuente de Datos, que no es más que un string que indica el tipo de base de datos, su dirección y otros detalles necesarios para su conexión.

query deja de ser una función más, para transformarse en un método de clase, al igual que con mysqli; no hace mucha diferencia, pero limpia un poco el namespace global.

$result es un poco más interesante. Si bien sigue siendo un objeto opaco, ahora es un generador: ya no es necesario llamar a una función para extraer un valor y avanzarlo; eso lo hace foreach, dejando más en claro que estamos haciendo algo con cada elemento.

En fin, cambios principalmente estéticos.

Ahora, cuando empezamos a ver características un poco más avanzadas, empieza a volverse más interesante.

Lo primero es que (omitiendo incompatibilidades entre las consultas SQL) lo único que tenemos que hacer para cambiar el tipo de base de datos que usamos (si antes usábamos una DB Access para pruebas, y lo subimos a un server con MySQL, por ejemplo) es cambiar el string de conexión.

Lo segundo es que agrega soporte global para cosas como consultas preparadas, aunque el motor no las soporte nativamente. Un beneficio de esto es que repetir una misma consulta con diferentes valores se vuelve más simple, y a veces hasta más rápido (si el motor lo soporta, no es necesario mandar (y procesar) la consulta entera, sino sólo los parámetros nuevos):

$query = $conexion->prepare("INSERT INTO foo (bar) VALUES (:bar)");
 
foreach ($array as $val) {
        $query->bindValue(":bar", $val);
        $query->execute()
}

Al hacer prepare, creamos una consulta que tiene un “hueco” para un valor (en este caso, llamado :bar). bindValue hace que el valor de ese hueco sea igual al de $val. Luego, en el foreach se cambia la variable y se ejecuta una consulta en cada ciclo, insertando en la tabla una fila para cada valor de $array.

El otro beneficio, mucho más importante, es que, al usar consultas preparadas, no es necesario preocuparse por inyecciones SQL. El driver se encarga de sanitizar cada parámetro de la manera que vea prudente (mysql_real_escape_string vs pg_escape_string vs SQLite3::escapeString). Por default, asume que todos los parámetros son strings, pero podemos especificar que se trata de otro tipo, de ser necesario.

El beneficio más grande, en mi opinión, es la consistencia: Da igual que el usemos PostgreSQL, MySQL, SQLite o incluso Access; sólo necesitamos conocer una forma de realizar consultas que sirve para casi todos los casos que se nos ocurra. Y todo esto es mencionando tan solo lo más básico que PDO tiene para ofrecer.

Ahora… ¿cuál es la contra?

PDO es una abstracción. Todas las abtracciones tienen dos problemas: el primero es que, por cada capa de abstracción, es necesario recorrer más camino para llegar al «fondo» (en este caso, las llamadas a las DB). Eso implica una pérdida de velocidad, sí, pero una que es casi irrelevante. El otro problema es que las característicás más “hardcore” de las DB se pueden perder, como mysql_server_info. Ambos problemas son casi completamente ignorables, excepto en los casos más extremos.

PDO es parte de PHP desde la versión 5.1. No hay excusa para no usarlo.


Viewing all articles
Browse latest Browse all 10

Latest Images

Trending Articles





Latest Images