Django: Bir güncellemeyi birden çok model üzerinden nasıl basamaklandırabilirim?

0

Soru

Nesneleri (Objekt) ve bakım görevlerini takip etmek için Django tabanlı bir uygulama yazıyorum. Nesneler bir konuma bağlanabilir.

Konum (0/1) --- (n) Nesne (1) --- (n) Görev

Konum, Nesne ve Görevin tümü aşağıdaki değerlere sahip bir durum alanına sahiptir:

    RED = "red"
    YELLOW = "yellow"
    GREEN = "green"
    STATUS = [
        (RED, "Overdue tasks"),
        (YELLOW, "Pending tasks"),
        (GREEN, "All good"),
    ]

Konum haritası işaretleyicisinin, ilgili Nesnelerin ve ültimatom Görevlerinin durumuna bağlı olarak rengini değiştirmesini istiyorum.

Django'nun en iyi uygulamalarını takip etmeye ve bir fat modeli oluşturmaya çalıştım.

from django.db import models
from locationapp.models import Location
from taskapp.models import Task
from rules.contrib.models import RulesModel

class Objekt(RulesModel):
    RED = "red"
    YELLOW = "yellow"
    GREEN = "green"
    STATUS = [
        (RED, "Overdue tasks"),
        (YELLOW, "Pending tasks"),
        (GREEN, "All good"),
    ]
    name = models.CharField(max_length=200)
    description = models.TextField(blank=True)
    location = models.ForeignKey(
        Location, on_delete=models.SET_NULL, null=True, blank=True
    )
    status = models.CharField(max_length=6, choices=STATUS, default=GREEN)

    def set_status(self):
        if Task.objects.filter(objekt=self.id).filter(status=Task.RED).exists():
            self.status = Objekt.RED
        elif Task.objects.filter(objekt=self.id).filter(status=Task.YELLOW).exists():
            self.status = Objekt.YELLOW
        else:
            self.status = Objekt.GREEN

Ama bir şekilde buradaki konseptimden emin değilim... Görevdeki bir güncelleştirme, ilgili Nesnedeki bir güncelleştirmeyi nasıl tetikleyebilir? Ve Nesne, gerektiğinde Konum güncellemesini nasıl daha da tetikleyecektir?

django model python
2021-11-22 21:49:18
1

En iyi cevabı

1

Potansiyel bir çözüm sinyalleri kullanmaktır. Şimdilik kereviz olmadan aşağıdaki gibi uyguladım:

# objektapp/apps.py
from django.apps import AppConfig


class ObjektappConfig(AppConfig):
    default_auto_field = 'django.db.models.BigAutoField'
    name = 'objektapp'

    def ready(self):
        import objektapp.signals
# objektapp/signals.py
from django.db.models.signals import post_save
from django.dispatch import receiver
from django.db import transaction
from taskapp.models import Task
from objektapp.models import Objekt

@receiver(post_save, sender=Task)
def set_status(sender, instance, created, **kwargs):
    # TODO: Use celery for async operation: https://docs.djangoproject.com/en/3.2/topics/db/transactions/
    transaction.on_commit(lambda: objekt_update_status(instance))

def objekt_update_status(task_instance):
    objekt = Objekt.objects.get(id=task_instance.objekt.id)

    new_objekt_status = Objekt.GREEN
    if Task.objects.filter(objekt=task_instance.objekt.id, status=Task.RED).exists():
        new_objekt_status = Objekt.RED
    elif Task.objects.filter(objekt=task_instance.objekt.id, status=Task.YELLOW).exists():
        new_objekt_status = Objekt.YELLOW

    if objekt.status != new_objekt_status:
        objekt.status = new_objekt_status
        objekt.save()

Nesneden gelen bir post_save sinyaline de tepki veren Konum modelinde yaptığım benzer bir kurulum. objekt_update_status() işlevini depolamak için en iyi yer olup olmadığından emin değilim signals.py dosya, ama içine koymaya çalışıyorum models.py döngüsel içe aktarma hatasıyla sonuçlandı.

2021-11-24 11:19:32

Diğer dillerde

Bu sayfa diğer dillerde

Русский
..................................................................................................................
Italiano
..................................................................................................................
Polski
..................................................................................................................
Română
..................................................................................................................
한국어
..................................................................................................................
हिन्दी
..................................................................................................................
Français
..................................................................................................................
Česk
..................................................................................................................
Português
..................................................................................................................
ไทย
..................................................................................................................
中文
..................................................................................................................
Español
..................................................................................................................
Slovenský
..................................................................................................................