sql >> Base de Datos >  >> RDS >> Mysql

Cómo proteger MySQL:segunda parte

En la publicación anterior sobre la seguridad de MySQL, hemos cubierto una variedad de opciones que se pueden usar para hacer que su(s) instancia(s) de MySQL sean más seguras. Incluían:

  • Medidas generales de seguridad de MySQL;
  • Control de acceso en MySQL;
  • Creación, modificación y eliminación de usuarios en MySQL;
  • Otorgar y revocar privilegios a y de usuarios en MySQL;
  • Comprobando qué privilegios se asignan a los usuarios en MySQL.

En esta publicación, profundizaremos en el resto de las opciones, que incluyen:

  • Categorías de cuentas en MySQL;
  • Roles en MySQL;
  • Cuentas reservadas en MySQL;
  • Administración de contraseñas en MySQL;
  • Bloqueo de cuenta en MySQL;
  • Complementos de seguridad ofrecidos por MySQL;
  • Proteger las copias de seguridad de MySQL.

Recuerde que, una vez más, no cubriremos absolutamente todo lo que necesita saber, pero intentaremos brindarle buenos puntos de partida para que haga su propia investigación.

Categorías de cuentas en MySQL

Las categorías de cuentas se introdujeron en MySQL 8, específicamente en MySQL 8.0.16. Aquí está el quid de la cuestión:

  • Hay dos categorías de cuentas separadas:usuarios normales y usuarios del sistema;
  • Un usuario normal es un usuario sin el privilegio SYSTEM_USER; un usuario del sistema es un usuario con el privilegio SYSTEM_USER;
  • Un usuario regular puede modificar cuentas regulares; dicho usuario no puede modificar cuentas del sistema;
  • Un usuario del sistema puede modificar tanto el sistema como las cuentas normales;
  • Las cuentas regulares pueden ser modificadas tanto por usuarios regulares como por usuarios del sistema;
  • Las cuentas del sistema solo pueden ser modificadas por los usuarios del sistema.

Para hacer uso de las categorías de cuenta en MySQL desde el punto de vista de la seguridad, tenga en cuenta que el privilegio SYSTEM_USER afecta cosas como la manipulación de la cuenta y la eliminación de sesiones y declaraciones dentro de ellas; este concepto en MySQL permite restringir ciertas modificaciones a ciertas cuentas, lo que hace que MySQL sea más seguro. Las categorías de cuentas también se pueden usar para proteger las cuentas del sistema contra la manipulación por parte de las cuentas regulares:para hacerlo, no otorgue privilegios de modificación del esquema mysql a las cuentas regulares.

Para otorgar privilegios SYSTEM_USER a una cuenta, use la siguiente consulta en una cuenta creada:

GRANT SYSTEM_USER ON *.* TO system_user;

Funciones en MySQL

En MySQL, los roles son colecciones de privilegios. Cuando otorga a una cuenta de usuario un rol en MySQL, otorga todos los privilegios asociados con ese rol. Los roles se pueden crear utilizando la instrucción CREATE ROLE:

CREATE ROLE ‘role_1’, ‘role_2’;

Los nombres de los roles constan de una parte de usuario y una parte de host:la parte de usuario no puede estar en blanco y la parte de host tiene el valor predeterminado "%" si no se especifica.

Cuando se crean roles, debe asignarles privilegios. Los privilegios se pueden asignar usando la instrucción GRANT:

  • CONCEDER TODO EN demo_database.* A 'demo_user'; otorgaría todos los privilegios a un usuario llamado demo_user en una base de datos llamada demo_database;
  • CONCEDER INSERTAR, SELECCIONAR, ACTUALIZAR, ELIMINAR EN la base de datos.* A 'demo_user'; otorgaría privilegios INSERTAR, SELECCIONAR, ACTUALIZAR y ELIMINAR a un usuario llamado demo_user en una base de datos llamada demo_database;
  • CONCEDER SELECCIÓN EN demo_database.* TO 'demo_user'; otorgaría privilegios SELECT a un usuario llamado demo_user en una base de datos llamada demo_database.

Para asignar una función a un usuario individual, utilice esta sintaxis:
 

GRANT ‘role_name’ TO ‘user_name’@’localhost’;

Para asignar varios roles a un usuario individual, use esta sintaxis:

GRANT ‘role_1’, ‘role_2’ TO ‘user_name’@’localhost’;

Para asignar roles a múltiples usuarios al mismo tiempo, use esta sintaxis:

GRANT ‘role_name’ TO ‘user1’@’localhost’, ‘user2’@’localhost’;

