Django Ajax CRUD Example Tutorial

Published On: 25/08/2022 | Category: Django


Hi Dev,

This article will give you example of django ajax crud example tutorial. it's simple example of django ajax crud example. this example will help you django ajax crud example tutorial. you can see django jquery ajax crud example. So, let's follow few step to create example of ajax django crud with popup modal.

jQuery Datatables provides us with quick search, pagination, ordering, sorting and etc. Datatables is basically jQuery plugins that allow you to add advanced interaction controls to your HTML tables data. Datatables also provide ajax for data searching and getting. you can give a very quick layout for search and sorting using Datatables. You can also implement Datatables in your django application.

In this example, we will create "post" table with "title" and "description" columns. we will use datatable to list a record with pagination, sorting, and filter (search). we will use the bootstrap 5 modal for create new records and update new records to create a crud (create read update delete) application in django.

Here i explained simply step by step example of how to create django ajax crud example.

You can see bellow preview of ajax crud app.

Preview:

List Page:

Create Page:

Edit Page:

Step 1: Create a Project

In this step, we’ll create a new django project using the django-admin. Head back to your command-line interface and run the following command:

django-admin startproject example
Step 2: Create a App

Now we'll create a single app called core to store a list of post names. We're keeping things intentionally basic. Stop the local server with Control+c and use the startapp command to create this new app.

python3 manage.py startapp core
Step 3: Update setting.py

Then update INSTALLED_APPS within our settings.py file to notify Django about the app.

settings.py

....
INSTALLED_APPS = [
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
    'core',
]
Step 4: Create a Model

Now go for the models we will We'll call our single model Post and it will have just two fields: title and description. And finally set __str__ to display the name of the post in admin interface.

core/models.py
from django.db import models

# Create your models here.
class Post(models.Model):
    
    # fields of the model
    title = models.CharField(max_length = 200)
    description = models.TextField()
 
    # with their title name
    def __str__(self):
        return self.title

Ok, all set. We can engender a migrations file for this change, then integrate it to our database via migrate.

python manage.py makemigrations
python manage.py migrate
Step 5: Create a Form

In this step We need to create a form that will be used .like add a bootstrap class and validation etc.. plus we need to add custom styling.

core/forms.py
from django import forms
from .models import Post

class PostForm(forms.ModelForm):

    class Meta:
        model = Post
        fields = ('title', 'description', )
Step 6: Creating the Views

In this step, we need to configure our five views. The index page will just be a template. load_data view is fetch the data into database in for datatables, PostStore View is update or create post in one view,post_edit function is basically retrivethe data from database while click the edit button and last one is it's amazing post_delete when click the delete button open the popup with sweetalert js open the core/views.py file and add:

core/views.py
from django.shortcuts import render, get_object_or_404
from .models import Post
from .forms import PostForm
from django.core import serializers
from django.http import HttpResponse, JsonResponse, HttpResponseRedirect
import json
from django.urls import reverse
from django.views.generic import View

# Create your views here.
def index(request):
    return render(request, 'index.html')

def load_data(request):
    object_list = Post.objects.all()
    json = serializers.serialize('json', object_list)
    return HttpResponse(json, content_type='application/json')

class PostStore(View):
    form_class = PostForm
    template_name = 'index.html'

    def post(self, request):
        form = self.form_class(request.POST)
        data = {'error': form.errors}
        if form.is_valid():
            try:
                title = request.POST.get('title')
                description = request.POST.get('description')

                obj = get_object_or_404(Post, id=request.POST.get('post_id'))
                obj.title=title
                obj.description=description
                obj.save()
                return JsonResponse({'success': True, 'message': 'Post Updated Successfully!'})
            except:
                obj = Post(title=request.POST.get('title'),description=request.POST.get('description')) #add more fields
                obj.save()
                return JsonResponse({'success': True, 'message': 'Post Created Successfully!'})
        else:
            return JsonResponse({'error': True, 'error': form.errors})
        return render(request, self.template_name,{'data':data})

def post_edit(request,id):
    if request.method == 'GET':

        posts = Post.objects.filter(id=id).first()

        return JsonResponse({'id':posts.id,'title':posts.title,'description':posts.description})
    else:
        return JsonResponse({'errors':'Something went wrong!'})

def post_delete(request,id):
    post = Post.objects.get(id=id)
    post.delete()
    return HttpResponseRedirect(reverse('index'))
Step 7: Creating the Templates

Next, then with your text editor create new templates files: core/templates/index.html file and the add:

