在实际工作环境中,有可能需要去运维百台服务器,甚至更多。以应用升级为例,对应用做升级操作,首先得停止应用服务,防止新的应用数据写入,并备份应用部署目录,然后替换成新的代码文件、配置文件等。替换完成后,启动应用服务。但是由于应用服务器数量过多,如果一台一台服务器去做升级,这会花费很多时间。这时,便可使用paramiko编写python脚本,让这些重复性的操作批量执行,去实现应用升级的自动化。这个小工具实现了在堡垒机模式和非堡机模式的运用。
1.maintool.py (控制整个脚本的执行),代码如下:
maintool.py执行效果如下:
2.operation.py(定义非堡垒机模式下的相关操作),代码如下:
3.blhost_
operation.py(定义堡垒机模式下的相关操作),代码如下:
至此,这个python小工具制作完成。
1.maintool.py (控制整个脚本的执行),代码如下:
点击(此处)折叠或打开
- #!/usr/bin/python
- #coding:utf-8
- import sys
- ######脚本执行操作提示
- def login():
- print """\033[1;34m
- 1:批量分发文件(非堡垒机模式)
- 2:批量执行命令(非堡垒机模式)
- 3:批量下载文件(非堡垒机模式)
- 4:单台执行命令(非堡垒机模式)
- 5:批量分发文件(堡垒机模式)
- 6:批量执行命令(堡垒机模式)
- 7:增加需要服务器(非堡垒机模式)
- 8:删除不需要服务器(非堡垒机模式)
- 9:查看当前服务器列表(非堡垒机模式)
- 10:退出\033[0m
- """
- #######定义用户选择函数
- def choice():
- import operation,blhost_operation
- while True:
- choice = raw_input("\033[1;32minput your choice:\033[0m").strip()
- choice_list = ['1','2','3','4','5','6','7','8','9','10','help','exit']
- if choice not in choice_list:
- print "\033[1;33mtry again!\033[0m"
- continue
- if choice == '1':
- operation.SendFile()###非堡机模式下文件分发
- login()
- if choice == '2':
- operation.ExecuteCmd()###非堡机模式下命令执行
- login()
- if choice == '3':
- operation.DownloadFile()###非堡机模式下文件下载
- login()
- if choice == '4':
- operation.SingleServer()###单台服务器操作
- login()
- if choice == '5':
- blhost_operation.SendFile()###堡垒机模式下文件分发
- login()
- if choice == '6':
- blhost_operation.ExecuteCmd()###堡垒机模式下命令执行
- login()
- if choice == '7':
- operation.AddServerList()###增加服务器名单
- if choice == '8':
- operation.DeleteServerList()###删除服务器名单
- if choice == '9':
- operation.ShowServerList()###展示服务器名单
- login()
- if choice == '10' or choice == 'exit':###退出脚本操作
- print "\033[1;31mThank you for your use!\033[0m"
- sys.exit(0)
- if choice == 'help':
- login()
- if __name__ == '__main__':
- login()
- choice()
maintool.py执行效果如下:
2.operation.py(定义非堡垒机模式下的相关操作),代码如下:
点击(此处)折叠或打开
- #!/usr/bin/python
- #coding:utf-8
- import sys,time,threading
- import getpass,commands
- import paramiko,fabric
- server_list=[] #HOSTNAME IP PWDROOT PWDWEBLOGIC PWDORACLE
- result_dict={}
- ######读取文件内容,读取完成后关闭文件
- f = open ('serverlist.txt')
- for i in f.readlines():
- server_list.append(i.split())
- f.close()
- ######非堡垒机下文件的传送
- def transfer(localpath,remotepath,hostname,username,password):
- port = 22
- try:
- t = paramiko.Transport((hostname,port))
- t.connect(username=username,password=password)
- sftp = paramiko.SFTPClient.from_transport(t)
- sftp.put(localpath,remotepath)
- t.close()
- result_dict[hostname] = hostname+"服务器文件传送完成"
- print result_dict[hostname]
- except Exception,e:
- print str(e)
- ######定义文件下载函数
- def download(remotepath,localpath,hostname,username,password):
- port = 22
- try:
- t = paramiko.Transport((hostname,port))
- t.connect(username=username,password=password)
- sftp = paramiko.SFTPClient.from_transport(t)
- sftp.get(remotepath,localpath)
- t.close()
- result_dict[hostname] = hostname+"服务器文件下载完成"
- print result_dict[hostname]
- except Exception,e:
- print str(e)
- ######定义命令执行函数
- def execmd(hostname,username,password,CMD):
- paramiko.util.log_to_file('syslogin.log')###将用户登录服务器日志输出到syslogin.log
- ssh = paramiko.SSHClient()###ssh登录服务器
- ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())###自动添加主机名及主机密钥到本地HostKeys对象,并将其保存,不依赖load_system_host_keys()的配置,即使~/.ssh/known_hosts不存在也不产生影响
- ssh.connect(hostname=hostname,username=username,password=password)
- stdin,stdout,stderr = ssh.exec_command(CMD)
- result = stdout.read()
- ssh.close()
- result_dict[hostname] = hostname+"服务器命令执行结果如下:"+"\n"+result
- print result_dict[hostname]
- ######执行结果打印
- def result_dict_print():
- global result_dict
- while True:
- if len(result_dict) == len(server_list):
- break
- print "\033[1;36m%s台服务器完成\033[0m" %(len(result_dict))
- result_dict = {}
- ######非保垒机模式下文件的分发
- def SendFile():
- while True:
- username = raw_input("\033[1;32m请输入你选择要用于发送文件的用户[root/weblogic/oracle]:\033[0m").strip()
- username_list = ['root','weblogic','oracle','\n','exit']
- if username not in username_list:
- print "\033[0;32minput error!Please try again!If you need exit,please input exit!\033[0m"
- continue
- if username == 'exit':
- sys.exit()
- localpath = raw_input("\033[1;32m本地文件(绝对路径):\033[0m").strip()
- remotepath = raw_input("\033[1;32m服务器目的地址(绝对路径):\033[0m").strip()
- if username == 'root':
- for list in server_list:
- p = threading.Thread(target=transfer,args=(localpath,remotepath,list[1],username,list[2],))
- p.start()
- for list in server_list:
- p.join(timeout=1)
- if username == 'weblogic' or username == '':
- username = 'weblogic'
- for list in server_list:
- p = threading.Thread(target=transfer,args=(localpath,remotepath,list[1],username,list[3],))
- p.start()
- if username == 'oracle':
- username = 'oracle'
- for list in server_list:
- p = threading.Thread(target=transfer,args=(localpath,remotepath,list[1],username,list[4],))
- p.start()
- result_dict_print()
- break
- ######非堡垒机模式下文件的下载
- def DownloadFile():
- while True:
- username = raw_input("\033[1;32m请输入你选择要用于下载文件的用户[root/weblogic/oracle]:\033[0m").strip()
- username_list = ['root','weblogic','oracle','\n','exit']
- if username not in username_list:
- print "\033[1;32minput error!Please try again!If you need exit,please input exit!\033[0m"
- continue
- if username == 'exit':
- sys.exit()
- remotepath = raw_input("\033[1;32m远程文件(绝对路径):\033[0m").strip()
- localpath = raw_input("\033[1;32m服务器目的地址(目录名,默认为/opt/zzx/python/bin):\033[0m").strip()
- if localpath == '':
- localpath = '/opt/zzx/python/bin'
- localpath = localpath+"/"
- print localpath
- count = remotepath.count('/')
- basename = remotepath.split('/')[count]
- if username == 'root':
- for list in server_list:
- p = threading.Thread(target=download,args=(remotepath,localpath+list[1]+"_"+basename,list[1],username,list[2],))
- p.start()
- for list in server_list:
- p.join(timeout=1)
- if username == 'weblogic' or username == '':
- username = 'weblogic'
- for list in server_list:
- localpath = result1+list[1]+"_"+result2
- p = threading.Thread(target=download,args=(remotepath,localpath,list[1],username,list[3],))
- p.start()
- if username == 'oracle':
- for list in server_list:
- localpath = result1+list[1]+"_"+result2
- p = threading.Thread(target=download,args=(remotepath,localpath,list[1],username,list[4],))
- p.start()
- result_dict_print()
- break
- ######非堡垒机模式下命令的执行
- def ExecuteCmd():
- while True:
- username = raw_input("\033[1;32m请输入你选择要用于执行命令的用户[root/weblogic/oracle]:\033[0m").strip()
- username_list = ['root','weblogic','oracle','\n','exit']
- if username not in username_list:
- print "\033[1;32minput error!Please try again!If you need exit,please input exit!\033[0m"
- continue
- if username == 'exit':
- sys.exit()
- CMD = raw_input("\033[1;37m请输入要执行的命令(不能带引号):\033[0m").strip()
- if CMD == 'exit':
- return
- if username == 'root':
- for list in server_list:
- p = threading.Thread(target=execmd,args=(list[1],username,list[2],CMD,))
- p.start()
- if username == 'weblogic' or username == '':
- username = 'weblogic'
- for list in server_list:
- p = threading.Thread(target=execmd,args=(list[1],username,list[3],CMD))
- p.start()
- if username == 'oracle':
- for list in server_list:
- p = threading.Thread(target=execmd,args=(list[1],username,list[4],CMD))
- p.start()
- result_dict_print()
- break
- ######单台服务器操作
- def SingleServer():
- IP = raw_input("\033[1;32m请输入要执行命令的服务器IP地址:\033[0m").strip()
- username = raw_input("\033[1;32m请输入要执行命令的服务器用户名:\033[0m").strip()
- password = getpass.getpass()
- CMD = raw_input("\033[1;32m请输入要执行的命令(不能带引号):\033[0m").strip()
- execmd(IP,username,password,CMD)
- ######服务器名单添加
- def AddServerList():
- hostname = raw_input("\033[1;32m请输入服务器名称(如localhost):\033[0m").strip()
- if hostname == 'quit' or hostname == 'exit':
- return
- ip = raw_input("\033[1;32m请输入服务器IP:\033[0m").strip()
- root_passwd = raw_input("\033[1;32m请输入服务器root用户密码:\033[0m").strip()
- weblogic_passwd = raw_input("\033[1;32m请输入服务器weblogic用户密码:\033[0m").strip()
- oracle_passwd = raw_input("\033[1;32m请输入服务器oracle用户密码:\033[0m").strip()
- f = file('serverlist.txt','a')
- f.write("%s %s %s %s %s\n"%(hostname,ip,root_passwd,weblogic_passwd,oracle_passwd))
- f.close()
- raw_input("\033[1;32m重新执行程序后生效(敲任意键退出)...\033[0m")
- time.sleep(0.2)
- sys.exit()
- ######服务器名单删除
- def DeleteServerList():
- IP = raw_input("\033[1;32m请输入要删除服务器IP:\033[0m").strip()
- if IP == 'quit' or IP == 'exit':
- return
- status,result = commands.getstatusoutput("sed -i '/\<%s\>/'d ./serverlist.txt" % IP)
- raw_input("\033[1;32m重新执行程序后生效(敲任意键退出)...\033[0m")
- time.sleep(0.2)
- sys.exit()
- ######服务器名单显示
- def ShowServerList():
- i = 0
- f = open('serverlist.txt','rb')
- for line in f.readlines():
- print line.strip()
- i = i+1
- f.close
- print "\n总共%s台服务器" % i
点击(此处)折叠或打开
- #!/usr/bin/python
- #coding:utf-8
- import sys,time,threading
- import getpass,commands,os
- import paramiko,fabric
- server_list=[] #HOSTNAME IP PWDROOT PWDWEBLOGIC PWDORACLE
- result_dict={}
- ######读取文件内容,读取完成后关闭文件
- f = open ('serverlist.txt')
- for i in f.readlines():
- server_list.append(i.split())
- f.close()
- ######堡垒机下文件的传送
- def transfer(bllocalpath,remotepath,blhostname,blusername,blpassword,hostname,username,password):
- passinfo='\'s password: '
- paramiko.util.log_to_file('blhost_upload.log')
-
- ssh=paramiko.SSHClient()
- ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())###自动添加主机名及主机密钥到本地HostKeys对象,并将其保存,不依赖load_system_host_keys()的配置,即使~/.ssh/known_hosts不存在也不产生影响
- ssh.connect(hostname=blhostname,username=blusername,password=blpassword)
-
- channel=ssh.invoke_shell()
- channel.settimeout(100)
- buff=''
- resp=''
- channel.send('scp '+bllocalpath+' '+username+'@'+hostname+':'+remotepath+'\n')
- while not buff.endswith(passinfo):
- try:
- resp=channel.recv(9999)
- except Exception,e:
- print "Error info:receive nothing"
- print str(e)
- channel.close()
- ssh.close()
- sys.exit()
- buff += resp
- if not buff.find('yes/no')==-1:
- channel.send('yes\n')
- buff=''
- buff=''
- channel.send(password+'\n')
- while not buff.endswith('# '):
- resp=channel.recv(9999)
- if not resp.find(passinfo)==-1:
- print "Error info:Authentication failed."
- print "Please confirm if your password is true!"
- channel.close()
- ssh.close()
- sys.exit()
- buff += resp
- channel.close()
- ssh.close()
- result_dict[hostname] = hostname+"服务器文件传送完成"
- print result_dict[hostname]
- ######堡垒机模式下命令执行
- def execmd(blhostname,blusername,blpassword,hostname,username,password,CMD):
- passinfo='\'s password: '
- paramiko.util.log_to_file('blhost_syslogin.log')
-
- ssh=paramiko.SSHClient()
- ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
- ssh.connect(hostname=blhostname,username=blusername,password=blpassword)
-
- channel=ssh.invoke_shell()
- channel.settimeout(100)
-
- buff=''
- resp=''
- channel.send('ssh '+username+'@'+hostname+'\n')
- while not buff.endswith(passinfo):
- try:
- resp=channel.recv(9999)
- except Exception,e:
- print "fail to connect"
- print "Error info: "+str(e)
- channel.close()
- ssh.close()
- sys.exit()
- buff += resp
- if not buff.find('yes/no')==-1:
- channel.send('yes\n')
- buff=''
- buff=''
- channel.send(password+'\n')
- while not buff.endswith('# '):
- resp=channel.recv(9999)
- if not resp.find(passinfo)==-1:
- print "Error info:Authentication failed"
- channel.close()
- ssh.close()
- sys.exit()
- buff += resp
- buff=''
- channel.send('%s\n' % CMD)
- try:
- while not buff.endswith('# '):
- resp=channel.recv(9999)
- buff += resp
- except Exception,e:
- print "Error info:"+str(e)
-
- result = buff
- channel.close()
- ssh.close()
- result_dict[hostname] = hostname+"服务器命令执行结果如下:"+"\n"+result
- print result_dict[hostname]
- ######执行结果打印
- def result_dict_print():
- global result_dict
- while True:
- if len(result_dict) == len(server_list):
- break
- print "\033[1;36m%s台服务器完成\033[0m" %(len(result_dict))
- result_dict={}
- ######堡垒机模式下文件的批量分发
- def SendFile():
- while True:
- blusername = raw_input("\033[1;32m请输入你选择要用于发送文件的堡垒机用户[root/weblogic/oracle]:\033[0m").strip()
- blusername_list = ['root','weblogic','oracle','','exit']
- if blusername not in blusername_list:
- print "\033[0;32minput error!Please try again!If you need exit,please input exit!\033[0m"
- continue
- if blusername == 'exit':
- return
- blhostname=raw_input("\033[1;32m请输入你选择要用于发送文件的堡垒机IP:\033[0m").strip()
- print "\033[1;32m请输入你选择要用于发送文件的堡垒机密码:\033[0m"
- blpassword=getpass.getpass()
- username=raw_input("\033[1;32m请输入你选择要用于接收文件的用户[root/weblogic/oracle]:\033[0m").strip()
- bllocalpath=raw_input("\033[1;32m堡垒机本地文件(绝对路径):\033[0m").strip()
- remotepath=raw_input("\033[1;32m服务器目的地址(绝对路径):\033[0m").strip()
- if blusername == 'root':
- for list in server_list:
- p = threading.Thread(target=transfer,args=(bllocalpath,remotepath,blhostname,blusername,blpassword,list[1],username,list[2],))
- p.start()
- for list in server_list:
- p.join(timeout=1)
- if blusername == 'weblogic' or blusername == '':
- blusername = 'weblogic'
- for list in server_list:
- p = threading.Thread(target=transfer,args=(bllocalpath,remotepath,blhostname,blusername,blpassword,list[1],username,list[3],))
- p.start()
- if blusername == 'oracle':
- for list in server_list:
- p = threading.Thread(target=transfer,args=(bllocalpath,remotepath,blhostname,blusername,blpassword,list[1],username,list[4],))
- p.start()
- result_dict_print()
- break
- ######堡垒机模式下命令的批量执行
- def ExecuteCmd():
- while True:
- blusername = raw_input("\033[1;32m请输入你选择要用于跳转的堡垒机用户[root/weblogic/oracle]:\033[0m").strip()
- blusername_list = ['root','weblogic','oracle','','exit']
- if blusername not in blusername_list:
- print "\033[0;32minput error!Please try again!If you need exit,please input exit!\033[0m"
- continue
- if blusername == 'exit':
- return
- blhostname=raw_input("\033[1;32m请输入你选择要用于跳转的堡垒机IP:\033[0m").strip()
- print "\033[1;32m请输入你选择要用于跳转的堡垒机密码:\033[0m"
- blpassword=getpass.getpass()
- username=raw_input("\033[1;32m请输入你选择要用于执行命令的用户[root/weblogic/oracle]:\033[0m").strip()
- CMD = raw_input("\033[1;37m请输入要执行的命令(不能带引号):\033[0m").strip()
- if CMD == 'exit':
- return
- if blusername == 'root':
- for list in server_list:
- p = threading.Thread(target=execmd,args=(blhostname,blusername,blpassword,list[1],username,list[2],CMD,))
- p.start()
- if username == 'weblogic' or username == '':
- username = 'weblogic'
- for list in server_list:
- p = threading.Thread(target=execmd,args=(blhostname,blusername,blpassword,list[1],username,list[3],CMD,))
- p.start()
- if username == 'oracle':
- for list in server_list:
- p = threading.Thread(target=execmd,args=(blhostname,blusername,blpassword,list[1],username,list[4],CMD,))
- p.start()
- result_dict_print()
- break
来自 “ ITPUB博客 ” ,链接:http://blog.itpub.net/31541436/viewspace-2155896/,如需转载,请注明出处,否则将追究法律责任。
转载于:http://blog.itpub.net/31541436/viewspace-2155896/