8

I'm submitting a JSON to a django view with AJAX. The JSON looks like the following:

{
   "code":"9910203040", // required
   "name":"Abc", // required
   "payments":[
      {
         "amount":300, // required
         "name":"efg", // required,
         "type": 2 // can be empty
      },
      {
         "amount":100,
         "name":"pqr",
         "type": 3
      }
   ]
}

The payments list can be of any size. How can I validate this in Django? Is it possible to use Django Forms to validate this? If it was Spring, I would create Request classes and use annotations on fields but can't figure out how to do this in Django.

1

4 Answers 4

22

You can use django rest framework to validate request data as mentioned by @zaphod100.10 ,

here is the serializer you can use to validate-

from rest_framework import serializers

class PaymentSerializer(serializers.Serializer):
    amount = serializers.IntegerField(required=True, min_value=0, null=True)
    name = serializers.CharField(required=True, max_length=128)
    type = serializers.IntegerField(required=True, min_value=0)

class ValidateFormSerializer(serializers.Serializer):
    code = serializers.CharField(required=True, max_length=32)
    name = serializers.CharField(required=True, max_length=128)
    payments = serializers.ListField(child=PaymentSerializer)

You need like this to validate it in the view section -

 import ValidateFormSerializer

# add this snippet in your view section
 valid_ser = ValidateFormSerializer(data=request.data)
 if valid_ser.is_valid():
       post_data = valid_ser.validated_data
 else:
      print(valid_ser.errors)

Let me know, if it is enough to solve your problem.

Sign up to request clarification or add additional context in comments.

4 Comments

I'm not using django rest framework in my project. Is there any alternate?
check docs.djangoproject.com/en/1.11/ref/forms/validation , is there any specific reason for not using django rest framework ?
Not actually. I've a single view function that accepts the complex JSON request like the above. All other views are plain form submissions. I'm just curious to know is there an elegant way to do this with django builtin api.
I'm using django rest-framework in my project. Thank you for your answer. However I've edited it a bit to match current api documentation.
3

There are a number of ways to validate json. I would list following:

  1. Marshmallow
  2. Schema Validation

Let me know if you need any help in using these

Comments

0

you can use django rest framework [1] it is very good for handling json requests.

for validating data you can use a serializer or a django form.

using a form:

@api_view(['POST'])
def my_view(request):
    payments = request.data.pop('payments', [])
    # validate the main object
    form = MyForm(request.data)
    if form.is_valid():
        obj = form.save()
    else:
        raise APIException(form.errors)
    for pdata in payments:
        form = PaymentForm(pdata)
        if form.is_valid():
            # your code
        else:
            raise APIException(form.errors)  
    return Response()

[1] http://www.django-rest-framework.org/

2 Comments

How can I write a form class that can validate list of objects?
You can loop over the list and validate each object. Let me edit the answer to show how.
0

You can use formsets. For example:

class UserForm(Form):
    code = forms.CharField()
    name = forms.CharField() 

class PaymentForm(Form):
    amount = forms.CharField()
    name = forms.CharField()
    type = forms.CharField()

class TestView(View):
    def post(self, request):
        response_data={}
        json_data=json.loads(request.body)
        UserFormSet = formset_factory(UserForm)
        userformset = UserFormSet(initial=[{'code' : json_data['code'], 'name' : json_data['name']}])
        PaymentFormSet = formset_factory(PaymentForm)
        paymentformset = PaymentFormSet(initial=json_data['payments'])
        for userform in userformset:
            #do something
        for paymentform in paymentformset:
            #do something
        return JsonResponse(response_data)

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.