Los roles pueden ser útiles para prevenir incidentes de seguridad porque si un atacante conoce la contraseña de un usuario no muy privilegiado, asumiendo erróneamente que el usuario es muy "poderoso" en cuanto a roles, su aplicación (y su base de datos) podría ser muy bien guardado.

Cuentas Reservadas en MySQL

Cuando se trata de cuentas reservadas, tenga en cuenta que MySQL crea cuentas durante la inicialización del directorio de datos. Hay algunas cuentas que deben considerarse reservadas en MySQL:

  • 'root'@'localhost':esta cuenta es una cuenta de superusuario y tiene privilegios divinos en todas las bases de datos MySQL (puede realizar cualquier operación en cualquier base de datos MySQL). Vale la pena señalar que también se puede cambiar el nombre del usuario raíz para evitar exponer una cuenta con muchos privilegios. Para cambiar el nombre de la cuenta, ejecute la siguiente consulta:
RENAME USER ‘root’@’localhost’ TO ‘username’@’localhost’;
  • Asegúrese de emitir un FLUSH PRIVILEGES; después de cambiar el nombre de la cuenta para que los cambios surtan efecto.
  • ‘mysql.sys’@’localhost’:esta cuenta es un usuario del sistema que se utiliza como definidor de vistas, procedimientos y funciones en el esquema del sistema. Agregado en MySQL 5.7.9 para evitar problemas que puedan surgir si se cambia el nombre de la cuenta raíz.
  • ‘mysql.session’@’localhost’:los complementos usan internamente esta cuenta para acceder al servidor.

En este caso, no puede hacer mucho en cuanto a la seguridad, pero tenga en cuenta que la cuenta raíz tiene privilegios divinos, lo que significa que puede realizar cualquier operación en cualquier base de datos MySQL y tenga cuidado. al decidir a quién otorgar los privilegios para acceder a la cuenta. Además, tenga en cuenta para qué se utilizan las otras cuentas de MySQL.

Administración de contraseñas en MySQL

MySQL también admite funciones de administración de contraseñas. Algunos de ellos incluyen:

  • La capacidad de hacer caducar periódicamente las contraseñas;
  • La capacidad de evitar la reutilización de contraseñas;
  • La capacidad de generar contraseñas;
  • La capacidad de verificar si la contraseña en uso es segura;
  • La capacidad de bloquear temporalmente a los usuarios después de demasiados intentos fallidos de inicio de sesión.

Ahora, analizaremos más a fondo estas opciones.

Para caducar una contraseña manualmente, use la instrucción ALTER USER así:

ALTER USER ‘user’@’localhost’ PASSWORD EXPIRE;

Para establecer una política global, modifique el archivo my.cnf para que incluya el parámetro default_password_lifetime. El parámetro se puede definir debajo de la sección [mysqld] (el siguiente ejemplo establece la vigencia de la contraseña en 3 meses (90 días)):

default_password_lifetime=90

Si desea que las contraseñas nunca caduquen, establezca el parámetro default_password_litetime en 0.
También puede establecer la caducidad de la contraseña para usuarios específicos. Si desea establecer el intervalo de caducidad de la contraseña para un usuario llamado demo_user, puede usar el siguiente ejemplo:

ALTER USER ‘demo_user’@’localhost’ PASSWORD EXPIRE INTERVAL 90 DAY;

Para deshabilitar la caducidad de la contraseña:

ALTER USER ‘demo_user’@’localhost’ PASSWORD EXPIRE NEVER;

Para restablecer la política de caducidad de contraseña global:

ALTER USER ‘demo_user’@’localhost’ PASSWORD EXPIRE DEFAULT;

​​Las restricciones de reutilización de contraseñas no permiten que se reutilicen; para utilizar esta función, utilice las variables password_history y password_reuse_interval. Puede poner estas variables en my.cnf mirando el ejemplo a continuación o configurarlas en tiempo de ejecución agregando SET PERSIST delante de las declaraciones a continuación.

Para prohibir la reutilización de cualquiera de las 5 contraseñas utilizadas anteriormente más recientes de 365 días, utilice:

password_history=5
password_reuse_interval=365

Para requerir un mínimo de 5 cambios de contraseña antes de permitir su reutilización:

ALTER USER ‘demo_user’@’localhost’ PASSWORD HISTORY 5;

Se puede hacer lo mismo al crear un usuario:reemplace ALTER USER con CREATE USER.

Para generar una contraseña aleatoria al crear un usuario, ejecute:

CREATE USER [email protected] IDENTIFIED BY RANDOM PASSWORD;

Para cambiar la contraseña de un usuario a una generada aleatoriamente:

SET PASSWORD FOR [email protected] TO RANDOM;

