django-multitenant icon indicating copy to clipboard operation
django-multitenant copied to clipboard

If Tenant reference is named tenant, tenant_id collides

Open s4ke opened this issue 3 years ago • 2 comments

We have models that have a tenant field set as tenant = .... and django therefore generates tenant_id as part of the django model. This collides with the usage of self.tenant_id.

To work around this, we have to manually override

    @property
    def tenant_field(self):
        return 'tenant_id'

s4ke avatar Oct 22 '20 23:10 s4ke

This should either be documented as a workaround, or we should check if maybe accessing tenant_id via self.__class__.tenant_id works instead.

s4ke avatar Oct 22 '20 23:10 s4ke

With the workaround in #99 in mind I don't think the proposed solution works. I think for our usecase will need to create custom Mixins?

s4ke avatar Oct 23 '20 19:10 s4ke

This workaround works really well, I've tested it on a big project.

This is the base class of every tenant related models we have.

class TenantAwareModel(TenantModel):
    tenant = models.ForeignKey(Tenant, on_delete=models.CASCADE)

    @property
    def tenant_field(self):
        return 'tenant_id'

    class Meta:
        abstract = True

Big thank you to @s4ke ! And +1 about adding this workaround in the documentation.

KrYpTeD974 avatar Nov 26 '22 12:11 KrYpTeD974

Huum Ok actually this does not completely work.

I have some weird cases where there's a MaximumRecursionError that is triggered when tenant_value gets called. This is what the program does:

  1. Get the tenant value
  2. Try to read the value from the cache
  3. Value does not exists
  4. Set the value
  5. Go into set_attr of TenantModelMixin
  6. Get the tenant_value (step 1)
  7. [loop again and again]

Currently I did not find a better solution than monkey_patching the set_attr method to remove it

def monkey_patch_tenant_model_mixin_setattr():
    from django_multitenant.mixins import TenantModelMixin
    from django.db.models import Model
    TenantModelMixin.__setattr__ = Model.__setattr__

In settings.py

from tenants.utils import monkey_patch_tenant_model_mixin_setattr
monkey_patch_tenant_model_mixin_setattr()

Just make to avoid modifying the tenant_id of an existing object.

Maybe there is a better way in django to detect that the tenant field has changed ?

KrYpTeD974 avatar Dec 05 '22 13:12 KrYpTeD974

For now, please change the tenant_id columns with different name. tenant_id is kind of reserved keyword. I will try to find a way to remove this constraint soon

gurkanindibay avatar Feb 17 '23 08:02 gurkanindibay

@s4ke @KrYpTeD974 Fixed with the pr https://github.com/citusdata/django-multitenant/pull/151

gurkanindibay avatar Feb 17 '23 15:02 gurkanindibay