CRUD Operation using AJAX in Django Application

CRUD Operation using AJAX in Django Application

In this tutorial, you will learn to use AJAX (Asynchronous JavaScript and XML) to perform CRUD (create, read, update, delete) operations on a Django application.

Why use AJAX? AJAX exchanges data rather than pages with the Web Server; this makes faster data round trips, more importantly, page loading is quicker, and the need for page refreshing is significantly reduced.

We will be going to build an application that allows users to like, add, and delete blogs using AJAX requests. Let’s get started.

Step 1: Getting Started with Django – Initiating Your Project

Firstly, visit How to Create Hello World Website App in Django to create a new Django project. Create a new Django project with the name ajax_crud, with the help of the below command:

$ django-admin startproject ajax_crud

Now you need to add an application(app) to your project. To do this, run the following command to create a new Django app with the name myblog.

$ cd ajax_crud
$ python manage.py startapp myblog

Now, you have created myblog app but Django doesn’t know about it. To make your app available to the project, add the myblog app in INSTALLED_APPS. To do this, open the ajax_crud/settings.py file, and include it in the INSTALLED_APPS list as shown in below code.

INSTALLED_APPS = [
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
    'myblog.apps.MyblogConfig',
]

Next, you need to add a template directory in TEMPLATES settings. You can do it by including [BASE_DIR / 'templates'] in the DIRS list as shown in the below code.

