【发布时间】:2020-04-10 14:37:59
【问题描述】:
我在想出一个好的解决方案来验证其字段设置在其 init 方法中的表单时遇到了一些麻烦。
快速解释我的模型:每个产品都应该有变体,每个变体又具有多个 VariationOptions。
- 每个产品都可以有多个变体,例如“颜色”或“材质”
- 变体可以有多个 VariationOptions (ManyToMany-Relation),例如“red”或“concrete”
在渲染 AddToCartForm 时,每个 Variation 对应一个 ChoiceField,其中 VariationOptions 用作所述 ChoiceField 的选项。 (见forms.py)
由于每个产品都可以有不同的变体,因此也可以有不同的字段,因此必须从包含产品变体 (views.py) 的查询集动态生成 AddToCart 表单,或者至少这是我现在的想法。
我的问题:
- 如何验证这种表单?
- 您有没有更好的方法来实现相同的想法?
非常感谢您的帮助。提前致谢!
这是我的简化代码:
MODELS.PY
class Product(models.Model):
..
class Variation(models.Model):
name = models.CharField()
product = models.ForeignKey(Product, on_delete=models.CASCADE, related_name='variations')
options = models.ManyToManyField(VariationOption, blank=True)
class VariationOption(models.Model):
value = CharField()
FORMS.PY
class AddToCart(forms.Form):
quantity = forms.PositiveIntegerField()
# for every variation get all its choices and add new ChoiceField to form
def __init__(self, variations, *args, **kwargs):
super(AddToCart, self).__init__(*args, **kwargs)
for variation in variations:
CHOICES = []
choices_list = list(variation.options.all())
for choice in choices_list:
CHOICES.append(tuple((choice.value, choice.value)))
self.fields[variation.name] = forms.ChoiceField(choices=CHOICES)
VIEWS.PY
def render_product(request):
...
variations = list(Variation.objects.prefetch_related('options').filter(product=product))
add_to_cart_form = AddToCartForm(variations=variations)
return render(...)
@require_POST
def add_to_cart_view(request):
form = AddToCartForm(request.POST) # This isn't working. I see why, but know no other way.
if form.is_valid():
....
【问题讨论】:
标签: python django django-models django-forms django-views