Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit6e74d35

Browse files
committed
Custom serialization of PrimaryKeyRelatedField values
Adds a 'pk_field' parameter which can be used to proxy serialization anddeserialization of arbitrary primary key values.
1 parentcdd3aca commit6e74d35

File tree

3 files changed

+45
-0
lines changed

3 files changed

+45
-0
lines changed

‎docs/api-guide/relations.md‎

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -116,6 +116,8 @@ By default this field is read-write, although you can change this behavior using
116116
*`queryset` - The queryset used for model instance lookups when validating the field input. Relationships must either set a queryset explicitly, or set`read_only=True`.
117117
*`many` - If applied to a to-many relationship, you should set this argument to`True`.
118118
*`allow_null` - If set to`True`, the field will accept values of`None` or the empty string for nullable relationships. Defaults to`False`.
119+
*`pk_field` - Set to a field to control serialization/deserialization of the primary key's value. For example,`pk_field=UUIDField(format='hex')` would serialize a UUID primary key into its compact hex representation.
120+
119121

120122
##HyperlinkedRelatedField
121123

‎rest_framework/relations.py‎

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -134,10 +134,16 @@ class PrimaryKeyRelatedField(RelatedField):
134134
'incorrect_type':_('Incorrect type. Expected pk value, received {data_type}.'),
135135
}
136136

137+
def__init__(self,**kwargs):
138+
self.pk_field=kwargs.pop('pk_field',None)
139+
super(PrimaryKeyRelatedField,self).__init__(**kwargs)
140+
137141
defuse_pk_only_optimization(self):
138142
returnTrue
139143

140144
defto_internal_value(self,data):
145+
ifself.pk_fieldisnotNone:
146+
data=self.pk_field.to_internal_value(data)
141147
try:
142148
returnself.get_queryset().get(pk=data)
143149
exceptObjectDoesNotExist:
@@ -146,6 +152,8 @@ def to_internal_value(self, data):
146152
self.fail('incorrect_type',data_type=type(data).__name__)
147153

148154
defto_representation(self,value):
155+
ifself.pk_fieldisnotNone:
156+
returnself.pk_field.to_representation(value)
149157
returnvalue.pk
150158

151159

‎tests/test_relations.py‎

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
importuuid
12
from .utilsimportmock_reverse,fail_reverse,BadType,MockObject,MockQueryset
23
fromdjango.core.exceptionsimportImproperlyConfigured
34
fromdjango.utils.datastructuresimportMultiValueDict
@@ -48,6 +49,40 @@ def test_pk_representation(self):
4849
assertrepresentation==self.instance.pk
4950

5051

52+
classTestProxiedPrimaryKeyRelatedField(APISimpleTestCase):
53+
defsetUp(self):
54+
self.queryset=MockQueryset([
55+
MockObject(pk=uuid.UUID(int=0),name='foo'),
56+
MockObject(pk=uuid.UUID(int=1),name='bar'),
57+
MockObject(pk=uuid.UUID(int=2),name='baz')
58+
])
59+
self.instance=self.queryset.items[2]
60+
self.field=serializers.PrimaryKeyRelatedField(
61+
queryset=self.queryset,
62+
pk_field=serializers.UUIDField(format='int')
63+
)
64+
65+
deftest_pk_related_lookup_exists(self):
66+
instance=self.field.to_internal_value(self.instance.pk.int)
67+
assertinstanceisself.instance
68+
69+
deftest_pk_related_lookup_does_not_exist(self):
70+
withpytest.raises(serializers.ValidationError)asexcinfo:
71+
self.field.to_internal_value(4)
72+
msg=excinfo.value.detail[0]
73+
assertmsg=='Invalid pk "00000000-0000-0000-0000-000000000004" - object does not exist'
74+
75+
deftest_pk_related_lookup_invalid_type(self):
76+
withpytest.raises(serializers.ValidationError)asexcinfo:
77+
self.field.to_internal_value(BadType())
78+
msg=excinfo.value.detail[0]
79+
assertmsg=='Incorrect type. Expected pk value, received BadType.'
80+
81+
deftest_pk_representation(self):
82+
representation=self.field.to_representation(self.instance)
83+
assertrepresentation==self.instance.pk.int
84+
85+
5186
classTestHyperlinkedIdentityField(APISimpleTestCase):
5287
defsetUp(self):
5388
self.instance=MockObject(pk=1,name='foo')

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp