The Gaudi Framework  v32r1 (f65d50dc)
GaudiKernel.Configurable Namespace Reference

Classes

class  Configurable
 
class  ConfigurableAlgorithm
 
class  ConfigurableAlgTool
 
class  ConfigurableAuditor
 
class  ConfigurableGeneric
 
class  ConfigurableService
 
class  ConfigurableUser
 
class  CreateSequencesVisitor
 
class  DummyDescriptor
 
class  Error
 
class  PropertyReference
 
class  SuperAlgorithm
 

Functions

def expandvars (data)
 
def isApplicable (self)
 rep += v.__str__( indent + 1 ) + os.linesep elif isinstance(v,GaudiHandleArray): for vi in v: if isinstance(vi,Configurable) and not vi.isPublic(): rep += vi.__str__( indent + 1 ) + os.linesep More...
 
def appendPostConfigAction (function)
 
def removePostConfigAction (function)
 
def applyConfigurableUsers ()
 
def applyConfigurableUsers_old ()
 
def getNeededConfigurables ()
 
def purge ()
 
def makeSequences (expression)
 

Variables

list __all__
 
 log = logging.getLogger('Configurable')
 
list postConfigActions = []
 
bool _appliedConfigurableUsers_ = False
 

Function Documentation

◆ appendPostConfigAction()

def GaudiKernel.Configurable.appendPostConfigAction (   function)
Add a new callable ('function') to the list of post-configuration actions.
If the callable is already in the list, it is moved to the end of the list.
The list is directly accessible as 'GaudiKernel.Configurable.postConfigActions'.

Definition at line 1495 of file Configurable.py.

1495 def appendPostConfigAction(function):
1496  """
1497  Add a new callable ('function') to the list of post-configuration actions.
1498  If the callable is already in the list, it is moved to the end of the list.
1499  The list is directly accessible as 'GaudiKernel.Configurable.postConfigActions'.
1500  """
1501  try:
1502  postConfigActions.remove(function)
1503  except:
1504  pass
1505  postConfigActions.append(function)
1506 
1507 
def appendPostConfigAction(function)

◆ applyConfigurableUsers()

def GaudiKernel.Configurable.applyConfigurableUsers ( )
Call the apply method of all the ConfigurableUser instances respecting the
dependencies. First the C.U.s that are not used by anybody, then the used
ones, when they are not used anymore.

Definition at line 1519 of file Configurable.py.

1520  """
1521  Call the apply method of all the ConfigurableUser instances respecting the
1522  dependencies. First the C.U.s that are not used by anybody, then the used
1523  ones, when they are not used anymore.
1524  """
1525  # Avoid double calls
1526  global _appliedConfigurableUsers_, postConfigActions
1527  if _appliedConfigurableUsers_:
1528  return
1529  _appliedConfigurableUsers_ = True
1530 
1531  def applicableConfUsers():
1532  '''
1533  Generator returning all the configurables that can be applied in the
1534  order in which they can be applied.
1535  '''
1536  # This is tricky...
1537  # We keep on looking for the first configurable that can be applied.
1538  # When we cannot find any, 'next()' raises a StopIteration that is
1539  # propagated outside of the infinite loop and the function, then handled
1540  # correctly from outside (it is the exception that is raised when you
1541  # exit from a generator).
1542  # Checking every time the full list is inefficient, but it is the
1543  # easiest way to fix bug #103803.
1544  # <https://savannah.cern.ch/bugs/?103803>
1545  while True:
1546  yield (c for c in Configurable.allConfigurables.values()
1547  if c.isApplicable()).next()
1548 
1549  debugApplyOrder = 'GAUDI_DUBUG_CONF_USER' in os.environ
1550  for c in applicableConfUsers():
1551  if c._enabled:
1552  log.info("applying configuration of %s", c.name())
1553  if debugApplyOrder:
1554  sys.stderr.write('applying %r' % c)
1555  c.__apply_configuration__()
1556  log.info(c)
1557  else:
1558  log.info("skipping configuration of %s", c.name())
1559  c._applied = True # flag the instance as already applied
1560  if hasattr(c, "__detach_used__"):
1561  # tells the used configurables that they are not needed anymore
1562  c.__detach_used__()
1563 
1564  # check for dependency loops
1565  leftConfUsers = [
1566  c for c in Configurable.allConfigurables.values() if
1567  hasattr(c, '__apply_configuration__') and c._enabled and not c._applied
1568  ]
1569  # if an enabled configurable has not been applied, there must be a dependency loop
1570  if leftConfUsers:
1571  raise Error("Detected loop in the ConfigurableUser"
1572  " dependencies: %r" % [c.name() for c in leftConfUsers])
1573  # ensure that all the Handles have been triggered
1574  known = set()
1575  unknown = set(Configurable.allConfigurables)
1576  while unknown:
1577  for k in unknown:
1578  if not known: # do not print during the first iteration
1579  log.debug('new configurable created automatically: %s', k)
1580  # this trigger the instantiation from handles
1581  Configurable.allConfigurables[k].properties()
1582  known.add(k)
1583  unknown -= known
1584  # Call post-config actions
1585  for action in postConfigActions:
1586  action()
1587 
1588 

