Django联系表单提交成功但数据未保存至数据库问题排查
问题:Django联系表单提交成功但数据未存入数据库
我正在为兄弟搭建网站,需实现联系表单功能。模板自带联系表单,我基于此自定义了ModelForm。目前表单渲染正常,提交后页面跳转,必填字段校验也能生效,但提交后数据并未保存到数据库,后台管理页面也无法查看。终端显示请求日志为"POST / HTTP/1.1" 200 15649,看似POST请求成功,却无数据存入数据库,请问我遗漏了什么?
相关代码
index.html
<form id="contact" action="" method="post"> {% csrf_token %} {{ form.as_p }} <div class="row"> <div class="col-md-12"> <h2>Contact me</h2> </div> <div class="col-md-6"> <fieldset> <input name="name" type="text" class="form-control" id="name" placeholder="Your name..." required=""> </fieldset> </div> <div class="col-md-6"> <fieldset> <input name="email" type="text" class="form-control" id="email" placeholder="Your email..." required=""> </fieldset> </div> <div class="col-md-12"> <fieldset> <textarea name="message" rows="6" class="form-control" id="message" placeholder="Your message..." required=""></textarea> </fieldset> </div> <div class="col-md-12"> <fieldset> <button type="submit" id="form-submit" class="button">Send Now</button> </fieldset> </div> </div> </form>
forms.py
from django import forms from .models import Contact class ContactForm(forms.ModelForm): class Meta: model = Contact fields = ['name', 'email', 'message']
views.py
from django.shortcuts import render from .forms import ContactForm # Create your views here. def home(request): return render(request, 'rattlesnake/index.html') def contactView(request): if request.method == 'POST': form = ContactForm(request.POST) if form.is_valid(): form.save() else: form = ContactForm() return render(request, 'rattlesnake/index.html', {'form':form})
models.py
from django.db import models class Contact(models.Model): name = models.CharField(max_length=100) email = models.EmailField() message = models.TextField() def __str__(self): return self.name
urls.py
from django.urls import path from . import views urlpatterns = [ path('', views.home, name='home'), path('contact/', views.contactView, name='contact'), ]
问题原因及修复方案
1. 表单提交的目标视图错误
表单action为空,默认提交到当前页面的URL(即/,对应home视图),但处理表单提交的逻辑在contactView视图(对应/contact/)。home视图没有处理POST请求的代码,自然不会保存数据。
修复:
修改表单的action属性,指向处理表单的视图URL:
<form id="contact" action="{% url 'contact' %}" method="post">
2. 模板中重复渲染表单字段
模板同时使用了{{ form.as_p }}(ModelForm自动生成的字段)和手动编写的input/textarea字段,导致表单提交时出现重复字段名,干扰表单验证和数据保存。
修复:
删除手动编写的字段,只保留ModelForm生成的字段,也可以通过自定义表单widget保留样式:
# forms.py 中添加widget定义 class ContactForm(forms.ModelForm): class Meta: model = Contact fields = ['name', 'email', 'message'] widgets = { 'name': forms.TextInput(attrs={'class': 'form-control', 'placeholder': 'Your name...'}), 'email': forms.EmailInput(attrs={'class': 'form-control', 'placeholder': 'Your email...'}), 'message': forms.Textarea(attrs={'class': 'form-control', 'placeholder': 'Your message...', 'rows':6}), }
模板中只保留ModelForm字段:
<form id="contact" action="{% url 'contact' %}" method="post"> {% csrf_token %} <div class="row"> <div class="col-md-12"> <h2>Contact me</h2> </div> <div class="col-md-6"> {{ form.name }} </div> <div class="col-md-6"> {{ form.email }} </div> <div class="col-md-12"> {{ form.message }} </div> <div class="col-md-12"> <fieldset> <button type="submit" id="form-submit" class="button">Send Now</button> </fieldset> </div> </div> </form>
3. 可选优化:防止重复提交
表单提交成功后添加重定向,避免用户刷新页面重复提交:
# views.py 修改contactView from django.shortcuts import render, redirect from .forms import ContactForm def contactView(request): if request.method == 'POST': form = ContactForm(request.POST) if form.is_valid(): form.save() return redirect('home') # 提交成功后重定向到首页 else: form = ContactForm() return render(request, 'rattlesnake/index.html', {'form':form})
内容的提问来源于stack exchange,提问作者indigold
相关产品推荐
相关产品推荐

