django formset bug?
碰到了一个郁闷的问题,修改inlineformset时,全部删掉子表,再新增一行时,报错.
背景: 用django配合jq做动态表格,实现用js动态添加/删除行,并通过inlineformset更新到数据库.示例代码在这里:https://github.com/TommyU/dynamic_form/
重现步骤:
1. 新增一个待办事宜,并设置清单,如下:

2. submit
3. 回头修改(通过列表的update按钮进入),把以上数据全部清空(圈起来的),只留下最后一行空白行,提交.

然后报错了,如下
Environment: Request Method: POST
Request URL: http://127.0.0.1:8000/todolist/update/14/ Django Version: 1.6.5
Python Version: 2.7.5
Installed Applications:
('django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'south',
'eForm',
'formset_test')
Installed Middleware:
('django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware',
'django.middleware.locale.LocaleMiddleware') Traceback:
File "C:\Python27\lib\site-packages\django\core\handlers\base.py" in get_response
112. response = wrapped_callback(request, *callback_args, **callback_kwargs)
File "C:\Python27\lib\site-packages\django\views\generic\base.py" in view
69. return self.dispatch(request, *args, **kwargs)
File "C:\Python27\lib\site-packages\django\views\generic\base.py" in dispatch
87. return handler(request, *args, **kwargs)
File "C:\Python27\lib\site-packages\django\views\generic\edit.py" in post
228. return super(BaseUpdateView, self).post(request, *args, **kwargs)
File "C:\Python27\lib\site-packages\django\views\generic\edit.py" in post
171. return self.form_valid(form)
File "E:/workspace/django_test/mysite/mysite\formset_test\views.py" in form_valid
31. if iter_form.is_valid():
File "C:\Python27\lib\site-packages\django\forms\formsets.py" in is_valid
292. err = self.errors
File "C:\Python27\lib\site-packages\django\forms\formsets.py" in errors
267. self.full_clean()
File "C:\Python27\lib\site-packages\django\forms\formsets.py" in full_clean
314. form = self.forms[i]
File "C:\Python27\lib\site-packages\django\utils\functional.py" in __get__
49. res = instance.__dict__[self.func.__name__] = self.func(instance)
File "C:\Python27\lib\site-packages\django\forms\formsets.py" in forms
133. forms = [self._construct_form(i) for i in xrange(self.total_form_count())]
File "C:\Python27\lib\site-packages\django\forms\models.py" in _construct_form
848. form = super(BaseInlineFormSet, self)._construct_form(i, **kwargs)
File "C:\Python27\lib\site-packages\django\forms\models.py" in _construct_form
567. connection=connections[self.get_queryset().db])
File "C:\Python27\lib\site-packages\django\db\models\fields\__init__.py" in get_db_prep_lookup
387. value = self.get_prep_lookup(lookup_type, value)
File "C:\Python27\lib\site-packages\django\db\models\fields\__init__.py" in get_prep_lookup
369. return self.get_prep_value(value)
File "C:\Python27\lib\site-packages\django\db\models\fields\__init__.py" in get_prep_value
613. return int(value) Exception Type: ValueError at /todolist/update/14/
Exception Value: invalid literal for int() with base 10: ''
post数据:

似乎一定要求子表必需有一行数据是原表的?
update对应的python代码如下:
class todo_listUpdateView(UpdateView):
model = todo_list
template_name = 'todo_list_create.html'
success_url = '/todolist/'
form_class = todo_listForm def get_context_data(self, **kwargs):
context = super(todo_listUpdateView, self).get_context_data(**kwargs)
if self.request.POST:
context.update(item_form = todo_itemSet(self.request.POST))
else:
context.update(item_form = todo_itemSet(instance =todo_list.objects.get(pk = self.kwargs.get('pk',False))))
return context def form_valid(self, form):
iter_form = todo_itemSet(self.request.POST,instance=self.object)
if iter_form.is_valid():
self.object = form.save()
iter_form.instance = self.object
iter_form.save()
return HttpResponseRedirect(self.get_success_url())
else:
return self.render_to_response(self.get_context_data())
============================经过调试,分析,看文档===================
发现如果用js直接把数据行给remove掉,如果全部move了,会报错.(原因有待分析).
其实,对于inlineformset的更新操作,django有做一个很不错的设计,直接给标志位打标记即可,什么都不用处理.核心修改如下:
1. 从create模板中分离出update模板(因为js处理不同)
2. 将update模板的deleteForm函数修改为:
function deleteForm(btn, prefix) {
$(".delete_mark",$(btn).parent().parent()).children().attr("checked","checked")
$(btn).parents('.item').hide();
return false;
}
同时update模板添加标志位:
<p class="delete_mark">{{form.DELETE}}</p>
py代码不用修改,就这么简单!(其实django都处理好了,有时间要分析下)
===============备注===================
重现以上bug的方法是将todo_listUpdateView的template_name修改为"todo_list_create.html",如下图所示:

