"Неправильный тип. Ожидаемое значение pk, получено User."

У меня есть две модели: заказ и маршрут. Маршрут имеет oneToMany отношение с Заказом, как вы можете видеть:

class Order(models.Model):
    customer = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.CASCADE, related_name='customer')
    retailer = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.CASCADE, related_name='retailer')
    date_publish = models.DateField(default=datetime.date.today)
    date_available = models.DateField()
    weight = models.DecimalField(decimal_places=2, max_digits=5)
    description = models.CharField(max_length=500, null=True)
    route = models.ForeignKey(Route, related_name='orders', null=True, on_delete=models.CASCADE)

class Route(models.Model):
    day = models.DateField()
    warehouse = models.ForeignKey(Warehouse, on_delete=models.CASCADE) 
    start_time = models.TimeField()

Когда создается маршрут, я хочу связать заказы с этим маршрутом, поэтому я сделал следующий сериализатор:

class routeSerializer(serializers.ModelSerializer):

    orders = OrderSerializer(many=True)

    class Meta:
        model = Route
        fields = ['day', 'warehouse', 'start_time', 'orders']

    def create(self, validated_data):
        orders_data = validated_data.pop('orders')
        route = Route.objects.create(**validated_data)

        for order_data in orders_data:
            order_serializer = OrderSerializer(data=order_data)
            order_serializer.is_valid(raise_exception=True)
            orders = order_serializer.save()
            orders.route = route
            orders.save()
        
        return route


class OrderSerializer(serializers.ModelSerializer):
    ordertimelocation = orderTimelocationSerializer(many=True)


    class Meta:
        model = Order
        fields = ['id', 'customer', 'retailer', 'date_available', 'weight', 'description', 'ordertimelocation']

    def create(self, validated_data):
        timelocations_data = validated_data.pop('ordertimelocation')
        order = Order.objects.create(**validated_data)
        
        for timelocation_data in timelocations_data:
            order_time_location_serializer = orderTimelocationSerializer(data=timelocation_data)
            order_time_location_serializer.is_valid(raise_exception=True)
            order_time_location = order_time_location_serializer.save()
            order_time_location.order = order
            order_time_location.save()

        return order

    def update(self, instance, validated_data):
        
        timelocations_data = validated_data.pop('ordertimelocation')
        ordertimelocation = instance.ordertimelocation

        for timelocation_data in timelocations_data:
            order_time_location_serializer = orderTimelocationSerializer(data=timelocation_data)
            order_time_location_serializer.is_valid(raise_exception=True)
            order_time_location = order_time_location_serializer.save()
            order_time_location.order = instance
            order_time_location.save()

        return instance

Просмотров:

class GetRoutes(generics.ListAPIView):
    queryset = Route.objects.all()
    serializer_class = routeSerializer

class CreateRoute(generics.CreateAPIView):
    queryset = Route.objects.all()
    serializer_class = routeSerializer

class CreateOrder(generics.CreateAPIView):
 
    queryset = Order.objects.all()
    serializer_class = OrderSerializer

class GetOrders(generics.ListAPIView):

    serializer_class = OrderSerializer

    def get_queryset(self):
        us = self.kwargs.get('us')
        return Order.objects.filter(customer_id=us) 
    
class GetOrder(generics.RetrieveAPIView):

    serializer_class = OrderSerializer

    def get_object(self, queryset=None, **kwargs):
        item = self.kwargs.get('order')
        return get_object_or_404(Order, id=item)
    
class UpdateOrder(generics.UpdateAPIView):

    serializer_class = OrderSerializer
    queryset = Order.objects.all()


Я посылаю запрос следующего содержания:

{
    "day" : "2021-12-12",
    "warehouse": "1",
    "start_time": "7:00",
    "orders": [
        {
            "id": 15,
            "customer": 1,
            "retailer": 2,
            "date_available": "2020-12-12",
            "weight": "1.20",
            "description": null,
            "ordertimelocation": [
                {
                    "longitude": "12.1223000000000000",
                    "latitude": "12.1223000000000000",
                    "time_interval": [
                        {
                            "start": "2021-07-21T10:10:00Z",
                            "end": "2021-07-21T10:10:00Z"
                        }
                    ]
                }
            ]
        }
    ]
}

Но сервер возвращает плохой запрос:


{
    "customer": [
        "Incorrect type. Expected pk value, received User."
    ],
    "retailer": [
        "Incorrect type. Expected pk value, received User."
    ]
}

Я новичок в django и не знаю, что такое значение 'pk' и почему он ожидает его вместо User.

PK - это primary key и здесь равно id

Для сохранения записи в db вместе с ее связями, django нужен PK связанного объекта

Но когда вы передаете этот pk в сериализатор, в функции validate() сериализатора, django, если переданный pk существует в базе данных и действителен, если да, он вернет объект модели

Например, вы передаете клиенту pk как 1, но после валидации появляется объект Customer с id 1. и вы передаете этот объект в order = Order.objects.create(**validated_data), но, как я уже говорил, вы должны передавать только PK

Так что одним из решений может быть:

validated_data['customer'] = validated_data['customer'].id
validated_data['retailer'] = validated_data['retailer'].id
order = Order.objects.create(**validated_data)

Другим решением является переопределение validate() функции и управление тем, что возвращается

Вернуться на верх