1. 程式人生 > 其它 >Linux兩臺主機之間建立信任(ssh免密碼)

Linux兩臺主機之間建立信任(ssh免密碼)

背景: 有時候我們在兩個主機之間複製檔案的時候,提示輸入密碼,很不方便,那如何免密碼複製呢?,就是使用通過linux公鑰和祕鑰,建立雙機信任關係。

在整理之前,我先說下ssh免密碼的要點 :

你想免密碼登陸到哪個主機哪個使用者, 就把你自己的公鑰檔案內容追加到遠端主機對應使用者下的authorized_keys檔案中(對面可能沒有這個檔案,建立即可)。

1. 生成祕鑰,並新增信任

我的環境中node1的ip是192.168.168.201,node2的ip是192.168.168.202.

[root@node1 ~]# ssh-keygen -t rsa -P '' -f ~/.ssh/id_rsa         #生成rsa
[root@node1 ~]# ssh-copy-id -i  ~/.ssh/id_rsa.pub [email protected]  #複製201的公鑰到202機器上,這樣就可以使用在201機器上免密碼登入202機器了。

[root@node2 ~]# ssh-keygen -t rsa -P '' -f ~/.ssh/id_rsa         #生成rsa
[root@node2 ~]# ssh-copy-id -i  ~/.ssh/id_rsa.pub [email protected]  #複製202的公鑰到201機器上,這樣就可以使用在202機器上免密碼登入201機器了。

注意:

  •   如果遠端主機的埠非22埠,需要指定-p port選項。
  •   ssh-copy-id是由openssh-clients包提供,沒有這個命令可以安裝這個包。
  • centos6,7使用ssh-copy-id的時候可以不用指定-i選項,centos5必須指定的。

2.信任自己主機

[root@node1 ~]# ssh-copy-id -i  ~/.ssh/id_rsa.pub [email protected] 
[root@node2 ~]# ssh-copy-id -i  ~/.ssh/id_rsa.pub [email protected] 

3.測試

[root@node1 ~]# ssh 192.168.168.202 'ip addr show dev eth0 '
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP qlen 1000
    link/ether 00:50:56:3f:42:13 brd ff:ff:ff:ff:ff:ff
    inet 192.168.168.202/24 brd 192.168.168.255 scope global eth0
    inet6 fe80::250:56ff:fe3f:4213/64 scope link 
       valid_lft forever preferred_lft forever

[root@node2 ~]# ssh 192.168.168.201 'ip addr show dev eth0'
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP qlen 1000
    link/ether 00:0c:29:c9:20:88 brd ff:ff:ff:ff:ff:ff
    inet 192.168.168.201/24 brd 192.168.168.255 scope global eth0
    inet 192.168.168.200/24 brd 192.168.168.255 scope global secondary eth0
    inet6 fe80::20c:29ff:fec9:2088/64 scope link 
       valid_lft forever preferred_lft forever

4 自動配置免密碼登陸

這裡有個情況, 有一個跳板機,內部好多自己的伺服器。遠端只能通過跳板機遠端內部伺服器,現在需要在跳板機上免密碼登陸內部的伺服器。

4.1 各個機器上面需要先生成各自的公鑰和密碼

4.2 跳板機編寫指令碼和配置檔案如下

#!/bin/bash 
#================================================
#FileName   :expect_ssh.sh
#Author     :zhaojiedi
#Description:
#DateTime   :2018-01-05 08:26:06
#Version    :V1.0
#Other      :
#================================================
host_username_password_file=hosts.txt

# install expect 
rpm -q expect &>/dev/null || yum install -yq expect &>/dev/null

# create id_rsa.pub file 
pubkey=~/.ssh/id_rsa.pub
if [ ! -e "$pubkey" ] ; then
        ssh-keygen  -P "" -t rsa  -f ~/.ssh/id_rsa
