« »
Dec 06

ADOdb es una librería de abstracción de base de datos para PHP muy potente. Dispone de una cantidad de usuarios y casos de éxito importante y ofrece muchas funcionalidades interesantes con soporte para una buena lista de engines de BD. Es un proyecto maduro, iniciado el año 2000, que si no conoces se merece una ojeada en su página oficial.

Como consecuencia de la cantidad de funcionalidades que ofrece es un layer tirando a lento (existen alternativas más rápidas y limpias). Esto es debido a que es un proyecto enorme con miles de lineas de código algunas de ellas, desgraciadamente, de no mucha calidad. Aunque a mi personalmente me gusta mucho y en todo proyecto software existen algunas partes un poco feas.

Dependiendo de la carga del site donde uses ADOdb o dependiendo de si necesitas todas sus funcionalidades es aconsejable estudiar bien otras alternativas mucho más lights. Como ADOdbLite (simulando ADOdb pero mucho más optimizada y con muchas menos funcionalidades), PDO (dispone de las características más importantes de ADOdb, es más rápida y se ha convertido en el estándar), PEAR MDB2 (sucesora de la clásica DB, potente y bastante rápida). Según John Lim, ADOdb no es que sea tan lenta, pero si la usas en un site con bastante carga y no realizas ninguna de las optimizaciones aquí descritas puedes estar perdiendo unos cuantos segundos en el total de una sesión de usuario (decenas o centenares de ms por página), y muchísimos más si entramos en el tema del uso de la cache de queries (que con esto ADOdb no es precisamente el culpable sino que proporciona un sistema de cache para el acceso a BD).

Es cierto que ADOdb arrasa en funcionalidades sobre las tres alternativas que he comentado pero como en muchas situaciones en el desarrollo en PHP vale la pena valorar las funcionalidades versus rendimiento. Estudiar bien el uso que le vamos a dar a la librería, la carga del site. frecuencia de las queries (dependiendo del tipo de web o de si disponemos de caches de contenido), etc.

Si a pesar de lo anterior te encanta ADOdb y lo quieres utilizar o si ya lo usas en algún proyecto y no puedes asumir un cambio, aquí van algunos consejos para mejorar el rendimiento del acceso a BD (optimizaciones para la librería y como usar la cache de queries).

[1] Usar la extensión de C de ADOdb. Si la instalas la librería PHP del ADOdb se encargará de usarla, aunque también puedes usar directamente las funciones adodb_* en tu código. Puedes descargarla aquí, dentro del archivo están las instrucciones para su instalación (archivo README.txt).

[2] Sobretodo, si tiras de la versión PHP de la librería usar un acelerador de código con opcode cache. Como APC o EAccelerator. Con sites con mucha carga, por mi experiencia personal, APC lo considero un sistema mucho más estable que el EA. El APC se instala como una extensión PECL del PHP.

[3] Usar la cache de ADOdb para tus queries. Esto se consigue con el uso de CacheExecute(). De las queries ejecutadas con este método se almacenan los recordsets devueltos a disco, esto es, con las siguientes queries idénticas el ADOdb devuelve el objeto serializado de disco hasta que no caduque.

Para poder usar CacheExecute() es necesario crear un directorio para la cache e iniciar el ADOdb como sigue:

[php] $ADODB_CACHE_DIR = ‘/var/directorio_para_la_cache’;
$db = NewADOConnection($dsn.’/’.$dbname);
$db->SetFetchMode(ADODB_FETCH_ASSOC); [/php]

Para lanzar una query almacenando cache durante un día:

[php] try {
$sql = ‘SELECT id FROM datos WHERE nombre=”‘.$n.'”‘;
$rs=$db->CacheExecute(86400,$sql);
// …
} catch (ADODB_Exception $e) {
// …
} [/php]

Contando claro que trabajamos con PHP5 y que hemos cargado el soporte para exceptions del ADOdb. Esto se consigue añadiendo:

[php] require_once ‘adodb/adodb-exceptions.inc.php’; [/php]

[4] Es interesante valorar memcached como sustituto de la cache a disco por defecto. ADOdb incluye el código necesario para usarlo. Memcached es teóricamente más rápido que el acceso a los recordsets serializados a disco, aunque la principal ventaja que ofrece es la reutilización de la cache entre distintos servidores.

Una vez instalado memcached, para iniciarlo:

# memcached -d -m 512 -l 127.0.0.1 -p 11211 -u www

Para iniciar el daemon con 512 MB de memoria escuchando sólo en localhost y corriendo como usuario www. Cambiar 127.0.0.1 por la IP de vuestro servidor tanto en el comando como en el código PHP que sigue, y www por el usuario que ejecute el Apache. Es necesario instalar una extensión PECL para trabajar con memcached.

