sử dụng su bên trong tập lệnh shell


12

Tôi đang tự động hóa một quy trình triển khai và tôi muốn có thể chỉ cần gọi một tệp .sh trên máy của mình, để nó tự xây dựng và tải .zip lên máy chủ và sau đó thực hiện một loạt các công cụ trên máy chủ. Một trong những điều tôi cần làm đòi hỏi tôi phải root. Vì vậy, những gì tôi muốn làm là đây:

ssh user@172.1.1.101 <<END_SCRIPT
su - 
#password... somehow...
#stop jboss
service server_instance stop
#a bunch of stuff here
#all done!
exit
END_SCRIPT

Điều này thậm chí có thể?


+1 câu hỏi hay. vấn đề thường gặp.
gMale

Câu trả lời:


15

Bạn đã xem xét một sudo ít mật khẩu thay thế?


1
Đây là cách tiếp cận tôi đã sử dụng trong quá khứ. Bạn có thể giới hạn sudo cho các lệnh được yêu cầu (bắt đầu / dừng dịch vụ), giới hạn các đặc quyền mà người dùng có để chính xác những gì bạn cần. Nó vẫn cảm thấy cồng kềnh, nhưng hoạt động.
Đánh dấu

Đây thực sự là những gì tôi đã làm ...
cmcculloh

5

Thay vì su, hãy sử dụng sudo với bộ NOPASSWD trong sudoers cho (các) lệnh thích hợp. Bạn sẽ muốn làm cho lệnh được thiết lập càng hạn chế càng tốt. Gọi nó chạy một kịch bản cho các lệnh gốc có thể là cách sạch nhất và dễ bảo mật nhất nếu bạn không quen với cú pháp tệp sudoer. Đối với các lệnh / tập lệnh yêu cầu môi trường đầy đủ được tải, sudo su - -c commandhoạt động mặc dù có thể quá mức cần thiết.



3

Bạn có thể truyền một lệnh làm đối số cho SSH để chỉ chạy lệnh đó trên máy chủ, rồi thoát:

ssh user@host "command to run"

Điều này cũng hoạt động cho một danh sách nhiều lệnh:

ssh user@host "command1; command2; command3"

Hay cách khác:

ssh user@host "
        command1
        command2
        command3
"

Như những người dùng khác đã chỉ ra trước tôi, chạy sutrên máy chủ sẽ khởi chạy một shell mới thay vì thực thi các lệnh tiếp theo trong tập lệnh dưới dạng root. Những gì bạn cần làm là sử dụng một trong hai sudohoặc su -cbuộc phân bổ TTY cho SSH bằng công -ttắc (bắt buộc nếu bạn cần nhập mật khẩu gốc):

ssh -t user@host 'su - -c "command"'
ssh -t user@host 'sudo command'

Tóm lại, một cách để hoàn thành những gì bạn muốn làm, sẽ là:

#!/bin/bash
ssh -t user@172.1.1.101 "
        sudo some_command
        sudo service server_instance stop
        sudo some_other_command
"

sudothường nhớ mức ủy quyền của bạn trong vài phút trước khi yêu cầu nhập lại mật khẩu gốc, chỉ cần thêm vào sudotất cả các lệnh bạn cần để chạy bằng root có thể là cách dễ nhất để chạy các lệnh như root trên máy chủ. Thêm một NOPASSWDquy tắc cho người dùng của bạn vào /etc/sudoerssẽ làm cho quá trình thậm chí mượt mà hơn.

Tôi hi vọng cái này giúp được :-)


Nếu bạn cần thêm thông tin về việc thêm NOPASSWDquy tắc đó , hãy kiểm tra các ví dụ ở cuối man sudoers. Ngoài ra, hãy nhớ sử dụng visudokhi chỉnh sửa sudoerstập tin của bạn để tránh bị hỏng!
jabirali

Tôi không thể làm cho "lệnh" su hoạt động. Làm thế nào tôi có thể cung cấp mật khẩu cho su?
cmcculloh

Nếu bạn chọn sử dụng su -cthay vì sudo, bạn nên chạy SSH bằng -tcờ - bạn sẽ được nhắc nhập mật khẩu gốc trên máy chủ khi lệnh được thực thi. Cung cấp mật khẩu trực tiếp sulàm đối số dòng lệnh không được hỗ trợ (theo như tôi biết), cũng không được khuyến nghị - vì đơn giản ps -ef | grep sucho thấy tất cả các đối số được truyền tới su, bao gồm mọi mật khẩu được cung cấp từ dòng lệnh ...
jabirali

