it-swarm.com.de

Wie kann ich Ajax in Django-Anwendungen integrieren?

Ich bin neu bei Django und ziemlich neu bei Ajax. Ich arbeite an einem Projekt, in dem ich die beiden integrieren muss. Ich glaube, dass ich die beiden Prinzipien verstehe, aber keine gute Erklärung für beide gefunden habe. 

Könnte mir jemand eine kurze Erklärung geben, wie sich die Codebase ändern muss, wenn sich beide zusammen integrieren?

Kann ich beispielsweise die Variable HttpResponse mit Ajax verwenden, oder müssen sich meine Antworten mit Ajax ändern? Wenn ja, können Sie bitte ein Beispiel geben, wie sich die Antworten auf die Anfragen ändern müssen? Wenn es einen Unterschied macht, sind die von mir zurückgegebenen Daten JSON. 

226
tjons

Auch wenn dies nicht ganz im Sinne von SO ist, liebe ich diese Frage, weil ich beim Start die gleichen Schwierigkeiten hatte, also gebe ich Ihnen eine kurze Anleitung. Natürlich verstehen Sie nicht die Prinzipien, die dahinter stehen (nehmen Sie es nicht als Beleidigung auf, aber wenn Sie es tun würden, würden Sie nicht danach fragen). 

Django ist serverseitig. Das heißt, ein Client geht zu URL, Sie haben eine Funktion innerhalb von Ansichten, die das wiedergibt, was er sieht, und eine Antwort in HTML zurückgibt. Lassen Sie uns es in Beispiele aufteilen:

views.py

def hello(request):
    return HttpResponse('Hello World!')

def home(request):
    return render_to_response('index.html', {'variable': 'world'})

index.html:

<h1>Hello {{ variable }}, welcome to my awesome site</h1>

urls.py

url(r'^hello/', 'myapp.views.hello'),
url(r'^home/', 'myapp.views.home'),

Das ist ein Beispiel für die einfachsten Verwendungen. Wenn Sie zu 127.0.0.1:8000/hello gehen, bedeutet dies eine Anforderung an die Hallo-Funktion. Wenn Sie zu 127.0.0.1:8000/home gehen, wird index.html zurückgegeben, und alle Variablen werden wie gewünscht ersetzt.

Jetzt lass uns über AJAX sprechen. AJAX - Aufrufe sind clientseitiger Code, der asynchrone Anforderungen ausführt. Das hört sich kompliziert an, bedeutet aber einfach, dass Sie im Hintergrund eine Anfrage an Sie richten und dann die Antwort bearbeiten. Wenn Sie also einen AJAX - Aufruf für eine URL durchführen, erhalten Sie dieselben Daten, die Sie erhalten würden, wenn ein Benutzer an diesen Ort gelangt. 

Ein Ajax-Aufruf von 127.0.0.1:8000/hello gibt beispielsweise dasselbe Ergebnis zurück, als würden Sie es besuchen. Nur dieses Mal haben Sie es in einer Js-Funktion und können damit umgehen, wie Sie möchten. Schauen wir uns einen einfachen Anwendungsfall an:

$.ajax({
    url: '127.0.0.1:8000/hello',
    type: 'get', // This is the default though, you don't actually need to always mention it
    success: function(data) {
        alert(data);
    },
    failure: function(data) { 
        alert('Got an error dude');
    }
}); 

Der allgemeine Prozess ist folgender:

  1. Der Aufruf geht an die URL 127.0.0.1:8000/hello, als ob Sie eine neue Registerkarte geöffnet hätten und dies selbst getan hätten.
  2. Wenn dies erfolgreich ist (Statuscode 200), führen Sie die Funktion für den Erfolg aus, die die empfangenen Daten alarmiert.
  3. Wenn dies fehlschlägt, führen Sie eine andere Funktion aus.

Was würde jetzt hier passieren? Sie würden eine Warnung mit "Hallo Welt" bekommen. Was passiert, wenn Sie einen Ajax-Anruf nach Hause tätigen? Dasselbe gilt, Sie erhalten eine Warnmeldung, die <h1>Hello world, welcome to my awesome site</h1> angibt.

