django-parler-rest
django-parler-rest copied to clipboard
"Input is not a valid dict" when posting to a model with file attribute
Hello I've just detected that we get the error :
"Input is not a valid dict"
when posting with requests.post
with a files
attribute.
the file
attribute will force the request as a multipart formencoded, so the data will be json stringified.
I've created a pull request for handling this behavior. https://github.com/django-parler/django-parler-rest/pull/20
Thanks for the PR! As mentioned in #20, do you have an example how to cause this error? For example, a curl
command or Django unit test?
Yes I was using a curl command like:
curl -H "Content-Type:multipart/form-data" -F translations="{\"en\": {\"display_name\": \"toto\"}}" -F name="test" -F type="3" -F "file=@./toto;type=application/json" http://my_domain.com/my_ressource/
Hi. This issue still exists - is there any update regarding this error?
What I did to make it work was using json.loads(data)
to format the submitted form data. Unfortunately django-parler is checking for isinstance(data, dict)
(line 128, here) which returns false
on JavaScript objects that where submitted by form data and previous stringified with json.stringify
.
Hope this helps someone.
Really helpful @crstian . I had the same issue and solved quickly with your solution !
I have added the change that was done by @GuillaumeCisco but the code doesn't appear to work: Is there anything I am doing wrong?
...
if isinstance(data, str):
# try to convert to json
try:
data = json.loads(data)
except:
self.fail('invalid_json_dump')
...
You should overload TranslatedFieldsField and call the overloaded class in your serializer like this:
import json
from parler_rest.fields import TranslatedFieldsField
from rest_framework import serializers
class TranslatedFieldFixed(TranslatedFieldsField):
def to_internal_value(self, data):
"""
Deserialize data from translations fields.
For each received language, delegate validation logic to
the translation model serializer.
"""
if data is None:
return
data = json.loads(data)
if not isinstance(data, dict):
self.fail('invalid')
if not self.allow_empty and len(data) == 0:
self.fail('empty')
result, errors = {}, {}
for lang_code, model_fields in data.items():
serializer = self.serializer_class(data=model_fields)
if serializer.is_valid():
result[lang_code] = serializer.validated_data
else:
errors[lang_code] = serializer.errors
if errors:
raise serializers.ValidationError(errors)
return result
But It would be best if the error is fixed directly in the library