Su contraseña aleatoria se mostrará debajo.

Recuerde que las contraseñas aleatorias predeterminadas tienen una longitud de 20 caracteres. La longitud puede ser controlada por la variable generate_random_password_length que tiene un rango de 5 a 255.

Para verificar si una contraseña utilizada es segura, puede usar la variable VALIDATE_PASSWORD_STRENGTH:la función muestra un número de 0 a 100, siendo 0 el más débil y 100 el más fuerte:
SELECCIONE VALIDATE_PASSWORD_STRENGTH('contraseña');

Bloqueo de cuenta en MySQL

MySQL 8.0.19 también introdujo la capacidad de bloquear cuentas de usuario temporalmente. Esto se puede lograr usando las variables FAILED_LOGIN_ATTEMPTS y PASSWORD_LOCK_TIME.

Para habilitar el bloqueo de cuenta al crear un usuario, ejecute:

CREATE USER ‘demo_user’@’localhost’ IDENTIFIED BY ‘password’ FAILED_LOGIN_ATTEMPTS 5 PASSWORD_LOCK_TIME 5;

El valor después de FAILED_LOGIN_ATTEMPTS especifica después de cuántos intentos fallidos se bloquea la cuenta, el valor después de PASSWORD_LOCK_TIME especifica el tiempo de bloqueo de la cuenta en días. También es posible especificar un valor que no termine hasta que se desbloquee la cuenta especificando PASSWORD_LOCK_TIME como SIN LÍMITES.

Complementos de seguridad ofrecidos por MySQL

MySQL también ofrece un par de complementos que pueden mejorar aún más las capacidades de seguridad. MySQL ofrece:

  • Complementos de autenticación;
  • Complementos de control de conexión;
  • Complementos de validación de contraseña;
  • Complementos de auditoría;
  • Complementos de cortafuegos;

Estos complementos se pueden usar para varias cosas en cuanto a seguridad:

Complementos de autenticación

Los complementos de autenticación pueden permitir a los usuarios elegir entre varios métodos de autenticación conectables disponibles en MySQL. Se pueden usar junto con declaraciones CREATE USER o ALTER USER. He aquí un ejemplo: 

CREATE USER ‘user_1’@’localhost’ IDENTIFIED WITH mysql_native_password BY ‘password’;

Esta consulta implementaría la autenticación mediante el método nativo de hash de contraseña.

Complementos de control de conexión

Los complementos de control de conexión pueden introducir un retraso cada vez mayor en las respuestas del servidor a los intentos de conexión si los intentos de conexión superan un cierto número; pueden detener posibles ataques de fuerza bruta. Esta biblioteca de complementos se introdujo en MySQL en la versión 5.7.17 y se puede agregar a MySQL a través de my.cnf o cargando los complementos en el servidor en tiempo de ejecución.
Para agregar los complementos a my.cnf , agregue la siguiente línea debajo de [mysqld]:

plugin-load-add=connection_control.so

Después de modificar el archivo, guarde los cambios y reinicie MySQL.
Para cargar los complementos en el servidor durante el tiempo de ejecución, ejecute:

INSTALL PLUGIN CONNECTION_CONTROL SONAME ‘connection_control.so’;
INSTALL PLUGIN CONNECTION_CONTROL_FAILED_LOGIN_ATTEMPTS SONAME ‘connection_control.so’;

Ajuste el sufijo .so según sea necesario. Si ha logrado todo correctamente, la tabla CONNECTION_CONTROL_FAILED_LOGIN_ATTEMPTS debería contener todos los intentos fallidos de conexión.

Complementos de validación de contraseña

Los complementos de validación de contraseñas pueden permitir a los usuarios usar contraseñas más seguras si se usan correctamente. El complemento de validación de contraseña se puede instalar a través de my.cnf o cargando el complemento en el servidor en tiempo de ejecución. Para instalar el complemento a través de my.cnf, agregue la siguiente línea debajo de [mysqld], luego reinicie el servidor:

plugin-load-add=validate_password.so

Para cargar el complemento en tiempo de ejecución, ejecute la siguiente instrucción:

INSTALL PLUGIN validate_password SONAME ‘validate_password.so’;

Para cargar el complemento durante el tiempo de ejecución y evitar que se elimine, agregue validate-password=FORCE_PLUS_PERMANENT a my.cnf.

Para evitar que el servidor se ejecute si el complemento no está inicializado, use la opción --validate-password con un valor de FORCE o FORCE_PLUS_PERMANENT.

La política de fortaleza de la contraseña también se puede cambiar:para hacerlo, cambie el valor de validate_password_policy a BAJO, MEDIO o FUERTE. El valor de BAJO comprueba solo la longitud de la contraseña, la política MEDIA agrega algunas condiciones y la política FUERTE agrega la condición de que las subcadenas de contraseña que constan de 4 o más caracteres no deben coincidir con palabras en un archivo de diccionario que se puede especificar modificando la variable validate_password_dictionary_file.

Complementos de llavero

Los complementos de llavero pueden permitir que los componentes y complementos del servidor almacenen de forma segura información confidencial para su recuperación. Para cargar el complemento en MySQL, agregue lo siguiente debajo de [mysqld]:

early-plugin-load=keyring_file.so

Para especificar el archivo del depósito de claves, agregue lo siguiente (la variable keyring_vault_config debe apuntar al archivo de configuración):

loose-keyring_vault_config=”/var/lib/mysql_keyring/keyring_vault.conf”

El archivo de depósito de claves debe contener la variable vault_url que define la dirección del servidor de la bóveda, la variable secret_mount_point que define el nombre del punto de montaje donde la bóveda del depósito de claves almacena las claves y un token que debe ser definido por el servidor de la bóveda. Opcionalmente, también se puede definir la variable vault_ca (debe apuntar al certificado de CA utilizado para firmar los certificados de la bóveda).

Reiniciar el servidor para que los cambios surtan efecto;

Complementos de auditoría

Los complementos de auditoría pueden habilitar la supervisión, el registro y el bloqueo de la actividad realizada en servidores MySQL. Para instalar MySQL Enterprise Audit, ejecute un script ubicado en el directorio compartido de su instancia de MySQL (evite poner la contraseña de su instancia de MySQL en la terminal; use my.cnf):

mysql < /path/to/audit_log_filter_linux_install.sql

También puede evitar que el complemento se elimine en tiempo de ejecución:agregue lo siguiente en la sección [mysqld]:

audit_log=FORCE_PLUS_PERMANENT

Reinicie el servidor para aplicar los cambios. Tenga en cuenta que el registro basado en reglas no registra eventos auditables de forma predeterminada, por lo que para que registre todo, cree un filtro:

SELECT audit_log_filter_set_filter(‘log_filter’, ‘{ “filter”: { “log”: true } }’);

Luego asígnelo a una cuenta:

SELECT audit_log_filter_set_user(‘%’, ‘log_filter’);

Tenga en cuenta que los complementos de auditoría solo están disponibles en MySQL Enterprise Edition;

Complementos de cortafuegos

Los complementos de firewall pueden permitir a los usuarios permitir o denegar la ejecución de instrucciones SQL específicas en función de patrones específicos. MySQL Enterprise Firewall se introdujo en MySQL 5.6.24:puede proteger los datos al monitorear, alertar y bloquear actividades no autorizadas:puede bloquear ataques de inyección SQL, monitorear amenazas y bloquear tráfico sospechoso, así como detectar intrusiones en la base de datos. El cortafuegos también puede registrar declaraciones bloqueadas:se pueden inspeccionar y también se puede observar un recuento en tiempo real de las declaraciones aprobadas y rechazadas.

Para instalar MySQL Enterprise Firewall, simplemente habilítelo al instalar MySQL Server en Windows, también se puede instalar, deshabilitar o desinstalar con la ayuda de MySQL Workbench 6.3.4. El cortafuegos también se puede instalar manualmente ejecutando un script en el directorio compartido de su instalación de MySQL. Para habilitar el firewall, agregue la siguiente línea debajo de [mysqld] y reinicie el servidor:

mysql_firewall_mode=ON

El firewall también se puede habilitar en tiempo de ejecución:

SET GLOBAL mysql_firewall_mode = ON;

Alternativamente, para conservar el cortafuegos (lo que significa que el cortafuegos no tendrá que volver a habilitarse en cada reinicio posterior del servidor):

SET PERSIST mysql_firewall_mode = ON;

Luego, otorgue un privilegio FIREWALL_ADMIN a cualquier cuenta que administre el firewall y el privilegio FIREWALL_USER a cualquier cuenta que solo deba tener acceso a sus propias reglas de firewall. Además, otorgue el privilegio EXECUTE para los procedimientos almacenados del firewall en la base de datos mysql. Para que el cortafuegos funcione, registre perfiles con él, luego entrene al cortafuegos para conocer las declaraciones permitidas que la base de datos puede ejecutar y luego dígale al cortafuegos que compare las declaraciones entrantes con la lista blanca establecida. Cada perfil tiene un modo operativo:APAGADO, GRABANDO, PROTEGIENDO o DETECTANDO. APAGADO deshabilita el perfil, GRABACIÓN entrena el firewall, PROTECCIÓN permite o deniega la ejecución de sentencias y DETECCIÓN detecta (pero no bloquea) los intentos de intrusión. Las reglas para un perfil específico se pueden restablecer configurando su valor en RESET. APAGADO desactivará el perfil. Para establecer el modo, utiliza la siguiente consulta, donde name es el nombre del perfil y OFF es el modo operativo: 