Mit anderen Worten - an AJAX - Aufrufen gibt es nichts Neues. Sie sind nur eine Möglichkeit für den Benutzer, Daten und Informationen abzurufen, ohne die Seite zu verlassen, und er sorgt für ein reibungsloses und sehr ordentliches Design Ihrer Website. Ein paar Richtlinien, die Sie beachten sollten:

  1. JQuery lernen. Ich kann das nicht genug betonen. Sie müssen es ein bisschen verstehen, um zu wissen, wie Sie mit den Daten umgehen, die Sie erhalten. Sie müssen auch einige grundlegende Javascript-Syntax verstehen (nicht weit von Python, Sie werden sich daran gewöhnen). Envatos Video-Tutorials für jQuery empfehle ich dringend, sie sind großartig und werden Sie auf den richtigen Weg bringen.
  2. Wann wird JSON verwendet?. Sie werden viele Beispiele sehen, bei denen die von den Django-Ansichten gesendeten Daten in JSON sind. Ich bin nicht ins Detail gegangen, weil es nicht wichtig ist wie es zu tun ist (es gibt viele Erklärungen) und viel wichtiger wann. Und die Antwort darauf ist - JSON-Daten sind serialisierte Daten. Das heißt, Daten, die Sie manipulieren können. Wie bereits erwähnt, wird ein AJAX - Aufruf die Antwort abrufen, als ob der Benutzer dies selbst getan hätte. Angenommen, Sie möchten nicht mit der gesamten HTML-Datei herumspielen, sondern Daten senden (eine Liste von Objekten möglicherweise). JSON ist dafür gut geeignet, da es als Objekt gesendet wird (JSON-Daten sehen wie ein Python-Wörterbuch aus), und Sie können dann darüber iterieren oder etwas anderes tun, was die Notwendigkeit des Durchsuchens unnötiger HTML-Dateien überflüssig macht.
  3. Zuletzt hinzufügen. Wenn Sie eine Web-App erstellen und AJAX implementieren möchten, tun Sie sich selbst einen Gefallen. Erstellen Sie zunächst die gesamte App ohne AJAX. Sehen Sie, dass alles funktioniert. Dann und nur dann beginnen Sie mit dem Schreiben der AJAX -Aufrufe. Das ist ein guter Prozess, mit dem Sie auch viel lernen können.
  4. Verwenden Sie die Entwickler-Tools von Chrome. Da AJAX -Aufrufe im Hintergrund ausgeführt werden, ist es manchmal sehr schwierig, sie zu debuggen. Sie sollten die Chrome-Entwicklerwerkzeuge (oder ähnliche Werkzeuge wie Firebug) und console.log-Dinge zum Debuggen verwenden. Ich werde es nicht im Detail erklären, sondern nur googeln und es herausfinden. Es wäre sehr hilfreich für Sie.
  5. CSRF-Bewusstsein. Denken Sie schließlich daran, dass Post-Anforderungen in Django den csrf_token erfordern. Bei AJAX - Aufrufen möchten Sie häufig Daten senden, ohne die Seite zu aktualisieren. Sie werden wahrscheinlich Schwierigkeiten bekommen, bevor Sie sich daran erinnern - Warten Sie, Sie haben vergessen, den csrf_token zu senden. Dies ist ein bekannter Anfänger-Roadblock in der AJAX-Django-Integration. Nachdem Sie jedoch gelernt haben, wie man Nizza spielt, ist es einfach.

Das ist alles, was mir in den Sinn kommt. Es ist ein riesiges Thema, aber es gibt wahrscheinlich nicht genug Beispiele. Arbeite dich langsam dorthin um, du wirst es irgendwann bekommen.

566
yuvi

Neben der hervorragenden Antwort von yuvi möchte ich ein kleines spezifisches Beispiel hinzufügen, wie mit Django umzugehen ist (jenseits von js, die verwendet werden sollen). Das Beispiel verwendet AjaxableResponseMixin und setzt ein Autorenmodell voraus.

import json

from Django.http import HttpResponse
from Django.views.generic.edit import CreateView
from myapp.models import Author

class AjaxableResponseMixin(object):
    """
    Mixin to add AJAX support to a form.
    Must be used with an object-based FormView (e.g. CreateView)
    """
    def render_to_json_response(self, context, **response_kwargs):
        data = json.dumps(context)
        response_kwargs['content_type'] = 'application/json'
        return HttpResponse(data, **response_kwargs)

    def form_invalid(self, form):
        response = super(AjaxableResponseMixin, self).form_invalid(form)
        if self.request.is_ajax():
            return self.render_to_json_response(form.errors, status=400)
        else:
            return response

    def form_valid(self, form):
        # We make sure to call the parent's form_valid() method because
        # it might do some processing (in the case of CreateView, it will
        # call form.save() for example).
        response = super(AjaxableResponseMixin, self).form_valid(form)
        if self.request.is_ajax():
            data = {
                'pk': self.object.pk,
            }
            return self.render_to_json_response(data)
        else:
            return response

