diff options
Diffstat (limited to 'bin/sunhpc')
-rwxr-xr-x | bin/sunhpc | 153 |
1 files changed, 153 insertions, 0 deletions
diff --git a/bin/sunhpc b/bin/sunhpc new file mode 100755 index 0000000..82f02f9 --- /dev/null +++ b/bin/sunhpc @@ -0,0 +1,153 @@ +#!/opt/sunpy3/bin/python3 +#coding:utf-8 + +import os +import sys +import pwd +import sunhpc +import syslog +import shutil +import sunhpc.invoke + +if sys.getdefaultencoding() != 'utf-8': + reload(sys) + sys.setdefaultencoding('utf-8') + +def ttySize(): + try: + (width, heigh) = shutil.get_terminal_size() + except: + width = 80 + return width + +os.environ['COLUMNS'] = str(ttySize()) +syslog.openlog('SunhpcCMD', syslog.LOG_PID, syslog.LOG_LOCAL0) + +try: + import sqlalchemy + import sunhpc.db.helper + + database = sunhpc.db.helper.DatabaseHelper() + database.connect() + +except ImportError: + raise +except sqlalchemy.exc.OperationalError: + raise + +# 如果参数为空,应当主动赋值帮助,就当成sunhpc help命令. +if len(sys.argv) == 1: + args = [ 'list', 'help'] +else: + args = sys.argv[1:] +# +# 如果这个sunhpc 没有参数, 则使用 sunhpc list help +# 否则, 使用第二个参数, 例如 sunhpc list +# 那么 args[0] = 永远指定第二个参数. +# 检查命令是否被圈引 +# sunhpc aa bb -- 那么cmd=['aa'] +# sunhpc "aa bb" -- 那么cmd=['aa','bb'] +module = None +cmd = args[0].split() + +# 一般不会执行这里. +# 只有命令参数带入引号,才会执行此处. +# 例如: sunhpc "aa bb" 而 sunhpc aa bb 则跳过此处. +if len(cmd) > 1: + s = 'sunhpc.commands.%s' % '.'.join(cmd) + # 此时模块路径应该是 sunhpc.commands.aa.bb + try: + # 如果没有此模块,则触发ModuleNotFoundError异常. + __import__(s) + + # 如果模块存在,但是报错,应该是头部没有进行import 相关模块. + # 触发 NameError 异常. + module = eval(s) + + # 设定变量,供后面for递减模块中args列表从第二个参数取值使用. + i = 1 + except: + module = None + +# 这里正式开始检查命令参数. +if not module: + # 递减sunhpc 参数. + for i in range(len(args), 0, -1): + s = 'sunhpc.commands.%s' % '.'.join(args[:i]) + # sunhpc.commands.aa.bb + # sunhpc.commands.aa + try: + # 倒序检查模块是否存在. + __import__(s) + module = eval(s) + if module: + # 如果找到模块,那么其余的参数,就会作为模块参数提供给此模块. + break + except ImportError: + continue + +# 如果没有找到提供的任何模块,则命令执行失败. +if not module: + print ('error - invalid sunhpc command "%s"' % args[0]) + sys.exit(-1) + +# 将模块路径重新转化成命令行形式格式. +# sunhpc.commands.aa.bb +# sunhpc commands aa bb 去除sunhpc commands. +# name = aa bb +name = ' '.join(s.split('.')[2:]) + +# 此时module已经找到相应的模块了. +# module = sunhpc.commands.aa.bb + +try: + # 检查module模块是否有Command类,如果没有则触发 AttributeError 异常. + command = getattr(module, 'Command')(database) +except AttributeError: + # 没有Command类,则会执行到此处.到这里我们需要调用帮助信息. + # + # 此时的bb模块中没有Command类. + # 命令:sunhpc aa bb + # 已知module路径. sunhpc.commands.aa.bb + # 已经name变量, aa bb + # + # 导入sunhpc帮助模块 + import sunhpc.commands.list.help + help = sunhpc.commands.list.help.Command(database) + # 将module路径转换成列表然后使用切片找出模块全路径和子路径. + fullmodpath = s.split('.') + submodpath = '/'.join(fullmodpath[2:]) + + # 执行Command类中run函数.第一个参数是字典,第二个是列表. + help.run({'subdir':submodpath}, []) + print (help.getText()) + sys.exit(-1) + +# 如果有Command类, 则执行主模块sunhpc.commands.__init__中的runWapper函数 +# 两种用途 +# 1, 收集命令参数并且转换成固定格式. +# 2, 开始执行命令入口函数. +# 如果触发自定义命令异常,则输出使用帮助信息. +if command.MustBeRoot and not (command.isRootUser() or command.isApacheUser()): + # 如果需要特权权限, 则需要提权操作. + os.system('sudo %s' % ' '.join(sys.argv)) +else: + # 收集参数等信息,然后运行模块run函数,错误则触发CommandError异常. + # runWrapper是主模块中的Command类中的入口函数. + # name : 当前模块路径. + # args : 当前有效模块后面全部视为参数. + try: + command.runWrapper(name, args[i:]) + text = command.getText() + if len(text) > 0: + print (text.rstrip()) + if text[len(text)-1] != '\n': + print () + except sunhpc.core.utils.CommandError as e: + msg = ' '.join(str(e).split()) + #print ("\033[91m[errs] %s\033[0m" % msg) + print (msg) + print (command.usage()) + exit(1) + +syslog.closelog() |