Về cách bạn gọi su -cqua SSH: ssh -t user@host 'su -lc "<br /> echo this is a test <br /> echo this is another test<br /> "<br />'
jabirali

Thay thế <br />ở trên với dòng mới trong kịch bản của bạn. Off-topic: Bạn có thể thêm dòng mới vào bình luận ServerFault không? Điều đó sẽ khá hữu ích khi đăng đoạn mã ...
jabirali

2

Không. Ngay cả khi bạn nhận được mật khẩu su, bạn vẫn phải đối phó với thực tế là susẽ mở một vỏ mới, điều đó có nghĩa là các lệnh tiếp theo của bạn sẽ không được chuyển đến nó. Bạn sẽ cần phải viết một kịch bản cho các hoạt động gốc cùng với một trình trợ giúp thực thi có thể gọi nó với các đặc quyền thích hợp.


2
Hầu hết các lệnh su chấp nhận tùy chọn -c sẽ lấy làm đối số cho (các) lệnh để chạy. Tôi đồng ý rằng một tập lệnh trên chính máy chủ có lẽ là tốt nhất so với việc gửi tất cả các cmds qua ssh.
Aaron Bush

1

Viết một kịch bản mong đợi. Tôi biết bạn đã tìm thấy câu trả lời cho điều này, nhưng điều này có thể hữu ích nếu bạn phải đăng nhập vào một loạt các máy chủ yêu cầu nhập mật khẩu tương tác.

Đó là một ngôn ngữ dựa trên TCL, vì vậy nó có thể hơi lạ so với các tập lệnh shell cũ. Nhưng nó xử lý tự động hóa nhập văn bản và, bạn đoán nó, "mong đợi" một số bit đầu ra nhất định trước khi nhập bất kỳ loại nhập mật khẩu tự động hoặc leo thang đặc quyền.

Đây là một liên kết tốt như một hướng dẫn: http://bash.cyberciti.biz/security/evelopect-ssh-login-script/

Chỉ trong trường hợp trang web bị sập:

#!/usr/bin/expect -f
# Expect script to supply root/admin password for remote ssh server
# and execute command.
# This script needs three argument to(s) connect to remote server:
# password = Password of remote UNIX server, for root user.
# ipaddr = IP Addreess of remote UNIX server, no hostname
# scriptname = Path to remote script which will execute on remote server
# For example:
#  ./sshlogin.exp password 192.168.1.11 who
# ------------------------------------------------------------------------
# Copyright (c) 2004 nixCraft project <http://cyberciti.biz/fb/>
# This script is licensed under GNU GPL version 2.0 or above
# -------------------------------------------------------------------------
# This script is part of nixCraft shell script collection (NSSC)
# Visit http://bash.cyberciti.biz/ for more information.
# ----------------------------------------------------------------------
# set Variables
set password [lrange $argv 0 0]
set ipaddr [lrange $argv 1 1]
set scriptname [lrange $argv 2 2]
set arg1 [lrange $argv 3 3]
set timeout -1
# now connect to remote UNIX box (ipaddr) with given script to execute
spawn ssh root@$ipaddr $scriptname $arg1
match_max 100000
# Look for passwod prompt
expect "*?assword:*"
# Send password aka $password
send -- "$password\r"
# send blank line (\r) to make sure we get back to gui
send -- "\r"
expect eof

1

Tôi biết điều này hơi muộn nhưng cá nhân tôi sẽ sử dụng Net :: SSH :: Expect, có sẵn từ CPAN.

http://search.cpan.org/~bnegrao/Net-SSH-Expect-1.09/lib/Net/SSH/Expect.pod


Mong đợi thực sự tốt đẹp trong nhiều trường hợp nếu bạn không thể sử dụng tập lệnh ssh / bash thông thường. Tuy nhiên, nó cũng trở nên thực sự nhanh chóng và khiến bạn giả sử "bất cứ thứ gì bạn tìm thấy" ở đầu xa. Nếu bạn có thể thay đổi hệ thống mục tiêu hoặc ảnh hưởng như thế nào nó cư xử ở tất cả Tôi muốn giới thiệu thử một tuyến đường khác nhau đầu tiên. Điểm tốt để đưa nó lên đây, mặc dù.
Theuni

0

Bạn có thể sử dụng 'ssh example.com su -lc "$ cmd"'.

Khi lệnh chứa các tùy chọn, bạn cần trích dẫn nó, nếu không "su" có thể ăn chúng ("su: tùy chọn không hợp lệ - 'A').

ssh -AX -tt example.com 'su -lc "tmux new-session -A"'
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.