django formset bug?的更多相关文章
- django request bug
bug描述:django请求request接收数据时,如果参数中包含分号时,会导致分号后面的消息丢失. 比如前台js调用代码 $.post('/get_params', { "A" ...
- Django formset
一 什么是formset Form组件或ModelForm用于做一个表单验证而formset是用于做多个表单的验证组件,用于做批量操作 二 formset的使用方法 1 设置form信息 class ...
- Django开发BUG汇总
使用版本知悉 limengjiedeMacBook-Pro:~ limengjie$ python --version Python :: Anaconda, Inc. limengjiedeMacB ...
- Django开发BUG "Model class WH_auth.models.User doesn't declare an explicit app_label and isn't in an application in INSTALLED_APPS."
当进行数据库迁移的时候发生问题,报错如下:RuntimeError: Model class WH_auth.models.User doesn't declare an explicit app_l ...
- python 全栈开发,Day111(客户管理之 编辑权限(二),Django表单集合Formset,ORM之limit_choices_to,构造家族结构)
昨日内容回顾 1. 权限系统的流程? 2. 权限的表有几个? 3. 技术点 中间件 session orm - 去重 - 去空 inclusion_tag filter 有序字典 settings配置 ...
- Django表单集合Formset的高级用法
Formset(表单集)是多个表单的集合.Formset在Web开发中应用很普遍,它可以让用户在同一个页面上提交多张表单,一键添加多个数据,比如一个页面上添加多个用户信息.今天小编我就介绍下Djang ...
- centos 下部署django nginx+uwsgi
为了建立一个工作站,也是麻烦了.... 感谢该博主: https://www.cnblogs.com/levelksk/p/7921066.html 1.安装centos 后首先安装python,下载 ...
- Django组件(三) Django之中间件
中间件概述 中间件顾名思义,是介于request与response处理之间的一道处理过程,相对比较轻量级,并且在全局上改变django的输入与输出.因为改变的是全局,所以需要谨慎实用,用不好会影响到性 ...
- Django【进阶】FBV 和 CBV
django中请求处理方式有2种:FBV 和 CBV 一.FBV FBV(function base views) 就是在视图里使用函数处理请求. 看代码: urls.py 1 2 3 4 5 6 7 ...
随机推荐
- ecshop登录
邮箱登录 a.找到function login(){} ,增加一个邮箱判断is_mail() , b.如果通过,增读取出username , c.再通过默认的login功能 1.需要修改文件incl ...
- php preg_match 过滤字符
$f = preg_match("/g3watches/",$date[0]['desc']); if ($f='1') { $this->error(L('不好意思,输入有 ...
- 数据库操作事务IsolationLevel 枚举
成员名称 说明 Chaos 无法覆盖隔离级别更高的事务中的挂起的更改. ReadCommitted 在正在读取数据时保持共享锁,以避免脏读,但是在事务结束之前可以更改数据,从而导致不可重复 ...
- 性能工具MiniProfiler在Asp.Net WebForm跟踪EntityFramework
http://www.xuebuyuan.com/356638.html 选择MiniProfiler.EF 默认会把MiniProfiler安装上,笔者程序是Asp.Net WebForm 不需要安 ...
- Python之路【第九篇】堡垒机基础&数据库操作
复习paramiko模块 Python的paramiko模块,是基于SSH用于连接远程服务器并执行相关操作. SSHClient #!/usr/bin/env python #-*- coding:u ...
- javascript Date 总结
构造函数 Date 对象的构造函数有以下4种: (1)var variable = new Date(); (2)var variable = new Date(millisenconds); (3) ...
- reactjs 注意点
render的return return前要留一空行 return的括号要分别各占一行,不能与html同行 return中的html必须要有顶层容器包裹 return中的循环不能用for,改用map方 ...
- QT读写ini配置文件
/********下面是写ini文件*************************/ //Qt中使用QSettings类读写ini文件 //QSettings构造函数的第一 ...
- (转载)ecshop制作成手机网站的方法
ecshop用手机访问的时候,会自动跳转到 /mobile 目录下,ecshop自带的wap模板是用wml制作的,如果按这种情况,又需要制作一套模板,太麻烦,现在都是智能手机时代,wml模板已经不能 ...
- thinkphp的url地址区分大小写?
在默认情况下: 在访问url地址的时候, 其中的 Action类名 即: 模块名称 是区分大小写的. (只有模块名, 即控制器名称) 可以根据设置 'URL_CASE_INSENSITIVE' =&g ...