#!/usr/bin/python ''' Created on May 14, 2015 @author: Nerses Gevorgyan ''' import os, sys import socket import pprint import subprocess from optparse import OptionParser import iocPortMap from iocPortMap import * # Initialization debug = 0 ssh_env_prefix = "ssh -x {0} \'" ssh_env_suffix = "\' 2>/dev/null" app_exe = "/usr/bin/procServ" if (debug): print app_exe, if (debug): print hostname = socket.gethostname()[:socket.gethostname().find('.')] def debug_msg(level, msg): if (level<=debug): print msg def checkDir(d): if (os.path.isdir(os.path.expandvars(d).replace('\n','')) == False): print("Could not find directory %s"%os.path.expandvars(d).replace('\n','')) else: debug_msg(1, "Ok") def checkFile(f): if (os.path.isfile(os.path.expandvars(f).replace('\n','')) == False): print("Could not find file %s"%os.path.expandvars(f).replace('\n','')) else: debug_msg(1, "Ok") def checkConfig(ioc): if (debug>0): print ioc, checkDir(hostPortMap[ioc]["path"]) checkFile(hostPortMap[ioc]["path"]+"/"+hostPortMap[ioc]["cmd"]) debug_msg(1, "Ok") def checkConfigAll(): for ioc in hostPortMap: checkConfig(ioc) def printConfig(): print "-----------------" print "IOC CONFIGURATION" print "-----------------" for ioc in hostPortMap: checkConfig(ioc) print ioc, ':', hostPortMap[ioc]['path'], ':', hostPortMap[ioc]['host'], ':', hostPortMap[ioc]['port'], ':', hostPortMap[ioc]['enabled'], ':', hostPortMap[ioc]['cmd'], ':', ':' def printCommands(): print "------------------" print "IOC START COMMANDS" print "------------------" for ioc in hostPortMap: checkConfig(ioc) print ssh_env_prefix.format(hostPortMap[ioc]['host']), "%s -n \"%s\" -i^D^C -c %s %s %s >/dev/null 2>&1"%(app_exe, hostPortMap[ioc]['title'], hostPortMap[ioc]['path'], hostPortMap[ioc]['port'], hostPortMap[ioc]['cmd']), ssh_env_suffix def checkCurrentHost(host): return (socket.getfqdn(host)[:socket.getfqdn(host).find('.')] == hostname) def printHostConfig(): print "---------------------------" print "IOC CONFIGURED FOR ", hostname print "---------------------------" for ioc in hostPortMap: if (checkCurrentHost(hostPortMap[ioc]['host'])): cmd = ssh_env_prefix.format(hostPortMap[ioc]['host']) cmd += app_exe cmd += " -n \"%s\" -i^D^C -c \"%s\" \"%s\" \"%s\" >/dev/null 2>&1"%(hostPortMap[ioc]['title'], hostPortMap[ioc]['path'], hostPortMap[ioc]['port'], hostPortMap[ioc]['cmd']) cmd += ssh_env_suffix print cmd def init_env(f): checkFile(f) command = ['/bin/tcsh', '-c', 'source ' + f + ' && env'] proc = subprocess.Popen(command, stdout = subprocess.PIPE) for line in proc.stdout: (key, _, value) = line.partition("=") os.environ[key] = value proc.communicate() if (debug>1): pprint.pprint(dict(os.environ)) def start_ioc(ioc): if (hostPortMap[ioc]['enable']!="enabled") : print ioc, " is DISABLED from running on port ",hostPortMap[ioc]['port'], " of ",hostPortMap[ioc]['host'] return checkConfig(ioc) cmd = ssh_env_prefix.format(hostPortMap[ioc]['host']) cmd += app_exe cmd += " -n \"%s\" -i^D^C"%(hostPortMap[ioc]['title']) cmd += " -c %s"%(hostPortMap[ioc]['path']) cmd += " -L \"/gluex/log/IOC/%s:%s:%s\".log"%(hostPortMap[ioc]['host'], hostPortMap[ioc]['port'], hostPortMap[ioc]['cmd']) cmd += " --logstamp" cmd += " %s %s >&/dev/null "%(hostPortMap[ioc]['port'], hostPortMap[ioc]['cmd']) cmd += ssh_env_suffix debug_msg(1, "IOC to start: " + ioc) debug_msg(1, "Command to start: " + cmd) # status = subprocess.call( cmd, shell=True) status = os.system(cmd) if (status != 0): print "Could not start ", ioc, " on port ", hostPortMap[ioc]['port'], " of ", hostPortMap[ioc]['host'] def test_ioc(ioc): checkConfig(ioc) print "%s -n \"%s\" -i^D^C -c %s %s %s >/dev/null 2>&1"%(app_exe, hostPortMap[ioc]['title'], hostPortMap[ioc]['path'], hostPortMap[ioc]['port'], hostPortMap[ioc]['cmd']) def stop_ioc(ioc): if (hostPortMap[ioc]['enable']!="enabled") : print ioc, " is DISABLED from running on port ",hostPortMap[ioc]['port'], " of ",hostPortMap[ioc]['host'] return # cmd = ssh_env_prefix.format(hostPortMap[ioc]['host']) # cmd +="kill -9 `ps -ef | " # cmd +="grep \"%s\" | "%(hostPortMap[ioc]['title']) # cmd +="grep \"%s\" | "%(hostPortMap[ioc]['port']) # cmd +="grep \"%s\" | "%(hostPortMap[ioc]['cmd']) # cmd +="grep -v grep | tr -s \" \" |cut -d \" \" -f 2`" # cmd += ssh_env_suffix cmd = ssh_env_prefix.format(hostPortMap[ioc]['host']) # cmd +="( echo \\\\0030; usleep 10000; echo \\\\0021 ; usleep 500000) | " cmd +="( echo \\\\0030; usleep 100000; echo \\\\0021 ; usleep 500000) | " cmd +="telnet localhost %s"%(hostPortMap[ioc]['port']) cmd += ssh_env_suffix #process = os.system(cmd) process = subprocess.Popen([cmd, ], stdout=subprocess.PIPE, shell=True) (out, err) = process.communicate() debug_msg(1, "IOC to stop: " + ioc) debug_msg(1, "command:" + cmd) debug_msg(1, "stdout:" + out) #debug_msg(1, "stderr:" + err) def status_ioc(ioc): cmd = ssh_env_prefix.format(hostPortMap[ioc]['host']) cmd +="ps -ef | " cmd +="grep \"%s\" | "%(hostPortMap[ioc]['title']) cmd +="grep \"%s\" | "%(hostPortMap[ioc]['port']) cmd +="grep \"%s\" | "%(hostPortMap[ioc]['cmd']) cmd +="grep -v grep | tr -s \" \" |cut -d \" \" -f 2" cmd += ssh_env_suffix #process = os.system(cmd) process = subprocess.Popen([cmd, ], stdout=subprocess.PIPE, shell=True) (out, err) = process.communicate() if (hostPortMap[ioc]['enable']=="enabled"): if (len(out)>0): print ioc, " is running on port ",hostPortMap[ioc]['port'], " of ",hostPortMap[ioc]['host']," with pid = ",out.rstrip() else: print ioc, " is NOT running on port ",hostPortMap[ioc]['port'], " of ",hostPortMap[ioc]['host'] else: print ioc, " is DISABLED from running on port ",hostPortMap[ioc]['port'], " of ",hostPortMap[ioc]['host'] def restart_ioc(ioc): stop_ioc(ioc) start_ioc(ioc) def check_ioc(ioc): cmd = ssh_env_prefix.format(hostPortMap[ioc]['host']) cmd +="ps -ef | " cmd +="grep \"%s\" | "%(hostPortMap[ioc]['title']) cmd +="grep \"%s\" | "%(hostPortMap[ioc]['port']) cmd +="grep \"%s\" | "%(hostPortMap[ioc]['cmd']) cmd +="grep -v grep | tr -s \" \" |cut -d \" \" -f 2" cmd += ssh_env_suffix #process = os.system(cmd) debug_msg(1,cmd) process = subprocess.Popen([cmd, ], stdout=subprocess.PIPE, shell=True) (out, err) = process.communicate() if (len(out)>0): return 0 else: return 1 def checkuser(): script_user="hdops" process_s = subprocess.Popen(["id -u "+script_user, ], stdout=subprocess.PIPE, shell=True) (script_uid, err) = process_s.communicate() process_u = subprocess.Popen(["id -u", ], stdout=subprocess.PIPE, shell=True) (uid, err) = process_u.communicate() if (script_uid != uid): print "You must be ",script_user," to run " + sys.argv[0] print "Please \"sudo -u ",script_user,"\" to run this script" sys.exit() def verify_ioc(ioc): cmd = ssh_env_prefix.format(hostPortMap[ioc]['host']) cmd +="sleep 1 | " cmd +="telnet localhost \"%s\" | "%hostPortMap[ioc]['port'] cmd +="grep -A 1 \"@@@ Child startup directory:\" | " cmd +="sed -e \"s/@@@ Child //g\" -e \"s/startup directory: //g\" -e \"s/started as://g\" " # cmd +=" | tr \'\\n\' \' \'" cmd += ssh_env_suffix #process = os.system(cmd) debug_msg(1,cmd) process = subprocess.Popen([cmd, ], stdout=subprocess.PIPE, shell=True) (out, err) = process.communicate() print "----- ", ioc ," -----" if (len(out)>0): (telnet_path, telnet_title, telnet_cmd) = out.replace('\n', ' ').split('"') if telnet_path.strip()[:len(hostPortMap[ioc]['path'].replace('$APP','/gluex/controls/epics/R3-14-12-3-1').strip())] != hostPortMap[ioc]['path'].replace('$APP','/gluex/controls/epics/R3-14-12-3-1').strip() : print "Mismatch found in the path" print telnet_path.strip() print hostPortMap[ioc]['path'].replace('$APP','/gluex/controls/epics/R3-14-12-3-1/app').strip() if telnet_cmd.strip().replace('./','') != hostPortMap[ioc]['cmd'].strip() : print "Mismatch found in the command" print telnet_cmd.strip().replace('./','') print hostPortMap[ioc]['cmd'] if telnet_title.strip() != hostPortMap[ioc]['title'].strip() : print "Mismatch found in the title" print telnet_title.strip() print hostPortMap[ioc]['title'] print "---------------------" if __name__ == '__main__': checkFile(app_exe) # init_env("/gluex/etc/hdonline.cshrc") functions = { "start" : start_ioc, "stop" : stop_ioc, "restart" : restart_ioc, "check" : check_ioc, "status" : status_ioc, "test" : test_ioc, "verify" : verify_ioc } # Parsing the options usage = "usage: %prog [-h] [-p iocpath] [-c alt_config] [-i iocname] start|stop|restart|check|status|test" usage += "\n\t" usage += "\n\tstart - start iocs specified in config file" usage += "\n\tstop - stop iocs specified in config file" usage += "\n\tcheck - start any iocs not running that are configured to run" usage += "\n\trestart - stop and start iocs specified in config file" usage += "\n\tstatus - dump a short status screen showing current status" usage += "\n\ttest - show how each IOC would be invoked but don't do anything" usage += "\n\tverify - login into IOC and print the path, title and command comparing with the available configuration" # usage += "" parser = OptionParser(usage) parser.add_option('-p', metavar='ioc_path', dest="path", help='Specify the iocBoot path (default: $CONFIG_DIR).') parser.add_option('-c', metavar='alt_config', dest="config", help='Specify the configuration file (default: $CONFIG_FILE).') parser.add_option('-i', metavar='ioc_name', dest="ioc", help='Specify the ioc. If not specified, the script assumes all iocs.') (options,args) = parser.parse_args() #print args, " check args[0]", args[0] not in functions.keys(), " len(args)=",len(args) if (len(args)!=1): parser.print_help() print sys.argv sys.exit("The command is missing.") if (args[0] not in functions.keys()): parser.print_help() sys.exit("Unknown command: "+args[0]) ioc='' debug_msg(1, "IOC = " + str(options.ioc)) if (options.ioc): if (options.ioc in hostPortMap.keys()): debug_msg(1, options.ioc + " is in hostPortMap: " + str(hostPortMap[options.ioc])) ioc=options.ioc else: sys.exit("No such IOC: " + options.ioc) if ioc=='': for i in hostPortMap: functions[args[0]](i) else: sys.exit(functions[args[0]](ioc)) sys.exit("The end of procServMgr.py scipt is reached.") #checkConfig("CDCVLT") #checkConfigAll() #printConfig() #printCommands() #printHostConfig() #start_ioc("CDCVLT") #stop_ioc("CDCVLT")