2016-11-18 38 views
0

我想我會問一個廣泛的問題,所以我對Django有了更好的理解,並且可以更容易地處理我可能遇到的任何類似問題。我遇到的具體問題是我編寫了第一個formset代碼,該代碼正確呈現表單,但在發佈時沒有創建新對象。Django - 我怎樣才能調試代碼,當POST錯誤似乎是在視圖中?

我可以從服務器看到表單已發佈,我沒有收到任何錯誤,但沒有數據添加到我的數據庫(從django admin和manage.py shell中檢查)。也許有可能讀取發佈在manage.py shell中的內容?我希望能夠檢查表單是否正確發佈了其數據並且已被視圖接收。然後我可以看到爲什麼數據沒有正確發佈或視圖沒有正確處理它。

對於具體問題,我會將我的代碼放置在下方,以防萬一您的某個嚮導可能發現一個簡單的初學者錯誤。我試圖遵循並適應this tutorial爲我自己的目的。

Models.py

class Chunk(models.Model): 
    name = models.CharField(max_length=250) 
    text = models.CharField(max_length=500) 
    images = models.FileField() 
    question = models.CharField(max_length=250) 
    expected_completion_time = models.IntegerField(default=1) 
    keywords = models.CharField(max_length=250, blank=True, null=True) 
    topic = models.CharField(max_length=250, blank=True, null=True) 
    course = models.CharField(max_length=250, blank=True, null=True) 
    is_flagged = models.BooleanField(default=False) 

    def get_absolute_url(self): 
     return reverse('detail', kwargs={'pk':self.pk}) 

    def __str__(self): 
     return self.name 


class Concept(Chunk): 
    application = models.CharField(max_length=500) 

    @property 
    def mode(self): 
     return "concept" 


class Subconcepts(models.Model): 
    subconcept = models.CharField(max_length=500) 
    concept = models.ForeignKey(Concept, on_delete=models.CASCADE) 

    def __str__(self): 
     return self.concept.name + ' - Subconcept' 

forms.py

class ConceptForm(forms.ModelForm): 
    # Form for creating Concept objects 
    class Meta: 
     model = Concept 
     fields = ['application', 'name', 'text', 'images', 'question', 'expected_completion_time', 'keywords', 'topic', 'course'] 


class SubconceptForm(forms.ModelForm): 
    # Form for creating Subconcept objects which are linked by ManyToOne fields to Concept objects 
    class Meta: 
     model = Subconcepts 
     fields = ['subconcept'] # Concept field excluded as will be set in view on form submission 


class BaseSubconceptFormset(BaseFormSet): 
    def clean(self): 
     # Validate that all subconcepts are unique 
     if any(self.errors): 
      return 
     subconcepts = [] 
     duplicates = False 

     for form in self.forms: 
      if form.cleaned_data: 
       subconcept = form.cleaned_data('subconcept') 

       if subconcept: 
        if subconcept in subconcepts: 
         duplicates = True 
        subconcepts.append(subconcept) 

       if duplicates: 
        raise forms.ValidationError(
         'Each key feature must be unique', 
         code='duplicate_subconcept' 
        ) 

views.py

def testformsets(request): 

    # Forms for creating a concept with appropriate subconcepts 
    SubconceptFormset = formset_factory(SubconceptForm, formset=BaseSubconceptFormset) 

    if request.method == 'POST': 
     concept_form = ConceptForm(request.POST) 
     subconcept_formset = SubconceptFormset(request.POST) 

     if concept_form.is_valid() and subconcept_formset.is_valid(): 
      concept = concept_form.save() 

      new_subconcepts = [] 

      for subconcept_form in subconcept_formset: 
       subconcept = subconcept_form.cleaned_data.get('subconcept') 
       new_subconcepts.append(Subconcepts(subconcept=subconcept, concept=concept)) 

      try: 
       with transaction.atomic(): 
        # Add all new subconcepts at once 
        Subconcepts.objects.bulk_create(new_subconcepts) 

        # And notify our users that it worked 
        messages.success(request, 'You have added new material') 

      except IntegrityError: # If the transaction failed 
       messages.error(request, 'There was an error saving your concept.') 
       return redirect('pomodoro/index.html') 

    else: 
     concept_form = ConceptForm() 
     subconcept_formset = SubconceptFormset() 

    context = { 
     'concept_form': concept_form, 
     'subconcept_formset': subconcept_formset 
    } 
    return render(request, 'pomodoro/formset_test.html', context) 
+0

將日誌記錄語句添加到視圖代碼。 –

+2

'concept = concept_form.save'你是不是要說'.save()'(帶圓括號)?否則,你會提交保存方法,但是你不會打電話給它。 –

+0

@JohnGordon感謝您發現(errors_spotted_by_django_wizards + = 1)。你是對的,我編輯過。看起來這並不是唯一的錯誤,因爲在表單提交中仍然沒有數據被保存到數據庫。你能告訴我更多關於日誌記錄的信息嗎?我不知道這個功能。也許有一些你可以指導我的文檔? – Era

回答

0

添加記錄語句到你的代碼。一個好的開始是記錄每個決定的結果和每個重要函數調用的結果,如下所示:

def myView(request): 

    import logging 
    logging.basicConfig(filename='mylog.log', level=logging.DEBUG) 

    if request.method == 'POST': 
     logging.debug('request.method=POST') 
     form = MyForm(request.POST) 
     logging.debug('form=%s', form) 

     if concept_form.is_valid(): 
      logging.debug('form is valid') 
      myform = form.save() 
      logging.debug('called form.save(), result=%s', myform) 

     else: 
      logging.debug('form is not valid') 
    else: 
     logging.debug('request.method is not POST') 
+0

謝謝,這正是我所需要的。它告訴我我的錯誤在哪裏,現在我需要解決如何解決它。再次感謝。 – Era