miércoles, 9 de septiembre de 2009

Optimización de un servidor MySQL

Las bases de datos MySQL son bastante utilizadas debido a que ofrecen una calidad bastante aceptable a coste 0. Por supuesto, no basta con instalar y listo. Hay que configurar y ajustar los parámetros adecuados al uso que se le vaya a dar. En cualquier caso, en entornos de producción los parámetros que trae por defecto no son suficientes.

En este post, explico una serie de pautas a tener en cuenta en la configuración que pueden servir de punto de partida para el ajuste fino de un servidor MySQL y el motor InnoDB, que es el que he utilizado mayormente ya que permite relación entre tablas.

-innodb_buffer_pool_size: se debe configurar al 70-80% de la memoria del servidor. Por ejemplo, si tienes un servidor de 4GB de RAM, 3G sería un valor adecuado.

-innodb_log_file_size: 256M parece un valor adecuado.

-innodb_log_buffer_size: 4M es un valor adecuado en la mayoría de los casos, a menos que uses grandes blobs. En ese caso, auméntalo un poco.

-innodb_flush_log_at_trx_commit=2 si no te interesan el ACID y puedes asumir que se pierdan transacciones en los dos últimos segundos en caso de fallo en el sistema operativo. Si usas replicación este valor debe estar a 1, tal y como comenté en el post sobre Replicación de bases de datos MySQL.

-innodb_thread_concurrency=8 Incluso con las correcciones sobre escalabilidad del motor InnoDB, tener limitada la concurrencia siempre ayuda. Puede ser mayor o menor dependiendo de tu aplicación, pero 8 es un buen comienzo.

-innodb_flush_method=O_DIRECT. Evita el doble buffer y reduce el uso de swap. En la mayoría de los casos mejora el rendimiento.

-innodb_file_per_table: divide el fichero de información InnoDB en varios, concretamente uno por tabla. Evita que toda la información vaya a un único fichero, aumentando el rendimiento.

Estos puntos anteriores los he sacado del MySQL Performance Blog. Te recomiendo que le eches un vistazo, ya que es posible que aspectos que he omitido porque no se adaptan a mi caso, sí que te interesen a ti. 

Ejemplo de configuración  

A continuación dejo un ejemplo de configuración en un servidor de 4 núcleos con 4MB de RAM y contiene el servidor dedicado únicamente a la base de datos MySQL.

El siguiente fichero ha de colocarse en /etc/mysql/conf.d .Yo lo he llamado innodb.cnf, por ejemplo.
#
# Configuración para optimización de la base de datos
#
[mysqld]
# ficheros de log
log_slow_queries=/var/log/mysql/mysql-slow.log
long_query_time=5 

innodb_buffer_pool_size=3G
innodb_log_file_size=512M
innodb_log_buffer_size=16M
innodb_file_per_table

key_buffer_size=64M
table_cache=1024
thread_cache=16
query_cache_size=256M
max_connections=300
max_user_connections=300
thread_concurrency=8
Puedes observar que se ha aumentado el parámetro innodb_log_buffer_size debido a que usamos gran cantidad de blobs.

Espero que os sirva como punto de partida. Por supuesto, el ajuste fino dependerá mucho del uso y de las aplicaciones.

No hay comentarios: