2010-06-29 41 views
7

Tôi đang vật lộn với vấn đề về nhập mật khẩu tự động trong ssh và giống như mọi người khác mà tôi đang gặp phải trong bóng tối về kỳ vọng. Cuối cùng tôi gom góp một kịch bản mà kinda làm việc:kỳ vọng thoát {} mà không có thời gian chờ

#!/usr/bin/expect -f 

# command line args 
set user_at_host [lrange $argv 0 0] 
set password [lrange $argv 1 1] 

set timeout 1 

# ssh command 
spawn ssh -S ~/.ssh/tmp.$user_at_host -M -N -f $user_at_host 

# deal with ssh prompts 
expect { 
    "*yes/no*" { send "yes\r" ; exp_continue } 
    "*assword:" { send "$password\r" ; exp_continue } 
} 

Kịch bản này chấm dứt chỉ nhờ vào dòng timeout 1, mà không có nó một cách đơn giản treo, và sẽ chấm dứt chỉ bằng cách tương tác người dùng (^C).

Khi dòng spawn là lệnh ssh thẳng về phía trước, tập lệnh chấm dứt ngay lập tức, tuy nhiên đây là not your straight forward ssh. Điều có thể khác nhau là tùy chọn -f làm cho nó chạy ở chế độ nền (nhưng tôi đã thử tập lệnh mà không có nó để không có kết quả).

Tôi đọc rằng interact hoặc expect eof có thể hữu ích, nhưng tôi không thể tìm thấy đúng câu thần chú thực sự sẽ làm điều đó.

Câu hỏi của tôi (Tôi nghĩ) là Làm cách nào để tạo tập lệnh mong đợi, tạo ra một quá trình nền, chấm dứt mà không có thời gian chờ?


Chỉnh sửa: Tôi nên dự kiến ​​(không có ý định chơi chữ) câu trả lời "sử dụng mật khẩu ssh". Trong khi đây là lời khuyên âm thanh, nó không phải là giải pháp thích hợp trong kịch bản của tôi: Tự động kiểm tra hệ thống được cài đặt vani trong môi trường đáng tin cậy, nơi thêm các khóa tin cậy vào hình ảnh là không mong muốn/có thể.

Trả lời

1

OK, vì vậy tôi tìm thấy một hoán vị mà dường như làm việc -

Trước tiên tôi cần một kịch bản wrapper mà sẽ cung cấp một dấu hiệu khi thực hiện xong:

#!/bin/bash 
"[email protected]" 
echo "done" 

Sau đó kịch bản mong đợi trở thành:

#!/usr/bin/expect -f 
set user_at_host [lrange $argv 0 0] 
set password [lrange $argv 1 1] 

# no need for timeout 1 
set timeout 60 

# use the wrapper 
spawn wrapper ssh -S ~/.ssh/tmp.$user_at_host -M -N -f $user_at_host 

expect { 
    "*yes/no*" { send "yes\r" ; exp_continue } 
    "*assword:" { send "$password\r" ; exp_continue } 
    # use the wrapper 
    "done" { exit } 
} 

Cảm ơn Douglas Leeder (đã bỏ phiếu) và jackman glenn (đã bỏ phiếu) để được tư vấn hữu ích. Tôi sẽ sẵn sàng không chấp nhận câu trả lời này, và chấp nhận bất kỳ câu trả lời thanh lịch hơn, có lẽ một trong đó làm đi với kịch bản wrapper.

Cảm ơn tất cả sự quan tâm của bạn.

1

Vòng lặp này:

expect { 
    "*yes/no*" { send "yes\r" ; exp_continue } 
    "*assword:" { send "${password}\r" ; exp_continue } 
} 

Không thể chấm dứt bất kỳ cách nào ngoại trừ thời gian chờ hoặc EOF; hai dòng khớp sẽ là exp_continue, do đó, hãy lặp lại vòng lặp.

Đi sâu vào nền nghĩa là giả mạo; cha mẹ chết, và đứa trẻ tiếp tục kết nối.

Cá nhân, tôi muốn giải quyết các yếu tố tương tác khác nhau:

  1. phím Máy chủ: Hoặc kết nối một lần bằng tay, hoặc chèn chìa khóa trực tiếp trong file known_hosts ssh.
  2. Mật khẩu: Tôi muốn sử dụng xác thực khóa cá nhân/khóa công khai. Sử dụng tác nhân để lưu trữ khóa hoặc có khóa mật khẩu.
+0

Có cách nào để thoát ngay sau khi '* mật khẩu:'? Khi tôi cố gắng thay thế 'exp_continue' bằng bất kỳ thứ gì khác, nó đã thoát ngay lập tức, nhưng dường như không gửi' the '$ {password}'. –

+0

Có thể một 'giấc ngủ 1' hoặc' mong đợi eof' hoặc 'chờ đợi'? –

+0

Xin lỗi vì đã đạp xe, nhưng tôi đang khoe khoang, và có lẽ bạn có thể giúp tôi giảm số lượng hoán vị mà tôi phải kiểm tra: 'Chờ eof'/'ngủ 1' ở trong hay ngoài' kỳ vọng {...} '" vòng lặp "? –

7

Bạn có thể muốn:

expect { 
    "*yes/no*" { send "yes\r" ; exp_continue } 
    "*assword:" { send "${password}\r" } 
} 
expect $the_prompt 
send "exit\r" 
expect eof 

CẬP NHẬT

tôi bị mất rằng bạn đang gửi một lệnh thông qua ssh. Tôi nghĩ rằng tất cả các bạn cần là:

spawn ssh [email protected] foo bar baz 
expect { 
    "*yes/no*" { send "yes\r" ; exp_continue } 
    "*assword:" { send "${password}\r" } 
    eof 
} 

Bạn muốn nhấn eof khi lệnh foo hoàn tất.

+0

Điều này đã không giải quyết được vấn đề của tôi, nhưng đã cho tôi một đầu mối quan trọng: Tôi cần một số lời nhắc khi hoàn thành. Xem câu trả lời của riêng tôi. Cảm ơn. –

0

đường tôi đã làm nó:

set user "****"  
set host "127.0.0.1"  
spawn shh [email protected]$host  
expect "password: "  
send "**??54"  
expect "$"  
interact 

(mà câu trả lời của bạn làm thế nào để sử dụng phương pháp tương tác)

Các vấn đề liên quan