Django Usecase模型单独更新delivery_date触发日期格式错误
问题描述
我有一个Usecase模型,尝试更新其中字段时遇到问题:模型包含delivery_date(交付日期)和estimated_date(预计交付日期)两个DateField字段,单独更新delivery_date时无法成功,只有同时更新estimated_date才能正常保存,否则会报错:
['“” value has an invalid date format. It must be in YYYY-MM-DD format.']
模型代码
class Usecase(models.Model): usecase_id = models.CharField(primary_key=True, max_length=20) usecase_name = models.CharField(max_length=256) user_email = models.ForeignKey('User', models.DO_NOTHING, db_column='user_email') usecase_type = models.ForeignKey('UsecaseType', models.DO_NOTHING) kpi = models.ForeignKey(Kpi, models.DO_NOTHING) usecase_description = models.CharField(max_length=5000) estimated_date = models.DateField() delivery_date = models.DateField()
视图代码
def edit_usecase(request, ucid): try: usecase_details = Usecase.objects.filter(usecase_id=ucid) context = {"usecase_details":usecase_details[0], "usecase_types": UsecaseType.objects.all(), "usecase_kpis": Kpi.objects.all()} if request.method == "POST": usecase_type = request.POST['usecase_type'] kpi = request.POST['kpi'] estimated_date = request.POST['estimated_date'] delivery_date = request.POST['delivery_date'] usecase_details = Usecase.objects.get(usecase_id=ucid) usecase_details.usecase_type_id=usecase_type usecase_details.kpi_id=kpi usecase_details.estimated_date=estimated_date usecase_details.delivery_date=delivery_date usecase_details.save() if usecase_details: messages.success(request, "Usecase Data was updated successfully!") return HttpResponseRedirect(reverse('usecase-details', args=[ucid])) else: messages.error(request, "Some Error was occurred!") return HttpResponseRedirect(reverse('update-usecase', args=[ucid])) return render(request, 'UpdateUsecase.html', context) except Exception as e: print(e) messages.error(request, "Some Error was occurred!") return HttpResponseRedirect(reverse('update-usecase', args=[ucid]))
模板代码
<form action="/update-usecase/{{usecase_details.usecase_id}}" method="POST"> {% csrf_token %} <div class="form-row mb-4"> <div class="col-lg-8 mr-f"> <label class="h6" for="project-name">Usecase Type:</label> <select name="usecase_type" class="custom-select my-1 mr-sm-2" id="usecase_type"> {% for usecase_type in usecase_types %} <option value="{{ usecase_type.usecase_type_id }}" {% if usecase_details.usecase_type.usecase_type_id == usecase_type.usecase_type_id %}selected{% endif %}>{{ usecase_type.usecase_type_name }}</option> {% endfor %} </select> </div> <div class="col-lg-8 mr-f"> <label class="h6" for="project-name">Usecase KPI:</label> <select name="kpi" class="custom-select my-1 mr-sm-2" id="kpi"> {% for kpi in usecase_kpis %} <option value="{{ kpi.kpi_id }}" {% if usecase_details.kpi.kpi_id == kpi.kpi_id %}selected{% endif %}>{{ kpi.kpi_name }}</option> {% endfor %} </select> </div> </div> <div class="form-row mb-4"> <div class="col-lg-8 mr-f"> <label class="h6" for="project-name">Estimated Delivery Date:</label> <input type="date" id="estimated_date" name="estimated_date" class="form-control" id="estimated_date" value="{{usecase_details.estimated_date}}"> </div> <div class="col-lg-8 mr-f"> <label class="h6" for="project-name">Delivery Date:</label> <input type="date" id="delivery_date" name="delivery_date" class="form-control" id="delivery_date" value=""> </div> </div> <input type="submit" class="btn btn-primary" value="Submit Changes"> </form>
问题原因及解决方法
原因分析
- 模板初始值为空:
delivery_date输入框的value被设为空字符串,用户不修改直接提交时,前端会传空值给后端,但模型中该字段是必填DateField,空字符串无法转换为合法日期,触发格式错误。 - 视图无条件覆盖字段:不管前端传的日期值是否为空,视图都直接赋值给模型字段,没有做判断。同时更新
estimated_date时,用户通常会填写有效日期,模型验证通过;单独更新时,delivery_date的空值直接触发验证失败。
解决步骤
1. 修复模板初始值
把delivery_date输入框的value改为模型已有值,用户不修改时提交原有日期而非空值:
<input type="date" id="delivery_date" name="delivery_date" class="form-control" value="{{usecase_details.delivery_date}}">
(注:原模板中该输入框重复写了两次id="delivery_date",建议删除其中一个,避免DOM元素ID冲突)
2. 视图增加空值判断
如果允许用户清空日期后提交,在视图中判断值是否为空,空值时不覆盖原有字段:
def edit_usecase(request, ucid): try: usecase_details = Usecase.objects.filter(usecase_id=ucid)[0] context = {"usecase_details":usecase_details, "usecase_types": UsecaseType.objects.all(), "usecase_kpis": Kpi.objects.all()} if request.method == "POST": usecase_details.usecase_type_id = request.POST['usecase_type'] usecase_details.kpi_id = request.POST['kpi'] # 仅当值不为空时更新日期字段 estimated_date = request.POST.get('estimated_date') if estimated_date: usecase_details.estimated_date = estimated_date delivery_date = request.POST.get('delivery_date') if delivery_date: usecase_details.delivery_date = delivery_date usecase_details.save() messages.success(request, "用例数据更新成功!") return HttpResponseRedirect(reverse('usecase-details', args=[ucid])) return render(request, 'UpdateUsecase.html', context) except Exception as e: print(e) messages.error(request, "更新失败,请检查输入格式!") return HttpResponseRedirect(reverse('update-usecase', args=[ucid]))
3. 可选:模型字段允许为空(按需)
如果业务允许delivery_date为空,可修改模型字段:
delivery_date = models.DateField(null=True, blank=True)
内容的提问来源于stack exchange,提问作者JHS99
相关产品推荐
相关产品推荐

