Django Форма не может отфильтровать внешний ключ при выпадающем списке - PullRequest
0 голосов
/ 26 февраля 2020

Редактировать: переписать описание для ясности

У меня есть класс "CustomUser", который я получил из полностью авторизированного учебника (Django Всеавторизованный учебник ) и у меня есть пользователь в качестве внешнего ключа в каждой модели, который работает по назначению и отображает только записи, относящиеся к текущему зарегистрированному пользователю для этого указанного c пользователя.

Например:

МОДЕЛЬ ОБРАЗОВАНИЯ (здесь работает правильно)

class Education(models.Model):
    user = models.ForeignKey(CustomUser, on_delete=models.CASCADE)
    EducationInstitutionName = models.CharField(verbose_name=_('Institution Name'), max_length=100, default=None)
    EducationLevel = models.CharField(verbose_name=_('Education Level'), choices=EDUCATIONLEVEL, max_length=100, default=None)
    EducationStartDate = models.DateField(verbose_name=_('Education Start Date'), default=None)
    EducationEndDate = models.DateField(verbose_name=_('Education End Date'), default=None)
    EducationCaoCode = models.CharField(choices=CAO_CODE, max_length=100, default=None)
    EducationDesc = models.CharField(verbose_name=_('Education Description'), max_length=250, default=None)


    def __str__(self):
        return self.EducationInstitutionName

Это работает отлично, и я достигаю того, что нужно.

Проблема возникает, когда у меня есть таблица Foreign Keys, которая является основной темой моего приложения, которое берет составные части резюме и позволяет вам комбинировать их для создания резюме сменных секций.

CV МОДЕЛЬ (Только модель, которая у меня есть, которая состоит из внешних ключей)

class Cv(models.Model):
    user = models.ForeignKey(
        CustomUser,
        on_delete=models.CASCADE,
    )
    CvName = models.CharField(verbose_name=_('CvName'), max_length=100, default=None)
    CvEducation = models.ForeignKey(Education, on_delete=models.CASCADE)
    CvSkills = models.ForeignKey(Skills, on_delete=models.CASCADE)
    CvWorkExperience = models.ForeignKey(WorkExperience, on_delete=models.CASCADE)

    def __str__(self):
        return self.CvName

CV FORM

Здесь я решаю проблему - я хочу отфильтровать поля только показать записи об образовании, навыках и опыте работы для текущий пользователь - в данный момент в раскрывающемся списке отображаются все существующие записи для моделей «Образование», «Навыки» и «Опыт работы», а не только те, которые относятся ТОЛЬКО к текущему зарегистрированному пользователю.

class CvForm(forms.ModelForm):
    class Meta:
        model = Cv
        fields = ('CvName', 'CvEducation', 'CvSkills', 'CvWorkExperience')

# TRYING TO FILTER BY CURRENT USER
    def __init__(self, user, *args, **kwargs):
        super(CvForm, self).__init__(*args, **kwargs)
        print(user)
        self.fields['CvEducation'].queryset = Education.objects.filter(user=user)
        self.fields['CvSkills'].queryset = Education.objects.filter(user=user)
        self.fields['CvWorkExperience'].queryset = Education.objects.filter(user=user)


    def save(self, commit=True):
        cv = super(CvForm, self).save(commit=False)
        cv.user = self.request.user
        cv.CvName = self.cleaned_data['CvName']
        cv.CvEducation = self.cleaned_data['CvEducation']
        cv.CvSkills = self.cleaned_data['CvSkills']
        cv.CvWorkExperience = self.cleaned_data['CvWorkExperience']
        cv.save()
        return cv

CV LIST VIEW VIEW (Это - правильно - показывает только завершенные CV записи, связанные с текущим вошедшим в систему пользователем)

class CvList(ListView):
    model = Cv
    fields = ['CvName', 'CvEducation', 'CvSkills', 'CvWorkExperience']
    success_url = reverse_lazy('Cv_list')

    def get_queryset(self):
        user_ids = CustomUser.objects.filter(username=self.request.user).values_list('id', flat=True)
        if user_ids:
            for uid in user_ids:
                return Cv.objects.filter(user__id=uid)
        else:
            return Cv.objects.all()

CV CREATE VIEW

class CvCreate(CreateView):
    model = Cv
    fields = ['CvName', 'CvEducation', 'CvSkills', 'CvWorkExperience']
    success_url = reverse_lazy('Cv_list')

    def form_valid(self, form):
        form.instance.user = self.request.user
        return super(CvCreate, self).form_valid(form)

    def get_queryset(self):
        user_ids = CustomUser.objects.filter(username=self.request.user).values_list('id', flat=True)
        if user_ids:
            for uid in user_ids:
                return Cv.objects.filter(user__id=uid)
        else:
            return Cv.objects.all()

Это дает мне ... Раскрывающийся список, показывающий всю таблицу Education, а не фильтруемый текущим пользователем

На этом изображении, когда я вошел как John Doe Я не должен видеть эту запись - "Джеймс Эду", поскольку он связан с другим пользователем Джеймс .

Это происходит во всех трех полях, которые у меня есть с иностранными ключами - CvEducation, CvSkills и CvWorkExperience

1 Ответ

0 голосов
/ 28 февраля 2020

Исправлено в конечном итоге (очень окольным путем):

МЕТОД ИНФОРМАЦИИ О ФОРМАХ

 def __init__(self, *args, **kwargs):
        initial_arguments = kwargs.get('initial', None)
        initial_arguments_list = list(initial_arguments.values())
        user_id = initial_arguments_list[0]
        super(CvForm, self).__init__(*args, **kwargs)
        self.fields['CvEducation'].queryset = Education.objects.filter(user__id=user_id)
        self.fields['CvSkills'].queryset = Skills.objects.filter(user__id=user_id)
        self.fields['CvWorkExperience'].queryset = WorkExperience.objects.filter(user__id=user_id)

СОЗДАТЬ ВИД

class CvCreate(CreateView):
    model = Cv
    success_url = reverse_lazy('Cv_list')
    form_class = CvForm
    exclude = ['user']

    def get_initial(self):
        self.initial.update({ 'created_by': self.request.user.id })
        return self.initial
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...