Invoke multiple commands inside a process in interactive ssh mode [duplicate]

橙三吉。 提交于 2019-12-23 03:27:11

问题


I started using paramiko for invoking commands on my server from python script on my computer.

I wrote the following code:

from paramiko import client

class ssh:
    client = None

    def __init__(self, address, port, username="user", password="password"):
        # Let the user know we're connecting to the server
        print("Connecting to server.")
        # Create a new SSH client
        self.client = client.SSHClient()
        # The following line is required if you want the script to be able to access a server that's not yet in the known_hosts file
        self.client.set_missing_host_key_policy(client.AutoAddPolicy())
        # Make the connection
        self.client.connect(address, port, username=username, password=password, look_for_keys=False)

    def sendcommand(self, command):
        # Check if connection is made previously
        if self.client is not None:
            stdin, stdout, stderr = self.client.exec_command(command)
            while not stdout.channel.exit_status_ready():
                # Print stdout data when available
                if stdout.channel.recv_ready():
                    # Retrieve the first 1024 bytes
                    _data = stdout.channel.recv(1024)
                    while stdout.channel.recv_ready():
                        # Retrieve the next 1024 bytes
                        _data += stdout.channel.recv(1024)

                    # Print as string with utf8 encoding
                    print(str(_data, "utf8"))
        else:
            print("Connection not opened.")


    def closeconnection(self):
        if self.client is not None:
            self.client.close()

def main():
    connection = ssh('10.40.2.222', 2022 , "user" , "password")
    connection.sendcommand("cd /opt/process/bin/; ./process_cli; scm")    
    print("here")

    #connection.sendcommand("yes")
    #connection.sendcommand("nsgadmin")
    #connection.sendcommand("ls")

    connection.closeconnection()

if __name__ == '__main__':
    main()

Now , the last command in the command I am sending to my server (scm) is a command that is should be sent to the process "process_cli" that I am running in the server and should print me the output of the process (the process gets input from the stdin of the server's shell and printing the output to the stdout of the server's shell).
When I am running in interactive mode everything ok but when I running the script I get success with connecting to my server and running all the basic shell commands on this server (example: ls , pwd etc.) but I can't run any commands on the process that is running inside this server.

How can I fix this issue?


回答1:


SSH "exec" channel (which is used by SSHClient.exec_command) executes each command in a separate shell. As a consequence:

  1. cd /opt/process/bin/ will have no effect at all on ./process_cli.
  2. scm will be executed as a shell command, not as a sub-command of process_cli.

You need to:

  1. Execute cd and process_cli as one command (in the same shell):

    stdin, stdout, stderr = client.exec_command('cd /opt/process/bin/ && ./process_cli') 
    

    or

    stdin, stdout, stderr = client.exec_command('/opt/process/bin/process_cli') 
    
  2. Feed the (sub)commands of process_cli to its standard input:

    stdin.write('scm\n')
    stdin.flush()
    

Similar questions:

  • Execute multiple commands in Paramiko so that commands are affected by their predecessors
  • Execute (sub)commands in secondary shell/command on SSH server in Paramiko


来源:https://stackoverflow.com/questions/55469294/invoke-multiple-commands-inside-a-process-in-interactive-ssh-mode

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!