def thread(): """ Run the shell in a normal synchronous thread. """ # Set stdin/out pair for this thread. sys.stdout.set_handler(self.pty.stdout) sys.stdin.set_handler(self.pty.stdin) # Authentication try: self.username = pty_based_auth( self.auth_backend, self.pty) if self.auth_backend else '' authenticated = True except NotAuthenticated: authenticated = False if authenticated: # Create loggers logger_interface = LoggerInterface() in_shell_logger = DefaultLogger(self.pty.stdout, print_group=False) # Create options. options = Options() # Run shell shell = WebShell(self.root_node, self.pty, options, logger_interface, username=self.username) shell.session = self # Assign session to shell self.shell = shell with logger_interface.attach_in_block(in_shell_logger): with nested(*[ logger_interface.attach_in_block(l) for l in self.extra_loggers ]): shell.cmdloop() # Remove references (shell and session had circular reference) self.shell = None shell.session = None # Write last dummy character to trigger the session_closed. # (telnet session will otherwise wait for enter keypress.) sys.stdout.write(' ') # Remove std handlers for this thread. sys.stdout.del_handler() sys.stdin.del_handler() if self.doneCallback: self.doneCallback() # Stop IO reader reactor.callFromThread(self.reader.stopReading)
def __init__(self, connection, clone_shell=None, cd_path=None): self.connection = connection # Create loggers self.logger_interface = LoggerInterface() # Run shell self.shell = SocketShell(connection.root_node, connection.pty, connection.runtime_options, self.logger_interface, clone_shell=clone_shell, connection=connection) self.cd_path = cd_path
def start(root_node, interactive=True, cd_path=None, logfile=None, action_name=None, parameters=None, shell=StandaloneShell, extra_loggers=None): """ Start the deployment shell in standalone modus. (No parrallel execution, no server/client. Just one interface, and everything sequential.) """ parameters = parameters or [] # Enable logging if logfile: logging.basicConfig(filename=logfile, level=logging.DEBUG) # Make sure that stdin and stdout are unbuffered # The alternative is to start Python with the -u option sys.stdin = os.fdopen(sys.stdin.fileno(), 'r', 0) sys.stdout = os.fdopen(sys.stdout.fileno(), 'w', 0) # Create Pty object pty = Pty(sys.stdin, sys.stdout, interactive=interactive) def sigwinch_handler(n, frame): pty.trigger_resize() signal.signal(signal.SIGWINCH, sigwinch_handler) # Initialize root node root_node = root_node() # Set process title setproctitle('deploy:%s run -s' % root_node.__class__.__name__) # Loggers in_shell_logger = DefaultLogger(print_group=False) logger_interface = LoggerInterface() extra_loggers = extra_loggers or [] with logger_interface.attach_in_block(in_shell_logger): with nested(* [logger_interface.attach_in_block(l) for l in extra_loggers]): # Create shell print 'Running single threaded shell...' shell = shell(root_node, pty, logger_interface) if cd_path is not None: shell.cd(cd_path) if action_name: try: return shell.run_action(action_name, *parameters) except ActionException, e: sys.exit(1) except: import traceback traceback.print_exc() sys.exit(1)
def thread(): """ Run the shell in a normal synchronous thread. """ # Set stdin/out pair for this thread. sys.stdout.set_handler(self.pty.stdout) sys.stdin.set_handler(self.pty.stdin) # Authentication try: self.username = pty_based_auth(self.auth_backend, self.pty) if self.auth_backend else '' authenticated = True except NotAuthenticated: authenticated = False if authenticated: # Create loggers logger_interface = LoggerInterface() in_shell_logger = DefaultLogger(self.pty.stdout, print_group=False) # Create options. options = Options() # Run shell shell = WebShell(self.root_node, self.pty, options, logger_interface, username=self.username) shell.session = self # Assign session to shell self.shell = shell with logger_interface.attach_in_block(in_shell_logger): with nested(* [logger_interface.attach_in_block(l) for l in self.extra_loggers]): shell.cmdloop() # Remove references (shell and session had circular reference) self.shell = None shell.session = None # Write last dummy character to trigger the session_closed. # (telnet session will otherwise wait for enter keypress.) sys.stdout.write(' ') # Remove std handlers for this thread. sys.stdout.del_handler() sys.stdin.del_handler() if self.doneCallback: self.doneCallback() # Stop IO reader reactor.callFromThread(self.reader.stopReading)
def default_from_node(cls, node): """ Create a default environment for this node to run. It will be attached to stdin/stdout and commands will be logged to stdout. The is the most obvious default to create an ``Env`` instance. :param node: :class:`~deployer.node.base.Node` instance """ from deployer.pseudo_terminal import Pty from deployer.loggers import LoggerInterface from deployer.loggers.default import DefaultLogger pty = Pty(stdin=sys.stdin, stdout=sys.stdout, interactive=False, term_var=os.environ.get('TERM', '')) logger_interface = LoggerInterface() logger_interface.attach(DefaultLogger()) return cls(node, pty=pty, logger=logger_interface, is_sandbox=False)
def start(settings): """ Start the deployment shell in standalone modus. (No parrallel execution, no server/client. Just one interface, and everything sequential.) """ # Make sure that stdin and stdout are unbuffered # The alternative is to start Python with the -u option sys.stdin = os.fdopen(sys.stdin.fileno(), 'r', 0) sys.stdout = os.fdopen(sys.stdout.fileno(), 'w', 0) # Create Pty object pty = Pty(sys.stdin, sys.stdout) def sigwinch_handler(n, frame): pty.trigger_resize() signal.signal(signal.SIGWINCH, sigwinch_handler) # Initialize settings settings = settings() # Loggers logger = create_logger() history_logger = HistoryLogger() extra_loggers = settings.Meta.extra_loggers logger_interface = LoggerInterface() logger_interface.attach(logger) logger_interface.attach(history_logger) for l in extra_loggers: logger_interface.attach(l) # Start shell command loop StandaloneShell(settings, pty, logger_interface, history_logger.history).cmdloop() for l in extra_loggers: logger_interface.detach(l)
def __init__(self, connection, clone_shell=None, cd_path=None): self.connection = connection # Create loggers self.logger_interface = LoggerInterface() # Run shell self.shell = SocketShell( connection.root_node, connection.pty, connection.runtime_options, self.logger_interface, clone_shell=clone_shell, connection=connection, ) self.cd_path = cd_path
class ConnectionShell(object): """ Start an interactive shell for a connection. (using a separate thread.) """ def __init__(self, connection, clone_shell=None, cd_path=None): self.connection = connection # Create loggers self.logger_interface = LoggerInterface() # Run shell self.shell = SocketShell( connection.root_node, connection.pty, connection.runtime_options, self.logger_interface, clone_shell=clone_shell, connection=connection, ) self.cd_path = cd_path def openNewShellFromThread(self): """ Open new interactive shell in a new window. (Clone location of current shell.) """ # Ask the client to open a new connection self.connection.openNewConnection(focus=True) try: # Blocking call to wait for a new incoming connection new_connection = PtyManager.getNewConnectionFromThread() # Start a new shell-thread into this connection. ConnectionShell(new_connection, clone_shell=self.shell).startThread() except PtyManager.NoPtyConnection as e: print "ERROR: could not open new terminal window..." def openNewShellFromReactor(self): self.connection.openNewConnection(focus=True) d = PtyManager.getNewConnection() @d.addCallback def openShell(new_connection): new_connection.startShell(clone_shell=self.shell) @d.addErrback def failed(failure): # Opening a new shell failed. pass def startThread(self, *a, **kw): threads.deferToThread(lambda: self.thread(*a, **kw)) def thread(self, action_name=None, parameters=None, open_scp_shell=False): parameters = parameters or [] # Set stdin/out pair for this thread. sys.stdout.set_handler(self.connection.pty.stdout) sys.stdin.set_handler(self.connection.pty.stdin) self.shell.session = self # Assign session to shell # in_shell_logger: Displaying of events in shell with self.logger_interface.attach_in_block(DefaultLogger(print_group=False)): # Attach the extra loggers. with nested(*[self.logger_interface.attach_in_block(l) for l in self.connection.extra_loggers]): # Start at correct location if self.cd_path: self.shell.cd(self.cd_path) if action_name and open_scp_shell: print "Don't provide 'action_name' and 'open_scp_shell' at the same time" exit_status = 1 elif open_scp_shell: self.shell.open_scp_shell() exit_status = 0 # When an action_name is given, call this action immediately, # otherwise, run the interactive cmdloop. elif action_name: try: self.shell.run_action(action_name, *parameters) exit_status = 0 except ActionException: exit_status = 1 except Exception: import traceback traceback.print_exc() exit_status = 1 else: self.shell.cmdloop() exit_status = 0 # Remove references (shell and session have circular reference) self.shell.session = None self.shell = None # Remove std handlers for this thread. sys.stdout.del_handler() sys.stdin.del_handler() # Close connection reactor.callFromThread(lambda: self.connection.finish(exit_status=exit_status, always_close=True))
def run(thr): # Set stdin/out pair for this thread. sys.stdout.set_handler(self.pty.stdout) sys.stdin.set_handler(self.pty.stdin) # Authentication if self.requires_authentication: try: self.username = pty_based_auth() authenticated = True except NotAuthenticated: authenticated = False else: authenticated = True if authenticated: # Create loggers logger_interface = LoggerInterface() in_shell_logger = DefaultLogger(self.pty.stdout, print_group=False) # Monitor for m in monitors: m.session_created(self) # Run shell shell = WebShell(settings, self.pty, logger_interface, username=self.username) shell.session = self # Assign session to shell self.shell = shell # in_shell_logger: Displaying of events in the shell itself logger_interface.attach(in_shell_logger) if self.command: shell.handle(self.command) else: shell.cmdloop() logger_interface.detach(in_shell_logger) # Monitor for m in monitors: m.session_closed(self) # Remove references (shell and session had circular reference) self.shell = None shell.session = None # Session done del active_sessions[self.id] sys.__stdout__.write('Ended session, id=%s...\n' % self.id) sys.__stdout__.flush() # Write last dummy character to trigger the session_closed. # (telnet session will otherwise wait for enter keypress.) sys.stdout.write(' ') # Remove std handlers for this thread. sys.stdout.del_handler() sys.stdin.del_handler() if self.doneCallback: self.doneCallback() # Stop IO reader self.reader.stopReading()
class ConnectionShell(object): """ Start an interactive shell for a connection. (using a separate thread.) """ def __init__(self, connection, clone_shell=None, cd_path=None): self.connection = connection # Create loggers self.logger_interface = LoggerInterface() # Run shell self.shell = SocketShell(connection.root_node, connection.pty, connection.runtime_options, self.logger_interface, clone_shell=clone_shell, connection=connection) self.cd_path = cd_path def openNewShellFromThread(self): """ Open new interactive shell in a new window. (Clone location of current shell.) """ # Ask the client to open a new connection self.connection.openNewConnection(focus=True) try: # Blocking call to wait for a new incoming connection new_connection = PtyManager.getNewConnectionFromThread() # Start a new shell-thread into this connection. ConnectionShell(new_connection, clone_shell=self.shell).startThread() except PtyManager.NoPtyConnection as e: print 'ERROR: could not open new terminal window...' def openNewShellFromReactor(self): self.connection.openNewConnection(focus=True) d = PtyManager.getNewConnection() @d.addCallback def openShell(new_connection): new_connection.startShell(clone_shell=self.shell) @d.addErrback def failed(failure): # Opening a new shell failed. pass def startThread(self, *a, **kw): threads.deferToThread(lambda: self.thread(*a, **kw)) def thread(self, action_name=None, parameters=None, open_scp_shell=False): parameters = parameters or [] # Set stdin/out pair for this thread. sys.stdout.set_handler(self.connection.pty.stdout) sys.stdin.set_handler(self.connection.pty.stdin) self.shell.session = self # Assign session to shell # in_shell_logger: Displaying of events in shell with self.logger_interface.attach_in_block(DefaultLogger(print_group=False)): # Attach the extra loggers. with nested(* [ self.logger_interface.attach_in_block(l) for l in self.connection.extra_loggers]): # Start at correct location if self.cd_path: self.shell.cd(self.cd_path) if action_name and open_scp_shell: print "Don't provide 'action_name' and 'open_scp_shell' at the same time" exit_status = 1 elif open_scp_shell: self.shell.open_scp_shell() exit_status = 0 # When an action_name is given, call this action immediately, # otherwise, run the interactive cmdloop. elif action_name: try: self.shell.run_action(action_name, *parameters) exit_status = 0 except ActionException: exit_status = 1 except Exception: import traceback traceback.print_exc() exit_status = 1 else: self.shell.cmdloop() exit_status = 0 # Remove references (shell and session have circular reference) self.shell.session = None self.shell = None # Remove std handlers for this thread. sys.stdout.del_handler() sys.stdin.del_handler() # Close connection reactor.callFromThread(lambda: self.connection.finish( exit_status=exit_status, always_close=True))
def start(root_node, interactive=True, cd_path=None, logfile=None, action_name=None, parameters=None, shell=StandaloneShell, extra_loggers=None, open_scp_shell=False): """ Start the deployment shell in standalone modus. (No parrallel execution, no server/client. Just one interface, and everything sequential.) """ parameters = parameters or [] # Enable logging if logfile: logging.basicConfig(filename=logfile, level=logging.DEBUG) # Make sure that stdin and stdout are unbuffered # The alternative is to start Python with the -u option sys.stdin = os.fdopen(sys.stdin.fileno(), 'r', 0) sys.stdout = os.fdopen(sys.stdout.fileno(), 'w', 0) # Create Pty object pty = Pty(sys.stdin, sys.stdout, interactive=interactive, term_var=os.environ.get('TERM', '')) def sigwinch_handler(n, frame): pty.trigger_resize() signal.signal(signal.SIGWINCH, sigwinch_handler) # Create runtime options options = Options() # Initialize root node root_node = root_node() # Set process title setproctitle('deploy:%s run -s' % root_node.__class__.__name__) # Loggers in_shell_logger = DefaultLogger(print_group=False) logger_interface = LoggerInterface() extra_loggers = extra_loggers or [] with logger_interface.attach_in_block(in_shell_logger): with nested( *[logger_interface.attach_in_block(l) for l in extra_loggers]): # Create shell print 'Running single threaded shell...' shell = shell(root_node, pty, options, logger_interface) if cd_path is not None: shell.cd(cd_path) if action_name and open_scp_shell: raise Exception( "Don't provide 'action_name' and 'open_scp_shell' at the same time" ) if open_scp_shell: shell.open_scp_shell() elif action_name: try: return shell.run_action(action_name, *parameters) except ActionException as e: sys.exit(1) except: import traceback traceback.print_exc() sys.exit(1) else: shell.cmdloop()