Django POST 验证将数字视为字符串



我有点困惑该怎么做,因为我认为这将是 Django 验证的一部分......我使用的是 1.8,因为我使用的是上次使用 1.8 测试的旧数据库连接库(重写旧数据的前端(。

models.py:

class Order(models.Model):
#rest of class#
RequestorNumber = models.SmallIntegerField(db_column='requestor_no')
class Requestor(models.Model):
RequestorNumber = models.SmallIntegerField(primary_key=True, db_column="requester_no")
Requestor = models.CharField(max_length=20, db_column = "requester")
def __str__(self):
return self.Requestor

forms.py

class OrderForm(forms.ModelForm):
RequestorNumber = forms.ModelChoiceField(queryset=Requestor.objects.all().order_by('RequestorNumber'), label="Requestor")

因此,这会在模板中创建一个正确的下拉列表,将值作为整数,文本作为描述,例如:

<option value="1" selected="selected">JOHN DOE</option>

提交表单后,POST QueryDict 在打印整个请求时具有正确的条目:

...
'OrderForm-RequestorNumber': ['1']
...

但这是以字符串形式出现的(正如我所期望的那样(,但是验证器在执行 is_valid(( 时会回击并且网页得到:

"JOHN DOE"值必须是整数。

这是设计使然吗? 我觉得它试图忽略为表单选择的值,并将对象的__str__定义作为需要保存的内容。 如果这是愚蠢的,我也都在想弄清楚什么是更正确的方法,唯一的问题是我无法更改数据库模式,并且所有表在元中都是 managed=False。

编辑:我覆盖了表单中的clean_RequestorNumber,以从字面上输出它认为应该保存的值,并且它给出了方法__str__的值而不是主键。

我需要更改此行为,但我无法确定源代码中正在进行验证的位置。在 models.py、fields.py 和 widgets.py 之间,我可以看到所需的验证、valid_choice验证和其他验证,但我无法发现这是在哪里推动的。 一旦我发现它,我就可以尝试编写自己的类,但我不知道要覆盖什么。

class OrderForm(forms.ModelForm):
def __init__(self, *args, **kwargs):
super(OrderForm, self).__init__(*args, **kwargs)
self.fields['RequestorNumber'].choices = [(x.pk, x.Requestor) for x in Requestor.objects.all()]
RequestorNumber = forms.ChoiceField()

在ModelChoiceField成为一件事之前,以旧的方式执行此操作可以正确验证。 不确定这是否在 1.8 之后修复,但我仍然无法在源中找到会为验证提供不正确行为的位置。 如果有人能指出我正确的方向,我会很高兴,因为我仍然宁愿修复我所在的版本,这样我就可以有一些更干净的代码来处理。 如果有人可以提供帮助,将把它留一个星期,然后把它标记为答案。

最新更新