как исправить экземпляр модели django

Sep 06 2020

сообщения об ошибках ValueError: Невозможно присвоить "<User: [email protected]>": "Diagnoses.owner" должен быть экземпляром "Patient"

Я получаю указанную выше ошибку, когда пытаюсь создать новую карту или диагнозы. Карта и диагнозы должны быть экземпляром пациента, точно так же, как пациент имеет карту и ставит диагноз. У класса пациента есть предварительный ключ, указывающий на пользователя. Вот код

views.py

    from django.shortcuts import render
from rest_framework.generics import ListCreateAPIView, RetrieveUpdateDestroyAPIView
from .serializers import PatientsSerializer, PatientsCardSerializer, PatientsDiagnosesSerializer
from .models import Patient, Card, Diagnoses
from rest_framework import permissions
from .permissions import IsOwner


# Patient Views
class PatientListAPIView(ListCreateAPIView):
    serializer_class = PatientsSerializer
    queryset = Patient.objects.all()
    permission_classes = (permissions.IsAuthenticated, IsOwner,) 
    def perform_create(self, serializer):
        return serializer.save(owner=self.request.user)
    def get_queryset(self):
        return self.queryset.filter(owner=self.request.user)

class PatientDetailAPIView(RetrieveUpdateDestroyAPIView):
    serializer_class = PatientsSerializer
    permission_classes = (permissions.IsAuthenticated, IsOwner,)
    queryset = Patient.objects.all()
    lookup_field = "id"
    def get_queryset(self):
        return self.queryset.filter(owner=self.request.user)


class PatientCardListAPIView(ListCreateAPIView):
    serializer_class = PatientsCardSerializer
    queryset = Card.objects.all()
    permission_classes = (permissions.IsAuthenticated,) 
    def perform_create(self, serializer):
        return serializer.save(owner=self.request.user)
    def get_queryset(self):
        return self.queryset.filter(owner=self.request.user)

class PatientCardDetailAPIView(RetrieveUpdateDestroyAPIView):
    serializer_class = PatientsCardSerializer
    permission_classes = (permissions.IsAuthenticated, IsOwner,)
    queryset = Card.objects.all()
    lookup_field = "id"
    def get_queryset(self):
        return self.queryset.filter(owner=self.request.user)



class PatientDiagnosesListAPIView(ListCreateAPIView):
    serializer_class = PatientsDiagnosesSerializer
    queryset = Diagnoses.objects.all()
    permission_classes = (permissions.IsAuthenticated,) 
    def perform_create(self, serializer):
        return serializer.save(owner=self.request.user)
    def get_queryset(self):
        return self.queryset.filter(owner=self.request.user)

class PatientDiagnosesDetailAPIView(RetrieveUpdateDestroyAPIView):
    serializer_class = PatientsDiagnosesSerializer
    permission_classes = (permissions.IsAuthenticated, IsOwner,)
    queryset = Diagnoses.objects.all()
    lookup_field = "id"
    def get_queryset(self):
        return self.queryset.filter(owner=self.request.user)

Models.py

class Patient(models.Model):
    name = models.CharField(max_length=255, null=True)
    country = models.CharField(max_length=255, null=True)
    state = models.CharField(max_length=255, null=True)
    phone = models.CharField(max_length=255, null=True)
    email = models.CharField(max_length=255, null=True)
    owner = models.ForeignKey(to=User, null=True, on_delete=models.CASCADE)
    def __str__(self):
        return self.name
class Card(models.Model):    
    name = models.CharField(max_length=255, null=True)
    card_number = models.CharField(max_length=255, null=True)    
    owner = models.OneToOneField(Patient, null=True, blank=True, on_delete=models.CASCADE)
    def __str__(self):
        return (self.patient.name)+"'s card"
   
class Diagnoses(models.Model):
    sickness = models.CharField(max_length=255, null=True)
    note = models.TextField(max_length=255, null=True)   
    owner = models.ForeignKey(Patient, null=True, on_delete=models.SET_NULL)
    def __str__(self):
        return (self.patient.name)+"'s diagnoses"

Ответы

1 CodexLink Sep 07 2020 at 04:19

Пока что self.request.userэто Userобъект. Из-за этого вы не можете сохранить его в API или в модели. И для ясности, это не PatientОбъект.

В зависимости от вашей ситуации я бы поставил Patientобъект в очередь с Userобъектом (если это был объект с односторонней ссылкой), поместил его в аргумент и выполнил метод save ().

class PatientCardListAPIView(ListCreateAPIView):
    serializer_class = PatientsCardSerializer
    queryset = Card.objects.all()
    permission_classes = (permissions.IsAuthenticated,) 

    def perform_create(self, serializer):
        getPatientFromUser = Patient.objects.get(owner=self.request.user)
        # getPatientFromUser returns `Patient` Instance. So you could bind it in `Card` Model.
        return serializer.save(owner=getPatientFromUser)

    def get_queryset(self):
        return self.queryset.filter(owner=self.request.user)

Ноты:

  1. Это решение для односторонней ссылки. ( Userупоминается как Patient)
  2. Если у вас есть перекрестная ссылка между Userи Patience(где Пользователь и Терпение имеют друг на друге ForeignKey), объявите свою UserМодель.
  3. Решение запрашивает пациента у пользователя. Поскольку пользователь несовместим с этим посторонним объектом.