signoffs.signoffs.utils#

Core objects documented here are imported from the public API in singoffs.signoffs.utils E.g.

    from signoffs.signoffs.utils import service

signoffs.core.utils#

Utility functions and classes

Module Contents#

Classes#

Accessor

A string describing a path from one object to another via attributes accesses.

ServiceDescriptor

A descriptor used to “inject” instances of a “service” class into its owner’s instances.

ClassServiceDescriptor

A descriptor used to “inject” instances of a “service” class onto its owner class.

Functions#

dynamic_import

Dynamically import the given object (class, function, constant, etc.) from the given module_path If obj_name is None, the last dotted item in the module_path will be imported

service

Factory to return specialized service descriptors.

class_service

Factory to return specialized class service descriptors.

API#

signoffs.core.utils.dynamic_import(abs_module_path, obj_name=None)[source]#

Dynamically import the given object (class, function, constant, etc.) from the given module_path If obj_name is None, the last dotted item in the module_path will be imported

class signoffs.core.utils.Accessor[source]#

Bases: str

A string describing a path from one object to another via attributes accesses.

Relations are separated by a __ character.

Shamelessly adapted from the amazing django_tables2 https://pypi.org/project/django-tables2/

Initialization

Initialize self. See help(type(self)) for accurate signature.

SEPARATOR#

‘__’

ALTERS_DATA_ERROR_FMT#

‘Refusing to call {method}() because .alters_data = True’

LOOKUP_ERROR_FMT#

‘Failed lookup for attribute [{attr}] in {obj}, when resolving the accessor {accessor}’

resolve(obj, safe=True, quiet=False)[source]#

Return an attribute described by the accessor by traversing the attributes of object

Callable objects are called, and their result is used, before proceeding with the resolving. Usage:

    >>> from django.contrib.auth.models import User
    >>> user = User(first_name='Brad')
    >>> x = Accessor("user__first_name")
    >>> x.resolve(user)
    "Brad"
Parameters:
  • obj – The root object to traverse.

  • safe (bool) – Don’t call anything with alters_data = True

  • quiet (bool) – Smother all exceptions and instead return None

Returns:

resolved target object

Raises:

TypeError, AttributeError, KeyError, ValueError – (unless quiet == True)

property bits#
get_field(model)[source]#

Return the django model field for model in context, following relations.

penultimate_accessor()[source]#

Split off the right-most separator.

Returns:

a 2-tuple (the Accessor for the left part, the remainder right-part)

Usage:

    >>> Accessor("user__profile__title").penultimate_accessor()
    'user__profile', 'title'
penultimate(obj, quiet=True)[source]#

Split the accessor on the right-most separator (‘__’),

Returns:

a 2-tuple (the resolved left part, the remainder right-part)

Usage:

    >>> Accessor("user__profile__title").penultimate(user)
    <Profile object>, 'title'
signoffs.core.utils.service(service_class, **kwargs)[source]#

Factory to return specialized service descriptors.

Returns:

a ServiceDescriptor for a specialized subclass of service_class, that has kwargs as class attributes

Usage:

    >>> class Service:
    ...     service_type = 'generic'
    ...     def __init__(self, owner, extra=None):
    ...         self.owner = owner
    ...         self.extra = extra
    ...     def __str__(self):
    ...         extra = f' with {self.extra}' if self.extra else ''
    ...         return f'A {self.service_type} service for {self.owner}{extra}'
    ... class Owner:
    ...     a_service = service(Service, service_type='special')(extra="whazoo")
    ...     def __str__(self):
    ...         return 'Owner'
    ... o = Owner()
    ... assert str(o.a_service) == "A special service for Owner with whazoo"
class signoffs.core.utils.ServiceDescriptor(service_class=None, **kwargs)[source]#

A descriptor used to “inject” instances of a “service” class into its owner’s instances.

A “service” provides services or strategies to its owner, but needs the owner instance to do its own work. Construction of the owner instance may not be under direct control, so service instantiation must be automated. Service class must expect owner instance as first positional parameter of its constructor.

Initialization

Inject service_class instance into the instance of the descriptor’s owner class

first positional arg for service_class initializer must be an instance of owner class kwargs are passed through to the service_class initializer

service_class#

None

__set_name__(owner, name)[source]#
__get__(instance, owner)[source]#
signoffs.core.utils.class_service(service_class, **kwargs)[source]#

Factory to return specialized class service descriptors.

Returns:

a ClassServiceDescriptor for a specialized subclass of service_class, that has kwargs as class attributes

class signoffs.core.utils.ClassServiceDescriptor(service_class=None, **kwargs)[source]#

A descriptor used to “inject” instances of a “service” class onto its owner class.

This is analogous to ServiceDescriptor but service instance is available on owner class First positional parameter of service_class class must be an owner class (type not instance!)

Initialization

Inject service_class instance, initialized with owner class, into the descriptor’s owner class

first positional arg for service_class initializer must be an owner class type kwargs are passed through to the service_class initializer

service_class#

None

__set_name__(owner, name)[source]#
__get__(instance, owner)[source]#