Por fin luego de tanto luchar pudimos hallar la contestación de esta contratiempo que muchos los lectores de este sitio web han presentado. Si tienes algo que compartir no dudes en compartir tu información.
Solución:
Aquí hay una función para ssh
con una contraseña usando pexpect
:
import pexpect
def ssh(host, cmd, user, password, timeout=30, bg_run=False):
"""SSH'es to a host using the supplied credentials and executes a command.
Throws an exception if the command doesn't return 0.
bgrun: run command in the background"""
fname = tempfile.mktemp()
fout = open(fname, 'w')
options = '-q -oStrictHostKeyChecking=no -oUserKnownHostsFile=/dev/null -oPubkeyAuthentication=no'
if bg_run:
options += ' -f'
ssh_cmd = 'ssh %[email protected]%s %s "%s"' % (user, host, options, cmd)
child = pexpect.spawn(ssh_cmd, timeout=timeout) #spawnu for Python 3
child.expect(['[pP]assword: '])
child.sendline(password)
child.logfile = fout
child.expect(pexpect.EOF)
child.close()
fout.close()
fin = open(fname, 'r')
stdout = fin.read()
fin.close()
if 0 != child.exitstatus:
raise Exception(stdout)
return stdout
Algo similar debería ser posible usando scp
.
El OpenSSH scp
La utilidad invoca el ssh
programa para hacer la conexión SSH al host remoto, y el proceso ssh maneja la autenticación. los ssh
La utilidad no acepta una contraseña en la línea de comando o en su entrada estándar. Creo que esta es una decisión deliberada por parte de los desarrolladores de OpenSSH, porque sienten que las personas deberían usar mecanismos más seguros como key-autenticación basada en. Cualquier solución para invocar ssh seguirá uno de estos enfoques:
- Usa un SSH key para la autenticación, en lugar de una contraseña.
- Utilice sshpass, expect o una herramienta similar para automatizar la respuesta a la solicitud de contraseña.
- Usar (abusar) de la función SSH_ASKPASS para obtener
ssh
para obtener la contraseña invocando otro comando, descrito aquí o aquí, o en algunas de las respuestas aquí. - Solicite al administrador del servidor SSH que habilite la autenticación basada en host y úsela. Tenga en cuenta que la autenticación basada en host solo es adecuada para determinados entornos de red. Ver notas adicionales aquí y aquí.
- Escriba su propio cliente ssh usando perl, python, java o su idioma favorito. Hay bibliotecas de clientes ssh disponibles para la mayoría de los lenguajes de programación modernos, y tendría control total sobre cómo el cliente obtiene la contraseña.
- Descargue el código fuente de ssh y cree una versión modificada de
ssh
que funciona como usted quiere. - Utilice un cliente ssh diferente. Hay otros clientes ssh disponibles, tanto gratuitos como comerciales. Uno de ellos podría adaptarse mejor a sus necesidades que el cliente OpenSSH.
En este caso particular, dado que ya estás invocando scp
de un script de python, parece que uno de estos sería el enfoque más razonable:
- Use pexpect, el módulo de expectativa de python, para invocar
scp
y darle la contraseña. - Utilice paramiko, la implementación ssh de Python, para realizar esta tarea ssh en lugar de invocar un programa externo.
La segunda respuesta que vinculó sugiere que use Pexpect (que generalmente es la forma correcta de interactuar con los programas de línea de comando que esperan entrada). Hay una bifurcación que funciona para python3 que puedes usar.