Reputation: 7270
Having this code:
class Part:
name = models.CharField(
_("Name of part"),
max_length=255,
help_text=_("Name of the part.")
class Meta:
verbose_name = _("Part")
verbose_name_plural = _("Parts")
abstract = True
class Book(Part):
isbn = models.CharField(
help_text=_("The ISBN of the book"),
max_length=15
)
for my models. I next step I need to link to the basic object. Done with this code:
class StorageItem(models.Model):
part = models.ForeignKey(
Part,
help_text=_("The part stored at this spot.")
)
I'm getting this error message:
ERRORS: StorageItem.part: (fields.E300) Field defines a relation with model 'Part', which is either not installed, or is abstract.
What is the correct approach to link an object to a group of different classes all derived from one base class?
Upvotes: 1
Views: 501
Reputation: 13078
Unfortunately it's not possible to add ForeignKeys
to abstract models. One way to get around this limitation is to use GenericForeignKey
:
class StorageItem(models.Model):
content_type = models.ForeignKey(ContentType)
object_id = models.PositiveIntegerField()
content_object = GenericForeignKey('content_type', 'object_id')
Then you can use the GenericForeignKey as follows:
book = Book.objects.create(name='test', isbn='-')
item = StorageItem(content_object=book)
item.save()
item.content_object # <Book>
A quick explanation of how this works:
content_type
stores the model that generic foreign key points toobject_id
stores the id of the modelcontent_object
is a shortcut for directly accessing the linked foreign key objectThe docs provide additional information on how to use this https://docs.djangoproject.com/en/1.9/ref/contrib/contenttypes/#generic-relations
Edit
Upon further research, it looks like django_polymorphic may also do what you want.
Upvotes: 1