17 'PropertyProxy',
'GaudiHandlePropertyProxy',
18 'GaudiHandleArrayPropertyProxy'
23 from GaudiKernel
import ConfigurableDb
27 log = logging.getLogger(
'PropertyProxy')
31 """A string version of isinstance().
32 <derived> is either an object instance, or a type
33 <base> is a string containing the name of the base class (or <derived> class)"""
34 if not isinstance(derived, type):
35 derived =
type(derived)
36 if derived.__name__ == base:
38 for b
in derived.__bases__:
46 errmsg =
"received an instance of %s, but %s expected" % (
type(value), tp)
55 elif isinstance(value, DataHandle):
60 raise ValueError(errmsg)
61 elif (tp
in [list, tuple, dict]):
62 if (
type(value)
is tp):
67 raise ValueError(errmsg)
74 except (TypeError, ValueError):
75 raise ValueError(errmsg)
81 def __init__(self, descr, docString=None, default=None):
87 if '[[deprecated]]' in docString:
89 if default
is not None:
98 default = property(getDefault, setDefault)
101 return (obj.getJobOptName()
102 or obj.getName()) +
'.' + self.
descr.__name__
107 except AttributeError:
110 if self.
__default.__class__
in [list, dict]:
122 log.warning(
'Property %s is deprecated: %s',
126 proptype, allowcompat =
None,
False
127 if hasattr(self,
'default'):
129 if self.
descr.__name__ ==
'OutputLevel':
138 if proptype
and proptype !=
type(
None)
and \
152 except AttributeError:
155 except ValueError
as e:
157 log.error(
'inconsistent value types for %s.%s (%s)' %
158 (obj.getName(), self.
descr.__name__, str(e)))
164 if not obj._isInSetDefaults()
or not obj
in self.
history:
166 if hasattr(self,
'default')
and self.
default ==
None:
167 obj.__iadd__(value, self.
descr)
170 self.
history.setdefault(obj, []).append(value)
179 """A class with some utilities for GaudiHandles and GaudiHandleArrays"""
181 def __init__(self, descr, docString, default, handleType, allowedType):
182 """<descr>: the real property in the object instance (from __slots__)
183 <docString>: the documentation string of this property
184 <default>: default value from C++ (via python generated by genconf)
185 <handleType>: real python handle type (e.g. PublicToolHandle, PrivateToolHandle, ...)
186 <allowedType>: allowed instance type for default
189 if not isinstance(default, allowedType):
190 raise TypeError(
"%s: %s default: %r is not a %s" %
191 (descr.__name__, self.__class__.__name__, default,
192 allowedType.__name__))
193 PropertyProxy.__init__(self, descr, docString, default)
201 except AttributeError:
204 default = obj.__class__.getDefaultProperty(self.
descr.__name__)
208 except AttributeError
as e:
210 raise RuntimeError(*e.args)
217 if not obj._isInSetDefaults()
or not obj
in self.
history:
222 self.
history.setdefault(obj, []).append(value)
225 """Check if <value> is a handle of the correct type"""
229 """Check if <value> is a configurable of the correct type"""
233 """Return the configurable instance corresponding to the toolhandle if possible.
234 Otherwise return None"""
237 typeAndNameTuple = typeAndName.split(
'/')
238 confType = typeAndNameTuple[0]
239 confClass = ConfigurableDb.getConfigurable(confType)
242 log.error(
"%s: Configurable %s is not a %s", requester, confType,
246 confName = typeAndNameTuple[1]
250 return confClass(confName)
254 isString =
type(default) == str
255 if not isString
and self.
isConfig(default):
258 elif isString
or self.
isHandle(default):
261 typeAndName = default
264 typeAndName = default.typeAndName
271 if '/' in typeAndName:
272 typeAndName = typeAndName.replace(
273 '/',
'/{}.'.
format(obj.name()), 1)
275 typeAndName =
"{0}/{1}.{0}".
format(typeAndName, obj.name())
282 except AttributeError
as e:
284 raise RuntimeError(*e.args)
287 "%s: Default configurable for class %s not found in ConfigurableDb.CfgDb"
291 raise TypeError(
"%s: default value %r is not of type %s or %s" %
300 isString =
type(value) == str
311 if not value.isInToolSvc():
312 suggestion =
'You may need to add jobOptions lines something like:' + os.linesep + \
313 'from AthenaCommon.AppMgr import ToolSvc' + os.linesep + \
315 if value.getName() == value.getType(
317 suggestion +=
'%s()' % value.__class__.__name__
319 suggestion +=
'%s(%r)' % (value.__class__.__name__,
323 ': Public tool %s is not yet in ToolSvc. %s' %
324 (value.getJobOptName(), suggestion))
327 elif value.hasParent(obj.getJobOptName()):
332 value = obj.copyChildAndSetParent(value, obj.getJobOptName())
334 obj.allConfigurables[value.name()] = value
338 "Property %s value %r is not a %s nor a %s nor a string" %
347 GaudiHandlePropertyProxyBase.__init__(self, descr, docString, default,
348 type(default), GaudiHandle)
353 """<descr>: the real property in the object instance (from __slots__)
354 <confTypeName>: string indicating the (base) class of allowed Configurables to be assigned.
355 <handleType>: real python handle type (e.g. PublicToolHandle, PrivateToolHandle, ...)
357 GaudiHandlePropertyProxyBase.__init__(self, descr, docString, default,
358 type(default).handleType,
363 if not isinstance(value, list)
and not isinstance(
366 "%s: Value %r is not a list nor a %s" %
373 cd = GaudiHandlePropertyProxyBase.convertDefaultToBeSet(
376 newDefault.append(cd)
384 cv = GaudiHandlePropertyProxyBase.convertValueToBeSet(self, obj, v)
393 PropertyProxy.__init__(self, descr, docString, default)
398 except AttributeError:
401 default = obj.__class__.getDefaultProperty(self.
descr.__name__)
405 except AttributeError
as e:
407 raise RuntimeError(*e.args)
412 if not obj._isInSetDefaults()
or not obj
in self.
history:
417 self.
history.setdefault(obj, []).append(value)
423 mode = obj.__class__.getDefaultProperty(self.
descr.__name__).mode()
424 _type = obj.__class__.getDefaultProperty(self.
descr.__name__).
type()
425 if type(value) == str:
427 elif isinstance(value, DataHandle):
428 return DataHandle(value.__str__(), mode, _type)
430 raise ValueError(
"received an instance of %s, but %s expected" %
431 (
type(value),
'str or DataHandle'))
437 if isinstance(default, GaudiHandleArray):
440 if isinstance(default, GaudiHandle):
443 if isinstance(default, DataHandle):