n6sdk.class_helpers¶
-
n6sdk.class_helpers.
attr_required
(*attr_names, **kwargs)[source]¶ A method decorator: provides a check for presence of specified attributes.
- Some positional args:
- Names of attributes that are required to be present and not to be the dummy_placeholder object (see below) when the decorated method is called.
- Kwargs:
- dummy_placeholder (default:
None
): - The object that is not treated as a required value.
- dummy_placeholder (default:
- Raises:
NotImplementedError
:- When at least one of the specified attributes is set to the dummy_placeholder object or does not exist.
>>> class XX(object): ... a = 1 ... ... @attr_required('a') ... def meth_a(self): ... print 'OK' ... ... @attr_required('a', 'b') ... def meth_ab(self): ... print 'Excellent' ... ... @attr_required('z', dummy_placeholder=NotImplemented) ... def meth_z(self): ... print 'Nice' ... >>> x = XX() >>> x.meth_a() OK >>> x.meth_ab() Traceback (most recent call last): ... NotImplementedError: ... >>> x.b = 42 >>> x.meth_ab() Excellent >>> del XX.a >>> x.meth_ab() Traceback (most recent call last): ... NotImplementedError: ... >>> XX.a = None >>> x.meth_ab() Traceback (most recent call last): ... NotImplementedError: ... >>> x.meth_z() Traceback (most recent call last): ... NotImplementedError: ... >>> x.z = None >>> x.meth_z() # OK as here `dummy_placeholder` is not None Nice >>> x.z = NotImplemented >>> x.meth_z() Traceback (most recent call last): ... NotImplementedError: ...
-
n6sdk.class_helpers.
singleton
(cls)[source]¶ A class decorator ensuring that the class can be instantiated only once.
- Args:
- cls: the decorated class.
- Returns:
- The same class (cls).
Trying to instantiate the decorated class more than once causes
RuntimeError
– unless, during provious instantiations,__init__()
of the decorated class did not succeed (caused an exception).Subclasses are also bound by this restriction (i.e. the decorated class and its subclasses are “counted” as one entity) – unless their
__init__()
is overridden in such a way that the__init__()
of the decorated class is not called.The check is thread-safe (protected with a lock).
>>> @singleton ... class X(object): ... pass ... >>> o = X() >>> o = X() Traceback (most recent call last): ... RuntimeError: ...
>>> @singleton ... class X2(object): ... def __init__(self, exc=None): ... if exc is not None: ... raise exc ... >>> o = X2(ValueError('foo')) Traceback (most recent call last): ... ValueError: foo >>> o = X2() >>> o = X2() Traceback (most recent call last): ... RuntimeError: ... >>> o = X2(ValueError('foo')) Traceback (most recent call last): ... RuntimeError: ...
>>> @singleton ... class Y(object): ... def __init__(self, a, b, c=42): ... print a, b, c ... >>> class Z(Y): ... pass ... >>> class ZZZ(Y): ... def __init__(self, a, b): ... # will *not* call Y.__init__ ... print 'zzz', a, b ... >>> o = Y('spam', b='ham') spam ham 42 >>> o = Y('spam', b='ham') Traceback (most recent call last): ... RuntimeError: ... >>> o = Z('spam', b='ham') Traceback (most recent call last): ... RuntimeError: ... >>> o = ZZZ('spam', b='ham') zzz spam ham
>>> @singleton ... class Y2(object): ... def __init__(self, a, b, c=42): ... print a, b, c ... >>> class Z2(Y2): ... pass ... >>> class ZZZZZ(Y): ... def __init__(self, a, b): ... # *will* call Y.__init__ ... super(ZZZZZ, self).__init__(a, b=b) ... >>> o = Z2('spam', b='ham') spam ham 42 >>> o = Z2('spam', b='ham') Traceback (most recent call last): ... RuntimeError: ... >>> o = Y2('spam', b='ham') Traceback (most recent call last): ... RuntimeError: ... >>> o = ZZZZZ('spam', b='ham') Traceback (most recent call last): ... RuntimeError: ...
>>> class A(object): ... def __init__(self, a, b, c=42): ... print a, b, c ... >>> @singleton ... class B(A): ... pass ... >>> o = A('spam', b='ham') spam ham 42 >>> o = B('spam', b='ham') spam ham 42 >>> o = B('spam', b='ham') Traceback (most recent call last): ... RuntimeError: ... >>> o = A('spam', b='ham') spam ham 42 >>> o = B('spam', b='ham') Traceback (most recent call last): ... RuntimeError: ...