def get( self, path: Union[List[str], str] = None, default=None, force_refresh: bool = False, ) -> Any: """ Retrieve cached data for this record. Arguments --------- path : list of str or str, optional Specifies the field to retrieve the value for. If no path is supplied, return the entire cached data structure for this record. default Default value to return if no value was found under provided path. force_refresh : bool, optional If set to True, force refresh the data cache from the server before reading the values. Defaults to False. Returns ------- Any Cached data. """ return get_by_path( path or [], self._get_record_data(force_refresh=force_refresh), default=default, )
def _convert_diff_to_changelist(self, difference: list, old_val, new_val) -> list: """ Convert difference between field values into a changelist. Arguments --------- difference : list List of changes needed to consider. old_val Previous value. new_val New value. Returns ------- list Changelist converted from different values. """ changed_values = set() for operation, path, values in deepcopy(difference): path = path.split(".") if isinstance(path, str) else path if operation in ["add", "remove"]: path.append(values[0][0]) while isinstance(path[-1], int): path.pop() changed_values.add(".".join(map(str, path))) return [( "changed_value", path, (get_by_path(path, old_val), get_by_path(path, new_val)), ) for path in changed_values]
def get( self, path: str = "", default: Any = None, force_refresh: bool = False, ) -> Union[dict, str]: """ Retrieve cached data for this record. Arguments --------- path : str, optional Specifies the field to retrieve the value for. If no path is supplied, return the entire cached data structure for this record. Defaults to empty string. default : Any, optional Default value to return if no value was found under provided path. Defaults to None. force_refresh : bool, optional If set to True, force refresh the data cache from the server before reading the values. Defaults to False. Returns ------- Union[dict, str] Cached data. """ obj = self._get_record_data(force_refresh=force_refresh) return get_by_path(path=path, obj=obj, default=default)
def _convert_diff_to_changelist(self, difference, old_val, new_val): # TODO: cached property? mappers = {} for name in dir(self.__class__): field = getattr(self.__class__, name) if isinstance(field, Mapper): mappers[name] = field changed_fields = set() changes = [] remaining = [] content_changed = False for d in deepcopy(difference): operation, path, values = d # normalize path path = path if path else [] path = path.split(".") if isinstance(path, str) else path if operation in ["add", "remove"]: path.append(values[0][0]) while isinstance(path[-1], int): path.pop() path = ".".join(map(str, path)) # check whether it was content that changed if path == "content": content_changed = True continue # check whether the value changed matches one of our mapped fields/properties fields = [(name, field) for name, field in mappers.items() if path.startswith(field.path)] if fields: changed_fields.add(fields[0]) continue remaining.append(d) if content_changed: old = deepcopy(old_val.get("content", [])) new = deepcopy(new_val.get("content", [])) # track what's been added and removed removed = set(old) - set(new) added = set(new) - set(old) for id in removed: changes.append(("content_removed", "content", id)) for id in added: changes.append(("content_added", "content", id)) # ignore the added/removed items, and see whether order has changed for id in removed: old.remove(id) for id in added: new.remove(id) if old != new: changes.append(("content_reordered", "content", (old, new))) for name, field in changed_fields: old = field.api_to_python(get_by_path(field.path, old_val)) new = field.api_to_python(get_by_path(field.path, new_val)) changes.append(("changed_field", name, (old, new))) return changes + super()._convert_diff_to_changelist( remaining, old_val, new_val)