Tengo un modelo de artículo bastante genérico, con relación m2m al modelo Tag. Quiero contar el uso de cada etiqueta, creo que la mejor manera sería desnormalizar el campo de conteo en el modelo de etiqueta y actualizarlo cada vez que se guarde el artículo. ¿Cómo puedo lograr esto, o tal vez hay una mejor manera?señal post_save en el campo m2m
Respuesta
Usted puede hacer esto mediante la creación de un intermediate model para la relación M2M y utilizarlo como su gancho para las señales post_save
y post_delete
para actualizar la columna desnormalizaremos en la tabla Article
.
Por ejemplo, hago esto por Favorecido Question
cuenta en soclone, donde User
s tienen una relación M2M con Question
s:
from django.contrib.auth.models import User
from django.db import connection, models, transaction
from django.db.models.signals import post_delete, post_save
class Question(models.Model):
# ...
favourite_count = models.PositiveIntegerField(default=0)
class FavouriteQuestion(models.Model):
question = models.ForeignKey(Question)
user = models.ForeignKey(User)
def update_question_favourite_count(instance, **kwargs):
"""
Updates the favourite count for the Question related to the given
FavouriteQuestion.
"""
if kwargs.get('raw', False):
return
cursor = connection.cursor()
cursor.execute(
'UPDATE soclone_question SET favourite_count = ('
'SELECT COUNT(*) from soclone_favouritequestion '
'WHERE soclone_favouritequestion.question_id = soclone_question.id'
') '
'WHERE id = %s', [instance.question_id])
transaction.commit_unless_managed()
post_save.connect(update_question_favourite_count, sender=FavouriteQuestion)
post_delete.connect(update_question_favourite_count, sender=FavouriteQuestion)
# Very, very naughty
User.add_to_class('favourite_questions',
models.ManyToManyField(Question, through=FavouriteQuestion,
related_name='favourited_by'))
Ha habido un poco de discusión sobre los django-desarrolladores lista de correo sobre la implementación un medio de denormalisations declarativa declaran para evitar tener que escribir el código como el de arriba:
Ésta es una nueva característica de Django 1.2: http://docs.djangoproject.com/en/dev/ref/signals/#m2m-changed
Sin embargo, ten cuidado con la señal m2m_changed porque no hay forma de saber qué ha cambiado exactamente dentro del controlador. –
¿No envía un argumento de acción? –
Básicamente, sabes cuál es el estado actual, pero no tienes forma de saber cuál era el estado antes de enviar la señal. Sin embargo, en el caso dado por la pregunta original, solo necesita saber la cantidad de archivos adjuntos, por lo que está bien. –
- 1. Django - ¿Cómo guardar datos m2m a través de la señal post_save?
- 2. Django señal post_save envía formsets línea obsoletas
- 3. Cómo pasar kwargs de guardar a la señal de post_save
- 4. ¿Cómo evito que los dispositivos entren en conflicto con el código de señal de django post_save?
- 5. Django: ¿cómo puedo saber si la señal post_save se activa en un nuevo objeto?
- 6. ¿Es posible suprimir selectivamente una señal post_save (u otra) en Django?
- 7. Django: Cómo acceder Instancia original (sin modificar), en señal de post_save
- 8. Django post_save señales en la actualización
- 9. Django: no se pueden detectar cambios en campo muchos a muchos con señal m2m_changed - auditoría en el modelo
- 10. Python factory_boy library m2m en el modelo Django?
- 11. Pedido predeterminado para elementos m2m por campo modelo intermedio en Django
- 12. señal Django m2m_changed no activado
- 13. Acceso a datos relacionados de la instancia del modelo recién creado usando el manejador de señal post_save
- 14. ¿Por qué Django post_save signal me da datos pre_save?
- 15. Cómo obtener la sesión del controlador de señal en Django
- 16. post_save en django para actualizar la instancia inmediatamente
- 17. Transformaciones bidireccionales de M2M con Eclipse EMF
- 18. Django: suprimir todas las relaciones M2M
- 19. ¿Cómo guardar un modelo sin enviar una señal?
- 20. ¿Por qué se sube post_save dos veces durante el guardado de un modelo de Django?
- 21. "¿A la señal" @ en el objeto SimpleXML?
- 22. Vistas basadas en clases para la relación M2M con el modelo intermedio
- 23. Django: ¿señal cuando el usuario inicia sesión?
- 24. campo Sharepoint LookUp en el campo Elección?
- 25. Haxe en el campo
- 26. Obtener la señal de inicio de sesión del usuario actual en Django
- 27. ¿Cómo puedo hacer que una señal de Django llame a un método modelo?
- 28. señal de iPhone fuerza
- 29. Enviar señal al proceso
- 30. Señal de captura en el proceso de fondo secundario
Hay una Gotcha con esta técnica sin embargo: si desea utilizar estas clases en una forma, form.save_m2m ya no funcionará – Rob