CALL mysql.sp_set_firewall_mode(name, ‘OFF’);

El complemento de firewall también está disponible solo en MySQL Enterprise Edition.

Proteger las copias de seguridad de MySQL

En lo que respecta a las copias de seguridad de MySQL, tiene un par de opciones.

  • Si está utilizando mysqldump, puede almacenar su nombre de usuario y contraseña en my.cnf e invocar mysqldump así (el siguiente comando volcará todas las bases de datos en un archivo /home/backup.sql):
$ mysqldump --defaults-extra-file=/var/lib/my.cnf --single-transaction --all-databases > /home/backup.sql
  • Al almacenar su nombre de usuario y contraseña dentro de my.cnf, no escribe su contraseña dentro de la terminal; este método para realizar copias de seguridad es más seguro porque mientras se ejecuta el volcado, el comando se puede ver a través de ps ax. comando.
  • También puede considerar usar mysqldump-secure, que es un script contenedor compatible con POSIX que es capaz de comprimir y cifrar copias de seguridad teniendo en cuenta una fuerte seguridad. .

  • Las copias de seguridad se pueden cifrar mediante OpenSSL; simplemente tome su copia de seguridad y luego cifre con el siguiente comando:

    $ openssl enc -aes-256-cbc -salt -in backup.tar.gz -out backup.tar.gz.enc -k password

    El comando anterior creará un nuevo archivo cifrado backup.tar.gz.enc en el directorio actual. El archivo se cifrará con la contraseña que eligió (reemplace la contraseña con la contraseña deseada). El archivo se puede descifrar más tarde ejecutando el siguiente comando:

    $ openssl aes-256-cbc -d -in backup.tar.gz.enc -out backup.tar.gz -k password

    Reemplace la contraseña con su contraseña.

  • mysqldump tiene otra opción para cifrar sus copias de seguridad (el siguiente ejemplo también las comprime con gzip):

    $ mysqldump --all-databases --single-transaction --triggers --routines | gzip | openssl  enc -aes-256-cbc -k password > backup.xb.enc

    Reemplace la contraseña con la contraseña deseada.

  • También puede cifrar sus copias de seguridad mediante mariabackup o xtrabackup. Aquí hay un ejemplo de la documentación de MariaDB:

    $ mariabackup --user=root --backup --stream=xbstream  | openssl  enc -aes-256-cbc -k password > backup.xb.enc

    Reemplace la contraseña con la contraseña deseada.

  • Las copias de seguridad también se pueden encriptar usando ClusterControl; si la opción de encriptación está habilitada para una copia de seguridad en particular, ClusterControl encriptará la copia de seguridad usando AES-256 CBC (el cifrado ocurre en el nodo de respaldo). Si la copia de seguridad se almacena en un nodo de controlador, los archivos de copia de seguridad se transmiten en un formato cifrado mediante socat o netcat. Si la compresión está habilitada, ClusterControl primero comprimirá la copia de seguridad y luego la cifrará. La clave de cifrado se generará automáticamente si no existe, luego se almacenará dentro de la configuración de CMON en la opción backup_encryption_key. Tenga en cuenta que esta clave está codificada y debe decodificarse primero. Para hacerlo, ejecute el siguiente comando:

    $ cat /etc/cmon.d/cmon_ClusterID.cnf | grep ^backup_encryption_key | cut -d"'" -f2 | base64 -d > keyfile.key

    El comando leerá backup_encryption_key y decodificará su valor en una salida binaria. El archivo de claves se puede usar para descifrar la copia de seguridad de la siguiente manera:

    $ cat backup.aes256 | openssl enc -d -aes-256-cbc -pass file:/path/to/keyfile.key > backup_file.xbstream.gz

    Para obtener más ejemplos, consulte la documentación de ClusterControl.

Conclusión

En estas publicaciones sobre la seguridad de MySQL, cubrimos algunas medidas de seguridad que pueden ser útiles si siente la necesidad de reforzar la seguridad de su(s) instancia(s) de MySQL. Si bien no cubrimos absolutamente todo, creemos que estos puntos pueden ser un buen punto de partida para reforzar la seguridad de su instalación de MySQL. Tome de estas publicaciones lo que quiera, haga su propia investigación y aplique las medidas de seguridad más aplicables en su situación.