def encode_value(value): """Converts a native Python value into a Firestore protobuf ``Value``. Args: value (Union[NoneType, bool, int, float, datetime.datetime, \ str, bytes, dict, ~google.cloud.Firestore.GeoPoint]): A native Python value to convert to a protobuf field. Returns: ~google.cloud.firestore_v1beta1.types.Value: A value encoded as a Firestore protobuf. Raises: TypeError: If the ``value`` is not one of the accepted types. """ if value is None: return document_pb2.Value(null_value=struct_pb2.NULL_VALUE) # Must come before six.integer_types since ``bool`` is an integer subtype. if isinstance(value, bool): return document_pb2.Value(boolean_value=value) if isinstance(value, six.integer_types): return document_pb2.Value(integer_value=value) if isinstance(value, float): return document_pb2.Value(double_value=value) if isinstance(value, datetime.datetime): return document_pb2.Value( timestamp_value=_datetime_to_pb_timestamp(value)) if isinstance(value, six.text_type): return document_pb2.Value(string_value=value) if isinstance(value, six.binary_type): return document_pb2.Value(bytes_value=value) # NOTE: We avoid doing an isinstance() check for a Document # here to avoid import cycles. document_path = getattr(value, '_document_path', None) if document_path is not None: return document_pb2.Value(reference_value=document_path) if isinstance(value, GeoPoint): return document_pb2.Value(geo_point_value=value.to_protobuf()) if isinstance(value, list): value_list = [encode_value(element) for element in value] value_pb = document_pb2.ArrayValue(values=value_list) return document_pb2.Value(array_value=value_pb) if isinstance(value, dict): value_dict = encode_dict(value) value_pb = document_pb2.MapValue(fields=value_dict) return document_pb2.Value(map_value=value_pb) raise TypeError( 'Cannot convert to a Firestore Value', value, 'Invalid type', type(value))
def test_array(self): from google.cloud.firestore_v1beta1.proto import document_pb2 sub_value1 = _value_pb(boolean_value=True) sub_value2 = _value_pb(double_value=14.1396484375) sub_value3 = _value_pb(bytes_value=b'\xde\xad\xbe\xef') array_pb = document_pb2.ArrayValue( values=[sub_value1, sub_value2, sub_value3]) value = _value_pb(array_value=array_pb) expected = [ sub_value1.boolean_value, sub_value2.double_value, sub_value3.bytes_value, ] self.assertEqual(self._call_fut(value), expected)
def make_array_value(values): value_list = [encode_value(element) for element in values] return document_pb2.ArrayValue(values=value_list)