Para iniciar ADOdb y indicar que queremos usar memcached para nuestros CacheExecute:

[php] $db = NewADOConnection($dsn.’/’.$dbname);
$db->SetFetchMode(ADODB_FETCH_ASSOC);
$db->memCache = true;
$db->memCacheHost = ‘localhost’;
$db->memCachePort = 11211;
$db->memCacheCompress = false;
$db->cacheSecs = 86400; [/php]

[5] Aunque bastante incómodo y en algunos casos peligroso (futuros ALTER TABLE) es más rápido acceder directamente a $recordset->fields mediante el ID numérico y fijar la variable $ADODB_FETCH_MODE = ADODB_FETCH_NUM.

[6] Finalmente podemos mirar de ejecutar los métodos _Execute() y _query() para lanzar nuestras queries. Estos son métodos mucho más crudos. _Execute() a diferencia de Execute() no emula binding, p.e. necesario para usar Prepare() si nuestra BD no lo soporta nativamente. Por el otro lado _query() si que es mucho más limitado, a parte de no emular binding tampoco devuelve recordset y no tiene debugging.

Con todo lo anterior podemos tener ADOdb bastante más optimizado aunque si tenemos un nuevo proyecto por delante quizás lo más aconsejable es usar PDO dado que todo apunta a que se convertirá en el estándar a seguir para el acceso a base de datos en PHP.

Acerca del tema de la cache de queries, sin ánimo de alargar más el post, sólo decir que es mucho más óptimo usar memcached para cachear objetos que no cachear las queries necesarias para generar estos objetos… si disponemos de unos buenos sistemas de caches de contenido (p.e. squid) y un sistema de cache de objetos genérico (memcached) cachear las queries deja de ser tan importante aunque te ofrece otro nivel de cache para jugar.

En un siguiente post dedicado a los sistemas de cache en PHP explicaré con más detalles como trabajar con APC y Memcached sobre servidores FreeBSD.

Be Sociable, Share!
Tagged with:

7 Responses to “Optimización del rendimiento de ADOdb en PHP”

  1. meneame.net says:

    Optimizar adodb en PHP…

    AdoDB es una capa de abstracción muy útil y muy usada en PHP, pero su uso intensivo acaba siendo leeeento. Aquí se dan unas pistas y acciones para optimizar su uso y aprovechar sus características….

  2. […] Documentos « Optimización del rendimiento de ADOdb en PHP […]

  3. […] Es cierto que todo lo comentado son problemas “menores” dependiendo de tus recursos (dinero y tiempo). Invirtiendo más dinero en hardware y más tiempo en desarrollo y mantenimiento puedes usar Smarty con toda tranquilidad. Siempre que saber que te estás gastando más dinero y que tardarás más en los desarrollos te inspire tranquilidad. En muchas ocasiones el uso de Smarty es ocasionado por dejarse impresionar por la cantidad de cosas que puedes hacer con él: cache, plugins, transformaciones de datos, forms, filtros, etc. Pero al igual que lo que comentaba acerca de la elección de ADOdb como layer de abstracción de base de datos, es importante valorar lo que vas a usar de todo lo que ofrece, y sobretodo tener en cuenta el coste en rendimiento y tiempo de desarrollo que va a suponer. […]

  4. […] Como prometía en el post dedicado a la optimización de ADOdb voy a explicar como instalar el sistema de cache APC sobre un servidor FreeBSD 6.x. El APC (Alternative PHP Cache) es un sistema de cache de opcode para PHP, sirve para cachear el código intermedio del PHP y así no tener que interpretar todos los scripts en cada ejecución. Para almacenar este código “compilado” se usa la memoria compartida del sistema. A parte el APC nos ofrece funciones para poder almacenar y recuperar datos de cache. […]

  5. Para el tema de cache que recomiendas es necesario tener un servidor dedicado, a no ser que uses AdoDB con php. Yo me he tenido que hacer un sistema cache custom a nivel de query (unos 800 Mb de cache de disco), primero con serialize/unserialize, después usando csv, para ahorrar espacio y augmentar rendimiento, pq tengo un servidor compartido.

    A dia de hoy 2008, pdo se ha convertido en un standard frente adodb?

  6. Ulices_ says:

    Hola, una ayudita, de como puedo conectarme
    a una db mysql, usando smarty

  7. Alvaro Josè Agàmez Licha says:

    Aunque PDO hasta el momento no ha tenido una acojida tan grande como me gustarìa, es una alternativa muy eficiente y limpia, la verdad apenas lo estoy estudiando pero me ha gustado mucho, es una extensión de PHP por tanto tiene un rendimiento mas alto.

Leave a Reply

preload preload preload