May 052016
 
Artículo Administración de Servidores

Muchas aplicaciones, como por ejemplo la popular base de datos MySQL, crean ficheros temporales en disco para la ejecución de algunos de sus procesos. El rendimiento de este tipo de aplicaciones se puede mejorar significativamente creando un disco sobre la memoria RAM del sistema, que es varios órdenes de magnitud más rápida que los discos magnéticos convencionales, o los más recientes discos SSD.

En este artículo veremos cómo se puede crear un disco en RAM, y cómo configurar MySQL para que haga uso del mismo, en un sistema Debian/Ubuntu. El procedimiento se puede aplicar con ligeras modificaciones a casi todas las demás distribuciones de Linux.

1 – Determinar la cantidad de memoria física disponible

Para poder utilizar un disco en memoria, el sistema debe disponer de una cantidad suficiente. El comando “free” nos indica la cantidad total de memoria disponible, y del uso que está haciendo el sistema de la misma:

# free -m
             total       used       free     shared    buffers     cached
Mem:         40323      22586      17737        816         42       1223
-/+ buffers/cache:      21320      19002
Swap:         2047         82       1965

En este ejemplo, vemos que el sistema dispone de un total de 40323 MBytes de memoria principal (40 GBytes), de los cuales hay 17 GBytes no utilizados.

2 – Crear el punto de montaje, y montar el disco RAM

La configuración por defecto de un sistema Debian/Ubuntu ya incluye un filesystem tmpfs montado en “/dev/shm”, que hace uso de la mitad de la memoria física disponible. Con el comando “df” podemos examinar los filesystems existentes:

$ df
Filesystem     1K-blocks      Used Available Use% Mounted on
/dev/sda2      825324976 461508928 321868864  59% /
udev               10240         0     10240   0% /dev
tmpfs            8258348    811312   7447036  10% /run
tmpfs           20645868         0  20645868   0% /dev/shm
tmpfs               5120         0      5120   0% /run/lock
tmpfs           20645868         0  20645868   0% /sys/fs/cgroup
/dev/sda1         230925     32084    182611  15% /boot
$

En otro tipo de distribuciones Linux, en donde no exista ya un filesystem tmpfs configurado, podemos crearlo de la siguiente forma:

En primer lugar, creamos un directorio en el cual se va a montar el disco RAM:

# mkdir /mnt/ramdisk

y a continuación montamos el disco con el comando:

# mount -t tmpfs -o size=10240m tmpfs /mnt/ramdisk

Con el comando “df”, podemos comprobar que el disco está creado y preparado para su uso:

# df -h /mnt/ramdisk
Filesystem      Size  Used Avail Use% Mounted on
tmpfs            10G     0   10G   0% /mnt/ramdisk

Opcionalmente, para que el disco se vuelva a montar cuando se reinicie el servidor, podemos añadir una línea al fichero /etc/fstab:

tmpfs       /mnt/ramdisk tmpfs   nodev,nosuid,noexec,nodiratime,size=10240M   0 0

3 – Configurar MySQL para que utilice el disco en memoria

La directriz “tmpdir” en el fichero de configuración /etc/mysql/my.cnf especifica la ubicación del directorio en el cual MySQL creará las tablas temporales que necesite para la ejecución de determinadas consultas. En primer lugar, creamos un directorio “mysqltmp” bajo el directorio en el que hemos montado el disco en memoria, y le asignamos como propietario el usuario con el que se ejecuta el servicio mysql:

# mkdir /mnt/ramdisk/mysqltmp
# chown mysql:mysql /mnt/ramdisk/mysqltmp

A continuación, editamos /etc/mysql/my.cnf para establecer dicho directorio como valor de la directriz “tmpdir”:

tmpdir          = /mnt/ramdisk/mysqltmp

Por último reiniciamos el servicio mysql para que tenga efecto la nueva configuración:

# /etc/init.d/mysql restart

4 – Crear tablas e índices en el disco en memoria

Otra posible optimización es utilizar el disco en memoria para almacenar no sólo las tablas temporales, sino las tablas permanentes.

Sin embargo, hay que ser consciente de que todo el contenido del disco en memoria desaparece cada vez que se reinicia el sistema, por lo que hay que establecer un procedimiento que permita recuperar esta información en el reinicio.

Supongamos que la base de datos contiene una tabla ‘mitabla’, que es accedida frecuentemente por las aplicaciones que se ejecutan en el servidor. Podemos crear en el disco en memoria una nueva tabla ‘mitabla_ram’, con la misma estructura que la tabla ‘mitabla’, y copiar a la misma el contenido de ‘mitabla’;

mysql> CREATE table `mitabla_ram`(
           .... 
           )
           DATA DIRECTORY '/mnt/shm/mysql'
           INDEX DIRECTORY '/mnt/shm/mysql';
mysql> INSERT INTO mitabla_ram (SELECT * FROM mitabla);

A continuación, cambiamos el nombre de las tablas para que la tabla en memoria pase a llamarse ‘mitabla’, y sea la tabla utilizada por la aplicación:

mysql> ALTER TABLE mitabla RENAME TO mitabla_disco;
mysql> ALTER TABLE mitabla_ram RENAME TO mitabla;

Por último debemos establecer un mecanismo para:

  • Guardar en disco el contenido de la tabla en memoria, con la periodicidad que se considere necesaria
  • En el reinicio del sistema, crear nuevamente la tabla en memoria, y cargarla con el contenido guardado en disco.

Referencias:

 Publicado por en 4:15 pm

 Deja un comentario

(requerido)

(requerido)