¿Qué es una alternativa segura al uso de una contraseña MySQL en la línea de comando?

35

Tenemos un script de línea de comandos PHP para versionar una base de datos. Ejecutamos este script cada vez que un desarrollador ha agregado un nuevo parche de base de datos.

El script ejecuta el parche con la línea de comando MySQL:

system('mysql --user=xxx --password=xxx < patch.sql');

Sin embargo, MySQL 5.6 ahora emite la siguiente advertencia:

Advertencia: el uso de una contraseña en la interfaz de línea de comandos puede ser inseguro

Lo cual es obviamente cierto, pero podría o no ser un problema para el usuario.

  • ¿Qué es lo seguro? alternativa entonces?
  • Alternativamente, ¿es posible deshabilitar esta advertencia?

Tenga en cuenta que no quiero tener que confiar en un archivo de contraseña externo.

Benjamín
fuente
2
Tener sus credenciales en un archivo no es un gran problema. Si una persona tiene privilegios de root en su servidor, puede omitir por completo el sistema de autenticación, simplemente reiniciando el servidor mysql con una opción en particular.
Zoredache
Este no es el mismo problema que en el duplicado sugerido . MySQL no solicita una contraseña, la proporciono y funciona bien. Estoy buscando alternativas para proporcionar la contraseña, excluyendo un archivo de contraseña.
Benjamin

Respuestas:

17

En la versión GA reciente de MySQL, es decir, la versión 5.6 , puede hacerlo a través del comando mysql_config_editor, como se describe en http://dev.mysql.com/doc/refman/5.6/en/mysql-config-editor.html

Básicamente, lo que hace es: encriptar sus credenciales de usuario / pase con un alias de host, y luego usar el alias de host, poner esta información en un archivo de configuración en su directorio de inicio, y luego, cuando lo necesite, en lugar de hacer algo como :

mysqldump -uroot --password=mycleartextpass mydatabase > dumpfile.sql

en su lugar escribes:

mysqldump --login-path=myhostalias mydatabase > dumpfile.sql

evitando así poner su contraseña en algún script en texto sin formato.

Para que esto funcione, primero debe (solo una vez) definirlo myhostaliascomo:

mysql_config_editor set --login-path=myhostalias --host=mysqlhost.localnet.com --user=root --password

Puede usar diferentes rutas de inicio de sesión para diferentes cuentas y / o hosts como desee. Muy buena idea si me preguntas.

Como nota, creo que esta funcionalidad NO existe en ninguna versión por debajo de 5.6.

Tuncay Göncüoğlu
fuente
nota: me doy cuenta de que mysql_config_editor en realidad crea un archivo de contraseña externo, sin embargo, esto no lo hace usted, es cómo funciona el sistema, por lo que no debe hacer / des / cifrar manualmente.
Tuncay Göncüoğlu
Gracias, estoy usando MySQL 5.6, así que esto no es un problema. Dicho esto, su enfoque sigue siendo problemático (al menos con la forma en que trabajamos actualmente), porque quiero tomar la contraseña de un archivo de configuración de PHP en tiempo real y pasarla dinámicamente a la línea de comando. Con lo que sugiere, aún tendría que usar la contraseña en la línea de comando cuando llame mysql_config_editor, por lo que desafortunadamente no aporta mucho más valor. También estoy tratando de evitar que el desarrollador lo haga manualmente, por lo que tengo que mantener tanto el archivo de configuración de PHP como la configuración de mysql.
Benjamin
Mi mejor solución es probablemente ignorar las advertencias por ahora. De hecho, me pregunto si hay algún problema de seguridad: debido a que se llama desde PHP, supongo que la línea de comando no está almacenada en el historial de bash ni en ningún otro lugar de la máquina.
Benjamin
no que yo sepa, no, bash history no lo almacena. sin embargo, la contraseña que está en texto sin formato en el archivo de configuración de php conlleva exactamente el mismo riesgo, solo que en otra forma. ¿tal vez prefiera almacenar la contraseña usando mysql_config_editor y almacenar la ruta de inicio de sesión en su archivo de configuración de php? De esa manera no expondrás tu contraseña en ningún lado. (pero aún tendrá que mantener la contraseña externa).
Tuncay Göncüoğlu
9

Use la opción --defaults-fileo --defaults-extra-file. Puede especificar el ID de usuario y la contraseña en él. Tiene el mismo formato que /etc/my.cnf.