fi
while read host username password ; do
        con=${username}"@"${host}
        echo $password
        expect <<EOF
        set timeout 20 
        spawn ssh-copy-id $con
        expect {
                "yes/no"  { send "yes\n" ; exp_continue }
                "password:" { send "${password}\n"; exp_continue }
        }
EOF
done < $host_username_password_file

樣例的配置檔案是這樣的。

[root@centos74 bin]$ cat hosts.txt 
172.18.46.6 root oracle

4.3 叢集主機免密碼配置

上面的跳板機配置免密碼登陸都是單向的, 但是對於叢集環境我們需要配置任意2個主機的主機信任的。

#!/bin/bash 

# 配置項
# 檔案格式是 ip usename password port 中間使用空格分割
host_username_password_file=/root/hosts.txt 

# 配置是否copy檔案到其他目標主機上去,只有第一個執行的主機需要copy,其他不需要的
need_copy_to_other=0
src_host="current_host_ip"
#echo $#
if [ "$#" -eq 0 ] ; then 
    need_copy_to_other=1
else
    src_host=$1
fi    

# 安裝 expect
rpm -q expect &> /dev/null || yum install -yq expect &>/dev/null 

# 建立 祕鑰檔案 

pubkey=~/.ssh/id_rsa.pub 
prikey=~/.ssh/id_rsa

if [ ! -e "$pubkey" ]  ; then 
    ssh-keygen -P "" -t rsa -f $prikey &>/dev/null
fi 
while read host username password port ; do 
    if [ -z "$host" ] ; then 
        continue
    fi    
    printf "%16s=======>%-16s\n" $src_host  $host

    #echo "==============================$host $username $password $port ========================================= "
    con=${username}"@"${host}
    cmd_with_argv="ssh-copy-id  -p $port $con "
    #echo $password 
    expect  <<-EOF 
    set timeout 600 
    log_user 0
    spawn -noecho $cmd_with_argv
    expect {
        "yes/no" { send "yes\n"; exp_continue } 
        "password:" { send "${password}\n"; exp_continue } 
    } 
    EOF
    &> /dev/null

    if [ "$need_copy_to_other" -eq 1 ] ; then 
        ip a | grep $host &> /dev/null
        if [ "$?" -ne 0 ] ; then 
            #echo "==>複製必要的檔案到遠端主機($host)上去"
            scp -q -p -P $port  $host_username_password_file $host:$host_username_password_file
            scp -q -p -P $port  $0  $host:$0
            #echo "==>在目標主機${host}上執行下"
            ssh -f -p $port $con "$0  $host "
        fi
    fi

done < $host_username_password_file
sleep 2
[root@localhost ~]# cat hosts.txt 
192.168.46.151 root oracle 22
192.168.46.152 root oracle 22
192.168.46.153 root oracle 22
192.168.46.154 root oracle 22
192.168.46.157 root oracle 22

使用方式

[root@localhost ~]# /root/expect.sh 
 current_host_ip=======>192.168.46.151  
 current_host_ip=======>192.168.46.152  
 current_host_ip=======>192.168.46.153  
  192.168.46.152=======>192.168.46.151  
  192.168.46.152=======>192.168.46.152  
  192.168.46.152=======>192.168.46.153  
 current_host_ip=======>192.168.46.154  
  192.168.46.153=======>192.168.46.151  
  192.168.46.152=======>192.168.46.154  
  192.168.46.153=======>192.168.46.152  
  192.168.46.152=======>192.168.46.157  
  192.168.46.153=======>192.168.46.153  
 current_host_ip=======>192.168.46.157  
  192.168.46.154=======>192.168.46.151  
  192.168.46.153=======>192.168.46.154  
  192.168.46.154=======>192.168.46.152  
  192.168.46.153=======>192.168.46.157  
  192.168.46.154=======>192.168.46.153  
  192.168.46.154=======>192.168.46.154  
  192.168.46.154=======>192.168.46.157 

-------------------------------------------

作者:趙傑迪 出處:http://www.cnblogs.com/zhaojiedi1992/

-------------------------------------------