Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Name conflict if tracked model has "instance" field #634

Open
wants to merge 4 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions AUTHORS.rst
Original file line number Diff line number Diff line change
Expand Up @@ -106,3 +106,4 @@
| Őry Máté <[email protected]>
| Nafees Anwar <[email protected]>
| meanmail <[email protected]>
| Boris Shemigon <[email protected]>
2 changes: 1 addition & 1 deletion docker-compose.yml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
services:
postgres:
image: postgres:13-alpine
image: postgres:14-alpine
environment:
POSTGRES_HOST_AUTH_METHOD: trust
POSTGRES_DB: modelutils
Expand Down
6 changes: 3 additions & 3 deletions model_utils/tracker.py
Original file line number Diff line number Diff line change
Expand Up @@ -398,9 +398,9 @@ def patch_init(self, model: type[models.Model]) -> None:
original = getattr(model, '__init__')

@wraps(original)
def inner(instance: models.Model, *args: Any, **kwargs: Any) -> None:
original(instance, *args, **kwargs)
self.initialize_tracker(model, instance)
def inner(*args: Any, **kwargs: Any) -> None:
original(*args, **kwargs)
self.initialize_tracker(model, args[0])

setattr(model, '__init__', inner)

Expand Down
7 changes: 7 additions & 0 deletions tests/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -326,6 +326,13 @@ class ModelTrackedMultiple(models.Model):
number_tracker = ModelTracker(fields=['number'])


class TrackedModelWithSpecialNamedField(models.Model):
instance = models.CharField(max_length=20)
name = models.CharField(max_length=20)

tracker = FieldTracker()


class InheritedModelTracked(ModelTracked):
name2 = models.CharField(max_length=20)

Expand Down
5 changes: 4 additions & 1 deletion tests/test_fields/test_field_tracker.py
Original file line number Diff line number Diff line change
Expand Up @@ -121,7 +121,10 @@ def test_pre_save_has_changed(self) -> None:

def test_save_with_args(self) -> None:
self.instance.number = 1
self.instance.save(False, False, None, None)
self.instance.save(force_insert=False,
force_update=False,
using=None,
update_fields=None)
self.assertChanged()

def test_first_save(self) -> None:
Expand Down
19 changes: 19 additions & 0 deletions tests/test_models/test_special_name_field_model.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
from __future__ import annotations

from django.test import TestCase

from tests.models import TrackedModelWithSpecialNamedField


class SpecialNamedFieldTests(TestCase):
def test_model_with_instance_field(self) -> None:
t = TrackedModelWithSpecialNamedField.objects.create(
instance="45.55",
name="test",
)
self.assertEqual(t.instance, "45.55")

t.instance = "56.78"
t.save()

t.delete()
5 changes: 3 additions & 2 deletions tests/test_models/test_timeframed_model.py
Original file line number Diff line number Diff line change
@@ -1,10 +1,11 @@
from __future__ import annotations

from datetime import datetime, timedelta
from datetime import timedelta

from django.core.exceptions import ImproperlyConfigured
from django.db import models
from django.test import TestCase
from django.utils.timezone import now

from model_utils.managers import QueryManager
from model_utils.models import TimeFramedModel
Expand All @@ -13,7 +14,7 @@

class TimeFramedModelTests(TestCase):
def setUp(self) -> None:
self.now = datetime.now()
self.now = now()

def test_not_yet_begun(self) -> None:
TimeFrame.objects.create(start=self.now + timedelta(days=2))
Expand Down
13 changes: 7 additions & 6 deletions tests/test_models/test_timestamped_model.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@

import time_machine
from django.test import TestCase
from django.utils.timezone import now

from tests.models import TimeStamp, TimeStampWithStatusModel

Expand Down Expand Up @@ -36,7 +37,7 @@ def test_overriding_created_via_object_creation_also_uses_creation_date_for_modi
Setting the created date when first creating an object
should be permissible.
"""
different_date = datetime.today() - timedelta(weeks=52)
different_date = now() - timedelta(weeks=52)
t1 = TimeStamp.objects.create(created=different_date)
self.assertEqual(t1.created, different_date)
self.assertEqual(t1.modified, different_date)
Expand All @@ -46,7 +47,7 @@ def test_overriding_modified_via_object_creation(self) -> None:
Setting the modified date explicitly should be possible when
first creating an object, but not thereafter.
"""
different_date = datetime.today() - timedelta(weeks=52)
different_date = now() - timedelta(weeks=52)
t1 = TimeStamp.objects.create(modified=different_date)
self.assertEqual(t1.modified, different_date)
self.assertNotEqual(t1.created, different_date)
Expand All @@ -56,7 +57,7 @@ def test_overriding_created_after_object_created(self) -> None:
The created date may be changed post-create
"""
t1 = TimeStamp.objects.create()
different_date = datetime.today() - timedelta(weeks=52)
different_date = now() - timedelta(weeks=52)
t1.created = different_date
t1.save()
self.assertEqual(t1.created, different_date)
Expand All @@ -67,7 +68,7 @@ def test_overriding_modified_after_object_created(self) -> None:
is saved, regardless of attempts to change it.
"""
t1 = TimeStamp.objects.create()
different_date = datetime.today() - timedelta(weeks=52)
different_date = now() - timedelta(weeks=52)
t1.modified = different_date
t1.save()
self.assertNotEqual(t1.modified, different_date)
Expand All @@ -79,13 +80,13 @@ def test_overrides_using_save(self) -> None:
After that, only created may be modified manually.
"""
t1 = TimeStamp()
different_date = datetime.today() - timedelta(weeks=52)
different_date = now() - timedelta(weeks=52)
t1.created = different_date
t1.modified = different_date
t1.save()
self.assertEqual(t1.created, different_date)
self.assertEqual(t1.modified, different_date)
different_date2 = datetime.today() - timedelta(weeks=26)
different_date2 = now() - timedelta(weeks=26)
t1.created = different_date2
t1.modified = different_date2
t1.save()
Expand Down