Django Form,从表单中计算新值并将其分配给模型

时间:2012-03-14 13:17:02

标签: django django-forms

我是Django和整个网络开发概念的新手。我只学过Java和C ++,但是我在大学做网络开发工作。我目前正在尝试实现一个表单 - (http://albedo.csrcdev.com/pages/submit)。在我的模型中,我还有一个字段没有显示在我的表单上,称为Albedo。 Albedo应该由sum(outgoing1,outgoing2,outgoing3)/ sum(incoming1,incoming2,incoming3)计算。所以我的问题是,我如何以及从何处从数据库中获取这些变量,并将新的计算值分配给Albedo。

我的同事告诉我将ModelForm用于我的表单,并尝试在views.py中进行操作,但现在我坐在这里卡住了,一无所有,他只是去度假了! :(

提前致谢,

大卫

views.py

@login_requried
def submit( request ):
if request.method =='POST':
     form = DataEntryForm( request.POST )
     model = DataEntry( )
     if form.is_valid():
        form.save()
        return HttpResponseRedirect('/map/rebuild/')                                            


else:                                                                                           
    form = DataEntryForm( )                                                                        

return render_to_response(
      'pages/submit.html', { 'form': form },
      context_instance=RequestContext(request) )

3 个答案:

答案 0 :(得分:4)

form = DataEntryForm(request.POST)
if form.is_valid():
    instance = form.save(commit=False)
    instance.albedo = do_calc(instance.whatever0, instance.whatever1)
    instance.save()
    return HttpResponseRedirect('/map/rebuild/')

请注意,您无需手动实例化model = DataEntry() - 如果DataEntryFormModelForm子类,则会在您调用.save()时创建模型。< / p>

将计算封装在DataEntry.update_albedo()方法或其他东西中可能是个好主意。您可以在instance.save()之前调用它,而不是在视图中进行计算。

答案 1 :(得分:3)

我会从save的{​​{1}}方法中分配此值。

假设ModelForm也是模型中的字段名称:

albedo

此外,如果Class MyModelForm(forms.ModelForm): class Meta: model = MyModel exclude = ('albedo') def calculate_albedo(outgoing1, outgoing2, outgoing3, incoming1, incoming2, incoming3): return sum([outgoing1, outgoing2, outgoing3]) / sum([incoming1, incoming2, incoming3]) def save(self, commit=True): form_data = self.cleaned_data self.instance.someval1 = form_data['someval1'] self.instance.someval2 = form_data['someval2'] self.instance.someval3 = form_data['someval3'] self.instance.albedo = self.calculate_albedo( form_data['outoing1'], form_data['outoing2'], form_data['outoing3'], form_data['incoming1'], form_data['incoming2'], form_data['incoming3']) return super(MyModelForm, self).save(commit) 不是类名,则应使用小写。这是Pythonic convention

答案 2 :(得分:0)

可能的解决方案是更新presave signal中的字段。采用这种方法:

  • 您的反照率字段会在保存模型之前更新。
  • 请记住,您可以执行save no commit save(commit=False)。这将更新您的字段而不对数据库进行提交更改。

我发布了一份来自django signals doc的示例:

from django.db.models.signals import pre_save
from django.dispatch import receiver
from myapp.models import MyModel

@receiver(pre_save, sender=MyModel)
def my_handler(sender, **kwargs):
    sender.Albedo = sender.outgoing1 + ...