◆ applyConfigurableUsers_old()

def GaudiKernel.Configurable.applyConfigurableUsers_old ( )
Obsolete (buggy) implementation of applyConfigurableUsers(), kept to provide
backward compatibility for configurations that where relying (implicitly) on
bug #103803, or on a specific (non guaranteed) order of execution.

@see applyConfigurableUsers()

Definition at line 1589 of file Configurable.py.

1590  """
1591  Obsolete (buggy) implementation of applyConfigurableUsers(), kept to provide
1592  backward compatibility for configurations that where relying (implicitly) on
1593  bug #103803, or on a specific (non guaranteed) order of execution.
1594 
1595  @see applyConfigurableUsers()
1596  """
1597  # Avoid double calls
1598  global _appliedConfigurableUsers_, postConfigActions
1599  if _appliedConfigurableUsers_:
1600  return
1601  _appliedConfigurableUsers_ = True
1602 
1603  debugApplyOrder = 'GAUDI_DUBUG_CONF_USER' in os.environ
1604  confUsers = [
1605  c for c in Configurable.allConfigurables.values()
1606  if hasattr(c, "__apply_configuration__")
1607  ]
1608  applied = True # needed to detect dependency loops
1609  while applied and confUsers:
1610  newConfUsers = [] # list of conf users that cannot be applied yet
1611  applied = False
1612  for c in confUsers:
1613  if hasattr(c, "__users__") and c.__users__:
1614  newConfUsers.append(c) # cannot use this one yet
1615  else: # it does not have users or the list is empty
1616  applied = True
1617  # the ConfigurableUser is enabled if it doesn't have an _enabled
1618  # property or its value is True
1619  enabled = (not hasattr(c, "_enabled")) or c._enabled
1620  if enabled:
1621  log.info("applying configuration of %s", c.name())
1622  if debugApplyOrder:
1623  sys.stderr.write('applying %r' % c)
1624  c.__apply_configuration__()
1625  log.info(c)
1626  else:
1627  log.info("skipping configuration of %s", c.name())
1628  if hasattr(c, "__detach_used__"):
1629  # tells the used configurables that they are not needed anymore
1630  c.__detach_used__()
1631  confUsers = newConfUsers # list of C.U.s still to go
1632  if confUsers:
1633  # this means that some C.U.s could not be applied because of a dependency loop
1634  raise Error("Detected loop in the ConfigurableUser "
1635  " dependencies: %r" % [c.name() for c in confUsers])
1636  # ensure that all the Handles have been triggered
1637  known = set()
1638  unknown = set(Configurable.allConfigurables)
1639  while unknown:
1640  for k in unknown:
1641  if not known: # do not print during the first iteration
1642  log.debug('new configurable created automatically: %s', k)
1643  # this trigger the instantiation from handles
1644  Configurable.allConfigurables[k].properties()
1645  known.add(k)
1646  unknown -= known
1647  # Call post-config actions
1648  for action in postConfigActions:
1649  action()
1650 
1651 

◆ expandvars()

def GaudiKernel.Configurable.expandvars (   data)
Expand environment variables "data".
Data can be string, list, tuple and dictionary. For collection, all the
contained strings will be manipulated (recursively).

Definition at line 35 of file Configurable.py.

35 def expandvars(data):
36  """
37  Expand environment variables "data".
38  Data can be string, list, tuple and dictionary. For collection, all the
39  contained strings will be manipulated (recursively).
40  """
41  import os.path
42  typ = type(data)
43  if typ is str:
44  return os.path.expandvars(data)
45  elif typ in [list, tuple]:
46  collect = []
47  for i in data:
48  collect.append(expandvars(i))
49  return typ(collect)
50  elif typ is dict:
51  collect = {}
52  for k in data:
53  collect[expandvars(k)] = expandvars(data[k])
54  return collect
55  return data
56 
57 

◆ getNeededConfigurables()

def GaudiKernel.Configurable.getNeededConfigurables ( )
Function to select all and only the configurables that have to be used in
GaudiPython.AppMgr constructor.
This is needed because in Athena the implementation have to be different (the
configuration is used in a different moment).

