Pregunta

Recientemente tuve que desempolvar mis habilidades en Perl y scripts de shell para ayudar a algunos colegas.A los colegas en cuestión se les ha encomendado la tarea de proporcionar algunos informes desde una aplicación interna con una gran base de datos Oracle, y simplemente no tienen las habilidades para hacerlo.Si bien algunos podrían cuestionar si yo tengo esas habilidades (sonrisa), aparentemente suficientes personas piensan que las tengo como para querer decir que no puedo escabullirme de ellas.

Entonces, a mi pregunta: para extraer los informes de la base de datos, mi secuencia de comandos obviamente tiene que conectarse y ejecutar consultas.Hasta ahora no he logrado encontrar una buena solución sobre dónde almacenar el nombre de usuario y la contraseña de la base de datos, por lo que actualmente se almacena como texto sin formato en el script.

¿Existe una buena solución para esto que alguien ya haya escrito, tal vez como un módulo CPAN?¿O hay algo más que es mejor hacer, como mantener la combinación de usuario/contraseña en un archivo completamente separado que está oculto en algún otro lugar del sistema de archivos?¿O debería mantenerlos trivialmente cifrados para evitar que se eliminen de mis scripts con un grep en todo el sistema?

Editar:La base de datos Oracle se encuentra en un servidor HP-UX.
El servidor de aplicaciones (que ejecuta los scripts de shell) es Solaris.
Configurar los scripts para que sean de mi propiedad no es posible, deben ser propiedad de una cuenta de servicio a la que tenga acceso varios miembros del personal de soporte.
Los scripts están pensados ​​para ejecutarse como trabajos cron.
Me encantaría utilizar la autenticación de clave pública, pero no conozco métodos para hacer que funcione con Oracle; si existe tal método, ¡ilumíneme!

¿Fue útil?

Solución

La mejor práctica, en mi humilde opinión, sería NO contener ninguna contraseña en un script de Shell/Perl.Para eso sirve la autenticación de clave pública.

Otros consejos

Si el script se ejecuta de forma remota desde el servidor.

  1. Haz tus informes vistas
  2. Otorgue al usuario en el que está iniciando sesión SÓLO acceso para seleccionar en las vistas del informe.
  3. Simplemente guarde la contraseña.

De esa manera, todo lo que el usuario puede hacer es seleccionar los datos para su informe.Incluso si alguien obtuviera la contraseña, estaría limitado en cuanto a lo que podría hacer con ella.

Personalmente, guardo contraseñas en archivos de configuración que luego se distribuyen independientemente de la aplicación y se pueden cambiar según la máquina/entorno específico.En los scripts de shell, puede obtenerlos dentro del script principal.

Sin embargo, en Perl existen diversos enfoques.Quizás desees investigar Obteneropt::Largo para opciones de línea de comando (y además Getopt::ArgvFile para almacenarlos en un archivo de configuración simple), o mirar algo como Configuración::ArchivosIni por algo con un poco más de poder detrás.Estos son los dos tipos que uso generalmente, pero hay otros módulos de archivos de configuración disponibles.

No hay una buena solución.Puedes ofuscar un poco las contraseñas, pero no puedes protegerlas.

Si tiene control sobre la configuración de su base de datos, puede intentar conectarse mediante una canalización con nombre (al menos mysql lo admite) sin una contraseña y dejar que el sistema operativo maneje los permisos.

También puedes almacenar las credenciales en un archivo con permisos restrictivos.

Como has etiquetado ksh y bash, asumiré Linux.

La mayor parte del problema es que si el usuario puede leer el script y localizar el método que utilizó para ocultar/cifrar el archivo, también podrá hacer lo mismo manualmente.

Una mejor manera puede ser hacer lo siguiente:

  1. Cree su script de modo que solo usted pueda verlo, leerlo o abrirlo.chmod 700 eso.Codifique las contraseñas.
  2. Tener un script de "lanzador" que sea ejecutable por el usuario y realice un sudo.

De esta manera, el usuario puede ver el script del iniciador y examinarlo para ver que solo tiene una única línea de comando.Pueden ejecutarlo y funciona, pero no tienen permisos para leer el código fuente del script sudo.

No estoy seguro de qué versión de Oracle estás ejecutando.En versiones anteriores de Oracle (anteriores a 9i Advanced Security), algunos administradores de bases de datos CREATE USER OPS$SCOTT IDENTIFIED BY EXTERNALLY y establecer REMOTE_OS_AUTHENT a verdadero.

Esto significaría que su máquina solar remota podría autenticarlo como SCOTT y luego su base de datos Oracle aceptaría esa autenticación.

Esta es una mala idea.

Como puede imaginar, cualquier Windows XP con un usuario local de SCOTT podría iniciar sesión en su base de datos sin contraseña.

Desafortunadamente, es la única opción que conozco de las bases de datos Oracle 9i para no almacenar nombres de usuario/contraseñas en su secuencia de comandos o en otro lugar al que pueda acceder la máquina cliente.

Cualquiera que sea su solución, vale la pena echarle un vistazo a Oracle. Bloqueo del proyecto antes de comprometerse.

Para almacenar contraseñas, puede realizar una rutina de cifrado de dos pasos, primero con una clave codificada en su script y, opcionalmente, una segunda vez con una clave almacenada en un archivo (que se configura mediante permisos de archivo para tener acceso restringido).

En una situación determinada, puede usar un archivo de clave (+ clave del script) o, si los requisitos de la situación no son tan buenos, puede simplemente usar el cifrado usando la clave codificada en el script.En ambos casos, la contraseña se cifrará en el archivo de configuración.

