2010-01-19 8 views
3

J'ai un projet Django, qui a un modèle "Adresse". Ceci est utilisé à plusieurs endroits - par un modèle "User Profile", par un modèle "Hospital", par un modèle "Insitution" etc.Django Generic Relations avec Django Admin

J'utilise les relations génériques de Django pour permettre à chacun de ces objets de créer un clé étrangère à adresse. Cependant, cela semble causer de l'étrangeté dans l'Admin Django (ou peut-être que je ne comprends pas comment il est censé être utilisé). Dans l'Admin Django, si j'essaie de créer une adresse, je vois des champs pour "Type de contenu" et "Identifiant d'objet". Le modèle ne sera pas validé/sauvegardé s'il n'est pas rempli. Je ne sais pas quoi y mettre. En fait, je voulais être capable de créer des objets Adresse autonomes. Puis, quand je crée un profil d'utilisateur, ou un hôpital, je pourrais lier ces derniers aux objets d'adresse, y compris la possibilité de plusieurs liens au même objet d'adresse.

Comment utiliser l'administrateur Django avec des relations génériques?

Aussi, j'ai également l'intention d'utiliser django-reversion pour le contrôle de la version des modèles, pas sûr si cela va causer des problèmes avec les relations génériques et l'administrateur?

Cheers, Victor

Edit: Je devrais ajouter, voici une question précédente que j'ai posté adresses et Inlines:

Django - Designing Model Relationships - Admin interface and Inline

Sur la base des réponses données là, c'est la raison pour laquelle le modèle d'adresse est celui avec une clé étrangère. Et comme un champ FK normal ne peut pointer que vers un type d'objet, c'est pourquoi nous utilisons des relations génériques. Chaque utilisateur, département, hôpital, etc. peut (et dans la plupart des cas) avoir plusieurs adresses.

La même adresse peut être utilisée par plusieurs entités, mais c'est plus rare, et la duplication est bonne ici, je suppose, non?

Donc, ce serait un un-à-plusieurs de l'utilisateur/département/hôpital aux adresses.

Dans cette question originale, ils ont également suggéré d'utiliser des classes abstraites et un modèle d'adresse différent pour chaque entité qui avait besoin d'une adresse. Je ne sais toujours pas si c'est la meilleure approche, ou s'il y a un moyen de faire fonctionner GenericRelations avec ce que j'essaie de faire ici.

Répondre

3

L'utilisation de relations génériques dans django est exactement cela. Un ForeignKey ContentType (type_contenu) et un IntegerField pour désigner l'ID d'instance (object_id). Ils sont utiles si vous ne savez pas quel type de contenu pointe vers ForeignKey. Puisque vous savez que vous ciblez le modèle Address, vous souhaitez utiliser le code ForeignKey(Address) au lieu des relations génériques.

En réponse à votre commentaire

En fait, il est beaucoup plus facile à utiliser ForeignKey puisque vous n'avez pas besoin de passer par ContentType.

class Address(models.Model): 
    street=models.CharField(max_length=100) 
    city=models.CharField(max_length=100) 


class Hospital(models.Model): 
    name=models.CharField(max_length=100) 
    created=models.DateTimeField() 
    address=models.ForeignKey(Address, related_name="hospitals") 

class Institution(models.Model): 
    name=models.CharField(max_length=100) 
    address=models.ForeignKey(Address, related_name="institutions") 


>>> instance=Institution.objects.get(id=1) 
>>> instance.address.city 
>>> address=Address.objects.get(id=1) 
>>> address.institutions.all() 
>>> address.hospitals.all() 

Vos modèles vont-ils partager des adresses? c'est à dire.Est-ce qu'un Hospital et un Institution et peut-être un UserProfile tous pointent vers la même instance d'adresse? Ou est-il plus probable que chacun aura sa propre adresse? J'essaie de comprendre pourquoi vous avez créé une classe distincte Address. Si c'est pour éviter de retaper les mêmes champs dans chaque classe, vous pouvez utiliser une classe de modèle abstrait et la sous-classer. Ou vous pourriez avoir besoin d'un OneToOneField qui est un pointeur bidirectionnel entre les deux instances.

+0

heya, Hmm, je pensais que du point de vue de la conception, vous mettriez le champ FK sur l'objet Adresse, et avoir ce lien vers chacun des les choses qui ont besoin d'une adresse (utilisateur, hôpital, institution, etc.). Cependant, puisque vous devez spécifier un type pour cela, c'est pourquoi j'ai utilisé Generic Relations. Cependant, si je mets le champ FK sur l'autre objet, cela ne brise-t-il pas la conception, ou bizarre l'ORM? Cheers, Victor – victorhooi

+0

@victorhool je pense que @czarchaic a raison, pour votre description la meilleure approche de la situation est un 'models.ForeignKey (adresse), ne casse pas la conception ni bizarre jusqu'à l'ORM, de toute façon si vous persistez en usage une relation générique, lisez le doc dans http://docs.djangoproject.com/fr/1.1/ref/contrib/contenttypes/#generic-relations-in-forms-and-admin – diegueus9

+0

Où vous mettez le FK dépend de de quel côté est le "plusieurs". Un utilisateur/hôpital/institution peut-il avoir plusieurs adresses? Ensuite, le FK devrait être sur l'adresse, pointant vers l'utilisateur/hôpital/institution. Mais si une seule adresse peut appartenir à plusieurs autres choses, alors vous voulez que le FK sur "l'autre chose" pointant vers l'adresse. –