Création d'une réponse JSON à l'aide de Django et Python

452

J'essaie de convertir un script de réponse Ajax côté serveur en Django HttpResponse, mais apparemment, cela ne fonctionne pas.

Voici le script côté serveur:

/* RECEIVE VALUE */
$validateValue=$_POST['validateValue'];
$validateId=$_POST['validateId'];
$validateError=$_POST['validateError'];

/* RETURN VALUE */
$arrayToJs = array();
$arrayToJs[0] = $validateId;
$arrayToJs[1] = $validateError;

if($validateValue =="Testuser"){  // Validate??
    $arrayToJs[2] = "true";       // RETURN TRUE
    echo '{"jsonValidateReturn":'.json_encode($arrayToJs).'}';  // RETURN ARRAY WITH success
}
else{
    for($x=0;$x<1000000;$x++){
        if($x == 990000){
            $arrayToJs[2] = "false";
            echo '{"jsonValidateReturn":'.json_encode($arrayToJs).'}';   // RETURNS ARRAY WITH ERROR.
        }
    }
}

Et voici le code converti

def validate_user(request):
    if request.method == 'POST':
        vld_value = request.POST.get('validateValue')
        vld_id = request.POST.get('validateId')
        vld_error = request.POST.get('validateError')

        array_to_js = [vld_id, vld_error, False]

        if vld_value == "TestUser":
            array_to_js[2] = True
            x = simplejson.dumps(array_to_js)
            return HttpResponse(x)
        else:
            array_to_js[2] = False
            x = simplejson.dumps(array_to_js)
            error = 'Error'
            return render_to_response('index.html',{'error':error},context_instance=RequestContext(request))
    return render_to_response('index.html',context_instance=RequestContext(request))

J'utilise simplejson pour encoder la liste Python (il retournera donc un tableau JSON). Je ne pouvais pas encore comprendre le problème. Mais je pense que j'ai fait quelque chose de mal à propos de «l'écho».

Commutateur
la source
Vous pouvez également utiliser le décorateur de vue ennuyeux pour Django @ajax_request.
zopieux

Réponses:

917

J'utilise généralement un dictionnaire, pas une liste pour renvoyer du contenu JSON.

import json

from django.http import HttpResponse

response_data = {}
response_data['result'] = 'error'
response_data['message'] = 'Some error message'

Avant Django 1.7, vous le renverriez comme ceci:

return HttpResponse(json.dumps(response_data), content_type="application/json")

Pour Django 1.7+, utilisez JsonResponsecomme indiqué dans cette réponse SO comme ceci:

from django.http import JsonResponse
return JsonResponse({'foo':'bar'})
À M
la source
4
Il est le type MIME, pas la liste qui devrait être lui attirer des ennuis. Alors que la plupart des JSON sont généralement un objet ("dictionnaire") au niveau supérieur, JSON est parfaitement satisfait d'un tableau au niveau supérieur.
Thanatos
6
Désolé, ce n'est pas clair d'après ce que j'ai écrit, mais je voulais seulement dire que j'utilise un dictionnaire parce qu'il est plus propre / plus facile lors de sa sérialisation en JSON.
Tom
'application / json' n'est pas correctement pris en charge dans les anciennes versions d'IE. Voici une discussion du problème github.com/blueimp/jQuery-File-Upload/issues/123
Victory
161

Nouveau dans Django 1.7

vous pouvez utiliser des objets JsonResponse .

à partir des documents:

from django.http import JsonResponse
return JsonResponse({'foo':'bar'})
srj
la source
2
Un inconvénient: il est par défaut ensure_asciiet je n'ai pas encore trouvé de moyen de le contourner. Créé une nouvelle question pour ceci: stackoverflow.com/q/34798703/854477
int_ua
@int_ua: il suffit d'ajouter json_dumps_params={"ensure_ascii": False}(nécessite Django 1.9 ou plus récent)
Martijn Pieters
139

J'utilise ça, ça marche bien.

from django.utils import simplejson
from django.http import HttpResponse

def some_view(request):
    to_json = {
        "key1": "value1",
        "key2": "value2"
    }
    return HttpResponse(simplejson.dumps(to_json), mimetype='application/json')

Alternative:

from django.utils import simplejson

class JsonResponse(HttpResponse):
    """
        JSON response
    """
    def __init__(self, content, mimetype='application/json', status=None, content_type=None):
        super(JsonResponse, self).__init__(
            content=simplejson.dumps(content),
            mimetype=mimetype,
            status=status,
            content_type=content_type,
        )

Dans Django 1.7, des objets JsonResponse ont été ajoutés au framework Django lui-même, ce qui rend cette tâche encore plus facile:

from django.http import JsonResponse
def some_view(request):
    return JsonResponse({"key": "value"})
Dingo
la source
1
Le problème est ici qu'il n'obtient pas la valeur du champ d'entrée vld_value = request.POST.get ('validateValue')
Switch
2
Avec python 2.7, il devrait juste être "import json"
Cullen Fluffy Jennings
1
Je pense que from django.utils import simplejsonc'est pour une compatibilité descendante.
Skylar Saveland
JsonResponse(status=404, data={'status':'false','message':message})
Belter
25

