DRF序列化器访问serializer.data报KeyError: 'lat'如何解决?
错误原因
- 核心问题是序列化器的语法错误:
lat、lng字段定义末尾多写了逗号,Python会自动把末尾带逗号的单值识别为单元素元组,而非DRF的字段对象。DRF序列化器只会将Field类型的类属性注册为参数字段,因此你写的lat、lng没有被序列化器识别,校验通过后的serializer.data里仅包含term字段,取lat时就触发KeyError。 - 另外自定义
Location类也存在相同语法问题:__init__方法中self.lat = latitude,、self.lng=longitude,末尾的逗号会把两个经纬度属性存为元组,后续拼接字符串时会抛出类型错误。 - 额外的小问题:视图里的序列化器变量名拼写为
serilizer,属于笔误,虽不影响运行但可读性差。
解决方案
- 修正序列化器的语法,删除字段末尾的多余逗号:
class LocationSerializer(serializers.Serializer): lat = serializers.DecimalField(max_digits=9, decimal_places=6) lng = serializers.DecimalField(max_digits=9, decimal_places=6) term = serializers.CharField(max_length=100)
- 修正
Location类的语法,删除属性赋值末尾的逗号,同时处理Decimal类型转字符串的逻辑(Decimal对象不能直接和字符串拼接):
class Location: def __init__(self, latitude, longitude, term): self.lat = latitude self.lng = longitude self.term = term def convert_latandlong_to_address(self): geolocator = Nominatim(user_agent="geoapiExercises") # 格式化字符串自动转Decimal为字符串 location = geolocator.reverse(f"{self.lat},{self.lng}") address = location.raw['address'] return address
- 视图层优先使用
serializer.validated_data取校验后的值,比serializer.data更安全,同时修正拼写笔误:
@api_view(['POST']) def get_prefer_locations(request): serializer = LocationSerializer(data=request.data) if serializer.is_valid(): print(request.data) location_obj=Location( serializer.validated_data['lat'], serializer.validated_data['lng'], serializer.validated_data['term'] ) address = location_obj.convert_latandlong_to_address()
内容的提问来源于stack exchange,提问作者Niloofar
相关产品推荐
相关产品推荐

