Django更新/创建架构 [英] Django update/create architecture

查看:75
本文介绍了Django更新/创建架构的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我为自己找到了一种创建和更新Django模型的方法.但是我想知道这是否是正确的方法.假设我们有两个模型A和B,其中一个A可以有多个B.

I have worked out a way for myself how to create and update my Django models. But I am wondering if this is the correct way. Let's say we have two models A and B, where one A can have many B's.

这里B有两个用户输入b1,b2,而"b3"定义为:b3 = b1 + b2

Here B has two user inputs b1, b2 and "b3" is defined as: b3 = b1 + b2

这里A也有两个用户输入字段a1,a2和"a3"定义为: a3 = a1 + a2 + b [0] .b3 + b [1] .b3 + ... + b [N] .b3

Here A also has two user input fields a1, a2 and "a3" is defined as: a3 = a1 + a2 + b[0].b3 + b[1].b3 + ... + b[N].b3

这里A取决于零个或多个B.如果B的更改之一,则A将需要重新计算它的a3字段.

Here A depends on the zero or more B's. If one of the B's changes, than A will need to recalculate it's a3 field.

A和B模型因此定义为:

The A and B models are therefore defined as:

class A(models.Model):
    a1      = models.FloatField(default=0)
    a2      = models.FloatField(default=0)
    a3      = models.FloatField(default=0)

    @classmethod
    def create( cls, a1, a2):
        a   = cls(a1  = a1, a2  = a2)
        return a

    def set_a(self, a):
        a.a3 = a.a1 + a.a2

        bs = B.objects.filter(a=a)
        for b in bs:
            a.a3 += b.b3
        a.save()
        return a

class B(models.Model):
    a       = models.ForeignKey('a.A', related_name='bs', on_delete=models.CASCADE)
    b1      = models.FloatField(default=0)
    b2      = models.FloatField(default=0)
    b3      = models.FloatField(default=0)

    @classmethod
    def create( cls, a, b1, b2):
        b   = cls(  a = a, b1  = b1, b2  = b2)
        return b

    def set_b(self, b):
        b.b3 = b.b1 + b.b2
        b.save()
        b.a.set_a(b.a)
        return b

"a"应用的创建和更新视图为:

The create and update views for the "a" app are:

class ACreateView(LoginRequiredMixin, CreateView):
    model = A
    template_name = 'a/create.html'
    form_class = AForm

    def form_valid(self, form):
        a = A.create(   a1      = form.cleaned_data['a1'],
                        a2      = form.cleaned_data['a2'])
        a = a.set_a(a)
        return HttpResponseRedirect(reverse('a:detail', args=(a.id,)))


class AUpdateView(LoginRequiredMixin, UpdateView):
    model = A
    template_name = 'a/detail-update.html'
    form_class = AForm

    def get_object(self):
        return get_object_or_404(A, pk=self.kwargs['pk_a'])

    def form_valid(self, form):
        a = self.get_object()
        a.a1        = form.cleaned_data['a1']
        a.a2        = form.cleaned_data['a2']
        a = a.set_a(a)
        return HttpResponseRedirect(reverse('a:detail', args=(a.id,)))    

现在的问题是这是正确的方法吗?在set_a(a)函数中使用save()命令是否正确?对于这个非常简单的示例来说似乎可行,但是如果模型增加了,那么复杂性就会增加,并且这种方法可能不再可行...

The question is now is this the correct way? Is it correct to have the save() command in the set_a(a) functions? It seems to work for this very simple example but if the models increase so the complexity will increase and this method is perhaps no longer viable...

推荐答案

另一种也许更优雅的方法是将a3和b3定义为属性,而不是将它们存储在数据库中.这样,在需要时立即计算a3和b3. B模型的b1和b2字段中的更新将立即导致a3属性的新更新值.

Another perhaps more elegant way is to define a3 and b3 as properties and not store them in the database. This way a3 and b3 are immediately calculated when needed. An update in the b1 and b2 fields of the B model will immediately result in a new updated value of the a3 property.

当然,缺点是我们无法(轻松地)在数据库中查询a3和b3,因为它们没有存储在数据库中.

Of course the disadvantage is that we cannot (easily) query the database for a3 and b3 since they are not stored in the database.

然后将A模型定义为:

from django.db import models
from b.models import B

class A(models.Model):
    a_name  = models.CharField(max_length=200)
    a1      = models.FloatField(default=0)
    a2      = models.FloatField(default=0)

    @classmethod
    def create( cls, a_name, a1, a2):
        a   = cls(  a_name = a_name, a1  = a1, a2  = a2)
        b1 = B.create(a = a, b_name = "auto_created_b1", b1 = 999, b2=0)
        return a

    @property
    def a3(self):
        a3 = self.a1 + self.a2
        bs = B.objects.filter(a=self)
        for b in bs:
            a3 += b.b3
        return a3

    def get_absolute_url(self):
        return reverse('a:detail', kwargs={'pk_a':self.id })

A模型的更新和创建视图是:

The update and create views for the A model is:

class ACreateView(LoginRequiredMixin, CreateView):
    model = A
    template_name = 'a/create.html'
    form_class = AForm

    def form_valid(self, form):
        a = A.create(   a_name  = form.cleaned_data['a_name'],
                        a1      = form.cleaned_data['a1'],
                        a2      = form.cleaned_data['a2'])
        a.save()
        return HttpResponseRedirect(reverse('a:detail', args=(a.id,)))

class AUpdateView(LoginRequiredMixin, UpdateView):
    model = A
    template_name = 'a/detail-update.html'
    form_class = AForm

    def get_object(self):
        return get_object_or_404(A, pk=self.kwargs['pk_a'])

    def form_valid(self, form):
        a = self.get_object()
        a.a_name    = form.cleaned_data['a_name']
        a.a1        = form.cleaned_data['a1']
        a.a2        = form.cleaned_data['a2']
        a.save()
        return HttpResponseRedirect(reverse('a:detail', args=(a.id,)))    

这篇关于Django更新/创建架构的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