class AuthorCreate(AjaxableResponseMixin, CreateView):
    model = Author
    fields = ['name']

Quelle: Django-Dokumentation, Formularverarbeitung mit klassenbasierten Ansichten

Der Link zur Version 1.6 von Django ist nicht mehr verfügbar, aktualisiert auf Version 1.11

18
Wtower

Einfach und schön. Sie müssen Ihre Ansichten nicht ändern. Bjax kümmert sich um alle Ihre Links. Schau dir das an: Bjax

Verwendungszweck:

<script src="bjax.min.js" type="text/javascript"></script>
<link href="bjax.min.css" rel="stylesheet" type="text/css" />

Fügen Sie dies schließlich in HEAD Ihrer HTML-Datei ein:

$('a').bjax();

Weitere Einstellungen finden Sie hier: Bjax Demo

7
endur

Ich habe versucht, AjaxableResponseMixin in meinem Projekt zu verwenden, hatte aber die folgende Fehlermeldung erhalten:

Nicht ordnungsgemäß konfiguriert: Keine URL, an die weitergeleitet werden soll. Geben Sie entweder eine URL an oder definieren Sie eine get_absolute_url-Methode für das Model.

Das liegt daran, dass CreateView eine redirect-Antwort zurückgibt, anstatt eine HttpResponse zurückzugeben, wenn Sie eine JSON-Anforderung an den Browser senden. Ich habe also einige Änderungen an der AjaxableResponseMixin vorgenommen. Wenn es sich bei der Anforderung um eine Ajax-Anforderung handelt, wird die super.form_valid-Methode nicht aufgerufen. Rufen Sie einfach die form.save() direkt auf.

from Django.http import JsonResponse
from Django import forms
from Django.db import models

class AjaxableResponseMixin(object):
    success_return_code = 1
    error_return_code = 0
    """
    Mixin to add AJAX support to a form.
    Must be used with an object-based FormView (e.g. CreateView)
    """
    def form_invalid(self, form):
        response = super(AjaxableResponseMixin, self).form_invalid(form)
        if self.request.is_ajax():
            form.errors.update({'result': self.error_return_code})
            return JsonResponse(form.errors, status=400)
        else:
            return response

    def form_valid(self, form):
        # We make sure to call the parent's form_valid() method because
        # it might do some processing (in the case of CreateView, it will
        # call form.save() for example).
        if self.request.is_ajax():
            self.object = form.save()
            data = {
                'result': self.success_return_code
            }
            return JsonResponse(data)
        else:
            response = super(AjaxableResponseMixin, self).form_valid(form)
            return response

class Product(models.Model):
    name = models.CharField('product name', max_length=255)

class ProductAddForm(forms.ModelForm):
    '''
    Product add form
    '''
    class Meta:
        model = Product
        exclude = ['id']


class PriceUnitAddView(AjaxableResponseMixin, CreateView):
    '''
    Product add view
    '''
    model = Product
    form_class = ProductAddForm
2
Enix

AJAX ist der beste Weg, um asynchrone Aufgaben zu erledigen. Das Tätigen von asynchronen Anrufen wird häufig bei der Erstellung von Websites verwendet. Wir werden anhand eines kurzen Beispiels lernen, wie wir AJAX in Django implementieren können. Wir müssen jQuery verwenden, um weniger Javascript zu schreiben.

Dies ist Contact example, das einfachste Beispiel, das ich verwende, um die Grundlagen von AJAX und seine Implementierung in Django zu erklären. In diesem Beispiel werden wir POST anfordern. Ich folge einem Beispiel dieses Beitrags: https://djangopy.org/learn/step-up-guide-to-implement-ajax-in-Django

models.py

Lassen Sie uns zunächst das Kontaktmodell mit den grundlegenden Details erstellen.

from Django.db import models

class Contact(models.Model):
    name = models.CharField(max_length = 100)
    email = models.EmailField()
    message = models.TextField()
    timestamp = models.DateTimeField(auto_now_add = True)

    def __str__(self):
        return self.name

