Django をよりよく理解し、遭遇する可能性のある同様の問題にもっと簡単に対処できるように、幅広い質問をしようと思いました。私が抱えている特定の問題は、フォームを正しくレンダリングする最初のフォームセット コードを作成したことですが、投稿されたときに新しいオブジェクトが作成されないことです。
フォームが投稿されたことをサーバーから確認できます。エラーは発生しませんが、データベースにデータが追加されていません (django admin および manage.py シェルから確認)。manage.py シェルに投稿された内容を読み取ることは可能でしょうか? フォームがデータを正しく投稿し、ビューで受信されたかどうかを確認できるようにしたいと思います。次に、データが正しく投稿されていないか、ビューがデータを正しく処理していない理由を確認できます。
特定の問題については、ウィザードの 1 人が見つけられる単純な初心者エラーの場合に備えて、以下にコードを配置します。私はこのチュートリアルに従って、自分の目的に合わせて適応しようとしました。
モデル.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'
フォーム.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'
)
ビュー.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)