Skip to content

Commit b541fa3

Browse files
committed
add integration test for setting IP from the request
1 parent dc672e1 commit b541fa3

File tree

8 files changed

+64
-17
lines changed

8 files changed

+64
-17
lines changed

docs/advanced.rst

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -391,8 +391,10 @@ source model. This is possible by combining the ``bases`` functionality with the
391391
392392
# define your signal handler/callback anywhere outside of models.py
393393
def add_history_ip_address(sender, **kwargs):
394+
thread = threading.local()
394395
history_instance = kwargs['history_instance']
395-
history_instance.ip_address = history_instance.request.META['REMOTE_ADDR']
396+
# (thread.request for use only in conjunction with the simple_history middleware)
397+
history_instance.ip_address = thread.request.META['REMOTE_ADDR']
396398
397399
398400
.. code-block:: python

simple_history/signals.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,8 @@
22

33

44
pre_create_historical_record = django.dispatch.Signal(providing_args=[
5-
'instance', 'history_date', 'history_user', 'history_change_reason',
5+
'instance', 'history_instance', 'history_date', 'history_user',
6+
'history_change_reason',
67
])
78
post_create_historical_record = django.dispatch.Signal(providing_args=[
89
'instance', 'history_instance', 'history_date', 'history_user',

simple_history/tests/apps.py

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,19 @@
11
from django.apps import AppConfig
2+
from simple_history.models import HistoricalRecords
23
from simple_history.signals import pre_create_historical_record
34

45

5-
def add_history_ip_address(sender, **kwargs):
6-
history_instance = kwargs['history_instance']
7-
history_instance.ip_address = '127.0.0.1'
8-
9-
106
class TestsConfig(AppConfig):
117
name = 'simple_history.tests'
128
verbose_name = 'Tests'
139

1410
def ready(self):
1511
from simple_history.tests.models \
1612
import HistoricalPollWithHistoricalIPAddress
13+
from simple_history.tests.tests.utils import add_history_ip_address
1714

1815
pre_create_historical_record.connect(
1916
add_history_ip_address,
20-
sender=HistoricalPollWithHistoricalIPAddress
17+
sender=HistoricalPollWithHistoricalIPAddress,
18+
dispatch_uid='add_history_ip_address'
2119
)

simple_history/tests/models.py

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,10 +52,12 @@ class Meta:
5252
class PollWithHistoricalIPAddress(models.Model):
5353
question = models.CharField(max_length=200)
5454
pub_date = models.DateTimeField('date published')
55-
place = models.ForeignKey('Place', on_delete=models.CASCADE)
5655

5756
history = HistoricalRecords(bases=[IPAddressHistoricalModel])
5857

58+
def get_absolute_url(self):
59+
return reverse('poll-detail', kwargs={'pk': self.pk})
60+
5961

6062
class Temperature(models.Model):
6163
location = models.CharField(max_length=200)

simple_history/tests/tests/test_models.py

Lines changed: 25 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -10,12 +10,14 @@
1010
from django.core.files.base import ContentFile
1111
from django.db import models
1212
from django.db.models.fields.proxy import OrderWrt
13-
from django.test import TestCase
13+
from django.test import TestCase, override_settings
14+
from django.urls import reverse
1415

1516
from simple_history.models import (
1617
HistoricalRecords,
1718
ModelChange
1819
)
20+
from simple_history.tests.tests.utils import middleware_override_settings
1921
from simple_history.utils import update_change_reason
2022
from ..external.models import ExternalModel2, ExternalModel4
2123
from ..models import (
@@ -1054,19 +1056,36 @@ def test_changed_value_lost(self):
10541056
class ExtraFieldsTestCase(TestCase):
10551057
def test_extra_ip_address_field_populated_on_save(self):
10561058
poll = PollWithHistoricalIPAddress.objects.create(
1057-
question="Will it blend?", pub_date=today,
1058-
place=Place.objects.create(name="Here")
1059+
question="Will it blend?", pub_date=today
10591060
)
10601061

10611062
poll_history = poll.history.order_by('history_date')[0]
10621063

1063-
self.assertEquals('127.0.0.1', poll_history.ip_address)
1064+
self.assertEquals('192.168.0.1', poll_history.ip_address)
10641065

10651066
def test_extra_ip_address_field_not_present_on_poll(self):
10661067
poll = PollWithHistoricalIPAddress.objects.create(
1067-
question="Will it blend?", pub_date=today,
1068-
place=Place.objects.create(name="Here")
1068+
question="Will it blend?", pub_date=today
10691069
)
10701070

10711071
with self.assertRaises(AttributeError):
10721072
poll.ip_address
1073+
1074+
1075+
@override_settings(**middleware_override_settings)
1076+
class ExtraFieldsIPAddressTestCase(TestCase):
1077+
def test_signal_is_able_to_retrieve_request_from_thread(self):
1078+
data = {
1079+
# workaround for bad interplay with signals and mocking; see
1080+
# simple_history.tests.tests.utils.add_history_ip_address
1081+
'question': 'read IP from request',
1082+
'pub_date': '2018-10-30'
1083+
}
1084+
1085+
self.client.post(reverse('pollip-add'), data=data)
1086+
1087+
polls = PollWithHistoricalIPAddress.objects.all()
1088+
self.assertEqual(1, polls.count())
1089+
1090+
poll_history = polls[0].history.first()
1091+
self.assertEqual('127.0.0.1', poll_history.ip_address)

simple_history/tests/tests/utils.py

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,3 +15,13 @@
1515
settings.MIDDLEWARE_CLASSES + [request_middleware]
1616
)
1717
}
18+
19+
20+
def add_history_ip_address(sender, **kwargs):
21+
history_instance = kwargs['history_instance']
22+
if history_instance.question == 'read IP from request':
23+
from simple_history.models import HistoricalRecords
24+
history_instance.ip_address = \
25+
HistoricalRecords.thread.request.META['REMOTE_ADDR']
26+
else:
27+
history_instance.ip_address = '192.168.0.1'

simple_history/tests/urls.py

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,8 @@
1010
PollDelete,
1111
PollDetail,
1212
PollList,
13-
PollUpdate
13+
PollUpdate,
14+
PollWithHistoricalIPAddressCreate,
1415
)
1516
from . import other_admin
1617

