user4981459
user4981459

Reputation:

Django reverse foreign key values aggregate

I have two models,

class UploadedMedia(models.Model):
    owner = models.ForeignKey(Account, on_delete=models.CASCADE)
    media_url = models.URLField(blank=True, null=True)
    created_at = models.DateTimeField(auto_now_add=True)
    updated_at = models.DateTimeField(auto_now=True)

class Account(AbstractBaseUser, PermissionsMixin):
    email = models.EmailField(
        blank=False,
        unique=True,
        db_index=True,
        max_length=255,
        help_text="Designates the email address and user name of the account.",
    )

    name = models.CharField(
        blank=True,
        unique=False,
        db_index=False,
        max_length=255,
        help_text="Designates the full name of the account.",
    )

I need to show max(created_at) for each record in Account model. Since it is a reverse foreign key I don't understand how can I achieve it. Please advise.

Upvotes: 0

Views: 939

Answers (1)

Abdul Aziz Barkat
Abdul Aziz Barkat

Reputation: 21797

One can access reverse relations by using the model name in lower case with _set appended so in your case you can write uploadedmedia_set to refer to the UploadedMedia of an Account.

from django.db.models import Max

result = Account.objects.annotate(max_created_at=Max('uploadedmedia_set__created_at'))

You can also set what name you want to use instead of this default by providing a related_name [Django docs] on your Foreign Key.

class UploadedMedia(models.Model):
    owner = models.ForeignKey(Account, on_delete=models.CASCADE, related_name='uploaded_media')
    ...

Now you can write:

result = Account.objects.annotate(max_created_at=Max('uploaded_media__created_at'))

Now you can simply access this annotated result by writing something like account.max_created_at (account is an instance of Account from the queryset result).

Upvotes: 1

Related Questions