Definition at line 1652 of file Configurable.py.

1653  """
1654  Function to select all and only the configurables that have to be used in
1655  GaudiPython.AppMgr constructor.
1656  This is needed because in Athena the implementation have to be different (the
1657  configuration is used in a different moment).
1658  """
1659  return [
1660  k for k, v in Configurable.allConfigurables.items()
1661  if v.getGaudiType() != "User"
1662  ] # Exclude ConfigurableUser instances
1663 
1664 

◆ isApplicable()

def GaudiKernel.Configurable.isApplicable (   self)

rep += v.__str__( indent + 1 ) + os.linesep elif isinstance(v,GaudiHandleArray): for vi in v: if isinstance(vi,Configurable) and not vi.isPublic(): rep += vi.__str__( indent + 1 ) + os.linesep

Return True is the instance can be "applied".
Always False for plain Configurable instances
(i.e. not ConfigurableUser).

Definition at line 997 of file Configurable.py.

997  def isApplicable(self):
998  '''
999  Return True is the instance can be "applied".
1000  Always False for plain Configurable instances
1001  (i.e. not ConfigurableUser).
1002  '''
1003  return False
1004 
1005 
1006 # classes for generic Gaudi component ===========
1007 
1008 
def isApplicable(self)
rep += v.__str__( indent + 1 ) + os.linesep elif isinstance(v,GaudiHandleArray): for vi in v: if isin...

◆ makeSequences()

def GaudiKernel.Configurable.makeSequences (   expression)
Convert a control flow expression to nested GaudiSequencers.

Definition at line 1739 of file Configurable.py.

1739 def makeSequences(expression):
1740  '''
1741  Convert a control flow expression to nested GaudiSequencers.
1742  '''
1743  if not isinstance(expression, ControlFlowNode):
1744  raise ValueError('ControlFlowNode instance expected, got %s' %
1745  type(expression).__name__)
1746  visitor = CreateSequencesVisitor()
1747  expression.visitNode(visitor)
1748  return visitor.sequence
1749 
1750 
def makeSequences(expression)

◆ purge()

def GaudiKernel.Configurable.purge ( )
Clean up all configurations and configurables.

Definition at line 1665 of file Configurable.py.

1665 def purge():
1666  """
1667  Clean up all configurations and configurables.
1668  """
1669  for c in Configurable.allConfigurables.values():
1670  c.__class__.configurables.clear()
1671  Configurable.allConfigurables.clear()
1672  # FIXME: (MCl) this is needed because instances of ConfigurableGeneric are not
1673  # migrated to the correct class when this is known.
1674  ConfigurableGeneric.configurables.clear()
1675  from ProcessJobOptions import _included_files
1676  import os.path
1677  import sys
1678  for file in _included_files:
1679  dirname, basname = os.path.split(file)
1680  basname, ext = os.path.splitext(basname)
1681  if basname in sys.modules:
1682  del sys.modules[basname]
1683  _included_files.clear()
1684 
1685 

◆ removePostConfigAction()

def GaudiKernel.Configurable.removePostConfigAction (   function)
Remove a callable from the list of post-config actions.
The list is directly accessible as 'GaudiKernel.Configurable.postConfigActions'.

Definition at line 1508 of file Configurable.py.

1508 def removePostConfigAction(function):
1509  """
1510  Remove a callable from the list of post-config actions.
1511  The list is directly accessible as 'GaudiKernel.Configurable.postConfigActions'.
1512  """
1513  postConfigActions.remove(function)
1514 
1515 
def removePostConfigAction(function)

Variable Documentation

◆ __all__

list GaudiKernel.Configurable.__all__
private
Initial value:
1 = [
2  'Configurable', 'ConfigurableAlgorithm', 'ConfigurableAlgTool',
3  'ConfigurableAuditor', 'ConfigurableService', 'ConfigurableUser',
4  'VERBOSE', 'DEBUG', 'INFO', 'WARNING', 'ERROR', 'FATAL',
5  'appendPostConfigAction', 'removePostConfigAction'
6 ]

Definition at line 23 of file Configurable.py.

◆ _appliedConfigurableUsers_

bool GaudiKernel.Configurable._appliedConfigurableUsers_ = False
private

Definition at line 1516 of file Configurable.py.

◆ log

GaudiKernel.Configurable.log = logging.getLogger('Configurable')

Definition at line 32 of file Configurable.py.

◆ postConfigActions

list GaudiKernel.Configurable.postConfigActions = []

Definition at line 1492 of file Configurable.py.