core/templates/index.html
<!DOCTYPE html>
<html>
<head>
    <title>Django Ajax CRUD Example Tutorial - Tuts-Station.com</title>
    <link href="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/5.0.1/css/bootstrap.min.css" rel="stylesheet">
    <link href="https://cdn.datatables.net/1.11.4/css/dataTables.bootstrap5.min.css" rel="stylesheet">
    <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css" />
    <script src="https://code.jquery.com/jquery-3.5.1.js"></script>  
    <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery-validate/1.19.0/jquery.validate.js"></script>
    <script src="https://cdn.datatables.net/1.11.4/js/jquery.dataTables.min.js"></script>
    <script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/js/bootstrap.bundle.min.js"></script>
    <script src="https://cdn.datatables.net/1.11.4/js/dataTables.bootstrap5.min.js"></script>
    <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/sweetalert/1.1.3/sweetalert.min.css" />
    <script src="https://cdnjs.cloudflare.com/ajax/libs/sweetalert/1.1.3/sweetalert.min.js"></script>
</head>
<body>
     
<div class="container mt-5">
    <div class="row">
        <div class="col-md-12">
            <div class="card">
                <div class="card-header">
                    <div class="row">
                        <div class="col-md-9">
                            <h3>Django Ajax CRUD Example Tutorial - <span class="text-primary">Tuts-Station.com</span></h3>
                        </div>
                        <div class="col-md-3 text-end">
                            <a class="btn btn-success" href="javascript:void(0)" id="createNewPost"> <i class="fa fa-plus"></i></a>
                        </div>
                    </div>
                </div>
                <div class="card-body">
                    <div class="alert alert-success success-msg" style="display:none"></div>
                    <table class="table table-bordered data-table">
                        <thead>
                            <tr>
                                <th width="20">ID</th>
                                <th width="400">Title</th>
                                <th>Description</th>
                                <th>Action</th>
                            </tr>
                        </thead>
                        <tbody>
                        </tbody>
                    </table>
                </div>
            </div>
        </div>
    </div>
</div>

<div class="modal fade" id="ajaxModel" aria-hidden="true">
    <div class="modal-dialog">
        <div class="modal-content">
            <div class="modal-header">
                <h4 class="modal-title" id="modelHeading"></h4>
            </div>
            <div class="modal-body">
                <div class="alert alert-danger error-msg" style="display:none">
                    <ul class="mb-0"></ul>
                </div>
                <form id="postForm" name="postForm" class="form-horizontal" novalidate>
                    {% csrf_token %}
                    <input type="hidden" name="post_id" id="post_id">
                    <div class="form-group">
                        <label for="title" class="col-sm-2 control-label">Title</label>
                        <div class="col-sm-12">
                            <input type="text" class="form-control" id="title" name="title" placeholder="Enter Title" value="" maxlength="50">
                        </div>
                    </div>
       
                    <div class="form-group">
                        <label class="col-sm-2 control-label">Description</label>
                        <div class="col-sm-12">
                            <textarea id="description" name="description" placeholder="Enter Description" class="form-control"></textarea>
                        </div>
                    </div>
        
                    <div class="col-sm-offset-2 col-sm-10 mt-2">
                     <button type="submit" class="btn btn-primary" id="saveBtn" value="create">Save changes
                     </button>
                    </div>
                </form>
            </div>
        </div>
    </div>
</div>

</body>
     
