Skip to content

Commit cb6884f

Browse files
Fix #310. preference_updated is now triggered when the preference is updated by the REST API
1 parent 4e1c7f1 commit cb6884f

File tree

2 files changed

+100
-10
lines changed

2 files changed

+100
-10
lines changed

dynamic_preferences/api/serializers.py

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
from rest_framework import serializers
2-
from dynamic_preferences.models import GlobalPreferenceModel
2+
3+
from dynamic_preferences.signals import preference_updated
34

45

56
class PreferenceValueField(serializers.Field):
@@ -62,8 +63,17 @@ def validate_value(self, value):
6263
return value
6364

6465
def update(self, instance, validated_data):
66+
old_value = instance.value
6567
instance.value = validated_data["value"]
6668
instance.save()
69+
preference_updated.send(
70+
sender=self.__class__,
71+
section=instance.section,
72+
name=instance.name,
73+
old_value=old_value,
74+
new_value=validated_data["value"],
75+
instance=instance
76+
)
6777
return instance
6878

6979

tests/test_rest_framework.py

Lines changed: 89 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,23 @@
11
import json
2-
32
from decimal import Decimal
3+
44
from django.urls import reverse
55

6-
from dynamic_preferences.registries import global_preferences_registry as registry
6+
from dynamic_preferences.api import serializers
7+
from dynamic_preferences.api.serializers import GlobalPreferenceSerializer
8+
from dynamic_preferences.registries import \
9+
global_preferences_registry as registry
10+
from dynamic_preferences.signals import preference_updated
711
from dynamic_preferences.users.registries import (
812
user_preferences_registry as user_registry,
913
)
10-
from dynamic_preferences.api import serializers
1114
from dynamic_preferences.users.serializers import UserPreferenceSerializer
1215

16+
try:
17+
from unittest.mock import MagicMock
18+
except ImportError:
19+
from mock import MagicMock
20+
1321

1422
def test_can_serialize_preference(db):
1523
manager = registry.manager()
@@ -78,7 +86,8 @@ def test_serializer_includes_additional_data_if_any(fake_user):
7886
pref = manager.get_db_pref(section="user", name="favorite_vegetable")
7987

8088
serializer = UserPreferenceSerializer(pref)
81-
assert serializer.data["additional_data"]["choices"] == pref.preference.choices
89+
assert serializer.data["additional_data"][
90+
"choices"] == pref.preference.choices
8291

8392

8493
def test_global_preference_list_requires_permission(db, client):
@@ -129,7 +138,8 @@ def test_can_list_preferences_with_section_filter(admin_client):
129138
def test_can_detail_preference(admin_client):
130139
manager = registry.manager()
131140
pref = manager.get_db_pref(section="user", name="max_users")
132-
url = reverse("api:global-detail", kwargs={"pk": pref.preference.identifier()})
141+
url = reverse("api:global-detail",
142+
kwargs={"pk": pref.preference.identifier()})
133143
response = admin_client.get(url)
134144
assert response.status_code == 200
135145

@@ -141,7 +151,8 @@ def test_can_detail_preference(admin_client):
141151
def test_can_update_preference(admin_client):
142152
manager = registry.manager()
143153
pref = manager.get_db_pref(section="user", name="max_users")
144-
url = reverse("api:global-detail", kwargs={"pk": pref.preference.identifier()})
154+
url = reverse("api:global-detail",
155+
kwargs={"pk": pref.preference.identifier()})
145156
response = admin_client.patch(
146157
url, json.dumps({"value": 16}), content_type="application/json"
147158
)
@@ -155,7 +166,8 @@ def test_can_update_preference(admin_client):
155166
def test_can_update_decimal_preference(admin_client):
156167
manager = registry.manager()
157168
pref = manager.get_db_pref(section="type", name="cost")
158-
url = reverse("api:global-detail", kwargs={"pk": pref.preference.identifier()})
169+
url = reverse("api:global-detail",
170+
kwargs={"pk": pref.preference.identifier()})
159171
response = admin_client.patch(
160172
url, json.dumps({"value": "111.11"}), content_type="application/json"
161173
)
@@ -189,7 +201,8 @@ def test_can_update_multiple_preferences(admin_client):
189201
def test_update_preference_returns_validation_error(admin_client):
190202
manager = registry.manager()
191203
pref = manager.get_db_pref(section="user", name="max_users")
192-
url = reverse("api:global-detail", kwargs={"pk": pref.preference.identifier()})
204+
url = reverse("api:global-detail",
205+
kwargs={"pk": pref.preference.identifier()})
193206
response = admin_client.patch(
194207
url, json.dumps({"value": 1001}), content_type="application/json"
195208
)
@@ -200,7 +213,8 @@ def test_update_preference_returns_validation_error(admin_client):
200213
assert payload["value"] == ["Wrong value!"]
201214

202215

203-
def test_update_multiple_preferences_with_validation_errors_rollback(admin_client):
216+
def test_update_multiple_preferences_with_validation_errors_rollback(
217+
admin_client):
204218
manager = registry.manager()
205219
pref = manager.get_db_pref(section="user", name="max_users")
206220
url = reverse("api:global-bulk")
@@ -221,3 +235,69 @@ def test_update_multiple_preferences_with_validation_errors_rollback(admin_clien
221235

222236
assert pref1.value == pref1.preference.default
223237
assert pref2.value == pref2.preference.default
238+
239+
240+
def test_update_preference_send_signal(admin_client):
241+
manager = registry.manager()
242+
pref = manager.get_db_pref(section="user", name="max_users")
243+
244+
receiver = MagicMock()
245+
preference_updated.connect(receiver)
246+
247+
url = reverse("api:global-detail",
248+
kwargs={"pk": pref.preference.identifier()})
249+
response = admin_client.patch(
250+
url, json.dumps({"value": 16}), content_type="application/json"
251+
)
252+
assert response.status_code == 200
253+
assert receiver.call_count == 1
254+
call_args = receiver.call_args[1]
255+
assert {
256+
"sender": GlobalPreferenceSerializer,
257+
"section": "user",
258+
"name": "max_users",
259+
"old_value": 100,
260+
"new_value": 16,
261+
"instance": pref
262+
}.items() <= call_args.items()
263+
264+
265+
def test_update_multiple_preferences_send_signal(admin_client):
266+
manager = registry.manager()
267+
max_user_pref = manager.get_db_pref(section="user", name="max_users")
268+
registration_allowed_pref = manager.get_db_pref(section="user",
269+
name="registration_allowed")
270+
271+
receiver = MagicMock()
272+
preference_updated.connect(receiver)
273+
274+
url = reverse("api:global-bulk")
275+
276+
payload = {
277+
"user__max_users": 16,
278+
"user__registration_allowed": True,
279+
}
280+
response = admin_client.post(
281+
url, json.dumps(payload), content_type="application/json"
282+
)
283+
assert response.status_code == 200
284+
assert receiver.call_count == 2
285+
call_args = receiver.call_args_list[0][1]
286+
assert {
287+
"sender": GlobalPreferenceSerializer,
288+
"section": "user",
289+
"name": "max_users",
290+
"old_value": 100,
291+
"new_value": 16,
292+
"instance": max_user_pref
293+
}.items() <= call_args.items()
294+
295+
call_args = receiver.call_args_list[1][1]
296+
assert {
297+
"sender": GlobalPreferenceSerializer,
298+
"section": "user",
299+
"name": "registration_allowed",
300+
"old_value": False,
301+
"new_value": True,
302+
"instance": registration_allowed_pref
303+
}.items() <= call_args.items()

0 commit comments

Comments
 (0)