522 This is to replace subsets of configuration flags like
525 newflags = flags.cloneAndReplace('Muon', 'Trigger.Offline.Muon')
528 _msg.debug(
"cloning flags and replacing %s by %s", subsetToReplace, replacementSubset)
533 subsetToReplace = subsetToReplace.strip(
".")
534 replacementSubset = replacementSubset.strip(
".")
537 if (subsetToReplace == replacementSubset):
538 raise RuntimeError(f
'Can not replace flags {subsetToReplace} with themselves')
541 for alias,src
in self.
_renames.items():
542 if src
is None:
continue
543 if src+
"." in subsetToReplace:
544 raise RuntimeError(f
'Can not replace flags {subsetToReplace} by {replacementSubset} because of already present replacement of {alias} by {src}')
547 newFlags = copy(self)
548 newFlags._renames = deepcopy(self.
_renames)
550 if replacementSubset
in newFlags._renames:
551 newFlags._renames[subsetToReplace] = newFlags._renames[replacementSubset]
553 newFlags._renames[subsetToReplace] = replacementSubset
556 if replacementSubset
not in newFlags._renames
or newFlags._renames[replacementSubset] == replacementSubset:
557 newFlags._renames[replacementSubset] =
None
559 del newFlags._renames[replacementSubset]
564 if replacementSubset
not in newFlags._renames:
565 newFlags._renames[replacementSubset] = replacementSubset
567 newFlags._hash =
None
592 def dump(self, pattern=".*", evaluate=False, formatStr="{:40} : {}
", maxLength=None):
594 compiled = re.compile(pattern)
595 def truncate(s):
return s[:maxLength] + (
"..." if maxLength
and len(s)>maxLength
else "")
596 reverse_renames = {value: key
for key, value
in self.
_renames.items()
if value
is not None}
599 if any([name.startswith(r)
for r
in reverse_renames.keys()
if r
is not None]):
600 for oldprefix, newprefix
in reverse_renames.items():
601 if name.startswith(oldprefix):
602 renamed = name.replace(oldprefix, newprefix)
604 if compiled.match(renamed):
610 print(formatStr.format(renamed,truncate(
"{} {}".format( val, rep )) ))
612 print(formatStr.format(renamed, truncate(
"{}".format(val)) ) )
613 except Exception
as e:
614 print(formatStr.format(renamed, truncate(
"Exception: {}".format( e )) ))
616 print(formatStr.format( renamed, truncate(
"{}".format(repr(self.
_flagdict[name] ) )) ))
619 print(
"Flag categories that can be loaded dynamically")
620 print(
"{:25} : {:>30} : {}".format(
"Category",
"Generator name",
"Defined in" ) )
621 for name,gen_and_prefix
in sorted(self.
_dynaflags.items()):
622 if compiled.match(name):
623 print(
"{:25} : {:>30} : {}".format( name, gen_and_prefix[0].__name__,
'/'.
join(gen_and_prefix[0].__code__.co_filename.split(
'/')[-2:]) ) )
625 print(
"Flag categories that are redirected by the cloneAndReplace")
626 for alias,src
in self.
_renames.items():
627 print(
"{:30} points to {:>30} ".format( alias, src
if src
else "nothing") )
699 def fillFromArgs(self, listOfArgs=None, parser=None, return_unknown=False):
701 Used to set flags from command-line parameters, like flags.fillFromArgs(sys.argv[1:])
703 if return_unknown=False, returns: args
704 otherwise returns: args, uknown_args
705 where unknown_args is the list of arguments that did not correspond to one of the flags
714 argList = listOfArgs
if listOfArgs
is not None else sys.argv[1:]
721 unrequiredActions = []
722 if "-h" in argList
or "--help" in argList:
724 if "-h" in argList: argList.remove(
"-h")
725 if "--help" in argList: argList.remove(
"--help")
727 for a
in parser._actions:
729 unrequiredActions.append(a)
731 (args,leftover)=parser.parse_known_args(argList)
732 for a
in unrequiredActions: a.required=
True
735 argList = [a
for a
in argList
if a
not in leftover]
739 """Check if dest is available in parser and has been set"""
740 return vars(args).
get(dest,
None)
is not None
743 self.Exec.DebugStage=args.debug
745 if arg_set(
'evtMax'):
746 self.Exec.MaxEvents=args.evtMax
748 if arg_set(
'interactive'):
749 self.Exec.Interactive=args.interactive
751 if arg_set(
'skipEvents'):
752 self.Exec.SkipEvents=args.skipEvents
754 if arg_set(
'filesInput'):
755 self.Input.Files = []
756 for f
in args.filesInput.split(
","):
759 self.Input.Files += found
if found
else [f]
761 if "-l" in argList
or "--loglevel" in argList:
762 from AthenaCommon
import Constants
763 self.Exec.OutputLevel = getattr(Constants, args.loglevel)
765 if arg_set(
'config_only')
and args.config_only
is not False:
766 from os
import environ
767 environ[
"PICKLECAFILE"] =
"" if args.config_only
is True else args.config_only
769 if arg_set(
'threads'):
770 self.Concurrency.NumThreads = args.threads
774 if args.concurrent_events
is None and self.Concurrency.NumConcurrentEvents==0:
775 self.Concurrency.NumConcurrentEvents = args.threads
777 if arg_set(
'concurrent_events'):
778 self.Concurrency.NumConcurrentEvents = args.concurrent_events
780 if arg_set(
'nprocs'):
781 self.Concurrency.NumProcs = args.nprocs
783 if arg_set(
'perfmon'):
784 from PerfMonComps.PerfMonConfigHelpers
import setPerfmonFlagsFromRunArgs
785 setPerfmonFlagsFromRunArgs(self, args)
788 self.Exec.MTEventService = args.mtes
790 if arg_set(
'mtes_channel'):
791 self.Exec.MTEventServiceChannel = args.mtes_channel
793 if arg_set(
'profile_python'):
794 from AthenaCommon.Debugging
import dumpPythonProfile
795 import atexit, cProfile, functools
796 cProfile._athena_python_profiler = cProfile.Profile()
797 cProfile._athena_python_profiler.enable()
800 atexit.register(functools.partial(dumpPythonProfile, args.profile_python))
803 self.Exec.MPI = args.mpi
811 if do_help
and '=' not in arg:
812 argList += arg.split(
".")
816 except KeyError
as e:
818 unknown_args += [arg]
823 if parser.epilog
is None: parser.epilog=
""
824 parser.epilog +=
" Note: Specify additional flags in form <flagName>=<value>."
825 subparsers = {
"":[parser,parser.add_subparsers(help=argparse.SUPPRESS)]}
827 logging.root.setLevel(logging.ERROR)
828 def getParser(category):
829 if category
not in subparsers.keys():
830 cat1,cat2 = category.rsplit(
".",1)
if "." in category
else (
"",category)
831 p,subp = getParser(cat1)
832 if subp.help==argparse.SUPPRESS:
833 subp.help =
"Flag subcategories:"
834 newp = subp.add_parser(cat2,help=
"{} flags".format(category),
835 formatter_class = argparse.ArgumentDefaultsHelpFormatter,usage=argparse.SUPPRESS)
836 newp._positionals.title =
"flags"
837 subparsers[category] = [newp,newp.add_subparsers(help=argparse.SUPPRESS)]
838 return subparsers[category]
841 category,flagName = name.rsplit(
".",1)
if "." in name
else (
"",name)
844 val = repr(flag.get(self))
847 if flag._help != argparse.SUPPRESS:
849 if flag._help
is not None:
850 helptext = f
": {flag._help}"
851 if flag._type
is not None:
852 helptext += f
' [type: {flag._type.__name__}]'
853 if val
is not None and helptext ==
"":
855 getParser(category)[0].add_argument(name, nargs=
'?', default=val, help=helptext)
857 parser._positionals.title =
'flags and positional arguments'
858 parser.parse_known_args(argList + [
"--help"])
863 return args,unknown_args