Leyendo más, usted dice que no quiere tener que depender de un archivo de contraseña externo, pero esa es la única forma realmente segura. Cualquier otra cosa dejará rastros en la tabla de proceso o algo así. Incluso puede poner el archivo de contraseña en el control de versiones si realmente lo desea. Hágalo 600 (o 400) y legible solo por mysql o el usuario con el que se está ejecutando.

LSD
fuente
1
No estoy en contra del archivo de contraseña por razones de seguridad, es solo que las credenciales de MySQL son parte de una configuración global en la aplicación PHP (utilizada también para la conexión PDO), y hacerlo significaría crear un archivo de contraseña (temporal) solo en aras de ejecutar la línea de comando mysql durante la vida útil del script (unos segundos).
Benjamin
¿Cómo hacer esto en Windows Server 2012? ¿Dónde está el archivo de configuración que contiene la opción --defaults-file?
Jake
Simplemente especifique el archivo como una opción para --defaults-file como en:mysql --defaults-file c:\some\dirs\my.cnf
lsd
@Benjamin, así que si no se trata de seguridad, simplemente escriba la contraseña en la línea de comando. ¿Qué hay de malo en hacer eso (además de la seguridad)?
Pacerier
@Benjamin si ya está usando MySQL desde PHP, ¿por qué está bifurcando el mysqlcliente de la consola?
Josip Rodin
5

Tiene 4 opciones por http://dev.mysql.com/doc/refman/5.1/en/password-security-user.html

  • Use una opción -pyour_passo --password=your_passen la línea de comando
  • Use la opción -po --passworden la línea de comando sin un valor de contraseña especificado. En este caso, el programa cliente solicita la contraseña de forma interactiva:
  • Almacene su contraseña en un archivo de opciones.
  • Almacene su contraseña en la MYSQL_PWDvariable de entorno

Para sus necesidades, MYSQL_PWDpuede ser una opción, pero no es más segura. Realmente debería generar un proceso interactivo --passwordy enviar la contraseña de forma interactiva, pero esa es una solución bastante compleja para este problema.

RS
fuente
1
¿Cómo sería MYSQL_PWD menos seguro que la línea de comando? El PW nunca aparece en la lista de procesos, lo que parece ser la principal preocupación
TheLQ
1
Claro que si. man pstiene -E Display the environment as well. desde la URL he vinculado a: Este método de especificar la contraseña de MySQL debe ser considerado extremadamente inseguro y no se debe utilizar. Algunas versiones de ps incluyen una opción para mostrar el entorno de los procesos en ejecución. En algunos sistemas, si configura MYSQL_PWD, su contraseña se expone a cualquier otro usuario que ejecute ps. Incluso en sistemas sin tal versión de ps, no es prudente suponer que no hay otros métodos por los cuales los usuarios puedan examinar los entornos de proceso.
RS
Retomando de esta opción MYSQL_PWD: supongo que si configura la variable de entorno al comienzo de algún script, invoca la línea de comando de MySQL y luego aclara que luego al final del script, podría reducir al mínimo el tiempo de exposición . ¿Suena razonable?
superjos
@kormoc, por favor explique el último párrafo. ¿Cuál es esa solución bastante compleja de la que estabas hablando?
Pacerier
1
Parece que usar la variable de entorno es más seguro que la línea de comando. En un sistema Debian predeterminado, puede hacer psy ver el argumento de la línea de comandos para cada proceso de cada usuario. Pero ps esolo muestra el entorno para sus propios procesos (a menos que sea root, por supuesto). Es solo marginalmente más seguro, pero aún así es más seguro.
jlh
4

Si su script PHP ya tiene una conexión de base de datos abierta, ¿por qué no lo usa mysqli_multi_query()para importar el archivo .sql? Si la sintaxis del archivo .sql es válida, por supuesto ...

Michael Hampton
fuente
No estoy seguro de lo bien que funcionaría con archivos .sql bastante grandes.
Benjamin
1
@Benjamin Imagino que no es peor que el cliente MySQL; si realmente le preocupa la seguridad, esta sería la forma menos hackea de hacerlo, y el tamaño es un problema que puede resolver de varias maneras.
voretaq7
¿Sabes si es posible con PDO?
Benjamin
PDO no parece tener una función equivalente para lanzar un montón de consultas a la base de datos de una vez. Lo siento. Fue una idea ...
Michael Hampton