ContentType Issue - Human é um idiota - não consigo descobrir como amarrar o modelo original a um modelo 'favorito' abstraído contenttype
-
27-09-2019 - |
Pergunta
Originalmente começou aqui: Django em consulta como resultado de string - literal inválido para int () com base 10
Eu tenho vários aplicativos no meu site, atualmente trabalhando com um aplicativo simples de "blog". Eu desenvolvi um aplicativo 'favorito', com bastante facilidade, que aproveita a estrutura do ContentType em Django para me permitir ter um 'favorito' de qualquer tipo ... tentando seguir o outro lado, no entanto, não sei o que eu Estou fazendo, e não consigo encontrar nenhum exemplo.
Vou começar com o modelo favorito:
favorito/models.py
from django.db import models
from django.contrib.contenttypes.models import ContentType
from django.contrib.contenttypes import generic
from django.contrib.auth.models import User
class Favorite(models.Model):
content_type = models.ForeignKey(ContentType)
object_id = models.PositiveIntegerField()
user = models.ForeignKey(User)
content_object = generic.GenericForeignKey()
class Admin:
list_display = ('key', 'id', 'user')
class Meta:
unique_together = ("content_type", "object_id", "user")
Agora, isso me permite percorrer os favoritos (na página "Favoritos" de um usuário, por exemplo) e obtenha os objetos de blog associados via {{Favorite.content_object.title}}.
O que eu quero agora e não consigo descobrir é o que eu preciso fazer com o modelo do blog para me permitir ter um pouco de amarração ao favorito (então, quando é exibido em uma lista, pode ser destacado, por exemplo).
Aqui está o modelo do blog:
blog/models.py
from django.db import models
from django.db.models import permalink
from django.template.defaultfilters import slugify
from category.models import Category
from section.models import Section
from favorite.models import Favorite
from django.contrib.auth.models import User
from django.contrib.contenttypes.models import ContentType
from django.contrib.contenttypes import generic
class Blog(models.Model):
title = models.CharField(max_length=200, unique=True)
slug = models.SlugField(max_length=140, editable=False)
author = models.ForeignKey(User)
homepage = models.URLField()
feed = models.URLField()
description = models.TextField()
page_views = models.IntegerField(null=True, blank=True, default=0 )
created_on = models.DateTimeField(auto_now_add = True)
updated_on = models.DateTimeField(auto_now = True)
def __unicode__(self):
return self.title
@models.permalink
def get_absolute_url(self):
return ('blog.views.show', [str(self.slug)])
def save(self, *args, **kwargs):
if not self.slug:
slug = slugify(self.title)
duplicate_count = Blog.objects.filter(slug__startswith = slug).count()
if duplicate_count:
slug = slug + str(duplicate_count)
self.slug = slug
super(Blog, self).save(*args, **kwargs)
class Entry(models.Model):
blog = models.ForeignKey('Blog')
title = models.CharField(max_length=200)
slug = models.SlugField(max_length=140, editable=False)
description = models.TextField()
url = models.URLField(unique=True)
image = models.URLField(blank=True, null=True)
created_on = models.DateTimeField(auto_now_add = True)
def __unicode__(self):
return self.title
def save(self, *args, **kwargs):
if not self.slug:
slug = slugify(self.title)
duplicate_count = Entry.objects.filter(slug__startswith = slug).count()
if duplicate_count:
slug = slug + str(duplicate_count)
self.slug = slug
super(Entry, self).save(*args, **kwargs)
class Meta:
verbose_name = "Entry"
verbose_name_plural = "Entries"
Alguma orientação?
Solução
O documento do django está aqui: Relações genéricas reversas. Basicamente, no próprio modelo do blog, você pode adicionar um GenericRelation
...
class Blog(models.Model):
favorites = generic.GenericRelation(Favorite)
Para um determinado blog, você pode encontrar todos os Favorite
modelos que estão associados a isso ...
b = Blog.objects.get(slug='hello-world-blog-slug')
all_blog_favorites = b.favorites.objects.all()
Ou veja se o usuário atual tem o blog favorito ...
user_has_blog_favorited = b.favorites.objects.filter(user=request.user).exists()