<script type="text/javascript">
    $(document).ready(function() {
        /*------------------------------------------
        --------------------------------------------
        Post Listing Page 
        --------------------------------------------
        --------------------------------------------*/
        var table = $('.data-table').DataTable({
            processing: true,
            serverSide: false,
            columnDefs: [
                {
                    "render": function ( data, type, row ) {
                        var btn = '';

                        btn = btn + " <button class='btn btn-primary editPost' data-pk='" + row.pk + "'>" + '<i class="fa fa-pencil"></i>' + "</button>";
                        btn = btn + " <button class='btn btn-danger deletePost' data-action='post/" + row.pk + "/delete' data-pk='" + row.pk + "'>" + '<i class="fa fa-trash"></i>' + "</button>";

                        return btn;
                    },
                    "targets": 3
                }
            ],
            ajax: {
                url: "{% url 'load_data' %}",
                dataSrc: "",
            },
            columns: [
                { data: "pk" },
                { data: "fields.title" },
                { data: "fields.description" },
            ]
        });

        /*------------------------------------------
        --------------------------------------------
        Click to Button
        --------------------------------------------
        --------------------------------------------*/
        $('#createNewPost').click(function () {
            $('#saveBtn').val("Create Post");
            $('#post_id').val('');
            $('#postForm').trigger("reset");
            $('#modelHeading').html("Create New Post");
            $('#ajaxModel').modal('show');
        });
      
        /*------------------------------------------
        --------------------------------------------
        Click to Edit Button
        --------------------------------------------
        --------------------------------------------*/
        $('body').on('click', '.editPost', function () {
            var post_id = $(this).data('pk');
            $.get("post" +'/' + post_id +'/edit/', function (data) {
                $('#modelHeading').html("Edit Post");
                $('#saveBtn').val("edit-post");
                $('#ajaxModel').modal('show');
                $('#post_id').val(data.id);
                $('#title').val(data.title);
                $('#description').val(data.description);
            })
        });
        
        /*------------------------------------------
        --------------------------------------------
        Print Error Msg 
        --------------------------------------------
        --------------------------------------------*/
        function printErrorMsg(msg) {
            $('.error-msg').find('ul').html('');
            $('.error-msg').css('display','block');
            $.each( msg, function( key, value ) {
                $(".error-msg").find("ul").append('<li>'+value+'</li>');
            });
        }

        /*------------------------------------------
        --------------------------------------------
        Create Post Code
        --------------------------------------------
        --------------------------------------------*/
        $('#saveBtn').click(function (e) {
            e.preventDefault();
            $(this).html('Sending..');
          
            $.ajax({
                data: $('#postForm').serialize(),
                url: "{% url 'post_store' %}",
                type: "POST",
                dataType: 'json',
                success: function (data) {
                    if ($.isEmptyObject(data.error)) {
                        $("input[name='title']").val('');
                        $("input[name='description']").val('');
                        $('#ajaxModel').modal('hide');
                        $('.success-msg').css('display','block');
                        $('.success-msg').text(data.message);
                    }else{
                        printErrorMsg(data.error)
                    }
                    $('#postForm').trigger("reset");
                    table.ajax.reload();
               
                },
                error: function (data) {
                    $('#saveBtn').html('Save Changes');
                }
            });
        });
      
        /*------------------------------------------
        --------------------------------------------
        Delete Post Code
        --------------------------------------------
        --------------------------------------------*/
        $("body").on("click",".deletePost",function(){
            var current_object = $(this);
            swal({
                title: "Are you sure?",
                text: "You will not be able to recover this imaginary file!",
                type: "error",
                showCancelButton: true,
                dangerMode: true,
                cancelButtonClass: '#DD6B55',
                confirmButtonColor: '#dc3545',
                confirmButtonText: 'Delete!',
            },function (result) {
                if (result) {
                    var action = current_object.attr('data-action');
                    var token = $("input[name=csrfmiddlewaretoken]").val();
                    var id = current_object.attr('data-pk');

                    $('body').html("<form class='form-inline remove-form' method='post' action='"+action+"'></form>");
                    $('body').find('.remove-form').append('<input name="_method" type="hidden" value="delete">');
                    $('body').find('.remove-form').append('<input name="csrfmiddlewaretoken" type="hidden" value="'+token+'">');
                    $('body').find('.remove-form').append('<input name="id" type="hidden" value="'+id+'">');
                    $('body').find('.remove-form').submit();
                }
            });
        });
    });
</script>
</html>
Step 8: Creating URLs

In this section, we need a urls.py file within the core app however Django doesn't create one for us with the startapp command. Create core/urls.py with your text editor and paste below code.

core/urls.py
from django.urls import path
from . import views

urlpatterns = [
    path('', views.index,name='index'),
    path('fetch/', views.load_data,name='load_data'),
    path('post-store/', views.PostStore.as_view(),name='post_store'),
    path('post/<int:id>/edit/', views.post_edit,name='post_edit'),
    path('post/<int:id>/delete', views.post_delete,name='post_delete'),
]

Next, we require to add a URL path for our core app which can be done by importing include and setting a path for it.

example/urls.py
from django.contrib import admin
from django.urls import path, include

urlpatterns = [
    path('admin/', admin.site.urls),
    path('', include('core.urls')),
]
Run the Server

In this step, we’ll run the local development server for playing with our app without deploying it to the web.

python manage.py runserver

Next, go to the http://localhost:8000/ address with a web browser.

Our basic django ajax crud using datatables is now complete! i hope it will help you....