我正在尝试在端点中添加一个新变量。
在使用cliente
之前,但现在我想添加user
(用于查找cliente
)。问题是user
不在我的Pedido
模型中,所以我使用user = serializers.IntegerField()
添加。我可以毫无问题地在方法中使用它,但是当返回实例pedido
时,出现了问题。
serializers.py
class PedidoWriterSerializer(serializers.ModelSerializer):
user = serializers.SerializerMethodField()
lineas = DetallePedidoSimpleSerializer(many=True, required=False)
class Meta:
model = Pedido
exclude = ('monto','entrega_realizada','pedido_confirmado', 'cliente',)
extra_kwargs = { 'user': {'write_only': True} }
def create(self, validated_data):
if 'lineas' in validated_data:
lineas = validated_data.pop('lineas')
if 'entrega_solicitada' in validated_data:
entregas_solicitadas = validated_data.pop('entrega_solicitada')
user = self._kwargs.get('data').get('user')
bandera = True
c = Cliente.objects.get(usuario_id=user)
validated_data['cliente'] = c
if (not c.habilitado):
bandera = False
if bandera:
total = 0
for l in lineas:
print(2)
print(l)
p = Producto.objects.get(pk=l['producto'].id)
if ((not p.activo) or (not p.stock) or (not(l['cantidad']>0 and
l['cantidad'] <1000))):
bandera = False
else:
today = datetime.now()
prom = p.ofertas.filter(activa=True,
desde__lte=today,
hasta__gte=today).last()
if prom:
monto_descuento = (p.precio * prom.descuento) / 100
total = (p.precio - monto_descuento) * l['cantidad']\
+ \
total
else:
total = p.precio * l['cantidad'] + total
if total < c.ciudad.monto_minimo:
bandera = False
if bandera:
for e in entregas_solicitadas:
he = Horario_Entrega.objects.get(pk=e.id)
if (not he.activo):
bandera = False
if bandera:
pedido = Pedido.objects.create(cliente=c)
for linea in lineas:
linea['pedido'] = pedido
Detalle_Pedido.objects.create(**linea)
for entrega in entregas_solicitadas:
pedido.entrega_solicitada.add(entrega)
print('algo')
self._kwargs.get('data').pop('user')
pedido.save()
# Everything is ok until this line
return pedido
else:
return None
viewset.py
class PedidoViewSet(viewsets.ModelViewSet):
queryset = Pedido.objects.select_related('cliente',
'entrega_pactada').prefetch_related('entrega_solicitada')
serializer_class = PedidoSerializer
filter_backends = (DjangoFilterBackend,)
filter_fields = ('cliente__id',)
authentication_classes = [JSONWebTokenAuthentication, ]
permission_classes = [permissions.IsAuthenticated, ]
def get_serializer_class(self):
if self.action == 'retrieve':
return PedidoSerializer
if self.action == 'list':
return PedidoSerializer
return PedidoWriterSerializer
def get_queryset(self):
queryset = super(PedidoViewSet,self).get_queryset()
today = timezone.now()
queryset = queryset.filter(fecha__gte = today - timedelta(days=30),
cliente__usuario__dni = self.request.user.dni).order_by(
'-fecha')
return queryset
这是错误消息:
ERROR Internal Server Error: /pedido/
Traceback (most recent call last):
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/rest_framework/fields.py", line 444, in get_attribute
return get_attribute(instance, self.source_attrs)
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/rest_framework/fields.py", line 103, in get_attribute
instance = getattr(instance, attr)
AttributeError: 'Pedido' object has no attribute 'user'
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/django/core/handlers/exception.py", line 41, in inner
response = get_response(request)
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/django/core/handlers/base.py", line 187, in _get_response
response = self.process_exception_by_middleware(e, request)
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/django/core/handlers/base.py", line 185, in _get_response
response = wrapped_callback(request, *callback_args, **callback_kwargs)
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/django/views/decorators/csrf.py", line 58, in wrapped_view
return view_func(*args, **kwargs)
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/rest_framework/viewsets.py", line 90, in view
return self.dispatch(request, *args, **kwargs)
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/rest_framework/views.py", line 489, in dispatch
response = self.handle_exception(exc)
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/rest_framework/views.py", line 449, in handle_exception
self.raise_uncaught_exception(exc)
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/rest_framework/views.py", line 486, in dispatch
response = handler(request, *args, **kwargs)
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/rest_framework/mixins.py", line 22, in create
headers = self.get_success_headers(serializer.data)
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/rest_framework/serializers.py", line 534, in data
ret = super(Serializer, self).data
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/rest_framework/serializers.py", line 263, in data
self._data = self.to_representation(self.instance)
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/rest_framework/serializers.py", line 488, in to_representation
attribute = field.get_attribute(instance)
File "/home/pedro/.virtualenvs/superEnv/lib/python3.5/site-packages/rest_framework/fields.py", line 463, in get_attribute
raise type(exc)(msg)
AttributeError: Got AttributeError when attempting to get a value for field `user` on serializer `PedidoWriterSerializer`.
The serializer field might be named incorrectly and not match any attribute or key on the `Pedido` instance.
Original exception text was: 'Pedido' object has no attribute 'user'.
答案 0 :(得分:0)
问题是您正在为用户字段使用SerializerMethodField()。这些类型的字段假定您在序列化器中将有一个具有相同名称的方法,并且该方法的返回值是用于该字段的值。
示例
class PedidoWriterSerializer(serializers.ModelSerializer):
user = serializers.SerializerMethodField()
def get_user(self, obj):
return "any logic needed to get the user value"
class Meta:
model = PedidoWriter
因此,当您获得序列化信息时,将有一个名为“ user”的字段,其中包含第二个参数“ obj”是ModelSerializer的实例,因此您可以使用以下方式访问Model的任何其他字段:该变量。