No existe una solución perfecta porque de alguna manera tienes que poder descifrar y obtener la contraseña en texto claro... y si puedes hacerlo, alguien más también puede hacerlo si tiene la información correcta.

Especialmente en la situación en la que les damos un script en Perl (vs.un exe) pueden ver fácilmente cómo realiza el cifrado (y la clave codificada)... por lo que también debe permitir la opción de usar un archivo de clave (que puede protegerse mediante permisos del sistema de archivos).

Algunos ejemplos prácticos de cómo implementarlo son aquí

En UNIX, siempre hago estos scripts con setuid y almaceno la información de usuario y contraseña en un archivo que está fuertemente protegido (el árbol de directorios completo no es legible/buscable por usuarios normales y el archivo en sí solo es legible por el propietario del script) .

Manténgalos en un archivo separado, trivialmente cifrado y cree un usuario separado en la base de datos con acceso de solo lectura a las tablas necesarias.Si cree que el archivo ha sido leído, puede cerrar el acceso solo a ese usuario.

Si quiere ser más sofisticado, un programa SUID podría verificar /proc//exe y cmdline (en Linux), y solo entonces liberar el nombre de usuario.

Tuve o tuve un problema similar con los desarrolladores que implementaban código SQL en MSSQL (de hecho, en cualquier base de datos en ese servidor MSSQL, por lo que el rol tenía que ser SysAdmin) usando ANT desde un servidor Solaris.Nuevamente no quería almacenar el nombre de usuario y la contraseña en los archivos ANT build.xml, por lo que mi solución, que sé que no es ideal, es la siguiente:

  1. Almacene pares de nombre/valor para nombre de usuario y contraseña en un archivo de texto sin formato
  2. Cifre el archivo (en Solaris) y utilice una frase de contraseña que solo conozcan ciertos administradores
  3. Deje sólo el archivo cifrado en el sistema Solaris
  4. ANT build.xml ejecuta un sudo decrypt y solicita una frase de contraseña, que ingresa el administrador
  5. Fuentes ANT descifraron el archivo cargando nombre de usuario y contraseña como variables para la cadena SQL
  6. ANT eliminó inmediatamente el archivo de texto sin formato
  7. ANT implementa código y sale

Todo esto sucede en cuestión de segundos y el nombre de usuario y la contraseña de SQL nunca son visiblemente accesibles en el servidor.Como el código lo implementan administradores autorizados en producción, los desarrolladores nunca necesitan incluirlo en su código.

Estoy seguro de que podría ser mejor, pero...

JB

Es una pena no haber visto nunca este hilo antes; parece muy interesante.Agregaré mi granito de arena para cualquiera que se encuentre con el hilo en el futuro.

Recomendaría usar la autenticación del sistema operativo en el servidor de base de datos: REMOTE_OS_AUTHENT sigue siendo FALSO.

Si está invocando el script desde otra máquina, configure una clave SSH sin frases y use SSH para llegar allí.Luego puede enviar los resultados de SQL a la máquina que realiza la llamada y ésta puede procesar esta información más a fondo.

Hacer esto evita tener que codificar una contraseña en cualquier lugar.Por supuesto, si un administrador malintencionado secuestrara la clave sin frase y la usara, también podría acceder a la cuenta de usuario en el host de base de datos y luego podría realizar cualquier operación que el usuario de base de datos autenticado en el sistema operativo pudiera realizar.Para mitigar esto, puede reducir al mínimo los permisos de la base de datos para ese usuario del sistema operativo, digamos "solo lectura".

ingo

En Windows, cree una carpeta y un archivo dentro de ella que contenga las contraseñas en texto sin cifrar.Configure el usuario que ejecutaría el trabajo programado (script o lote) como la única persona con acceso de lectura/escritura a esta carpeta y archivo.(eliminar incluso el administrador).A todos los demás scripts, agregue código para leer la contraseña de texto sin cifrar de este archivo restringido.

Esto debería ser suficiente para unos pocos.

Palabras clave:Codificación de contraseña

Hay soluciones comerciales o más avanzadas, como Cyberark AIM, que pueden hacerlo mejor, pero al hacerlo de forma gratuita y lista para usar, he estado aprovechando la clave pública/privada SSH porque, por un lado, los pares de claves SSH probablemente ya creados conforman el politica de seguridad;en segundo lugar, los pares de claves SSH ya tienen un conjunto de protocolos estándar para proteger las claves mediante el permiso de archivo, el refuerzo continuo del sistema (como tripwire) o la rotación de claves.

Así es como lo hice:

  1. Genere los pares de claves ssh si aún no lo ha hecho.Los pares de claves y el directorio estarán protegidos por el protocolo/permiso predeterminado del sistema.ssh-keygen –t rsa –b 2048

  2. Use la clave pública SSH para cifrar la cadena y almacenado en el mismo directorio .ssh $ ECHO "Secretword" | OpenSSL rsautl -Enrypt -inkey ~/.ssh/id_rsa.pub -pubin -out ~/.ssh/secret.dat

  3. use la clave privada ssh para descifrar la clave y pase los parámetros a scripts/AP en tiempo real.El script/programa para incluir la línea para descifrar en tiempo real:cadena =openssl rsautl -decrypt -inkey ~/.ssh/id_rsa -in ~/.ssh/secret.dat

PD: He estado experimentando con la solución sin agente CYBERARK AIM.Es una especie de dolor que requiere cambios significativos/cambios de API para la API/script.Los mantendremos informados sobre cómo va eso.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top