歡迎來到Linux教程網
Linux教程網
Linux教程網
Linux教程網
Linux教程網 >> Linux基礎 >> 關於Linux >> 通過screen實現近乎並發的shell遠程調用思考和部分實現

通過screen實現近乎並發的shell遠程調用思考和部分實現

日期:2017/3/3 16:12:31   编辑:關於Linux

假設一種場景,需要在多個節點需要執行相同命令(考慮命令的不確定性),一般使用for 循環,ssh直接調用。例:需要查看每個節點的根目錄使用情況:

實際上,僅僅需將上述幾行命令寫成一個腳本,將要執行的命令設為位置參數,即可在一個互信的集群內滿足這些要求了,看似問題得到了解決,筆者此前也的確是這麼做的,但是問題出現了,有些命令的執行過程漫長,而這種按順序執行的方法,在執行有些命令時,等待的時間絕對是讓人崩潰的,譬如:如果在成百上千個節點集群內,為每個節點更新庫(yum update),或者生成yum緩存(yum makecache),或者每個節點都是新的,裡面有好多磁盤需要格式化掛載,如果使用for循環按順序執行,相信我,格式化的磁盤的等待時間會讓你無法忍受的,如果這個任務還是在規定的時間必須完成的話.......

好吧,啰嗦半天,需求出現了,先思考要解決的問題,後有簡單的部分實現和測試

1、所有節點是互信的,通過安裝系統時實現(系統安裝階段實現)

2、所有節點可以使用常規的正則表達式取出對應的IP列表(腳本實現)

3、必須已安裝screen包,通過調用這個命令實現近乎並發執行任務(腳本實現)

4、命令執行結果的返回值獲取,用以判斷是否成功執行(未實現)

5、screen的資源釋放問題(未實現)

6、考慮網絡故障的錯誤處理(未實現)

7、考慮執行失敗的錯誤處理(未實現)

8、如果需要在每個節點執行的任務過多,可考慮將需要執行的任務寫成一個簡單的執行腳本,做推送,並控制執行;4、5、6、7的實現可考慮此方法。

9、考慮遠程執行命令時環境變量的問題(未實現)

10、不足之處,歡迎補充:

代碼部分實現如下:

代碼環境如下:

系統為CentOS6.3 x86_64 均已安裝screen包和互信

在互信的節點將命令:yum makecache 分別在如下三個節點執行:

10.1.6.1 disk1.mos.com disk1

10.1.6.2 disk2.mos.com disk2

10.1.6.3 disk3.mos.com disk3

#!/bin/bash
CMD=${1:-/usr/bin/yum makecache}
CMD_SN="disk_ver.1"
DATE="/bin/date +%k:%M:%S/%Y-%m-%d"
SSH="/usr/bin/ssh -q -o StrictHostKeyChecking=no"
SCREEN=/usr/bin/screen
LIST=(`cat /etc/hosts|grep mos.com|awk '{print $1}'`)
for i in ${LIST[@]};do
    $SSH $i $SCREEN -dmS $CMD_SN
    $SSH $i $SCREEN -S $CMD_SN -X screen $CMD
    echo -en "`$DATE` $i done.\n\n"
done

 

在三個節點分別放置一個簡單的腳本,用來查看命令是否被成功執行,代碼如下:

#!/bin/bash
Date="/bin/date +%k:%M:%S/%Y-%m-%d"
Mlog=/var/log/mon.log
TEE(){
        /usr/bin/tee -a $Mlog
}
while :;do
    INFO=`ps aux|grep -v grep|grep yum`
    if [ -n "$INFO" ];then
        echo -en "`$Date` : $INFO \n\n" |TEE
    fi
    sleep 1
done

在控制節點執行腳本,結果如下:

在三個節點看到任務啟動時間如下:

寫文不易,列位看官若覺得還能湊合,給好評哦,親..

剛弄完這個,忽然想到這個東西放後台應該也是可以的,經測試的確可以,因此,代碼可改為:

#!/bin/bash
CMD=${1:-/usr/bin/yum makecache}
DATE="/bin/date +%k:%M:%S/%Y-%m-%d"
LOG=/var/log/ctrl.log
SSH="/usr/bin/ssh -q -o StrictHostKeyChecking=no"
LIST=(`cat /etc/hosts|grep mos.com|awk '{print $1}'`)
for i in ${LIST[@]};do
        $SSH $i $CMD &>> $LOG &          
        echo -en "`$DATE` $i done.\n\n"
done

記錄所有輸出至日志文件,通過日志可判斷執行結果對錯。這樣一來,上述幾條中的第4、7都可完成,第5條的問題也不存在,僅剩第6和9兩條的需再做思考

本文出自 “自強不息” 博客,請務必保留此出處http://mos1989.blog.51cto.com/4226977/1255884

Copyright © Linux教程網 All Rights Reserved