• linux 自动上传程序


    linux下expect安装

    expect据说是交互性很强的脚本语言,想安装了玩玩试试,没想到竟然让我纠结两天才安装上,只是因为expect依赖于tcl,但linux系统里一般不自带安装tcl,需要手动安装

    expect版本 5.43

    http://download.chinaunix.net/download/0003000/2845.shtml

    tcl版本 8.4.19

    http://sourceforge.net/projects/tcl/files/Tcl/8.4.19/tcl8.4.19-src.tar.gz/download

    下载两个包,分别解压

    1。先安装tcl

      进入tcl解压目录,然后进入unix目录

      #./configure

      #make

      #make install

    2.后安装expect

      进入expect解压目录

      #./configure --with-tclinclude=/usr/src/tcl8.4.19/generic/ --with-tclconfig=/usr/local/lib/

      #make

      #make install

    完成,测试

      #expect

      expect1.1> 
      expect1.1>

    一切OK

    2.升级脚本

    对之前的版本进行升级,增加支持密码从命令行输入方式,增加提示那些机器上传成功或者失败提示
    对于运维来说,同时管理多台机器是很辛苦的事情,特别是CDN运维需要上传一个文件到1000台机器的话,靠人工一个个上传非常费劲,为此我写了一个批量scp文件到多台机器上的小程序。
    其中用到了expect:
      Expect在这个程序里就是用来帮助自动输入scp的密码,Expect主要用于把需要人工交互的程序变为程序自动化完成,这个对于运维批量部署系统,批量无人值守安装,批量执行命令,批量上传下载
     现代的Shell对程序提供了最小限度的控制(开始,停止,等等),而把交互的特性留给了用户。 这意味着有些程序,你不能非交互的运行,比如说passwd。 有一些程序可以非交互的运行,但在很大程度上丧失了灵活性,比如说fsck。这表明Unix的工具构造逻辑开始出现问题。Expect恰恰填补了其中的一些裂痕,解决了在Unix环境中长期存在着的一些问题。

     
      Expect使用Tcl作为语言核心。不仅如此,不管程序是交互和还是非交互的,Expect都能运用。

     
    1.multi_scp_upload.sh的源代码
     
    #!/bin/bash  
    #author: yifangyou  
    #create time:2011-05-17  
    #用来通过scp批量上传文件或者目录到目标机器的指定目录  
    #配置文件格式:  
    #ssh_hosts=("1.1.1.1" "2.2.2.2")  
    #ssh_ports=("22" "22") 这个可以缺省,缺省值为22,或者个数比ssh_hosts少时,使用缺省值  
    #ssh_users=("root" "root") 这个可以缺省,缺省值为root,,或者个数比ssh_hosts少时,使用缺省值  
    #ssh_passwords=("323" "222") 这个可以缺省,缺省的话需要从命令行输入,或者个数比ssh_hosts少时,使用命令行输入  
    #执行:sh multi_scp.sh conf_file_path file target  
    if [ -z "$3" ]  
    then 
    echo "sh multi_scp.sh conf_file_path file target";  
    exit;  
    fi  
    default_ssh_user="root" 
    default_ssh_port="22";  
    #upload shell script file path  
    scp_upload=scp_upload.sh  
    #configure file path  
    conf_file=$1  
    #then upload file path  
    scp_file=$2  
    #remote hosttarget file or dir path  
    scp_target=$3  
    #判断conf_file配置文件是存在  
    if [ ! -e "$conf_file" ]  
    then 
    echo "$conf_file is not exists";  
    exit;  
    fi  
    #判断scp_file是文件或者目录  
    if [ ! -e "$scp_file" ] && [ ! -d "$scp_file" ]  
    then 
    echo "$scp_file is not exists";  
    exit;  
    fi  
    #read configure file  
    source $conf_file  
    #若是没有在配置文件里提供密码,则在命令行输入  
    if [ "${#ssh_passwords[@]}" = "0" ] || [ "${#ssh_passwords[@]}" -lt "${#ssh_hosts[@]}" ]  
    then 
    read -p "please input password:" -s default_ssh_password  
    fi  
    success_hosts="";  
    fail_hosts="";  
    for((i=0;i<${#ssh_hosts[@]};i++))  
    do  
    #remote ssh host  
    ssh_host=${ssh_hosts[$i]};  
    #remote ssh port  
    ssh_port=${ssh_ports[$i]};  
    if [ "$ssh_port" = "" ]  
    then 
    ssh_port=$default_ssh_port;  
    fi  
    #remote ssh user 
    ssh_user=${ssh_users[$i]};  
    if [ "$ssh_user" = "" ]  
    then 
    ssh_user=$default_ssh_user;  
    fi  
    #remote ssh password 
    ssh_password=${ssh_passwords[$i]};  
    if [ "$ssh_password" = "" ]  
    then 
    ssh_password=$default_ssh_password;  
    fi  
    echo "["`date +"%F %T"`"] (scp -r $scp_file $ssh_user@$ssh_host:$ssh_port:$scp_target) start" 
    #scp file or dir  
    /usr/bin/expect scp_upload.sh "$ssh_host" "$ssh_port" "$ssh_user" "$ssh_password" "$scp_file" "$scp_target" 
    if [ "$?" -eq "0" ]  
    then 
    success_hosts="$success_hosts,$ssh_host" 
    else 
    fail_hosts="$fail_hosts,$ssh_host" 
    fi  
    echo "["`date +"%F %T"`"] (scp -r $scp_file $ssh_user@$ssh_host:$ssh_port:$scp_target) end" 
    echo "" 
    done  
    echo "success_hosts=[$success_hosts]" 
    echo "fail_hosts=[$fail_hosts]" 
    2.scp_upload.sh的源代码
     
    #!/usr/bin/expect  
    #author: yifangyou  
    #create time:2011-05-17  
    #host  
    set scphost "[lindex $argv 0]" 
    #ssh端口  
    set port "[lindex $argv 1]" 
    #ssh用户名  
    set scpuser "[lindex $argv 2]" 
    #ssh密码  
    set scppw "[lindex $argv 3]" 
    #要上传的文件名或者目录  
    set file "[lindex $argv 4]" 
    #要上传到远程机器的文件名或者目录  
    set target "[lindex $argv 5]" 
    spawn scp -r -P $port $file $scpuser@$scphost:$target  
    #设置超时时间,防止远程机器防火墙没有开,而挂起  
    set timeout 30  
    expect {  
    #respose: "root@1.2.3.4s password:",自动输入密码  
    "*password*" {  
    set timeout 30  
    send "$scppw " 
    }  
    #the first connect will respose "Are you sure you want to continue connecting (yes/no)? yes" 
    "*yes*" {  
    set timeout 30  
    send "yes " 
    set timeout 30  
    expect "*password*" 
    set timeout 30  
    send "$scppw " 
    }  
    busy {send_user " <error:busy>";exit 1;}  
    failed {send_user " <error:failed>";exit 2;}  
    timeout {send_user " <error:timeout>";exit 3;}  
    }  
    #Permission denied not try again,回报出错信息  
    set timeout 30  
    expect {  
    "*denied*" {  
    send_user " <error:Permission denied>" 
    exit 4  
    }  
    "*No such file*" {  
    send_user " <error:No such file>" 
    exit 5  
    }  
    busy {send_user " <error:busy>";exit 6;}  
    failed {send_user " <error:failed>";exit 7;}  
    timeout {send_user " <error:timeout>";exit 8;}  
    }  
    exit 0 
    3.配置文件格式scp.conf
     
    #ssh_hosts=("1.1.1.1" "2.2.2.2")  
    #ssh_ports=("22" "22") #wheen port_num < host_num use default=22,or ssh_ports is undefined use 22 as default value  
    #ssh_users=("root" "root") #wheen user_num < host_num use default=root,or ssh_users is undefined use root as default value  
    #ssh_passwords=("323" "222") #wheen password_num < host_num use default=input password,or ssh_users is undefined use input password 
    4.运行代码
    找一台机器可以和要上传的机器联通,安装好expect(可以用expect命令测试是否已经安装过了)

    把scp_upload.sh,multi_scp_upload.sh,scp.conf放到同一个目录下,运行multi_scp_upload.sh即可 

  • 相关阅读:
    模拟退火求二维费马点
    二叉查找树
    Linux中让普通用户拥有超级用户的权限
    python 正则表达式应用——缩写词扩充
    解决单链表中的环问题
    python数学函数
    train,dev,test数据集作用
    朴素贝叶斯法(二)——基本方法
    生成模型与判别模型
    ImportError: cannot import name wordnet
  • 原文地址:https://www.cnblogs.com/xianqingzh/p/2606814.html
Copyright © 2020-2023  润新知