I want to use a generic parser for multiple scripts, so to keep code cleaner I want to have one place where all the common arguments can be handled. I can do this by subclassing ArgumentParser, but I've run into the problem of adding groups. When I add a group, they no longer have access to the custom methods I wrote. To get around this, I've basically copied the add_argument_group method and added the additional functions. I know this is a terrible solution, any advice for how to properly achieve this?
class CustomParser(argparse.ArgumentParser):
def __init__(self, *args, **kwrds):
super(CustomParser, self).__init__(*args, **kwrds)
def add_enzyme(self):
self.add_argument('--enzyme', help="The enzyme to cleave with. Also valid is a"
" cleavage pattern such as [KR]|{P}.",
choices=protein_config.ENZYMES.keys(), type=str, default='trypsin')
def add_fasta(self, help="The fasta file to operate on."):
self.add_argument('-f', '--fasta', nargs='?', help=help, type=argparse.FileType('r'), default=sys.stdin)
def add_out(self, help='The file to write results to. Leave blank for stdout,'):
self.add_argument('-o', '--out', nargs='?', help=help, type=argparse.FileType('w'), default=sys.stdout)
def add_argument_group(self, *args, **kwargs):
group = argparse._ArgumentGroup(self, *args, **kwargs)
self._action_groups.append(group)
group.add_enzyme = self.add_enzyme
group.add_fasta = self.add_fasta
group.add_out = self.add_out
return group
I would add the group-methods dynamically like this:
from types import MethodType
class CustomParser(argparse.ArgumentParser):
def __init__(self, *args, **kwrds):
super(CustomParser, self).__init__(*args, **kwrds)
def add_argument_group(self, *args, **kwargs):
def add_enzyme(self):
self.add_argument(
'--enzyme',
help="The enzyme to cleave with. Also valid is a"
" cleavage pattern such as [KR]|{P}.",
choices=protein_config.ENZYMES.keys(), type=str, default='trypsin')
def add_fasta(self, help="The fasta file to operate on."):
self.add_argument(
'-f', '--fasta', nargs='?', help=help, type=argparse.FileType('r'),
default=sys.stdin)
def add_out(self, help='The file to write results to. Leave blank for stdout,'):
self.add_argument(
'-o', '--out', nargs='?', help=help, type=argparse.FileType('w'),
default=sys.stdout)
group = super(CustomParser, self).add_argument_group(*args, **kwargs)
setattr(group, add_enzyme.__name__, MethodType(add_enzyme, group, type(group)))
setattr(group, add_fasta.__name__, MethodType(add_fasta, group, type(group)))
setattr(group, add_out.__name__, MethodType(add_out, group, type(group)))
#self._action_groups.append(group)
return group
Think that works, can't really test since I don't have your dependencies. And hope that was what you needed. I commented out the call to self._action_groups.append
since I'm guessing it wont be needed due to proper super call.
Have you tried using a parents
parser?
import argparse
parent = argparse.ArgumentParser(add_help=False)
group = parent.add_argument_group('standard')
group.add_argument('--enzyme', help="The enzyme to cleave with")
group.add_argument('-f', '--fasta', nargs='?', help='help')
group.add_argument('-o', '--out', nargs='?',type=argparse.FileType('w'))
parser = argparse.ArgumentParser(parents=[parent])
parser.add_argument('--custom')
parser.print_help()
produces
usage: stack21938846.py [-h] [--enzyme ENZYME] [-f [FASTA]] [-o [OUT]]
[--custom CUSTOM]
optional arguments:
-h, --help show this help message and exit
--custom CUSTOM
standard:
--enzyme ENZYME The enzyme to cleave with
-f [FASTA], --fasta [FASTA]
help
-o [OUT], --out [OUT]
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.