52 lines
1.5 KiB
Python
52 lines
1.5 KiB
Python
from abc import abstractmethod
|
|
from argparse import ArgumentParser, Namespace
|
|
from prettyparse import Usage
|
|
|
|
|
|
class BaseScript:
|
|
"""A class to standardize the way scripts are defined"""
|
|
usage = Usage()
|
|
|
|
def __init__(self, args):
|
|
self.args = args
|
|
|
|
@classmethod
|
|
def create(cls, **args):
|
|
values = {}
|
|
for arg_name, arg_data in cls.usage.arguments.items():
|
|
if arg_name in args:
|
|
values[arg_name] = args.pop(arg_name)
|
|
else:
|
|
if 'default' not in arg_data and arg_name and not arg_data['_0'].startswith('-'):
|
|
raise TypeError('Calling script without required "{}" argument.'.format(arg_name))
|
|
typ = arg_data.get('type')
|
|
if arg_data.get('action', '').startswith('store_') and not typ:
|
|
typ = bool
|
|
if not typ:
|
|
typ = lambda x: x
|
|
values[arg_name] = typ(arg_data.get('default'))
|
|
args = Namespace(**values)
|
|
cls.usage.render_args(args)
|
|
return cls(args)
|
|
|
|
@abstractmethod
|
|
def run(self):
|
|
pass
|
|
|
|
@classmethod
|
|
def run_main(cls):
|
|
parser = ArgumentParser()
|
|
cls.usage.apply(parser)
|
|
args = cls.usage.render_args(parser.parse_args())
|
|
|
|
try:
|
|
script = cls(args)
|
|
except ValueError as e:
|
|
parser.error('Error parsing args: ' + str(e))
|
|
raise SystemExit(1)
|
|
|
|
try:
|
|
script.run()
|
|
except KeyboardInterrupt:
|
|
print()
|