使用Django从数据库中预填充HTML表单表 [英] Pre-populate HTML form table from database using Django
问题描述
我有一个基于类的视图(在 views.py 中为 IndexView ),该视图显示了一个表,其中包含所有存储在数据库中的数据.
使用def get_queryset(self)
在 index.html 中呈现此视图以获取所有数据.还没有问题.
I have a class-based view (IndexView at views.py) that shows a table with all the data stored in the database.
This view is rendered in index.html using a def get_queryset(self)
to obtain all the data. No issues yet.
对我来说,困难的部分是尝试使用表单来进行操作,以便能够修改和保存金额列. 我在使用AJAX保存新值的POST部分没有任何问题. 我遇到问题的地方是从数据库获取初始值以填充Django表单( forms.py )
The difficult part for me is trying to do it using a form, to be able to modify and save the amount column. I have no issues with the POST part, where I use AJAX to save the new values. Where I'm having issues is getting the initial values from the database to populate a Django Form (forms.py)
我尝试在表单字段的定义中使用initial
参数(在 forms.py 处),甚至在表单定义中覆盖__init__
,但但我不知道如何获得一个价值" .我的意思是,我在测试中越靠近的地方在 MultipleChoiceField 中填充了:
forms.ModelMultipleChoiceField(queryset=Item.objects.order_by('code__name'))
(获得Item object (1), Item object (2), etc.
的多选字段)
I tried using initial
argument in the definition of the form fields (at forms.py), even overriding __init__
at the form definition, but I don't know how to get "one value". I mean, the closer I've been in my tests was populating a MultipleChoiceField with:
forms.ModelMultipleChoiceField(queryset=Item.objects.order_by('code__name'))
(achieving a multiple choice field of Item object (1), Item object (2), etc.
)
但是如何用数据库的内容填充单个 IntegerField 或 CharField ,以在模板中显示基于表单的表字段?
But how do you populate a single IntegerField or CharField with the content of the database to show a form-based table field in the template?
在处理整个表之前,我首先尝试使用单个项目(以试图理解如何引用一个项目/值来使用数据库填充它们):
I'm trying first with a single item (to try to understand how to reference one item/value to populate them using the database) before doing it with the whole table:
index.hml:
...
<form class='my-ajax-form' method='POST' action='.' data-url='{{ request.build_absolute_uri|safe }}'>
{% csrf_token %}
{{form.as_table|safe}}
<button type='submit'>Save changes</button>
</form>
...
models.py :
class Code(models.Model):
name = models.CharField(max_length=6)
description = models.CharField(max_length=100)
def __str__(self):
return self.name
class Item(models.Model):
code = models.ForeignKey(Code, on_delete=models.DO_NOTHING)
amount = models.IntegerField(default=0)
forms.py:
class ItemForm(forms.Form):
code = forms.CharField(max_length=6)
description = forms.CharField(max_length=100)
amount = forms.IntegerField()
views.py:
class IndexView(generic.ListView, AjaxFormMixin, FormView):
template_name = 'inventory/index.html'
context_object_name = 'items_list'
form_class = ItemForm
def form_invalid(self, form):
...
def form_valid(self, form):
...
def get_queryset(self):
...
我检查了这些文档&一些类似的旧问题,但我尝试了一些建议/示例,但均未成功:
I checked these docs & some similar old issues, but I tried some of the suggestions/examples with no success:
- https://docs.djangoproject. com/en/2.0/topics/forms/modelforms/#a-full-example
- https://www.webforefront.com/django/formprocessing.html
- 预填充Django表单
- 用数据库中的数据填充django表单在视野中
- https://docs.djangoproject.com/en/2.0/topics/forms/modelforms/#a-full-example
- https://www.webforefront.com/django/formprocessing.html
- Pre-populating Django Forms
- Populate a django form with data from database in view
我正在使用Django 2.0.2
I'm using Django 2.0.2
任何帮助将不胜感激. 预先感谢.
Any help would be appreciated. Thanks in advance.
尝试使用Andi建议的UpdateView进行操作.已添加(尝试通过ID获得一个值):
Trying to do something using UpdateView as andi suggests. Added (trying to get one value by id):
class ItemUpdate(UpdateView):
form_class = JoinForm
def get_object(self,queryset=None):
obj = Item.objects.get(id=self.kwargs['2'])
return obj
并指向path('', views.ItemUpdate.as_view(), name='index')
的网址,但始终获取KeyError: '2'
And pointed url to path('', views.ItemUpdate.as_view(), name='index')
but always get KeyError: '2'
推荐答案
直接在模型上使用通用from django.views.generic.edit import UpdateView
是什么?
what about using generic from django.views.generic.edit import UpdateView
straight on model?
https://docs. djangoproject.com/en/2.0/ref/class-based-views/generic-editing/#updateview
views.py:
from django.forms import ModelForm, CharField, Textarea
from django.urls import reverse_lazy
from django.views.generic import UpdateView
from demo.models import Item
class ItemForm(ModelForm):
description = CharField(widget=Textarea)
class Meta:
model = Item
fields = ['code', 'amount']
def save(self, commit=True):
item = super(ItemForm, self).save(commit=commit)
item.code.description = self.cleaned_data['description']
item.code.save()
def get_initial_for_field(self, field, field_name):
if field_name == 'description':
return self.instance.code.description
else:
return super(ItemForm, self).get_initial_for_field(field, field_name)
class ItemUpdateView(UpdateView):
form_class = ItemForm
model = Item
def get_success_url(self):
return reverse_lazy('item-detail', kwargs={'pk': 1})
urls.py
from django.conf.urls import url
from django.contrib import admin
from django.urls import path
from demo.views import ItemUpdateView
urlpatterns = [
url(r'^admin/', admin.site.urls),
path(r'items/<int:pk>/', ItemUpdateView.as_view(), name='item-detail')
]
/templates/demo/item_form.html
/templates/demo/item_form.html
<form action="" method="post">{% csrf_token %}
{{ form.as_p }}
<input type="submit" value="Update" />
</form>
如果不清楚有关设置或配置的某些信息,请参阅带有示例的回购: https://github.com /andilabs/cbv
If something regarding settings or config is unclear please refer to the repo with demo: https://github.com/andilabs/cbv
添加了modelformset,可在ListView中生成所需的内容
added modelformset producing what you need in ListView
from django.forms import modelformset_factory
class ItemListView(ListView):
model = Item
def get_context_data(self, **kwargs):
data = super(ItemListView, self).get_context_data()
formset = modelformset_factory(Item, form=ItemForm)()
data['formset'] = formset
return data
这仅以表格形式显示数据,请您多做休息.
this just displays data in forms, you have take care of rest.
这篇关于使用Django从数据库中预填充HTML表单表的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!