Source code for typerighter.views

from typerighter import types


[docs]class Field(object): """A descriptor used to join a mutable View instance, that stores data, with the immutable Type instance, that only defines methods for operating on data. """ def __init__(self, name): self.name = name def __get__(self, instance, cls): if self.name in instance._data: return instance._data[self.name] return None def __set__(self, instance, value): instance._data[self.name] = value def __delete__(self, instance): del instance._data[self.name]
[docs]class View(object): """A View combines a `Record` with a dictionary to provide an object modeled after the record that can store data in a familiar object oriented manner. """ def __init__(self, record, data=None): self._record = record self._data = data def to_primitive(self, **convert_args): return self._record.to_primitive(self._data, **convert_args) def to_native(self, **convert_args): return self._record.to_native(self._data, **convert_args) def validate(self): return self._record.validate(self._data) def __iter__(self): for k, v in self._data.items(): if v is not types.Unset: yield k, v def __getattr__(self, name): if hasattr(self._record, name): return getattr(self._record, name)
[docs]def make_view(record, data=None): """Takes both a record and some data and produces View instance. :param Type record: The type that defines the view's shape :param dict data: Any initial data for the view's fields """ if not data: data = {} # Wrap each field of the record in a `Field` instance attrs = {} for field_name, _ in record: attr = Field(field_name) attrs[field_name] = attr # Collect any factory setters for name in dir(record): if name.startswith('set_'): attr = getattr(record.__class__, name) attrs[name] = attr view_cls_name = '%sView' % (record.__class__.__name__) # Instantiate a View definition with the new fields RecordView = type(view_cls_name, (View,), attrs) return RecordView(record, data=data)