rsinger86/django-lifecycle

Using @hook on a model with a GenericForeignKey doesn't work

zeraien opened this issue · 3 comments

Not sure I am doing something wrong, but I used @hook on a model with a GenericForeignKey and this was the result...

in _get_field_names
    if instance._meta.get_field(f.name).get_internal_type() == "ForeignKey":
AttributeError: 'GenericForeignKey' object has no attribute 'get_internal_type'

The underlying model:

class AbstractCheckbox(models.Model):
    class Meta:
        abstract = True
    is_checked = models.BooleanField(default=False, db_index=True)

class Checkbox(AbstractCheckbox, LifecycleModelMixin):
    content_type = models.ForeignKey(ContentType,null=True, blank=True, on_delete=models.PROTECT)
    object_id = models.PositiveIntegerField(null=True, blank=True, db_index=True)
    parent = GenericForeignKey(ct_field='content_type', fk_field='object_id')

    @hook('after_update', when='is_checked', has_changed=True)
    def checkbox_changed(self):
          pass

I am also experiencing this issue.

Traceback (most recent call last):
  File "/usr/local/lib/pulp/lib64/python3.7/site-packages/rq/worker.py", line 883, in perform_job
    rv = job.perform()
  File "/usr/local/lib/pulp/lib64/python3.7/site-packages/rq/job.py", line 645, in perform
    self._result = self._execute()
  File "/usr/local/lib/pulp/lib64/python3.7/site-packages/rq/job.py", line 651, in _execute
    return self.func(*self.args, **self.kwargs)
  File "/home/vagrant/devel/pulpcore/pulpcore/app/tasks/upload.py", line 33, in commit
    resource = CreatedResource(content_object=artifact)
  File "/usr/local/lib/pulp/lib64/python3.7/site-packages/django_lifecycle/mixins.py", line 21, in __init__
    self._initial_state = self._snapshot_state()
  File "/usr/local/lib/pulp/lib64/python3.7/site-packages/django_lifecycle/mixins.py", line 26, in _snapshot_state
    for watched_related_field in self._watched_fk_model_fields:
  File "/usr/local/lib/pulp/lib64/python3.7/site-packages/django/utils/functional.py", line 80, in __get__
    res = instance.__dict__[self.name] = self.func(instance)
  File "/usr/local/lib/pulp/lib64/python3.7/site-packages/django_lifecycle/mixins.py", line 169, in _watched_fk_model_fields
    for method in self._potentially_hooked_methods:
  File "/usr/local/lib/pulp/lib64/python3.7/site-packages/django/utils/functional.py", line 80, in __get__
    res = instance.__dict__[self.name] = self.func(instance)
  File "/usr/local/lib/pulp/lib64/python3.7/site-packages/django_lifecycle/mixins.py", line 145, in _potentially_hooked_methods
    skip = set(get_unhookable_attribute_names(self))
  File "/usr/local/lib/pulp/lib64/python3.7/site-packages/django_lifecycle/utils.py", line 68, in get_unhookable_attribute_names
    + ["_run_hooked_methods"]
  File "/usr/local/lib/pulp/lib64/python3.7/site-packages/django_lifecycle/utils.py", line 57, in _get_field_names
    if instance._meta.get_field(f.name).get_internal_type() == "ForeignKey":
AttributeError: 'GenericForeignKey' object has no attribute 'get_internal_type'

I opened a PR to work around this issue here: #58

Thanks, I appreciate the fix.