TEMPLATES = [
    {
        'BACKEND': 'django.template.backends.django.DjangoTemplates',
        'DIRS': [BASE_DIR / 'templates'],
        ...

Step 2: Defining Models in Django – Creating a Model

You will need a table(model) in the database where all your blogs will be saved. To define a model in Django, navigate to the myblog/models.py file and add the fields for the Blog table as given below.

from django.db import models

class Blog(models.Model):
    title = models.CharField(max_length=128)
    likes = models.IntegerField(default=0)

    def __str__(self):
        return self.title

For creating a Blog table in the database, execute the following command in the command prompt.

$ python manage.py makemigrations myblog
$ python manage.py migrate

Step 3: Creating Views for Your Django App

In the myblog/views.py file, import the necessary libraries, and the Blog model.

from django.shortcuts import render
from django.http import JsonResponse
from .models import Blog

Add an index view that will render the index.html template file.

def index(request):
    context_dict = {}

    # Get all blogs titles in ascending order
    blogs = Blog.objects.order_by('title')
    context_dict['blogs'] = blogs

    return render(request, "myblog/index.html", context=context_dict)

Let’s now begin performing CRUD operations step-by-step.

1. CRUD Operation: CREATE

Create an add_new_blog_ajax view that will add a new blog through an AJAX request.

def add_new_blog_ajax(request):
    if request.method == 'GET':
        blog_title = request.GET.get('blog_title')

        if blog_title:
            Blog.objects.create(title=blog_title, likes=0)
            return JsonResponse({'status': "created"})
        else:
            return JsonResponse({'status': "failed"})

2. CRUD Operation: READ and UPDATE

For Read and Update operations, you need to create the add_likes_ajax view. This view will retrieve the blog for a given blog_id and increase its likes count. Finally, it will send the updated likes count in an Ajax response.

def add_likes_ajax(request):
    if request.method == 'GET':
        blog_id = request.GET.get('blog_id')
        likes = 0
        if blog_id:
            blog = Blog.objects.get(id=int(blog_id))
            if blog:
                likes = blog.likes + 1
                blog.likes = likes
                blog.save()
        return JsonResponse({'total_likes': likes})

3. CRUD Operation: DELETE

Below is the code implementation to Delete operation. Add a view called delete_blog_ajax in your view.py file. To delete a blog, it will read blog_id and if it is found then it will be deleted using an AJAX request.

def delete_blog_ajax(request):
    if request.method == 'GET':
        blog_id = request.GET.get('blog_id')

        if blog_id:
            blog = Blog.objects.get(id=int(blog_id))
            if blog:
                blog.delete()
                return JsonResponse({'status': "deleted"})
            else:
                return JsonResponse({'status': "error"})

Step 4: Creating URLs for your Django Project

Open the file ajax_crud/urls.py and add the following code.

from django.contrib import admin
from django.urls import path, include
from myblog import views

urlpatterns = [
    path('admin/', admin.site.urls),
    path("", include("myblog.urls")),
]

To add URLs for the myblog app, open the myblog/urls.py file. If the file is not available, create a new file called urls.py and add the following code to this file.

from django.urls import path
from myblog import views

app_name = 'myblog'

urlpatterns = [
    path('', views.index, name="index"),
    path('add_new_blog_ajax/', views.add_new_blog_ajax, name='add_new_blog_ajax'),
    path('add_likes_ajax/', views.add_likes_ajax, name='add_likes_ajax'),
    path('delete_blog_ajax/', views.delete_blog_ajax, name='delete_blog_ajax'),
]

Step 5: Creating Templates for Django App

Create a file named index.html in the myblog/templates/myblog directory and add the following code to it.

<!DOCTYPE html>
<html lang="en">
<head>
	<meta charset="UTF-8">
	<meta name="viewport" content="width=device-width, initial-scale=1.0">
	<title>CRUD Operating in AJAX</title>
    <style>
        .container {
            width: 1000px;
            margin: auto;
            margin-top: 30px;
        }

        table {
            border-collapse: collapse;
        }

        table th, table td {
            border: 1px solid #000;
            height: 20px;
            padding: 15px;
        }

        table th {
            background-color: darkgrey;
        }

        button {
            width: 100px;
            height: 40px;
        }

        #new-blog {
            height: 35px;
            width: 300px;
        }
    </style>
</head>
<body>
    <div class="container">
        New Blog Title:
        <input type="text" name="new-blog" id="new-blog">
        <button type="button" class="add-new-blog">Add</button>

        <h1>All Blogs</h1>
        <table>
            <tr>
                <th>Blog Title</th>
                <th>Total likes</th>
                <th></th>
                <th></th>
            </tr>
            {% if blogs %}
                {% for blog in blogs %}
                    <tr>
                        <td>{{ blog.title }}</td>
                        <td id="like-count">{{ blog.likes }}</td>
                        <td><button class="like-button" data-blogid="{{blog.id}}" type="button">Like</button></td>
                        <td><button class="delete-button" data-blogid="{{blog.id}}" type="button">Delete</button></td>
                    </tr>
                {% endfor %}
            {% endif %}
        </table>
    </div>

    <!-- Import jquery for using AJAX -->
    <script src="https://code.jquery.com/jquery-3.6.0.min.js"></script>

    <script>
        $(document).ready(function() {

            /*Create Operation*/
            $('.add-new-blog').on('click', function() {
                var blogTitle = $("#new-blog").val();

                $.ajax({
                    url: "{% url 'myblog:add_new_blog_ajax' %}",
                    type: 'GET',
                    data: {
                        blog_title: blogTitle,
                    },
                }).done(function(response) {
                    if(response.status == 'created') {
                        $("#new-blog").val("");

                        /*For simiplicy we are reloading page to see changes. You can update code to
                        insert new tr tag in table.*/
                        location.reload();
                    }
                })
            });

            /* Read and Update Operation */
            $('.like-button').on('click', function() {
                var blogID = $(this).attr("data-blogid");
                var likeTag = $(this).parent().siblings('#like-count');

                $.ajax({
                    url: "{% url 'myblog:add_likes_ajax' %}",
                    type: 'GET',
                    data: {
                        blog_id: blogID,
                    },
                }).done(function(response) {
                    likeTag.text(response.total_likes)
                    likeTag = null;
                });
            });

            /* Delete Operation */
            $('.delete-button').on('click', function() {
                var blogID = $(this).attr("data-blogid");

                $.ajax({
                    url: "{% url 'myblog:delete_blog_ajax' %}",
                    type: 'GET',
                    data: {
                        blog_id: blogID,
                    },
                }).done(function(response) {
                    /*For simiplicy we are relading page to see changes. You can update code to
                    remove current tr tag from table.*/
                    location.reload();
                });
            });

        });
    </script>
</body>
</html>

Execute the project by typing the following command:

$ python manage.py runserver

After running the server with the command mentioned earlier, navigate to http://127.0.0.1:8000/ to view the webpage similar to the image below. Create some blogs and you can now like them and delete specific blogs using the Delete button

crud-ajax-output
Scroll to Top