template onetoonefield onetoone one many foreign examples django

many - onetoonefield django



OneToOneField y eliminaciĆ³n (2)

Dado que el Profile vincula con el User , es el modelo dependiente en la relación. Por lo tanto, cuando elimina un usuario, elimina todos los modelos dependientes. Sin embargo, cuando elimina un perfil, dado que el User no depende del perfil, no se elimina.

Desafortunadamente, según los docs on_delete Django, no hay on_delete regla on_delete que elimine las relaciones con los padres. Para hacerlo, puede sobrescribir el método de delete del Profile :

class Profile(models.Model): # ... def delete(self, *args, **kwargs): self.user.delete() return super(self.__class__, self).delete(*args, **kwargs)

Entonces al hacer:

Profile.objects.get(...).delete()

también eliminará el usuario del perfil. Sin embargo, no se llamará al método de eliminación cuando se eliminen los perfiles utilizando querysets (que es lo que se llama en Django Admin), ya que Django usa SQL DELETE para eliminar objetos de forma masiva:

Profile.objects.filter(...).delete()

En ese caso, según lo recomendado por Django docs , tendrá que usar la señal post_delete ( docs ).

from django.dispatch import receiver from django.db.models.signals import post_delete @receiver(post_delete, sender=Profile) def post_delete_user(sender, instance, *args, **kwargs): if instance.user: # just in case user is not specified instance.user.delete()

Tengo el siguiente modelo:

from django.db import models from django.contrib.auth.models import User class Profile(models.Model): user = models.OneToOneField(User) # ... def __unicode__(self): return u''%s %s'' % (self.user.first_name, self.user.last_name)

Cuando utilizo el administrador de Django para eliminar al usuario, el perfil también se elimina, que es lo que quiero. Sin embargo, cuando se utiliza el administrador de Django para eliminar el perfil, el usuario no se elimina, que no es lo que quiero. ¿Cómo puedo hacer que eliminar el perfil también elimine al usuario?


Use una señal en el método de eliminación del Profile para ir y eliminar el Usuario relacionado:

from django.db.models.signals import post_delete def delete_related_user(sender, **kwargs): deleted_profile = kwargs[''instance''] deleted_profile.user.delete() post_delete.connect(delete_related_user, sender=Profile)