Depuis Django 1.7, vous disposez d'une JsonResponse standard, c'est exactement ce dont vous avez besoin:

from django.http import JsonResponse
...
return JsonResponse(array_to_js, safe=False)

Vous n'avez même pas besoin de json.dump votre tableau.

Akhorus
la source
16
from django.http import HttpResponse
import json

class JsonResponse(HttpResponse):
    def __init__(self, content={}, mimetype=None, status=None,
             content_type='application/json'):
        super(JsonResponse, self).__init__(json.dumps(content), mimetype=mimetype,
                                           status=status, content_type=content_type)

Et dans la vue:

resp_data = {'my_key': 'my value',}
return JsonResponse(resp_data)
Dmitry Demidenko
la source
15

Pour ceux qui utilisent Django 1.7+

from django.http import JsonResponse

def your_view(request):
    json_object = {'key': "value"}
    return JsonResponse(json_object)

documents officiels

Andres
la source
11

Vous voudrez utiliser le sérialiseur django pour vous aider avec les trucs unicode:

from django.core import serializers

json_serializer = serializers.get_serializer("json")()
    response =  json_serializer.serialize(list, ensure_ascii=False, indent=2, use_natural_keys=True)
    return HttpResponse(response, mimetype="application/json")
ReduxDJ
la source
2
C'était ma version préférée, mais j'ai réalisé qu'elle ne mange que Django QuerySets .
patroqueeet
10

Avec les vues basées sur la classe Django, vous pouvez écrire:

from django.views import View
from django.http import JsonResponse

class JsonView(View):
    def get(self, request):
        return JsonResponse({'some': 'data'})

et avec Django-Rest-Framework, vous pouvez écrire:

from rest_framework.views import APIView
from rest_framework.response import Response

class JsonView(APIView):
    def get(self, request):
        return Response({'some': 'data'})
elim
la source
6

C'est très pratique avec Django version 1.7 ou supérieure car vous avez la classe JsonResponse, qui est une sous-classe de HttpResponse.

from django.http import JsonResponse
    def profile(request):
        data = {
            'name': 'Raghav',
            'location': 'India',
            'is_active': False,
            'count': 28
        }
        return JsonResponse(data)

Pour les anciennes versions de Django, vous devez utiliser un objet HttpResponse.

import json
from django.http import HttpResponse

def profile(request):
    data = {
        'name': 'Raghav',
        'location': 'India',
        'is_active': False,
        'count': 28
    }
    dump = json.dumps(data)
    return HttpResponse(dump, content_type='application/json')
Tanmay D
la source
6

Comment utiliser le moteur d'application Google avec Ajax (JSON)?

Code Javascript avec JQuery:

$.ajax({
    url: '/ajax',
    dataType : 'json',
    cache: false,
    success: function(data) {
        alert('Load was performed.'+data.ajax_resp);
    }
});

Code Python

class Ajax(webapp2.RequestHandler):
    def get(self):
        my_response = {'ajax_resp':'Hello, webapp World!'}
        datos = json.dumps(my_response)

        self.response.headers.add_header('content-type', 'application/json', charset='utf-8')
        self.response.out.write(datos)
Samiro
la source
4

Ceci est ma version préférée utilisant une vue basée sur une classe. Il suffit de sous-classer la vue de base et de remplacer la méthode get ().

import json

class MyJsonView(View):

    def get(self, *args, **kwargs):
        resp = {'my_key': 'my value',}
        return HttpResponse(json.dumps(resp), mimetype="application/json" )
ballon droïde
la source
4

Code Django views.py:

def view(request):
    if request.method == 'POST':
        print request.body
        data = request.body
        return HttpResponse(json.dumps(data))

Code HTML view.html:

<!DOCTYPE html>
<html>
<head>
<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<script>
$(document).ready(function(){
    $("#mySelect").change(function(){
        selected = $("#mySelect option:selected").text()
        $.ajax({
            type: 'POST',
            dataType: 'json',
            contentType: 'application/json; charset=utf-8',
            url: '/view/',
            data: {
                    'fruit': selected
                  },
            success: function(result) {
                        document.write(result)
                    }
    });
  });
});
</script>
</head>
<body>

<form>
    {{data}}
    <br>
Select your favorite fruit:
<select id="mySelect">
  <option value="apple" selected >Select fruit</option>
  <option value="apple">Apple</option>
  <option value="orange">Orange</option>
  <option value="pineapple">Pineapple</option>
  <option value="banana">Banana</option>
</select>
</form>
</body>
</html>
Rajan Mandanka
la source
4

Importez d'abord ceci:

from django.http import HttpResponse

Si vous avez déjà le JSON:

def your_method(request):
    your_json = [{'key1': value, 'key2': value}]
    return HttpResponse(your_json, 'application/json')

Si vous obtenez le JSON d'une autre requête HTTP:

def your_method(request):
    response = request.get('https://www.example.com/get/json')
    return HttpResponse(response, 'application/json')
Sakthivel Karthikeyan
la source
2

Utiliser JsonResponse

from django.http import JsonResponse
Suraj Verma
la source
Cette réponse a besoin de contexte et d'explication.
theUtherSide
1

Dans View, utilisez ceci:

form.field.errors|striptags

pour obtenir des messages de validation sans html

Deepak Sharma
la source