Editing django-rest-framework serializer object before save
Question:
I want to edit a django-rest-framwork
serializer object before it is saved. This is how I currently do it –
def upload(request):
if request.method == 'POST':
form = ImageForm(request.POST, request.FILES)
if form.is_valid(): # All validation rules pass
obj = form.save(commit=False)
obj.user_id = 15
obj.save()
How can I do it with a django-rest-framework
serializer object?
@api_view(['POST','GET'])
def upload_serializers(request):
if request.method == 'POST':
serializer = FilesSerializer(data=request.DATA, files=request.FILES)
if serializer.is_valid():
serializer.save()
Answers:
Now edited for REST framework 3
With REST framework 3 the pattern is now:
if serializer.is_valid():
serializer.save(user_id=15)
Note that the serializers do not now ever expose an unsaved object instance as serializer.object
, however you can inspect the raw validated data as serializer.validated_data
.
If you’re using the generic views and you want to modify the save behavior you can use the perform_create
and/or perform_update
hooks…
def perform_create(self, serializer):
serializer.save(user_id=15)
You can edit the serializer’s object before save the serializer:
if serializer.is_valid():
serializer.object.user_id = 15 # <----- this line
serializer.save()
Just in case you need to modify the data before validation, there is another option without needing to override the functions create
or perform_create
. Just use the to_internal_value
function on your serializers class:
class MySerializer(serializers.ModelSerializer):
class Meta:
model = MyModel
def to_internal_value(self, data):
data['field1'] = "new value for field 1"
data['field2'] = "new value for field 2"
data['field3'] = "new value for field 3"
return super().to_internal_value(data)
So we can modify the data before doing the validation.
I want to edit a django-rest-framwork
serializer object before it is saved. This is how I currently do it –
def upload(request):
if request.method == 'POST':
form = ImageForm(request.POST, request.FILES)
if form.is_valid(): # All validation rules pass
obj = form.save(commit=False)
obj.user_id = 15
obj.save()
How can I do it with a django-rest-framework
serializer object?
@api_view(['POST','GET'])
def upload_serializers(request):
if request.method == 'POST':
serializer = FilesSerializer(data=request.DATA, files=request.FILES)
if serializer.is_valid():
serializer.save()
Now edited for REST framework 3
With REST framework 3 the pattern is now:
if serializer.is_valid():
serializer.save(user_id=15)
Note that the serializers do not now ever expose an unsaved object instance as serializer.object
, however you can inspect the raw validated data as serializer.validated_data
.
If you’re using the generic views and you want to modify the save behavior you can use the perform_create
and/or perform_update
hooks…
def perform_create(self, serializer):
serializer.save(user_id=15)
You can edit the serializer’s object before save the serializer:
if serializer.is_valid():
serializer.object.user_id = 15 # <----- this line
serializer.save()
Just in case you need to modify the data before validation, there is another option without needing to override the functions create
or perform_create
. Just use the to_internal_value
function on your serializers class:
class MySerializer(serializers.ModelSerializer):
class Meta:
model = MyModel
def to_internal_value(self, data):
data['field1'] = "new value for field 1"
data['field2'] = "new value for field 2"
data['field3'] = "new value for field 3"
return super().to_internal_value(data)
So we can modify the data before doing the validation.