def from_serializable_dict(x):
    """
    Reconstruct a dictionary by recursively reconstructing all its keys and
    values.

    This is the most hackish part since we rely on key names such as
    __name__, __class__, __module__ as metadata about how to reconstruct
    an object.

    TODO: It would be cleaner to always wrap each object in a layer of type
    metadata and then have an inner dictionary which represents the flattened
    result of to_dict() for user-defined objects.
    """
    if "__name__" in x:
        return _lookup_value(x.pop("__module__"), x.pop("__name__"))

    non_string_key_objects = [
        from_json(serialized_key)
        for serialized_key
        in x.pop(SERIALIZED_DICTIONARY_KEYS_FIELD, [])
    ]
    converted_dict = type(x)()
    for k, v in x.items():
        serialized_key_index = parse_serialized_keys_index(k)
        if serialized_key_index is not None:
            k = non_string_key_objects[serialized_key_index]

        converted_dict[k] = from_serializable_repr(v)
    if "__class__" in converted_dict:
        class_object = converted_dict.pop("__class__")
        if "__value__" in converted_dict:
            return class_object(converted_dict["__value__"])
        elif hasattr(class_object, "from_dict"):
            return class_object.from_dict(converted_dict)
        else:
            return class_object(**converted_dict)
    return converted_dict
def from_serializable_dict ( x ) : if "__name__" in x : return _lookup_value ( x . pop ( "__module__" ) , x . pop ( "__name__" ) ) non_string_key_objects = [ from_json ( serialized_key ) for serialized_key in x . pop ( SERIALIZED_DICTIONARY_KEYS_FIELD , [ ] ) ] converted_dict = type ( x ) ( ) for k , v in x . items ( ) : serialized_key_index = parse_serialized_keys_index ( k ) if serialized_key_index is not None : k = non_string_key_objects [ serialized_key_index ] converted_dict [ k ] = from_serializable_repr ( v ) if "__class__" in converted_dict : class_object = converted_dict . pop ( "__class__" ) if "__value__" in converted_dict : return class_object ( converted_dict [ "__value__" ] ) elif hasattr ( class_object , "from_dict" ) : return class_object . from_dict ( converted_dict ) else : return class_object ( ** converted_dict ) return converted_dict
Reconstruct a dictionary by recursively reconstructing all its keys and
    values.

    This is the most hackish part since we rely on key names such as
    __name__, __class__, __module__ as metadata about how to reconstruct
    an object.

    TODO: It would be cleaner to always wrap each object in a layer of type
    metadata and then have an inner dictionary which represents the flattened
    result of to_dict() for user-defined objects.