@@ -26,6 +27,11 @@
2627
BucketDataRegisterRequestUserDetail.as_view(),
2728
name='bucket_data-detail'),
2829
url(r'^poll/add/$', PollCreate.as_view(), name='poll-add'),
30+
url(
31+
r'^pollwithhistoricalipaddress/add$',
32+
PollWithHistoricalIPAddressCreate.as_view(),
33+
name='pollip-add'
34+
),
2935
url(r'^poll/(?P<pk>[0-9]+)/$', PollUpdate.as_view(), name='poll-update'),
3036
url(r'^poll/(?P<pk>[0-9]+)/delete/$', PollDelete.as_view(),
3137
name='poll-delete'),

simple_history/tests/view.py

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,14 +7,23 @@
77
UpdateView
88
)
99

10-
from simple_history.tests.models import BucketDataRegisterRequestUser, Poll
10+
from simple_history.tests.models import (
11+
BucketDataRegisterRequestUser,
12+
Poll,
13+
PollWithHistoricalIPAddress
14+
)
1115

1216

1317
class PollCreate(CreateView):
1418
model = Poll
1519
fields = ['question', 'pub_date']
1620

1721

22+
class PollWithHistoricalIPAddressCreate(CreateView):
23+
model = PollWithHistoricalIPAddress
24+
fields = ['question', 'pub_date']
25+
26+
1827
class PollUpdate(UpdateView):
1928
model = Poll
2029
fields = ['question', 'pub_date']

0 commit comments

Comments
 (0)