openssh
secure shell,安全的遠程登錄;openssh和dropbear都是它的開源實現,ssh協議有v1和v2倆個版本,現在使用的都是v2版,v1已經不安全了;ssh基於DH算法做密鑰交換,基於RSA或DSA實現身份認證;ssh有倆種方式驗證:密碼驗證和秘鑰驗證。
openssl的組成包包括openssl、openssl-clients和openssl-server,基於C/S架構。
客戶端:ssh
常見的客戶端工具有:Windows版的putty、securecrt、xshell;linux中有ssh、sftp、scp、slogin等
配置文件:/etc/ssh/ssh_config
Port 22 #默認登錄的ssh端口 StrictHostKeyChecking ask | no #首次登錄不顯示檢查提示 CheckHostIP no #檢查主機地址是否是可信的
ssh命令:
用法:ssh username@host [CMD]
選項:
- -p port:遠程服務器監聽的端口
- -l username:指定用戶名
- -b IP:指定連接的源IP(自己主機的IP)
- -v:調試模式
- -C:壓縮方式
- -X:支持x11轉發
- -Y:支持信任x11轉發
- -t:強制偽tty分配,例:ssh -t remoteserver1 ssh remoteserver2
- -f 后台啟用
- -N 不打開遠程shell,處於等待狀態
- -g 啟用網關功能
客戶端第一次連接服務器端的時候,服務器會將自己的公鑰發送給客戶端並保存到客戶端的~/.ssh/known_hosts文件中,下次連接則不會再次詢問。
基於密碼的驗證:
1)客戶端發起ssh請求,服務器會把自己的公鑰發送給用戶;
2)用戶會根據服務器發來的公鑰對密碼進行加密;
3)加密后的信息回傳給服務器,服務器用自己的私鑰解密,如果密碼正確,則用戶登錄成功。
基於秘鑰的驗證:
1)首先在客戶端生成一對密鑰(ssh-keygen);
2)並將客戶端的公鑰ssh-copy-id 拷貝到服務端;
3)當客戶端再次發送一個連接請求,包括ip、用戶名;
4)服務端得到客戶端的請求后,會到authorized_keys中查找,如果有響應的IP和用戶,就會隨機生成一個字符串;
5)服務端將使用客戶端拷貝過來的公鑰進行加密,然后發送給客戶端;
6)得到服務端發來的消息后,客戶端會使用私鑰進行解密,然后將解密后的字符串發送給服務端;
7)服務端接受到客戶端發來的字符串后,跟之前的字符串進行對比,如果一致,就允許免密碼登錄。
示例:配置基於秘鑰驗證
1、在客戶端生成秘鑰對
# ssh-keygen -t rsa -P "" -f ~/.ssh/id_rsa #未加密 # ssh-keygen -p #為私鑰加密
2、將公鑰文件復制到服務器對應用戶的家目錄中(~/.ssh/authorized_keys)
# ssh-copy-id -i ~/.ssh/id_rsa.pub root@192.168.0.7
3、如果私鑰加密,為了避免我們每次使用都需要輸入密碼,我們可以使用代理
[root@rhel6 ~]# ssh-agent bash [root@rhel6 ~]# ssh-add Enter passphrase for /root/.ssh/id_rsa: ****** Identity added: /root/.ssh/id_rsa (/root/.ssh/id_rsa) [root@rhel6 ~]# ssh 192.168.0.7 Last login: Sat May 19 10:21:24 2018 from 192.168.0.6 [root@centos7 ~]#
ssh的端口轉發
SSH 會自動加密和解密所有 SSH 客戶端與服務端之間的網絡數據。但是,SSH 還能夠將其他 TCP 端口的網絡數據通過 SSH 鏈接來轉發,並且自動提供了相應的加密及解密服務。這一過程也被叫做“隧道”(tunneling),這是因為 SSH 為其他 TCP 鏈接提供了一個安全的通道來進行傳輸而得名。例如,Telnet,SMTP,LDAP 這些 TCP 應用均能夠從中得益,避免了用戶名,密碼以及隱私信息的明文傳輸。而與此同時,如果工作環境中的防火牆限制了一些網絡端口的使用,但是允許 SSH 的連接,也能夠通過將 TCP 端口轉發來使用 SSH 進行通訊。
1、本地轉發:
我們在Client端,想訪問內網的Telnet服務器,但是直接訪問Telnet服務器是不安全的,明文用戶名密碼容易被截獲,現在我們就需要借助ssh的端口轉發功能搭建一條隧道。
Client端:
# ssh -L 本地端口:Telnet-server_IP:Telnet-server_Port sshd_IP #建立隧道 # ssh -f -L 1080:192.168.0.10:23 -N 192.168.0.7 # telnet 127.0.0.1 1080
其他的服務也是同樣的原理,只有把端口改變成對應的就好了
2、遠程轉發
我們在sshd服務器端,如果在互聯網上有用戶需要登錄Telnet-server,我們可以在sshd端開啟一個安全的隧道
ssh服務器端:
# ssh -R 客戶端PORT:Telnet_IP:Telnet_Port 客戶端IP # ssh -f -R 1080:192.168.0.10:23 -N 192.168.0.6 # telnet 127.0.0.1 1080
3、動態轉發
例如當用firefox訪問internet時,本機的1080端口做為代理服務器,firefox的訪問請求被轉發到sshserver上,由sshserver替之訪問internet; 在本機firefox設置代理socket proxy:127.0.0.1:1080。
在linux客戶端做以下操作
# ssh -D 1080 root@可訪問互聯網主機IP # curl --socks5 127.0.0.1:1080 http://www.qq.com
服務器端:sshd
配置文件:/etc/ssh/sshd_conf
#Port 22 #監聽端口 #AddressFamily any #支持IPv4和ipv6 #ListenAddress 0.0.0.0 #監聽地址 HostKey /etc/ssh/ssh_host_rsa_key #私鑰文件 SyslogFacility AUTHPRIV #記錄日志/var/log/secure #LogLevel INFO #記錄日志的級別 #LoginGraceTime 2m #2分鍾登錄超時時長(在輸入密碼的時候) #PermitRootLogin yes #是否允許root登錄 #StrictModes yes #檢查文件的所有者和權限 #MaxAuthTries 6 #最大的驗證次數 #MaxSessions 10 #一個會話可以克隆幾次 #PubkeyAuthentication yes #是否允許基於key驗證 AuthorizedKeysFile .ssh/authorized_keys #秘鑰驗證公鑰存放路徑 PasswordAuthentication yes #是否允許基於密碼的連接 GSSAPIAuthentication no #基於GSSAPI驗證 #ClientAliveInterval 0 #是否允許客戶端的活動間隔時間,0 不限制 #ClientAliveCountMax 3 #非活動連接的通知次數 UseDNS no #禁用DNS反向解析 #MaxStartups 10:30:100 #未認證連接最大值,默認值10,當達到10個以上,會斷開30%,當達到100個的時候全部斷開 #Banner none #提示信息,指定一個文件 #AllowUsers user1 user2 user3 #白名單 #DenyUsers #黑名單
ssh服務安全建議配置
- 建議使用非默認端口
- 限制可登錄用戶
- 設定空閑會話超時時長
- 利用防火牆設置ssh訪問策略
- 僅監聽特定的IP地址
- 基於口令認證時,使用強密碼策略
- 使用基於密鑰的認證
- 禁止使用空密碼
- 禁止root用戶直接登錄
- 限制ssh的訪問頻度和並發在線數
- 經常分析日志
scp
用於遠程復制,基於ssh
用法:
scp [options] [user@]host:/sourcefile /destpath :將自己的文件上傳到服務器
scp [options] /sourcefile [user@]host:/destpath :將服務器的文件下載到本地
選項:
- -C: 壓縮數據流
- -r: 遞歸復制
- -p: 保持原文件的屬性信息
- -q: 靜默模式
- -P PORT: 指明服務器的監聽的端口
sftp
基於ssh的交互式文件傳輸工具,用法與ftp工具相似
用法:sftp username@host
常用指令:ls cd mkdir rmdir pwd get put
dropbear
ssh的另一個開源實現軟件
示例:源碼編譯安裝dropbear(環境:CentOS6.9)
1、獲取源碼
[root@centos6 ~]# wget https://matt.ucc.asn.au/dropbear/dropbear-2018.76.tar.bz2 [root@centos6 ~]# tar xf dropbear-2018.76.tar.bz2 [root@centos6 ~]# cd dropbear-2018.76
2、配置
[root@centos6 dropbear-2018.76]# ./configure --prefix=/usr/local --sysconfdir=/etc/
3、編譯安裝
# make PROGRAMS="dropbear dbclient dropbearkey dropbearconvert" # make PROGRAMS="dropbear dbclient dropbearkey dropbearconvert" install
4、創建私鑰
[root@centos6 ~]# mkdir /etc/dropbear [root@centos6 ~]# dropbearkey -t rsa -f /etc/dropbear/dropbear_rsa_host_key -s 4096
5、啟動服務並監聽2222端口
[root@centos6 ~]# dropbear -p 2222
6、測試
[root@centos6 ~]# ss -tnlp |grep 2222 LISTEN 0 128 :::2222 :::* users:(("dropbear",10519,5)) LISTEN 0 128 *:2222 *:* users:(("dropbear",10519,4)) [root@centos7 ~]# ssh -p 2222 192.168.0.6
expect
expect 是由Don Libes基於Tcl( Tool Command Language )語言開發的,主要應用於自動化交互式操作的場景,借助Expect處理交互的命令,可以將交互過程如:ssh登錄,ftp登錄等寫在一個腳本上,使之自動化完成。尤其適用於需要對多台服務器執行相同操作的環境中,可以大大提高系統管理人員的工作效率。
用法:expect [ 選項 ] [ -c cmds ] [ [ -[f|b] ] cmdfile ] [ args ]
選項:
-c:從命令行執行expect腳本,默認expect是交互地執行的
-d:可以輸出輸出調試信息
命令:
spawn:啟動新的進程
send:用於向進程發送字符串
expect:從進程接收字符串
interact:允許用戶交互
exp_continue:匹配多個字符串在執行動作后加此命令
示例:使用expect批量推送ssh的秘鑰
#!/bin/bash rpm -q expect &>/dev/null || yum -q -y install expect #在客戶端生成秘鑰對 [ ! -e ~/.ssh/id_rsa ] && ssh-keygen -t rsa -P "" -f ~/.ssh/id_rsa &>/dev/null read -p "Host_ip_list: " ip_list_file read -p "Username: " username read -s -p "Password: " password [ ! -e "$ip_list_file" ] && echo "$ip_list_file not exist." && exit [ -z "$ip_list_file" -o -z "$username" -o -z "$password" ] && echo "input error!" && exit localhost_ip=`hostname -I |cut -d' ' -f1` #將自己當成服務器並且把公鑰傳給自己 expect <<EOF set timeout 10 spawn ssh-copy-id -i /root/.ssh/id_rsa.pub $localhost_ip expect { "yes/no" { send "yes\n"; exp_continue} "password" { send "$password\n"} } expect eof EOF #登錄一次所有的服務器,獲取公鑰保存到known_hosts文件中,避免其他主機登錄再次詢問 while read ipaddr1; do expect <<EOF set timeout 10 spawn ssh ${username}@${ipaddr1} ':' expect { "yes/no" { send "yes\n"; exp_continue} "password" { send "$password\n"} } expect eof EOF done < "$ip_list_file" #將自己的秘鑰對、known_hosts和authorized_keys文件復制到所有主機,從而達到所有主機可以互相基於秘鑰驗證 while read ipaddr2; do expect <<EOF set timeout 10 spawn scp -pr .ssh/ ${username}@${ipaddr2}: expect { "yes/no" { send "yes\n"; exp_continue} "password" { send "$password\n"} } expect eof EOF done < "$ip_list_file"
pssh
pssh是一個python編寫可以在多台服務器上執行命令的工具
常用選項:
- --version:查看版本
- -h:主機文件列表,內容格式”[user@]host[:port]”
- -H:主機字符串,內容格式”[user@]host[:port]”
- -l:登錄使用的用戶名
- -p:並發的線程數【可選】
- -o:輸出的文件目錄【可選】
- -e:錯誤輸入文件【可選】
- -t:TIMEOUT 超時時間設置,0無限制【可選】
- -O:SSH的選項
- -v:詳細模式
- -A:手動輸入密碼模式
- -x:額外的命令行參數使用空白符號,引號,反斜線處理
- -X:額外的命令行參數,單個參數模式,同-x
- -i:每個服務器內部處理信息輸出
- -P:打印出服務器返回信息
# pssh -l root -h ip.txt -i "date;hostname" #批量在多台服務器上執行date和hostname命令
pscp.pssh:將本地文件批量復制到遠程主機
- -v 顯示復制過程
- -a 復制過程中保留常規屬性
- -r 遞歸復制目錄
# pscp.pssh -l root -h ip.txt /data/testfile /data
pslurp:將遠程主機的文件批量復制到本地
- -L 指定從遠程主機下載到本機的存儲的目錄,local是下載到本地后的名稱
- -r 遞歸復制目錄
# pslurp -l root -h ip.txt -L /data/ /etc/passwd user #批量下載服務器上的文件保存到/data目錄下並且改名為user
rsync
基於ssh和rsh服務實現高效率的遠程系統之間復制文件,與scp的區別是rsync只復制有更改的文件。
常用選項:
- -n 模擬復制過程
- -v 顯示詳細過程
- -r 遞歸復制目錄樹
- -p 保留權限
- -t 保留時間戳
- -g 保留組信息
- -o 保留所有者信息
- -l 將軟鏈接文件本身進行復制(默認)
- -L 將軟鏈接文件指向的文件復制
- -a 存檔,不保留ACL(-A)和SELinux屬性(-X)
# rsync -av /data 192.168.0.7:/data #復制/data目錄和目錄下的文件到另一台主機 # rsync -av /data/ 192.168.0.7:/data #只復制目錄下的文件
示例:rsync+inotify實現文件同步
備份服務器:
1、准備工作
# mkdir /backup # useradd rsync -s /sbin/nologin -M # chown rsync.rsync /backup/
2、配置rsyncd
# vim /etc/rsyncd.conf uid = rsync gid = rsync use chroot = no max connections = 200 timeout = 300 pid file = /var/run/rsyncd.pid lock file = /var/run/rsync.lock log file = /var/log/rsyncd.log [backup] path = /backup/ ignore errors read only = false list = false hosts allow = 192.168.0.0/24 hosts deny = 0.0.0.0/32 auth users = rsync_backup secrets file = /etc/rsync.password # echo "rsync_backup:123456" >/etc/rsync.password # chmod 600 /etc/rsync.password
3、啟動服務
# rsync --daemon # ss -tanl |grep 873 LISTEN 0 5 :::873 :::* LISTEN 0 5 *:873 *:*
數據服務器:
1、准備工作
# echo "123456" >/etc/rsync.password 創建虛擬用戶密碼文件 # chmod 600 /etc/rsync.password # rsync -avz test.txt rsync_backup@192.168.0.9::backup --password-file=/etc/rsync.password #測試rsync daemon是否就緒 # yum -y install inotify-tools
2、編寫監控腳本
# vim chkfile.sh #!/bin/bash host=192.168.0.9 #備份服務器的ip地址 src=/data/ #本地監控的目錄 dst=backup #備份服務器的rsync服務的模塊名 user=rsync_backup #備份服務器的rsync服務的虛擬用戶 rsync_passfile=/etc/rsync.password #本地調用rsync服務的密碼文件 [ -z "$src" -o -z "${rsync_passfile}" ] && echo "Check File and Folder" && exit /usr/bin/inotifywait -mrq --timefmt '%d/%m/%y %H:%M' --format '%T %w%f' -e close_write,delete,create,attrib $src | while read file; do cd $src && rsync -aruz -R --delete ./ --timeout=100 $user@$host::$dst --password-file=${rsync_passfile} >/dev/null 2>&1 done
3、監控並測試
# chmod +x chkfile.sh # ./chkfile.sh &
個人學習筆記 2018-05-19 17:51:18