首页 > 解决方案 > Django 编辑表单

问题描述

我正在使用 Django v1.11.8 和 Python 2.7.6

我有一些关于编辑表单的问题。有人可以解释一下如何在 Django 中编写正确的编辑表单吗?我整天都在工作,但仍然遇到一些问题......我在互联网上看到了很多例子,但我仍然做错了什么。

我的 ModelForm 看起来像这样:

class UpdateVoteForm(ModelForm):
    class Meta:
        model = Vote
        fields = ['question', 'ans_a', 'ans_b', 'ans_c', 'ans_d', 'ans_e', 'ans_f', 'type', 'council', 'user', 'created_date', 'group']

查看功能:

def update_vote_from(request, pk):
    vote_inst = get_object_or_404(Vote, pk = pk)
    if request.method == 'POST':

        form = UpdateVoteForm(request.POST, instance=vote_inst)
        if form.is_valid():
            #vote_inst = form.save(commit=False)
            #vote_inst.created_date = datetime.date.today()
            form.save()

            return HttpResponseRedirect(reverse('voting-list'))

    else:
        form = UpdateVoteForm()

    return render(request, 'votes-form.html', {'form': form, 'vote_inst': vote_inst})

网址:

urlpatterns = [
    url(r'^$', views.index, name='index'),
    url(r'^votersList/$', views.VotersView.as_view(), name='voters-list'), 
    url(r'^vote/create/$', views.add_vote_from, name='vote-create'),
    url(r'^vote/(?P<pk>\d+)/edit/$', views.update_vote_from, name='vote-update'),     
]

和模板:

{% extends "base_generic.html" %}

{% block content %}

<div class="containter">
<form action="" method="post">
    {% csrf_token %}

<label for="user">Właściciel: </label>
    <select id="user" name="user">
        {% for user in vote_inst.user.all %}
            <option value="{{ user }}"{% if vote_inst.user == user %} selected{% endif %}>{{ user }}</option>
        {% endfor %}
    </select>

    <label for="user">Kto: </label>
    <input id="user" type="text" name="user" value="{{ vote_inst.user }}">

    <label for="question">Pytanie: </label>
    <textarea id="question" name="question" style="height:70px" value="{{ vote_inst.question.value }}"></textarea>

    <label for="ans_a">Odpowiedź A: </label>
    <input id="ans_a" type="text" name="ans_a" placeholder="Wpisz odpowiedź A" value="{{ vote_inst.ans_a }}">

    <label for="ans_b">Odpowiedź B: </label>
    <input id="ans_b" type="text" name="ans_b" value="{{ vote_inst.ans_b }}">

    <label for="ans_c">Odpowiedź C: </label>
    <input id="ans_c" type="text" name="ans_c" value="{{ vote_inst.ans_c }}">

    <label for="ans_d">Odpowiedź D: </label>
    <input id="ans_d" type="text" name="ans_d" value="{{ vote_inst.ans_d }}">

    <label for="ans_e">Odpowiedź E: </label>
    <input id="ans_e" type="text" name="ans_e" value="{{ vote_inst.ans_e }}">

    <label for="ans_f">Odpowiedź F: </label>
    <input id="ans_f" type="text" name="ans_f" value="{{ vote_inst.ans_f }}">

    <label for="type">Typ głosowania: </label>
    <select id="type" name="type">
        {% for x,y in vote_inst.type_choices %}
            <option value="{{ x }}"{% if vote_inst.type == x %} selected{% endif %}>{{ y }}</option>
        {% endfor %}
    </select>    
    <input type="submit" value="Zatwierdź" />


</form>
</div>

{% endblock %}

模型:

class Vote(models.Model):

    STATUS_INACTIVE = 0
    STATUS_ACTIVE_NOW = 1
    STATUS_FINISHED = 2
    STATUS_DELETED = 3

    TYPE_UNDECLARED = 0
    TYPE_PUBLIC = 1
    TYPE_NONPUBLIC = 2

    NO_RESULT = 0
    RESULT_A = 1
    RESULT_B = 2
    RESULT_C = 3
    RESULT_D = 4
    RESULT_E = 5
    RESULT_F = 6

    user = models.ForeignKey(User, on_delete=models.CASCADE)
    group = models.ForeignKey(Group, on_delete=models.CASCADE)
    voted_list = models.ManyToManyField(
        Voter,
        through='Voted',
        #through_fields=('Vote', 'Voter'),
    )
    council = models.ForeignKey(Council, on_delete=models.CASCADE)
    type_choices = (
        (TYPE_PUBLIC, 'Jawne'),
        (TYPE_NONPUBLIC, 'Niejawne'),
    )
    type = models.IntegerField(choices=type_choices, default=TYPE_PUBLIC)
    status_choices = (
        (STATUS_INACTIVE, 'Nieaktywne'),
        (STATUS_ACTIVE_NOW, 'Aktywne'),
        (STATUS_FINISHED, 'Zakończone'),
    )
    status = models.IntegerField(choices=status_choices, default=STATUS_INACTIVE)
    question = models.TextField()
    ans_a = models.TextField(null=True, blank=True)
    ans_b = models.TextField(null=True, blank=True)
    ans_c = models.TextField(null=True, blank=True)
    ans_d = models.TextField(null=True, blank=True)
    ans_e = models.TextField(null=True, blank=True)
    ans_f = models.TextField(null=True, blank=True)
    result_choices = (
        (NO_RESULT, 'No result'),
        (RESULT_A, 'A'),
        (RESULT_B, 'B'),
        (RESULT_C, 'C'),
        (RESULT_D, 'D'),
        (RESULT_E, 'E'),
        (RESULT_F, 'F'),
    )
    result = models.IntegerField(choices=result_choices, default=NO_RESULT)
    begin_date = models.DateTimeField(null=True, blank=True)
    finish_date = models.DateTimeField(null=True, blank=True)
    created_date = models.DateTimeField(default=timezone.now)

    def get_status(self):
        return self.status_choices[self.status][1]

    def get_absolute_url(self):
        return reverse('vote-update', args=[str(self.id)])

    def __unicode__(self):
        return "%s" % self.question

class User(models.Model):
    STATUS_INACTIVE = 0
    STATUS_ACTIVE = 1
    STATUS_DELETED = 2

    PRIVILIGES_UNDECLARED = 0
    PRIVILIGES_ADMIN = 1
    PRIVILIGES_MANAGER = 2
    PRIVILIGES_REPORTER = 3

    forename = models.CharField(max_length=50)
    name = models.CharField(max_length=50)
    login = models.CharField(max_length=30)
    password = models.CharField(max_length=50)
    last_login = models.DateTimeField(null=True, blank=True)
    priviliges_choices = (
        (PRIVILIGES_UNDECLARED ,'Undeclared'),
        (PRIVILIGES_ADMIN      ,'Administrator'),
        (PRIVILIGES_MANAGER    ,'Voting Manager'),
        (PRIVILIGES_REPORTER   ,'Reporter'),
    )
    priviligies = models.IntegerField(choices=priviliges_choices, default=PRIVILIGES_UNDECLARED)
    status_choices = (
        (STATUS_INACTIVE ,'Inactive'),
        (STATUS_ACTIVE   ,'Active'),
        (STATUS_DELETED  ,'Deleted'),
    )
    status = models.IntegerField(choices=status_choices, default=STATUS_INACTIVE)

    def get_absolute_url(self):
        return reverse('user-detail', args=[str(self.id)])

    def __unicode__(self):
        return "%s: %s %s" % (self.login, self.forename, self.name)

有几件事:

  1. 尝试编辑某些投票实例时未填充文本区域
  2. 选择列表为空,我认为我的“for”循环很糟糕。
  3. 提交按钮什么都不做...因为 form.is_valid() 返回 0。
  4. 我认为我做错了不使用 Django 用户模型,你怎么看?
  5. 如果您发现任何不良的编码行为,也请告诉我。
  6. 我应该继续使用 Python 2.7 和 Django 1.11 吗?我对 Py2.7 感觉更好,但如果它在未来引起更多问题,我可以改变它。

标签: pythondjangodjango-modelsdjango-formsdjango-templates

解决方案


你不应该做这些。您的大多数问题都是由尝试自己输出表单字段引起的,而不是让 Django 来做。删除所有这些,要么只使用{{ form.as_p }},要么遍历表单字段并输出每个字段:

{{ form.user.label_tag }}
{{ form.user }}
{{ form.user.errors }}

推荐阅读