Ошибка ключа Django kwargs.pop (‘pk’)

#python #django #django-class-based-views

#python #django #представления на основе классов django

Вопрос:

Я использую CBV в Django 1.9 и в CreateView, когда я пытаюсь передать дополнительный параметр (‘pk’) в свою форму, используя self.kwargs.pop (‘pk’), я получаю «Ошибку ключа», но если я получаю параметр по индексу, он работает, вот мой код:

 def get_form(self, form_class=None, **kwargs):
    self.project_version_pk = self.kwargs.pop('pk')
    form = super(HRCreateView, self).get_form(form_class)
    form.fields['project_version'].queryset = form.fields['project_version'].queryset.filter(pk=self.project_version_pk)
    form.fields['project_version'].initial = self.project_version_pk
    return form

def get(self, request, *args, **kwargs):
    self.object = None
    form_class = self.get_form_class()
    form = self.get_form(form_class, pk=self.kwargs['pk'])

    return self.render_to_response(
        self.get_context_data(form=form)
  

И я получаю эту ошибку:

встроенные.Ошибка ключа KeyError: ‘pk’

 File "RelationView.py", line 65, in get_form

self.project_version_pk = self.kwargs.pop('pk')

KeyError: 'pk'
  

Но если я прочитаю ключ таким образом, он сработает:

 def get_form(self, form_class=None, **kwargs):
    self.project_version_pk = self.kwargs['pk']
    form = super(HRCreateView, self).get_form(form_class)
    form.fields['project_version'].queryset = form.fields['project_version'].queryset.filter(pk=self.project_version_pk)
    form.fields['project_version'].initial = self.project_version_pk
    return form
  

Я не совсем понимаю, почему параметр отсутствует в pop() или что является наилучшей практикой для этого.

Ответ №1:

Во-первых, вы не должны переопределять get . В CreateView Django уже вызывает get_form вас — внутри get_context_data . Это причина проблемы, с которой вы столкнулись; вы вызываете get_form и открываете pk, чтобы его больше не было в kwargs; но Django снова вызывает его в get_context_data, но во второй раз он не может найти pk, потому что вы удалили его в первый раз.

Так что не используйте pop; но, как я уже сказал, не делайте этого вообще. Единственное, что вам действительно нужно переопределить, это get_form .

Комментарии:

1. Хорошо, спасибо за ответ, но если я не переопределю get, как я могу перейти 'pk' к get_form методу?

2. Вам не нужно. В любом случае вы не используете ни один из аргументов этого метода.

3. Я передаю 'pk' , хотя это form = self.get_form(form_class, pk=self.kwargs['pk']) в get методе, как форма может быть получена 'pk' без необходимости передачи из другого метода? это потому, что у меня одинаковая форма для CreateView и UpdateView, и мне нужно передать 'pk' только con CreateView. Извините, может быть, все это очевидно для вас, но я работаю с Django всего несколько месяцев, заранее благодарю.

4. Но self.kwargs это не то же самое, что kwargs, которые передаются в метод; вы их вообще не используете.

5. Как предполагается, я должен передать 'pk' get_form метод to?