forms.py

Erstellen Sie das Formular für das obige Modell.

from Django import forms
from .models import Contact

class ContactForm(forms.ModelForm):
    class Meta:
        model = Contact
        exclude = ["timestamp", ]

views.py

Die Ansichten ähneln der funktionsbasierten Erstellungsansicht, aber anstatt mit Render zurückzukehren, verwenden wir die JsonResponse-Antwort.

from Django.http import JsonResponse
from .forms import ContactForm

def postContact(request):
    if request.method == "POST" and request.is_ajax():
        form = ContactForm(request.POST)
        form.save()
        return JsonResponse({"success":True}, status=200)
    return JsonResponse({"success":False}, status=400)

urls.py

Lassen Sie uns die Route der obigen Ansicht erstellen.

from Django.contrib import admin
from Django.urls import path
from app_1 import views as app1

urlpatterns = [
    path('ajax/contact', app1.postContact, name ='contact_submit'),
]

template

Rendern Sie in den Frontend-Bereich das Formular, das über dem Formular-Tag erstellt wurde, zusammen mit csrf_token und der Schaltfläche zum Senden. Beachten Sie, dass wir die JQuery-Bibliothek aufgenommen haben.

<form id = "contactForm" method= "POST">{% csrf_token %}
   {{ contactForm.as_p }}
  <input type="submit" name="contact-submit" class="btn btn-primary" />
</form>

<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>

Javascript

Lassen Sie uns nun über den Javascript-Teil sprechen. Auf dem Formular, das wir senden, stellen wir eine Ajax-Anfrage vom Typ POST, nehmen die Formulardaten und senden sie an die Serverseite.

$("#contactForm").submit(function(e){
    // prevent from normal form behaviour
        e.preventDefault();
        // serialize the form data  
        var serializedData = $(this).serialize();
        $.ajax({
            type : 'POST',
            url :  "{% url 'contact_submit' %}",
            data : serializedData,
            success : function(response){
            //reset the form after successful submit
                $("#contactForm")[0].reset(); 
            },
            error : function(response){
                console.log(response)
            }
        });
   });

Dies ist nur ein einfaches Beispiel für den Einstieg in AJAX mit Django. Wenn Sie mit mehreren weiteren Beispielen tauchen möchten, lesen Sie diesen Artikel: https://djangopy.org/learn/ Step-up-Guide-zu-implementieren-Ajax-in-Django

1
Jai Singhal

Ich schreibe das, weil die akzeptierte Antwort ziemlich alt ist und es eine Auffrischung braucht. 

So würde ich Ajax mit Django im Jahr 2019 integrieren :) Und ein reales Beispiel, wann wir Ajax brauchen würden: - 

Nehmen wir an, ich habe ein Modell mit registrierten Benutzernamen und mit Hilfe von Ajax möchte ich wissen, ob ein bestimmter Benutzername existiert. 

html:

<p id="response_msg"></p> 
<form id="username_exists_form" method='GET'>
      Name: <input type="username" name="username" />
      <button type='submit'> Check </button>           
</form>   

ajax:

$('#username_exists_form').on('submit',function(e){
    e.preventDefault();
    var username = $(this).find('input').val();
    $.get('/exists/',
          {'username': username},   
          function(response){ $('#response_msg').text(response.msg); }
    );
}); 

urls.py:

from Django.contrib import admin
from Django.urls import path
from . import views

urlpatterns = [
    path('admin/', admin.site.urls),
    path('exists/', views.username_exists, name='exists'),
]

views.py:

def username_exists(request):
    data = {'msg':''}   
    if request.method == 'GET':
        username = request.GET.get('username').lower()
        exists = Usernames.objects.filter(name=username).exists()
        if exists:
            data['msg'] = username + ' already exists.'
        else:
            data['msg'] = username + ' does not exists.'
    return JsonResponse(data)

Render_to_response , das veraltet ist und anstelle von HttpResponse durch render und ab Django 1.7 ersetzt wurde, verwenden wir JsonResponse für die Ajax-Antwort. Da er mit einem JSON-Encoder geliefert wird, müssen Sie die Daten nicht serialisieren, bevor Sie das Antwortobjekt zurückgeben. HttpResponse wird jedoch nicht veraltet.

0
Ahtisham