Django-fr

Forum

#1 19-04-2012 11:52:54

torrak
Membre
Inscription : 31-08-2011
Messages : 47

Content Type et generic foreign key dans Admin

Bonjour,

Je suis un peu nouveau dans django et je suis en train de créer ma première petite application (qui est en train d'en devenir une plus grosse). Dans cette application je me sert des Generic Foreign Key (contenttype) afin de mettre en place une relation entre des objets assez spécifiques. Le problème est que je ne comprend pas comment les GenericForeignKey fonctionnent et ce notamment au niveau de la base de données, quelle table est ajoutée ? Comment se font les relations ?

Au final j'ai bien intégré les genericforeignkey , mon model n'affiche pas d'erreurs par contre j'ai beaucoup de mal avec l'interface d'admin qui ne semble pas fonctionner, voici une partie de mon code:

class personnel(models.Model):
     prenom = models.CharField(max_length=30)
     nom = models.CharField(max_length = 50)
     e_mail = models.EmailField(max_length = 70)
     en_activite = models.BooleanField()
     Structure = models.CharField(max_length = 50, choices = STRUCTURES_CHOIX)

     class Meta:
          verbose_name = ('Personnel')
          verbose_name_plural = ('Personnels')

     def __unicode__(self):
          return u'%s, %s, %s' % (self.prenom, self.nom, self.Structure)

class StructureService(models.Model):

     NomStructure = models.CharField(max_length = 50, choices = STRUCTURES_CHOIX)
     Service = models.CharField(max_length = 50, choices = SERVICES_CHOIX)

     class Meta:
          verbose_name = (u'Matériel de structure')
          verbose_name_plural = (u'Matériels des structures')

     def __unicode__(self):
          return u'%s, %s' % (self.NomStructure, self.Service)
     
class PersonStruct(models.Model):
     PersStructLimitation = {'model_in' :('personnel', 'StructureService')}
     content_type = models.ForeignKey(ContentType, limit_choices_to = PersStructLimitation)
     object_id = models.PositiveIntegerField()
     content_object = generic.GenericForeignKey('content_type', 'object_id')
     #id_perso = models.ForeignKey(personnel, blank=True, null = True)
     #id_struct = models.ForeignKey(StructureService, blank=True, null = True)
     #type = models

     class Meta:
          verbose_name = (u'Materiel du personnel/structure')
          verbose_name_plural = (u'Materiels des personnels/structures')
          #unique_together =[("id_perso","type")]

     def __unicode__(self):
          return u'%s' % (self.object_id)

Une partie de mon interface d'admin

class PersonnelStructInLine(generic.GenericTabularInline):
     model = PersonStruct

class PersonnelAdmin(admin.ModelAdmin):
    list_display = ('prenom', 'nom', 'e_mail', 'en_activite', 'Structure')
    #inlines = [MatStructInLine]
    list_filter = ('Structure',)
    ordering = ('-nom',)
    search_fields = ('nom', 'Structure',)
    inlines = (MdpAdmin, PersonnelStructInLine)

Et l'erreur qui est affiché....

database error

ERREUR:  la colonne CCLS_INFO_personstruct.content_type_id n'existe pas
LINE 1: SELECT "CCLS_INFO_personstruct"."id", "CCLS_INFO_personstruc...

Voilà si quelqu'un peut m'éclaircir les idées

Par avance Merci

Hors ligne

#2 21-04-2012 20:52:14

David Thenon
Membre
Inscription : 11-08-2010
Messages : 156
Site Web

Re : Content Type et generic foreign key dans Admin

Salut,

Vu le message d'erreur SQL,il doit manquer le champ de relation du
content_type dans ta table.

À priori ton modèle devait déjà exister en BDD et tu a appliqué la partie
"generic" seulement après, non ? Parce que dans ce cas syncdb n'appliquera pas
les modifications, il ne modifient jamais les structures de tables, il ne fait
que insérer celles qui n'existaient pas encore et faire un peu de ménage dans
les permissions obsolètes.

Vérifie ta table, si tu n'avais pas encore de données dedans, tu l'a vires et
tu refais un syncdb, sinon il faut que tu appliques toi même les modifs,
utilise la commande "sqlall" de django-admin pour avoir un schéma SQL de ce à
quoi elle doit ressembler (n'oublie pas d'ajouter les index).

> [snip] Le problème est que je ne comprend pas comment les
> GenericForeignKey fonctionnent et ce notamment au niveau de la base de
> données, quelle table est ajoutée ? Comment se font les relations ?

Aucune table ajoutée en plus de celle de ton modèle, tout fonctionne avec la
relation sur le content_type (provenant de l'appli
"django.contrib.contenttypes" configurée par défaut dans tes settings), tout
les modèles de données y ont une entrée unique dans ce modèle (ça doit être
dans la table "CCLS_INFO_django_content_type" chez toi). Le système de Generic
se débrouille à peu près tout seul pour faire des reverses sur le content_type
/ objet de ton modèle et vice versa.

> mon model n'affiche pas d'erreurs

Tu veux dire avec la validation automatique du modèle ? Ou bien lorsque tu
effectues des queryset sur ton modèle "PersonStruct" ?

La validation automatique des modèles ne fait que valider le code, il ne va
pas vérifier en BDD que la structure correspond.

Par contre si tu fais un queryset tout simple sur ton modèle, il devrait
constemment te renvoyer une erreur du serveur BDD comme quoi la structure
n'est pas correcte (comme celui que tu a joins à ton message).

Hors ligne

#3 04-05-2012 08:40:44

torrak
Membre
Inscription : 31-08-2011
Messages : 47

Re : Content Type et generic foreign key dans Admin

Pardon pour ma réponse tardive,

Effectivement il faut relancer entièrement la base de données.

Tout marche avec le code ci-dessus.

Merci beaucoup à David Thenon

Hors ligne

Pied de page des forums