创建django表单的简单方法是什么

What is the easy way to create django form

比如我有Student模型

class Student(models.Model):
    first_name = models.CharField(max_lenght=100)
    last_name = models.CharField(max_lenght=100)
    learning_group = models.CharField(max_lenght=100)

所以我想为某个组中的每个学生创建以下表格:

|学生 |标记 |缺席 |

|约翰·史密斯 |输入标记 |输入缺勤时间|

感谢您的帮助。

编辑:

我将缺席和标记字段存储在 JSonField() 中,它看起来像这样
{ student_pk: 1, 标记: 5, 缺席: 3 }
那么我尝试了什么:

起初我试图通过覆盖 forms.Form init 方法来实现它,但格式错误

def MarkBookForm(forms.Form):
    def __init__(self, *args, **kwargs):
        self.students = kwargs.pop('students', None)
        super(MarkBookForm, self).__init__(*args, **kwargs)
        for student in self.students:
            self.fields["student_{}".format(student.pk)] = forms.CharField(initial="{} {}".format(student.first_name, student.last_name)
            self.fields["mark_{}".format(student.pk)] = forms.FloatField()
            self.fields["absent_{}".format(student.pk)] = forms.FloatField()

这就是我想要的

这就是我所做的

首先你应该为 markabsent 定义你的模型 您可以像这样使用某事(未测试 :)):

models.py:

    class MyModel(models.Model):
        field1 = models.CharField(max_length=40, blank=False, null=False)
        field2 = models.CharField(max_length=60, blank=True, null=True)

forms.py:

    class FormForMyModel(forms.Form):
        form_field1 = forms.CharField(max_length=40, required=True)
        form_field2 = forms.CharField(max_length=60, required=False)

views.py:

    def create_a_my_model(request):
        if request.method == 'POST':
            form = FormForMyModel(request.POST)
            if form.is_valid():
                my_model = MyModel()
                my_model.field1 = form.cleaned_data.get('form_field1', 'default1')
                my_model.field2 = form.cleaned_data.get('form_field2', 'default2')
                my_model.save()
        else:        
            form = FormForMyModel()
        context_data = {'form': form}
        return HttpResponse('templtate.html', context_data)

以上示例概述了通用表单工作流程。

您会注意到上面示例中的两个烦人的问题:

  1. 我必须分别定义 MyModel 上的字段和 FormForMyModel 上的字段。但是,这两组(类型)字段之间有很多相似之处,因此这是一种重复工作。添加标签、验证器等时相似性会增加。
  2. 创建 MyModel 实例有点傻,必须手动分配所有这些值。

这是 ModelForm 的用武之地。

所以回到两个问题:

  1. 我没有为每个模型字段定义一个表单字段,我只是在Metaclass中定义了model = MyModel。这指示表单从模型字段自动生成表单字段。

  2. 模型表单有 save 方法可用。这可用于在视图中的一行中创建模型实例,而不是手动分配 field-by-field.

所以,让我们用 ModelForm:

做上面的例子
models.py:

    class MyModel(models.Model):
        field1 = models.CharField(max_length=40, blank=False, null=False)
        field2 = models.CharField(max_length=60, blank=True, null=True)

forms.py:

    class MyModelForm(forms.ModelForm):  # extending ModelForm, not Form as before
        class Meta:
            model = MyModel

views.py:

    def create_a_my_model(request):
        if request.method == 'POST':
            form = MyModelForm(request.POST)
            if form.is_valid():
                # save the model to database, directly from the form:
                my_model = form.save()  # reference to my_model is often not needed at all, a simple form.save() is ok
                # alternatively:
                # my_model = form.save(commit=False)  # create model, but don't save to database
                # my.model.something = whatever  # if I need to do something before saving it
                # my.model.save()
        else:        
            form = MyModelForm()
        context_data = {'form': form}
        return HttpResponse('templtate.html', context_data)