2012-02-03 3 views
3

서버 목록에서 반복하여 명령을 실행하거나 로그인 할 수 있도록 서버 그룹에서 sshd configs를 변경하는 암호를 &으로 변경하려고합니다. 암호없는 SSH 키를 사용하여 루트를 통해.pexpect와 ssh : su - root 다음에 명령 문자열을 형식화하는 방법 -c

나는 이것을 bash에서 쉽게 할 수 있지만 파이썬을 배우려고 노력 중이며 (분명히) 수동으로 암호를 입력하지 않으려합니다.

import pexpect 

USER="user" 
HOST="192.168.1.1" 
USERPASS="userpass" 
ROOTPASS="rootpass" 

COMMAND1="scp /Users/user/.ssh/id_rsa.pub /Users/user/github/ssh-pexpect/sshd_config %[email protected]%s:/tmp/" % (USER, HOST) 

COMMAND2="ssh -o StrictHostKeyChecking=no -t %[email protected]%s \"su - root -c \"chown root:root /tmp/id_rsa.pub; chmod 600 /tmp/id_rsa.pub; chown root:root /tmp/sshd_config; mkdir /root/.ssh; chown root:root /root/.ssh; chmod 700 /root/.ssh; mv /tmp/id_rsa.pub /root/.ssh/authorized_keys; mv /tmp/sshd_config /etc/ssh/; service sshd reload\"\"" % (USER, HOST) 

child = pexpect.spawn(COMMAND1) 
child.expect('password:') 
child.sendline(USERPASS) 
child.expect(pexpect.EOF) 
print child.before 

child = pexpect.spawn(COMMAND2) 
child.expect('password:') 
child.sendline(USERPASS) 
child.expect('Password:') 
child.sendline(ROOTPASS) 
child.expect(pexpect.EOF) 
print child.before 

내가 실행하는 명령어 1 (scp'ing :

scp ~/.ssh/id_rsa.pub /etc/ssh/sshd_config [email protected]:/tmp/ 

ssh -o StrictHostKeyChecking=no -t [email protected] "su - root -c \"chown root:root /tmp/id_rsa.pub; chmod 600 /tmp/id_rsa.pub; chown root:root /tmp/sshd_config; mkdir /root/.ssh; chown root:root /root/.ssh; chmod 700 /root/.ssh; mv /tmp/id_rsa.pub /root/.ssh/authorized_keys; mv /tmp/sshd_config /etc/ssh/; service sshd reload\"" 

내가 pexpect 파이썬에서 이렇게 가까이 왔 : 여기

는 내가하고 싶은 일의 떠들썩한 파티입니다) 잘 작동합니다. 그러나 Command2를 실패 : 나는 스크립트를 실행하기 전에 원격 서버의/etc/ssh/sshd_config 파일을 제거하면

server1:ssh-pexpect user$ python test4.py 

id_rsa.pub         100% 410  0.4KB/s 00:00  
sshd_config         100% 3498  3.4KB/s 00:00  

Traceback (most recent call last): 
    File "test4.py", line 25, in <module> 
    child.expect(pexpect.EOF) 
    File "/Library/Python/2.7/site-packages/pexpect.py", line 1316, in expect 
    return self.expect_list(compiled_pattern_list, timeout, searchwindowsize) 
    File "/Library/Python/2.7/site-packages/pexpect.py", line 1330, in expect_list 
    return self.expect_loop(searcher_re(pattern_list), timeout, searchwindowsize) 
    File "/Library/Python/2.7/site-packages/pexpect.py", line 1414, in expect_loop 
    raise TIMEOUT (str(e) + '\n' + str(self)) 
pexpect.TIMEOUT: Timeout exceeded in read_nonblocking(). 
<pexpect.spawn object at 0x102b796d0> 
version: 2.4 ($Revision: 516 $) 
command: /usr/bin/ssh 
args: ['/usr/bin/ssh', '-o', 'StrictHostKeyChecking=no', '-t', '[email protected]', 'su - root -c chown', 'root:root', '/tmp/id_rsa.pub;', 'chmod', '600', '/tmp/id_rsa.pub;', 'chown', 'root:root', '/tmp/sshd_config;', 'mkdir', '/root/.ssh;', 'chown', 'root:root', '/root/.ssh;', 'chmod', '700', '/root/.ssh;', 'mv', '/tmp/id_rsa.pub', '/root/.ssh/authorized_keys;', 'mv', '/tmp/sshd_config', '/etc/ssh/;', 'service', 'sshd', 'reload'] 
searcher: searcher_re: 
    0: EOF 
buffer (last 100 chars): : Permission denied 
mv: try to overwrite `/etc/ssh/sshd_config', overriding mode 0600 (rw-------)? 
before (last 100 chars): : Permission denied 
mv: try to overwrite `/etc/ssh/sshd_config', overriding mode 0600 (rw-------)? 
after: <class 'pexpect.TIMEOUT'> 
match: None 
match_index: None 
exitstatus: None 
flag_eof: False 
pid: 3612 
child_fd: 4 
closed: False 
timeout: 30 
delimiter: <class 'pexpect.EOF'> 
logfile: None 
logfile_read: None 
logfile_send: None 
maxread: 2000 
ignorecase: False 
searchwindowsize: None 
delaybeforesend: 0.05 
delayafterclose: 0.1 
delayafterterminate: 0.1 

내가 얻을 :

server1:ssh-pexpect user$ python test4.py 
id_rsa.pub         100% 410  0.4KB/s 00:00  
sshd_config         100% 3498  3.4KB/s 00:00  


chown: missing operand 
Try `chown --help' for more information. 
chown: changing ownership of `/tmp/sshd_config': Operation not permitted 
mkdir: cannot create directory `/root/.ssh': Permission denied 
chown: cannot access `/root/.ssh': Permission denied 
chmod: cannot access `/root/.ssh': Permission denied 
mv: accessing `/root/.ssh/authorized_keys': Permission denied 
mv: cannot move `/tmp/sshd_config' to `/etc/ssh/sshd_config': Permission denied 
bash: service: command not found 
Connection to 192.168.1.1 closed. 

내가 디버깅하는 방법을 모르겠어요 이게 어디서 엉망인지 알아봐. 그래도 COMMAND2 구문 분석이 적절하다고 생각하지 않습니다. Python에 익숙하지 않으므로 조언을 제공해 주시면 감사하겠습니다. 감사합니다. .

+0

적절한 보안을 위해 원격 호스트의 '/ tmp' 디렉토리에 제한된 디렉토리를 복사해야합니다. 악의적 인 사용자가'/ tmp'에'id_rsa.pub'라는 이름으로 심볼릭 링크를 만든다면, 그들은 여러 가지 불쾌한 일을 할 수 있습니다. 약간 더 나은 보안을 위해, 파일을 홈 디렉토리에 복사하십시오. 아마, 침입자는 권한이 없습니다. – tripleee

답변

3

COMMAND2를 큰 따옴표로 묶고 포함 된 큰 따옴표를 올바르게 이스케이프 처리해야하지만 이미 이스케이프 된 큰 따옴표를 이중 탈출해야합니다. 즉, 실제로 파이썬 문제가 아닙니다. 하지만 가장 바깥 쪽 따옴표를 파이썬 삼중 따옴표로 바꿀 수는 있습니다. 읽을 수도 있습니다.

편집 : 실제로, 인용문의 모호성을 제거하면됩니다. 셸은 작은 따옴표도 제공하므로 작은 따옴표를 사용하는 솔루션이 좋습니다. 파이썬은 작은 따옴표 나 다른 많은 인용 부호를 사용할 수있게 해줄 것입니다. 만약 당신이 이미 문제를 풀지 않았다면 추천 할 것입니다. (문자열 자체를 변경할 필요가없는 따옴표를 선택할 수 있기 때문에; 오류의 경우).

그래서, 이들의 괜찮을한다 : 나는 인접한 큰 따옴표를 명확하게하기 위해 삼중 따옴표에 공간을 추가하는 데 필요한

COMMAND2='ssh -o StrictHostKeyChecking=no -t %[email protected]%s "su - root -c \"chown root:root /tmp/id_rsa.pub; chmod 600 /tmp/id_rsa.pub; chown root:root /tmp/sshd_config; mkdir /root/.ssh; chown root:root /root/.ssh; chmod 700 /root/.ssh; mv /tmp/id_rsa.pub /root/.ssh/authorized_keys; mv /tmp/sshd_config /etc/ssh/; service sshd reload\""' % (USER, HOST) 

COMMAND2="""ssh -o StrictHostKeyChecking=no -t %[email protected]%s "su - root -c \"chown root:root /tmp/id_rsa.pub; chmod 600 /tmp/id_rsa.pub; chown root:root /tmp/sshd_config; mkdir /root/.ssh; chown root:root /root/.ssh; chmod 700 /root/.ssh; mv /tmp/id_rsa.pub /root/.ssh/authorized_keys; mv /tmp/sshd_config /etc/ssh/; service sshd reload\"" """ % (USER, HOST) 

COMMAND2="ssh -o StrictHostKeyChecking=no -t %[email protected]%s 'su - root -c \"chown root:root /tmp/id_rsa.pub; chmod 600 /tmp/id_rsa.pub; chown root:root /tmp/sshd_config; mkdir /root/.ssh; chown root:root /root/.ssh; chmod 700 /root/.ssh; mv /tmp/id_rsa.pub /root/.ssh/authorized_keys; mv /tmp/sshd_config /etc/ssh/; service sshd reload\"'" % (USER, HOST) 

. 그러나 대신에 트리플 작은 따옴표를 사용할 수 있습니다. 또한, (단일 또는 이중) 삼중 따옴표 크게 가독성이 향상, 당신은 줄 바꿈을 포함 할 수 있습니다 :

COMMAND2='''ssh -o StrictHostKeyChecking=no -t %[email protected]%s "su - root -c ' 
    chown root:root /tmp/id_rsa.pub 
    chmod 600 /tmp/id_rsa.pub 
    chown root:root /tmp/sshd_config 
    mkdir /root/.ssh 
    chown root:root /root/.ssh 
    chmod 700 /root/.ssh 
    mv /tmp/id_rsa.pub /root/.ssh/authorized_keys 
    mv /tmp/sshd_config /etc/ssh/ 
    service sshd reload'"''' % (USER, HOST) 
+0

감사합니다. 문자열의 예를 복사하거나 지나칠 수 있습니까? 나는 double-escaping과 triple quoting의 가장 바깥 쪽 따옴표를 여러 버전으로 시도했지만 아직 COMMAND2를 제대로 해석하지 못했습니다. 확실히 파이썬 문제가 아니라 내 뇌에 문제가 있습니다. :) –

+0

명확하고 훌륭한 설명에 감사드립니다. –

1

나는 따옴표 탈출하는 방법을 알아낼 대신 노력의 작은 따옴표가는 결국 :

COMMAND2="ssh -o StrictHostKeyChecking=no -t %[email protected]%s \"su - root -c 'chown root:root /tmp/id_rsa.pub; chmod 600 /tmp/id_rsa.pub; chown root:root /tmp/sshd_config; mkdir /root/.ssh; chown root:root /root/.ssh; chmod 700 /root/.ssh; mv /tmp/id_rsa.pub /root/.ssh/authorized_keys; mv /tmp/sshd_config /etc/ssh/; service sshd reload'\"" % (USER, HOST) 
관련 문제