5 from GaudiKernel.DataHandle
import DataHandle
6 import GaudiKernel.GaudiHandles
as GaudiHandles
8 from AthenaCommon.Logging
import logging
9 from AthenaCommon.Debugging
import DbgStage
10 from AthenaCommon.CFElements
import (isSequence, findSubSequence, findAlgorithm, iterSequences,
11 checkSequenceConsistency, findAllAlgorithmsByName)
13 from AthenaConfiguration.AccumulatorCache
import AccumulatorCachable
14 from AthenaConfiguration.ComponentFactory
import CompFactory, isComponentAccumulatorCfg
15 from AthenaConfiguration.Deduplication
import deduplicate, deduplicateOne, DeduplicationFailed
16 from AthenaConfiguration.DebuggingContext
import (Context, raiseWithCurrentContext, shortCallStack,
17 createContextForDeduplication)
20 from collections.abc
import Sequence
27 _basicServicesToCreateOrder=(
"CoreDumpSvc/CoreDumpSvc",
28 "GeoModelSvc/GeoModelSvc",
29 "DetDescrCnvSvc/DetDescrCnvSvc")
34 ComponentAccumulator._checkUnmerged =
False
35 atexit.register(__exit)
41 props = {**c.getDefaultProperties(), **c._properties}
if printDefaults
else c._properties
43 for propname, propval
in sorted(props.items()):
46 if isinstance(propval, GaudiConfig2.Configurable):
47 msg.info(
"%s * %s: %s",
" "*nestLevel, propname, propval.getFullJobOptName())
50 elif isinstance(propval, GaudiHandles.PrivateToolHandleArray):
51 msg.info(
"%s * %s: PrivateToolHandleArray of size %s",
" "*nestLevel, propname, len(propval))
53 msg.info(
"%s * %s/%s",
" "*(nestLevel+3), el.__cpp_type__, el.getName())
57 elif isinstance(propval, DataHandle):
58 propval = propval.Path
60 msg.info(
"%s * %s: %r",
" "*nestLevel, propname, propval)
66 if not onlyComponents
or c.getName()
in onlyComponents:
68 elif c.getName()+
'-' in onlyComponents:
69 ret.append((c,
False))
86 ComponentAccumulator initialised with legacy (global) Configurable behavior!
87 CA Deduplication is impossible in this mode.
88 Create the CA using the AthenaCommon.Configurable.ConfigurableCABehavior context manager.
91 self.
_msg=logging.getLogger(
'ComponentAccumulator')
92 if isinstance(sequence, str):
93 kwargs={
'IgnoreFilterPassed' :
True,
94 'StopOverride' :
True }
95 if sequence ==
'AthAlgSeq' :
96 kwargs.setdefault(
'ProcessDynamicDataDependencies',
True)
97 kwargs.setdefault(
'ExtraDataForDynamicConsumers',[])
100 sequence = CompFactory.AthSequencer(sequence, **kwargs)
132 summary =
"This CA contains {0} service(s), {1} conditions algorithm(s), {2} event algorithm(s) and {3} public tool(s):\n"\
137 summary +=
" Private AlgTool: " + self.
_privateTools[-1].getFullJobOptName() +
"\n"
139 summary +=
" Private AlgTool: " + self.
_privateTools.getFullJobOptName() +
"\n"
142 summary +=
" Primary Component: " + self.
_primaryComp.getFullJobOptName() +
"\n"
144 summary +=
" Sequence(s): " +
", ".
join([s.name+(
" (main)" if s == self.
_sequence else "")
for s
in self.
_allSequences]) +
"\n"
160 from AthenaConfiguration.AccumulatorCache
import AccumulatorDecorator
161 AccumulatorDecorator.clearCache()
173 log = logging.getLogger(
"ComponentAccumulator")
174 log.error(
"ComponentAccumulator was never merged. %s\n", self.
_inspect())
176 traceback.print_stack()
177 if getattr(self,
'_privateTools',
None)
is not None:
178 log = logging.getLogger(
"ComponentAccumulator")
179 log.error(
"Deleting a ComponentAccumulator with dangling private tool(s): %s",
183 """Called by AccumulatorCache when deleting item from cache"""
188 state = self.__dict__.
copy()
194 self.__dict__.update(state)
196 self.
_msg=logging.getLogger(
'ComponentAccumulator')
199 def printCondAlgs(self, summariseProps=False, onlyComponents=[], printDefaults=False):
200 self.
_msg.
info(
"Condition Algorithms" )
201 for (c, flag)
in filterComponents (self.
_conditionsAlgs, onlyComponents):
203 if summariseProps
and flag:
213 onlyComponents = [], printDefaults=False, printSequenceTreeOnly=False, prefix=None):
214 msg = logging.getLogger(prefix)
if prefix
else self.
_msg
216 msg.info(
"Event Algorithm Sequences" )
218 def printSeqAndAlgs(seq, nestLevel = 0,
219 onlyComponents = []):
221 if name
in seq._properties:
222 return seq._properties[name]
223 return seq._descriptors[name].default
225 msg.info(
"%s\\__ %s (seq: %s %s)",
" "*nestLevel, seq.name,
226 "SEQ" if __prop(
"Sequential")
else "PAR",
229 msg.info(
"%s\\__ %s",
" "*nestLevel, seq.name)
234 printSeqAndAlgs(c, nestLevel, onlyComponents = onlyComponents )
237 msg.info(
"%s\\__ %s (alg) %s",
" "*nestLevel, c.getFullJobOptName(), self.
_componentsContext.
get(c.name,
""))
239 msg.info(
"%s\\__ %s",
" "*nestLevel, c.name )
240 if summariseProps
and flag:
245 msg.info(
"Top sequence %d", n )
246 printSeqAndAlgs(s, onlyComponents = onlyComponents)
248 if printSequenceTreeOnly:
252 onlyComponents = onlyComponents)
253 msg.info(
"Services" )
254 msg.info( [ s[0].name + (
" (created) " if s[0].name
in self.
_servicesToCreate else "")
255 for s
in filterComponents (self.
_services, onlyComponents) ] )
256 msg.info(
"Public Tools" )
258 for (t, flag)
in filterComponents (self.
_publicTools, onlyComponents):
261 if summariseProps
and flag:
264 msg.info(
"Private Tools")
273 msg.info(
"Auditors" )
276 msg.info(
"theApp properties" )
278 msg.info(
" %s : %s", k, v)
282 Returns information about inputs needed and outputs produced by this CA
284 It is a list of dictionaries containing the: type, key, R / W, the component and name of the property via which it is set
286 def __getHandles(comp):
288 for i
in comp.ExtraInputs:
289 io.append({
"type": i.split(
"#")[0],
290 "key": i.split(
"#")[1],
291 "comp": comp.getFullJobOptName(),
293 "prop":
"ExtraInputs"})
294 for i
in comp.ExtraOutputs:
295 io.append({
"type": i.split(
"#")[0],
296 "key": i.split(
"#")[1],
297 "comp": comp.getFullJobOptName(),
299 "prop":
"ExtraOutputs"})
301 for prop, descr
in comp._descriptors.items():
302 if isinstance(descr.default, DataHandle):
303 io.append( {
"type": descr.default.type(),
304 "key": comp._properties[prop]
if prop
in comp._properties
else descr.default.path(),
305 "comp": comp.getFullJobOptName(),
306 "mode": descr.default.mode(),
309 if "PrivateToolHandle" == descr.cpp_type
and prop
in comp._properties:
310 io.extend( __getHandles(comp._properties[prop]) )
311 if "PrivateToolHandleArray" == descr.cpp_type
and prop
in comp._properties:
312 for tool
in getattr(comp, prop):
313 io.extend( __getHandles(tool))
318 ret.extend(__getHandles(comp))
323 """ Adds new sequence. If second argument is present then it is added under another sequence """
326 raise TypeError(
'{} is not a sequence'.
format(newseq.name))
328 if not isinstance(newseq, GaudiConfig2.Configurable):
329 raise ConfigurationError(
'{} is not the Conf2 Sequence, ComponentAccumulator handles only the former'.
format(newseq.name))
332 if len(algorithmsInside) != 0:
333 raise ConfigurationError(
'{} contains algorithms (or sub-sequences contain them). That is not supported. Construct ComponentAccumulator and merge it instead'.
format(newseq.name))
336 if parentName
is None:
343 parent.Members.append(newseq)
344 if "trackSequence" in ComponentAccumulator.debugMode:
349 self.
_msg.warning(
"addEventAlgo: Overwriting primary component of this CA. Was %s/%s, now %s/%s",
351 newseq.__cpp_type__, newseq.name)
358 if sequenceName
is None:
364 """Use this method to carry private AlgTool(s) to the caller when returning this ComponentAccumulator.
365 The method accepts either a single private AlgTool or a list of private AlgTools (typically assigned to ToolHandleArray)
368 raise ConfigurationError(
"This ComponentAccumulator holds already a (list of) private tool(s). "
369 "Only one (list of) private tool(s) is allowed")
371 if isinstance(privTool, Sequence):
373 if t.__component_type__ !=
'AlgTool':
374 raise ConfigurationError(
"ComponentAccumulator.setPrivateTools accepts only ConfigurableAlgTools "
375 f
"or lists of ConfigurableAlgTools. Encountered {type(t)} in a list")
377 if privTool.__component_type__ !=
"AlgTool":
378 raise ConfigurationError(
"ComponentAccumulator.setPrivateTools accepts only ConfigurableAlgTools "
379 f
"or lists of ConfigurableAlgTools. Encountered {type(privTool)}")
382 if "trackPrivateTool" in ComponentAccumulator.debugMode:
389 """Get the (list of) private AlgTools from this ComponentAccumulator.
390 The CA will not keep any reference to the AlgTool. Throw an exception if
391 no tools are available unless quiet=True.
394 if not quiet
and tool
is None:
400 """ Merging in the other accumulator and getting the (list of) private AlgTools
401 from this ComponentAccumulator.
404 raise RuntimeError(
"popToolsAndMerge called on object of type None: "
405 "did you forget to return a CA from a config function?")
406 tool = other.popPrivateTools()
411 """ Get the current PerfMon domain. """
415 """ Mark the beginning of a new PerfMon domain. """
416 self.
_msg.
debug(f
"Toggling the current algorithm domain to {name}")
420 """ The actual registry keeps "alg":"domain".
421 This function inverts the registry to get "domain":["algs"].
425 result[v] = [i]
if v
not in result.keys()
else result[v] + [i]
429 """ Return the PerfMon domain of the given algorithm """
433 self.
_msg.
info(f
"Algorithm {name} is not in PerfMon domains registry")
437 """ Add the algorithm to the domains registry. """
441 self.
_msg.
debug(f
"Added algorithm {name} to the PerfMon domain {domain}")
443 if overwrite
and domain:
444 self.
_msg.
info(f
"Reassigned algorithm {name} "
445 f
"from {self._domainsRegistry[name]} "
446 f
"to {domain} PerfMon domain")
449 self.
_msg.
debug(f
"Algorithm {name} is already in the PerfMon "
450 "domain, if you want to reassign do overwrite=True")
453 """ Print the PerfMon domains. """
455 self.
_msg.
info(
":: This CA contains the following PerfMon domains ::")
456 self.
_msg.
info(f
":: There are a total of {len(self._domainsRegistry)} "
457 f
"registered algorithms in {len(invertedDomains)} domains ::")
458 for domain, algs
in invertedDomains.items():
459 self.
_msg.
info(f
"+ Domain : {domain}")
462 self.
_msg.
info(
":: End of PerfMon domains ::")
464 def addEventAlgo(self, algorithms,sequenceName=None,primary=False,domain=None):
465 if not isinstance(algorithms, Sequence):
467 algorithms=[algorithms,]
469 if sequenceName
is None:
481 for algo
in algorithms:
482 if not isinstance(algo, GaudiConfig2.Configurable):
483 raise TypeError(f
"Attempt to add wrong type: {type(algo).__name__} as event algorithm")
485 if algo.__component_type__ !=
"Algorithm":
486 raise TypeError(f
"Attempt to add an {algo.__component_type__} as event algorithm")
496 if not existingAlgInDest:
502 if len(algorithms)>1:
503 self.
_msg.warning(
"Called addEvenAlgo with a list of algorithms and primary==True. "
504 "Designating the first algorithm as primary component")
506 self.
_msg.warning(
"addEventAlgo: Overwriting primary component of this CA. Was %s/%s, now %s/%s",
508 algorithms[0].__cpp_type__, algorithms[0].name)
513 if "trackEventAlgo" in ComponentAccumulator.debugMode:
514 for algo
in algorithms:
520 """Get algorithm with `name`"""
526 """Get all algorithms within sequence"""
531 """Add Conditions algorithm"""
532 if not isinstance(algo, GaudiConfig2.Configurable):
533 raise TypeError(f
"Attempt to add wrong type: {type(algo).__name__} as conditions algorithm")
535 if algo.__component_type__ !=
"Algorithm":
536 raise TypeError(f
"Attempt to add wrong type: {algo.__component_type__} as conditions algorithm")
543 self.
_msg.warning(
"addCondAlgo: Overwriting primary component of this CA. Was %s/%s, now %s/%s",
545 algo.__cpp_type__, algo.name)
550 if "trackCondAlgo" in ComponentAccumulator.debugMode:
559 """Get all conditions algorithms"""
563 """Get conditions algorithm by name"""
567 """Add service and return the deduplicated instance"""
568 if not isinstance(newSvc, GaudiConfig2.Configurable):
569 raise TypeError(f
"Attempt to add wrong type: {type(newSvc).__name__} as service")
571 if newSvc.__component_type__ !=
"Service":
572 raise TypeError(f
"Attempt to add wrong type: {newSvc.__component_type__} as service")
579 self.
_msg.warning(
"addService: Overwriting primary component of this CA. Was %s/%s, now %s/%s",
581 newSvc.__cpp_type__, newSvc.name)
587 sname = newSvc.getFullJobOptName()
590 if "trackService" in ComponentAccumulator.debugMode:
596 """Add Auditor to ComponentAccumulator and return the deduplicated instance.
597 This function will also create the required AuditorSvc."""
598 if not isinstance(auditor, GaudiConfig2.Configurable):
599 raise TypeError(f
"Attempt to add wrong type: {type(auditor).__name__} as auditor")
601 if auditor.__component_type__ !=
"Auditor":
602 raise TypeError(f
"Attempt to add wrong type: {auditor.__component_type__} as auditor")
607 newAuditor = self.
addService(CompFactory.AuditorSvc(Auditors=[auditor.getFullJobOptName()]))
613 """Add public tool and return the deduplicated instance."""
614 if not isinstance(newTool, GaudiConfig2.Configurable):
615 raise TypeError(f
"Attempt to add wrong type: {type(newTool).__name__} as public AlgTool")
617 if newTool.__component_type__ !=
"AlgTool":
618 raise TypeError(f
"Attempt to add wrong type: {newTool.__component_type__} as public AlgTool")
625 self.
_msg.warning(
"addPublicTool: Overwriting primary component of this CA. Was %s/%s, now %s/%s",
627 newTool.__cpp_type__, newTool.name)
631 if "trackPublicTool" in ComponentAccumulator.debugMode:
638 """Get designated primary component"""
647 """ Merging in the other accumulator and getting the primary component"""
649 raise RuntimeError(
"merge called on object of type None: did you forget to return a CA from a config function?")
650 comp = other.getPrimary()
654 def __getOne(self, allcomps, name=None, typename="???"):
655 selcomps = allcomps
if name
is None else [ t
for t
in allcomps
if t.name == name ]
656 if len( selcomps ) == 0:
659 if len( selcomps ) == 1:
661 nmstr = f
'with name {name} ' if name
else ''
662 raise ConfigurationError(
"Number of {} available {}{} which is != 1 expected by this API".
format(typename, nmstr, len(selcomps)) )
668 """Returns single public tool, exception if either not found or to many found"""
675 """Returns single service, exception if either not found or to many found"""
677 return self._primarySvc
682 """Retuns a single auditor, exception if not found"""
687 lenBefore=len(s.Members)
688 s.Members = [a
for a
in s.Members
if not a.getName()==name]
689 lenAfter=len(s.Members)
690 if lenAfter == lenBefore:
691 self.
_msg.warning(
"Algorithm %s not found in sequence %s",name,sequence)
693 self.
_msg.
info(
"Removed algorithm %s from sequence %s",name,sequence)
697 self.
_msg.warning(
"Algorithm %s not found in self._sequence ???",name)
702 lenBefore=len(s.Members)
703 s.Members = [a
for a
in s.Members
if not a.getName()==name]
704 lenAfter=len(s.Members)
705 if lenAfter == lenBefore:
706 self.
_msg.warning(
"Algorithm %s not found in sequence %s",name,sequence)
708 self.
_msg.
info(
"Removed algorithm %s from sequence %s",name,sequence)
712 self.
_msg.warning(
"Algorithm %s not found in self._sequence ??? Returning 'None'",name)
719 if lenAfter == lenBefore:
720 self.
_msg.warning(
"Condition Algorithm %s not found",name)
722 self.
_msg.
info(
"Removed conditions Algorithm %s",name)
729 if lenAfter == lenBefore:
730 self.
_msg.warning(
"Service %s not found",name)
732 self.
_msg.
info(
"Removed Service %s",name)
739 if lenAfter == lenBefore:
740 self.
_msg.warning(
"Public tool %s not found",name)
742 self.
_msg.
info(
"Removed public tool %s",name)
749 if lenAfter == lenBefore:
750 self.
_msg.warning(
"Auditor %s not found",name)
752 self.
_msg.
info(
"Removed auditor %s",name)
763 self.
_msg.
debug(
"ApplicationMgr property '%s' already set to '%s'.", key, value)
766 self.
_msg.
info(
"ApplicationMgr property '%s' already set to '%s'. Overwriting with %s", key, self.
_theAppProps[key], value)
769 raise DeduplicationFailed(
"AppMgr property {} set twice: {} and {}".
format(key, self.
_theAppProps[key], value))
773 if stage
not in DbgStage.allowed_values:
774 raise RuntimeError(
"Allowed arguments for setDebugStage are [{}]".
format(
",".
join(DbgStage.allowed_values)))
778 def merge(self,other, sequenceName=None):
779 """Merging in the other accumulator"""
781 raise RuntimeError(
"merge called on object of type None: "
782 "did you forget to return a CA from a config function?")
784 if not isinstance(other,ComponentAccumulator):
785 raise TypeError(f
"Attempt to merge wrong type {type(other).__name__}. "
786 "Only instances of ComponentAccumulator can be added")
788 context = (Context.hint
if not ComponentAccumulator.debugMode
else
789 Context(
"When merging the ComponentAccumulator:\n{} \nto:\n{}".
format(other._inspect(), self.
_inspect())))
791 if other._privateTools
is not None:
792 if isinstance(other._privateTools, Sequence):
794 "merge called on ComponentAccumulator with a dangling (array of) private tools\n"))
797 "merge called on ComponentAccumulator with a dangling private tool "
798 f
"{other._privateTools.__cpp_type__}/{other._privateTools.name}"))
800 if not other._isMergable:
802 "Attempted to merge a top level ComponentAccumulator. Revert the order of merging\n"))
804 def mergeSequences( dest, src ):
808 if dest.name == src.name:
810 props = (dest._properties.keys() | src._properties.keys()) - {
'Members'}
811 for seqProp
in props:
813 if dest._properties[seqProp] != src._properties[seqProp]:
815 f
"Merging two sequences with name '{dest.name}' but property '{seqProp}' "
816 f
"has different values: {getattr(dest, seqProp)} vs {getattr(src, seqProp)}")
817 except KeyError
as e:
819 f
"Merging two sequences with name '{dest.name}' but property '{e}' is not "
820 f
"set in one of them")
822 for childIdx, c
in enumerate(src.Members):
826 mergeSequences(sub, c )
828 self.
_msg.
debug(
" Merging sequence %s to a destination sequence %s", c.name, dest.name )
830 for name, existingAlgs
in algorithmsByName.items():
832 algInstance, _, _ = existingAlgs[0]
840 for _, parent, idx
in existingAlgs:
844 dest.Members.append(c)
858 if not existingAlgInDest:
859 self.
_msg.
debug(
" Adding algorithm %s to a sequence %s", c.name, dest.name )
860 dest.Members.append(c)
872 for otherSeq
in other._allSequences:
875 destSeqName = otherSeq.name
876 if sequenceName
and otherSeq == other._sequence:
877 destSeqName = sequenceName
878 self.
_msg.
verbose(
" Will move sequence %s to %s", otherSeq.name, destSeqName )
882 mergeSequences(ourSeq, otherSeq)
884 self.
_msg.
verbose(
" Succeeded to merge sequence %s to %s", otherSeq.name, ourSeq.name )
886 self.
_msg.
verbose(
" Failed to merge sequence %s to any existing one, destination CA will have several top/dangling sequences", otherSeq.name )
896 for name
in other._algorithms:
902 for condAlg
in other._conditionsAlgs:
906 for svc
in other._services:
908 self.
addService(svc, create = svc.getFullJobOptName()
in other._servicesToCreate)
910 for pt
in other._publicTools:
915 for aud
in other._auditors:
920 for (k,v)
in other._theAppProps.items():
923 other._wasMerged=
True
935 """ Declares CA as merged
937 This is temporarily needed by HLT and should not be used elsewhere
942 """ returns iterable over all components """
950 def store(self,outfile, withDefaultHandles=False):
952 Saves CA in pickle form
954 when withDefaultHandles is True, also the handles that are not set are saved
960 if withDefaultHandles:
961 from AthenaConfiguration.Utils
import loadDefaultComps, exposeHandles
965 pickle.dump(self,outfile)
974 ROOT.gROOT.SetBatch(
True)
977 appPropsToSet, mspPropsToSet, bshPropsToSet = self.
gatherProps()
980 from Gaudi.Main
import BootstrapHelper
982 bsh = BootstrapHelper()
983 app = bsh.createApplicationMgr()
985 for k, v
in appPropsToSet.items():
986 self.
_msg.
debug(
"Setting property %s : %s", k, v)
987 app.setProperty(k, v)
991 msp = app.getService(
"MessageSvc")
992 for k, v
in mspPropsToSet.items():
993 self.
_msg.
debug(
"Setting property %s : %s", k, v)
994 bsh.setProperty(msp, k.encode(), v.encode())
997 for comp, name, value
in bshPropsToSet:
998 self.
_msg.
debug(
"Adding %s.%s = %s", comp, name, value)
999 app.setOption(f
"{comp}.{name}", value)
1012 svc.getFullJobOptName(),
1015 svcToCreate.append(svc.getFullJobOptName())
1018 for bs
in reversed(_basicServicesToCreateOrder):
1019 if bs
in svcToCreate:
1020 svcToCreate.insert(0, svcToCreate.pop( svcToCreate.index(bs) ) )
1022 extSvc.append(
"PyAthena::PyComponentMgr/PyComponentMgr")
1024 appPropsToSet[
"ExtSvc"] =
str(extSvc)
1025 appPropsToSet[
"CreateSvc"] =
str(svcToCreate)
1027 def getCompsToBeAdded(comp, namePrefix=""):
1028 name = namePrefix + comp.getName()
1029 for k, v
in comp._properties.items():
1032 if isinstance(v, GaudiConfig2.Configurable):
1034 bshPropsToSet.append((name, k, v.getFullJobOptName()))
1036 getCompsToBeAdded(v, namePrefix=name +
".")
1038 elif isinstance(v, GaudiHandles.PrivateToolHandleArray):
1040 bshPropsToSet.append(
1041 (name, k,
str([v1.getFullJobOptName()
for v1
in v]),)
1045 getCompsToBeAdded(v1, namePrefix=name +
".")
1050 if isinstance(v, list)
and v
and isinstance(v[0], DataHandle):
1051 v = [
str(x)
for x
in v]
1054 v = [alg.getFullJobOptName()
for alg
in comp.Members]
1055 vstr =
"" if v
is None else str(v)
1056 bshPropsToSet.append((name, k, vstr))
1059 from AthenaPython
import PyAthenaComps
1068 if svc.getName() !=
"MessageSvc":
1069 getCompsToBeAdded(svc)
1070 if isinstance(svc, PySvc):
1073 mspPropsToSet.update((k,
str(v))
for k,v
in svc._properties.items())
1077 getCompsToBeAdded(alg)
1078 if isinstance(alg, PyAlg):
1084 getCompsToBeAdded(alg)
1085 condalgseq.append(alg.getFullJobOptName())
1086 if isinstance(alg, PyAlg):
1088 bshPropsToSet.append((
"AthCondSeq",
"Members",
str(condalgseq)))
1092 getCompsToBeAdded(pt, namePrefix=
"ToolSvc.")
1096 getCompsToBeAdded(aud)
1098 return appPropsToSet, mspPropsToSet, bshPropsToSet
1101 from os
import environ
1102 outpklfile = environ.get(
"PICKLECAFILE",
None)
1103 if outpklfile
is not None:
1105 self.
_msg.
info(
"Storing configuration in pickle file %s",outpklfile)
1106 with open(outpklfile,
"wb")
as f:
1110 self.
_msg.
info(
"Exiting after configuration stage")
1111 from Gaudi.Main
import BootstrapHelper
1112 return BootstrapHelper.StatusCode(
True)
1121 environ[
'TDAQ_ERS_NO_SIGNAL_HANDLERS']=
'1'
1122 from AthenaCommon.Debugging
import allowPtrace, hookDebugger
1131 if maxEvents
is None:
1139 from sys
import exit
1145 self.
_msg.
info(f
"Athena job with pid {os.getpid()}")
1149 sc = app.initialize()
1150 if not sc.isSuccess():
1151 self.
_msg.
error(
"Failed to initialize AppMgr")
1155 if not sc.isSuccess():
1156 self.
_msg.
error(
"Failed to start AppMgr")
1165 from AthenaPython.PyAthena
import py_svc
1166 sg=
py_svc(
"StoreGateSvc/StoreGateSvc")
1169 sc = app.run(maxEvents)
1170 if not sc.isSuccess():
1171 self.
_msg.
error(
"Failure running application")
1175 if not scStop.isSuccess():
1176 self.
_msg.
error(
"Failed to stop AppMgr")
1182 scFin=app.finalize()
1183 if not scFin.isSuccess():
1184 self.
_msg.
error(
"Failed to finalize AppMgr")
1187 sc1 = app.terminate()
1191 """Utility to set properties of components using wildcards.
1194 ca.foreach_component("*/HLTTop/*/*Hypo*").OutputLevel = VERBOSE
1196 The components name and location in the CF tree are translated into a UNIX-like path
1197 and are matched using the `fnmatch` library. If the property is set successfully
1198 an INFO message is printed else a WARNING.
1200 The convention for paths of nested components is as follows:
1201 Sequence : only the name is used in the path
1202 Algorithm : "type/name" is used
1203 Private Tool : ToolHandle property name plus "type/name" is used
1204 Public Tool : located under "ToolSvc/" and "type/name" is used
1205 Service : located under "SvcMgr/" and "type/name" is used
1207 from AthenaConfiguration.PropSetterProxy
import PropSetterProxy
1208 return PropSetterProxy(self, path)
1212 """Setup and start a useful interactive session including auto-completion and history"""
1216 vars = sys.modules[
'__main__'].__dict__
1217 vars.update(globals())
1218 vars.update(localVarDic)
1221 from AthenaCommon.Interactive
import configureInteractivePrompt
1225 code.interact(local=vars)
1229 print(
"Interactive mode")
1230 print(
"\tThe ComponentAccumulator is known as 'self', you can inspect it but changes are not taken into account.")
1231 print(
"\tThe application is known as 'app' but not yet initialized.")
1232 print(
"\t^D will exit the interactive mode and athena will continue.")
1233 print(
"\texit() will terminate the program now.")
1238 print(
"Interactive mode")
1239 print(
"\tThe application is known as 'app' and initialized.")
1240 print(
"\tYou can process N events with 'app.run(N)'.")
1241 print(
"\tStoreGate is accessible as 'sg'.")
1242 print(
"\t^D will exit the interactive mode and athena will finalize.")
1248 from AthenaConfiguration.LegacySupport
import (conf2toConfigurable,
1254 raise RuntimeError(
"conf2toConfigurable cannot be called in a CA job")
1256 raise RuntimeError(
"CAtoGlobalWrapper cannot be called in a CA job")
1258 raise RuntimeError(
"appendCAtoAthena cannot be called in a CA job")