블로킹 모드에서 명령을 실행할 수있게 해주는 ssh 에이전트를 구현하려고합니다. 출력은 채널에서 즉시 읽혀집니다. 사용할 수 있습니다.Python paramiko : stderr 리다이렉트는 get_pty = True의 영향을받습니다.
from paramiko import client
class SSH_Agent:
def __init__(self, server_name, username = getpass.getuser(), password = None, connection_timeout = CONNECTION_TIMEOUT):
self.ssh_agent = client.SSHClient()
self.ssh_agent.set_missing_host_key_policy(client.AutoAddPolicy())
self.ssh_agent.connect(server_name, username = username, password = password if password is not None else username, timeout = connection_timeout)
def execute_command(self, command, out_streams = [sys.stdout], err_streams = [sys.stderr], poll_intervals = POLL_INTERVALS):
stdin, stdout, stderr = self.ssh_agent.exec_command(command)
channel = stdout.channel
stdin.close()
channel.shutdown_write()
while not channel.closed or channel.recv_ready() or channel.recv_stderr_ready():
got_data = False
output_channels = select.select([channel], [], [], poll_intervals)[0]
if output_channels:
channel = output_channels[0]
if channel.recv_ready():
for stream in out_streams:
stream.write(channel.recv(len(channel.in_buffer)))
stream.flush()
got_data = True
if channel.recv_stderr_ready():
for stream in err_streams:
stream.write(channel.recv_stderr(len(channel.in_stderr_buffer)))
stream.flush()
got_data = True
if not got_data \
and channel.exit_status_ready() \
and not channel.recv_ready() \
and not channel.recv_stderr_ready():
channel.shutdown_read()
channel.close()
break
return channel.recv_exit_status()
나는 그것을 테스트 할 때
, 그것은 명령을 실행할 때 나는이 얻을 것을 제외하고는 잘 작동 (이 구현은 하나를 기반으로 내가 SO 어딘가에 여기) :
는 여기에 지금까지 가지고 무엇을 :
tput: No value for $TERM and no -T specified
나는 온라인으로 조금 읽어 및
ssh
세션 뒤에 실제 단자가 없기 때문에 그런 일이 발견.
그래서 내가 전화를 시도
paramiko
의
exec_command()
get_pty = True
과 :
stdin, stdout, stderr = self.ssh_agent.exec_command(command, get_pty = True)
그러나 나는 모든 것을 어떤 이유로 stdout
로 이동 (채널에 stderr
에 대한 데이터를 얻을 수있는 능력을 잃고 있다는 것을 발견 즉 channel.recv_stderr_ready()
은 결코 True
이 아닙니다.
recv_stderr_ready() 데이터 버퍼링되고있는 경우는 true 준비
반환은이 채널의 표준 오류 스트림에서 읽을 수 : 사실, 나는 다음 문서에서 발견. pty가없는 exec_command 또는 invoke_shell을 사용하는 채널 만 stderr 스트림에 대한 데이터를 갖습니다.
반환 값 :이 채널의 recv_stderr 호출로, 적어도 1 바이트는 즉시 리턴되는 경우는 true. 그렇지 않으면 거짓.
어떻게 둘 다 가질 수 있습니까? 즉
는 어떻게이 제거 할 수 있습니다
tput: No value for $TERM and no -T specified
아직도 내가 선택 어디든지 stderr
를 지시 할 수있는 능력을 가지면서?
편집 :
내가 그냥 생각이 ...
내가 어떻게 든 원격 셸이 TERM
변수를 정의 할 수 있었다 그 오류를 제거하려면? 이 방법이 일반적인 방법입니까 아니면 문제를 숨기는 유일한 방법일까요?
좋습니다. 그것은 트릭을했다. –