Mad Wombat
Mad Wombat

Reputation: 15105

How to create a custom manager for related objects?

I have these related models and one has a custom manager

class Device(Model):
    name = CharField()

class DeviceSettingManager(Manager):
    use_for_related_fields = True

class Setting(Model):
    name = CharField()
    value = CharField()
    device = ForeignKey(Device, related_name='settings')

    objects = DeviceSettingManager

but when I run Django shell, I see the "RelatedManager" manager being used

>>> d = Device.objects.all()[0]
>>> type(d.settings)
django.db.models.fields.related.create_foreign_related_manager..RelatedManager

How do I get the DeviceSettingManager to be used for settings for the device?

Upvotes: 1

Views: 1332

Answers (1)

Moses Koledoye
Moses Koledoye

Reputation: 78556

Never mind the result from calling type() on the manager, the DeviceSettingManager is actually in use. You can check this by doing:

class DeviceSettingManager(models.Manager):
    use_for_related_fields = True

    def manager_status(self):
        print("Device Setting Manager is Active")

And calling:

>>> d = Device.objects.all()[0]
>>> d.settings.manager_status()
Device Setting Manager is Active

Even if you explicitly pass a manager to the related object, like:

>> d.settings(manager="settings_objects")

And of course:

class Setting(Model):
    name = CharField()
    value = CharField()
    device = ForeignKey(Device, related_name='settings')

    settings_objects = DeviceSettingManager() # Notice the parenthesis

The class of the manager will still be shown as: django.db.models.fields.related_descriptors.create_reverse_many_to_one_manager.<locals>.RelatedManager

Never mind the class name.

Upvotes: 2

Related Questions