Open In App

Event Management System Using Python Django

Last Updated : 07 Mar, 2024
Improve
Improve
Like Article
Like
Save
Share
Report

In today’s fast-paced world, businesses, schools, and groups need to organize events well. An Event Management System (EMS) makes planning and managing events easier. This article will explain the structure, important parts, and how to build a helpful Event Management System with Django.

Event Management System using Django

Here, we will create the Event Management System using Django step-by-step, below is a step-by-step guide to the Event Management System using Django in Python:

Starting the Project Folder

To start the project use this command

django-admin startproject event_management_system
cd event_management_system

To start the app use this command

python manage.py startapp event_management_system_app

Now add this app to the ‘settings.py’

INSTALLED_APPS = [
"django.contrib.admin",
"django.contrib.auth",
"django.contrib.contenttypes",
"django.contrib.sessions",
"django.contrib.messages",
"django.contrib.staticfiles",
"event_management_system_app",
]

File Structure

fiel

File Structure:

Setting Necessary Files

models.py: This Django code defines two models, Category and Event. The Category model has a name field, while the Event model includes fields such as name, category (linked to Category model with a ForeignKey), start and end dates, priority, description, location, and organizer, each with specific data types and default values.

Python3




from django.db import models
 
class Category(models.Model):
    name = models.CharField(max_length=100)
 
class Event(models.Model):
    name = models.CharField(max_length=100)
    category = models.ForeignKey(Category, on_delete=models.CASCADE)
    start_date = models.DateTimeField()
    end_date = models.DateTimeField()
    priority = models.IntegerField(default=1)
    description = models.TextField(default='')
    location = models.CharField(max_length=255, default='')
    organizer = models.CharField(max_length=100, default='')


views.py: This Django code defines views for an Event Management System. It includes functions to delete events, create events with associated categories, update event details, list categories and their events, create categories, and delete categories if they don’t have associated events. Additionally, there’s a view for displaying a chart indicating the number of pending events for each category based on their start dates.

Python3




from django.utils import timezone
from django.shortcuts import render, get_object_or_404
from django.contrib import messages
from .models import Category, Event
from django.shortcuts import render, redirect
from django.urls import reverse
 
 
def delete_event(request, event_id):
    if request.method == 'POST':
        event = Event.objects.get(id=event_id)
        event.delete()
    return redirect(reverse('category_list'))
 
 
def create_event(request):
    if request.method == 'POST':
        # Retrieve data from the POST request
        name = request.POST.get('name')
        category_id = request.POST.get('category')
        start_date = request.POST.get('start_date')
        end_date = request.POST.get('end_date')
        priority = request.POST.get('priority')
        description = request.POST.get('description')
        location = request.POST.get('location')
        organizer = request.POST.get('organizer')
 
        # Retrieve the Category object
        category = Category.objects.get(pk=category_id)
 
        # Create the Event object
        event = Event.objects.create(
            name=name,
            category=category,
            start_date=start_date,
            end_date=end_date,
            priority=priority,
            description=description,
            location=location,
            organizer=organizer
        )
 
        # Redirect to the event list page
        return redirect('category_list')
    else:
        categories = Category.objects.all()
        return render(request, 'event_management_system_app/create_event.html', {'categories': categories})
 
 
def update_event(request, event_id):
    event = Event.objects.get(pk=event_id)
    if request.method == 'POST':
        # Update event fields based on form data
        event.name = request.POST.get('name')
        event.start_date = request.POST.get('start_date')
        event.end_date = request.POST.get('end_date')
        event.priority = request.POST.get('priority')
        event.description = request.POST.get('description')
        event.location = request.POST.get('location')
        event.organizer = request.POST.get('organizer')
        event.save()
        return redirect('category_list')
    else:
        # Render update event page with event data
        return render(request, 'event_management_system_app/update_event.html', {'event': event})
 
def category_list(request):
    categories = Category.objects.all()
    return render(request, 'event_management_system_app/category_list.html', {'categories': categories})
 
def create_category(request):
    if request.method == 'POST':
        name = request.POST.get('name')
        Category.objects.create(name=name)
        return redirect('category_list')
    return render(request, 'event_management_system_app/create_category.html')
 
 
def delete_category(request, category_id):
    category = Category.objects.get(pk=category_id)
    if category.event_set.exists():
        messages.error(
            request, "You cannot delete this category as it contains events.")
    else:
        category.delete()
        messages.success(request, "Category deleted successfully.")
    return redirect('category_list')
 
def category_events(request, category_id):
    category = get_object_or_404(Category, pk=category_id)
    events = category.event_set.all()
    return render(request, 'event_management_system_app/category_events.html', {'category': category, 'events': events})
 
def event_chart(request):
    categories = Category.objects.all()
    pending_counts = {}
    for category in categories:
        pending_counts[category.name] = Event.objects.filter(
            category=category,
            start_date__gt=timezone.now()
        ).count()
    return render(request, 'event_management_system_app/event_chart.html', {'pending_counts': pending_counts})


urls.py: This Django urlpatterns configuration maps URLs to corresponding views in an Event Management System. The patterns include paths for listing categories, creating categories, viewing category events, deleting categories, creating events, updating events, deleting events, and displaying an event chart

Python3




from django.contrib import admin
from django.urls import path
 
from event_management_system_app import views
 
urlpatterns = [
    path('admin/', admin.site.urls),
    path('', views.category_list, name='category_list'),
    path('categories/create/', views.create_category, name='create_category'),
    path('categories/<int:category_id>/', views.category_events, name='category_events'),
    path('categories/delete/<int:category_id>/', views.delete_category, name='delete_category'),
    path('events/create/', views.create_event, name='create_event'),
    path('events/update/<int:event_id>/', views.update_event, name='update_event'),
    path('events/delete/<int:event_id>/', views.delete_event, name='delete_event'),
    path('event-chart/', views.event_chart, name='event_chart'),
]


Creating GUI

category_events.html: This HTML file utilizes Bootstrap for a clean Event Management System interface, featuring buttons for adding events and navigating categories. It incorporates JavaScript to dynamically sort events by priority and display countdown timers for upcoming events in real-time. The modal design allows users to view detailed information about each event.

HTML




<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>{{ category.name }} Events</title>
</head>
<body>
  <div class="container mt-5">
    <h2 class="text-center">{{ category.name }} Events</h2>
    <br>
    <div class="mb-3">
      <a href="{% url 'create_event' %}" class="btn btn-primary">Add New Event</a> <!-- Button to add new event -->
      <a href="{% url 'category_list' %}" class="btn btn-secondary ml-2">Back to Categories</a> <!-- Button to go back to categories -->
    </div>
    <table id="eventTable" class="table">
      <thead>
        <tr>
          <th>Name</th>
          <th>Start Date</th>
          <th>Time Left</th>
          <th>Priority <button class="btn btn-link" onclick="sortByPriority()">â–²</button></th> <!-- Button for sorting by priority -->
          <th>Actions</th> <!-- Column for actions -->
        </tr>
      </thead>
      <tbody>
        {% for event in events %}
          <tr>
            <td>{{ event.name }}</td>
            <td>{{ event.start_date }}</td>
            <td>
              <div id="countdown_{{ event.id }}" class="countdown-timer"></div>
            </td>
            <td>{{ event.priority }}</td>
            <td>
              <a href="{% url 'update_event' event.id %}" class="btn btn-primary btn-sm">Update</a> <!-- Button to update event -->
              <form method="post" action="{% url 'delete_event' event.id %}" style="display: inline;">
                {% csrf_token %}
                <button type="submit" class="btn btn-danger btn-sm">Delete</button> <!-- Button to delete event -->
              </form>
              <button type="button" class="btn btn-info btn-sm" data-toggle="modal" data-target="#eventModal_{{ event.id }}">Details</button> <!-- Button to open modal -->
            </td>
          </tr>
        {% endfor %}
      </tbody>
    </table>
  </div>
 
  <!-- Modal for event details -->
  {% for event in events %}
    <div class="modal fade" id="eventModal_{{ event.id }}" tabindex="-1" role="dialog" aria-labelledby="eventModalLabel_{{ event.id }}" aria-hidden="true">
      <div class="modal-dialog" role="document">
        <div class="modal-content">
          <div class="modal-header">
            <h5 class="modal-title" id="eventModalLabel_{{ event.id }}">{{ event.name }}</h5>
            <button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">×</span></button>
          </div>
          <div class="modal-body">
            <p>
              <strong>Name:</strong> {{ event.name }}
            </p>
            <p>
              <strong>Category:</strong> {{ event.category.name }}
            </p>
            <p>
              <strong>Start Date:</strong> {{ event.start_date }}
            </p>
            <p>
              <strong>End Date:</strong> {{ event.end_date }}
            </p>
            <p>
              <strong>Priority:</strong> {{ event.priority }}
            </p>
            <p>
              <strong>Description:</strong> {{ event.description }}
            </p>
            <p>
              <strong>Location:</strong> {{ event.location }}
            </p>
            <p>
              <strong>Organizer:</strong> {{ event.organizer }}
            </p>
          </div>
          <div class="modal-footer">
            <button type="button" class="btn btn-secondary" data-dismiss="modal">Close</button>
          </div>
        </div>
      </div>
    </div>
  {% endfor %}
 
  <!-- JavaScript to update countdown timers and sorting -->
  <script>
    function sortByPriority() {
      var table, rows, switching, i, x, y, shouldSwitch;
      table = document.getElementById("eventTable");
      switching = true;
      while (switching) {
        switching = false;
        rows = table.getElementsByTagName("tr");
        for (i = 1; i < (rows.length - 1); i++) {
          shouldSwitch = false;
          x = rows[i].getElementsByTagName("td")[3]; // Index of Priority column
          y = rows[i + 1].getElementsByTagName("td")[3];
          if (parseInt(x.innerHTML) < parseInt(y.innerHTML)) {
            shouldSwitch = true;
            break;
          }
        }
        if (shouldSwitch) {
          rows[i].parentNode.insertBefore(rows[i + 1], rows[i]);
          switching = true;
        }
      }
    }
 
    // Function to update countdown timer for each event
    function updateCountdownTimers() {
      {% for event in events %}
      // Get the start date of the event and convert it to a JavaScript Date object
      var startDate = new Date('{{ event.start_date|date:"Y/m/d H:i:s" }}');
      var now = new Date();
 
      // Calculate the time difference between now and the start date
      var timeDiff = startDate - now;
 
      // If the event has not started yet, display the countdown timer
      if (timeDiff > 0) {
        var days = Math.floor(timeDiff / (1000 * 60 * 60 * 24));
        var hours = Math.floor((timeDiff % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60));
        var minutes = Math.floor((timeDiff % (1000 * 60 * 60)) / (1000 * 60));
        var seconds = Math.floor((timeDiff % (1000 * 60)) / 1000);
 
        // Display the countdown timer in the format: DD:HH:MM:SS
        document.getElementById('countdown_{{ event.id }}').innerText = days + "d " + hours + "h "
          + minutes + "m " + seconds + "s ";
      } else {
        // If the event has already started, display a message indicating that it has started
        document.getElementById('countdown_{{ event.id }}').innerText = "Event has started";
      }
      {% endfor %}
    }
 
    // Call the updateCountdownTimers function every second to update the countdown timers in real-time
    setInterval(updateCountdownTimers, 1000);
  </script>
 
  <!-- Bootstrap JS (Optional - for certain Bootstrap features like modals) -->
</body>
</html>


category_list.html: This HTML file creates a Category List page for an Event Management System using Bootstrap. It includes buttons to create a new category and view an event chart. The table displays existing categories with links to their events and options to delete each category. Additionally, JavaScript is used to display alert messages.

HTML




<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Category List</title>
    <!-- Bootstrap CSS -->
  </head>
  <body>
    <!-- Message display section -->
 
    <div class="container mt-5">
      <div class="text-center">
        <h2>Categories</h2>
      </div>
      <br>
 
      <a href="{% url 'create_category' %}" class="btn btn-primary mb-3">Create Category</a> <!-- Button to create category -->
      <a href="{% url 'event_chart' %}" class="btn btn-info mb-3">View Event Chart</a> <!-- Button to view event chart -->
      <table class="table">
        <thead>
          <tr>
            <th>Name</th>
            <th>Actions</th> <!-- Column for actions -->
          </tr>
        </thead>
        <tbody>
          {% for category in categories %}
            <tr>
              <td>
                <a href="{% url 'category_events' category.id %}">{{ category.name }}</a>
              </td> <!-- Link to category_events page -->
              <td>
                <form method="post" action="{% url 'delete_category' category.id %}" style="display: inline;">
                  {% csrf_token %}
                  <button type="submit" class="btn btn-danger btn-sm">Delete</button> <!-- Button to delete category -->
                </form>
              </td>
            </tr>
          {% endfor %}
        </tbody>
      </table>
    </div>
    <script>
        // JavaScript function to display the message in a popup form
        {% if messages %}
            {% for message in messages %}
                alert("{{ message }}");
            {% endfor %}
        {% endif %}
    </script>
    <!-- Bootstrap JS (Optional - for certain Bootstrap features like modals) -->
  </body>
</html>


create_category.html: This HTML file creates a page for creating a new category in an Event Management System using Bootstrap. The form includes a field for the category name, and the submission button triggers the creation process. Bootstrap styling enhances the visual presentation, making it user-friendly.

HTML




<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Create Category</title>
    <!-- Bootstrap CSS -->
  </head>
  <body>
    <div class="container mt-5">
      <h2  class="text-center">Create Category</h2>
      <br>
      <form method="post" action="{% url 'create_category' %}">
        {% csrf_token %}
        <div class="form-group">
          <label for="categoryName">Category Name:</label>
          <input type="text" class="form-control" id="categoryName" name="name" placeholder="Enter category name" required />
        </div>
        <button type="submit" class="btn btn-primary">Create</button>
      </form>
    </div>
 
    <!-- Bootstrap JS (Optional - for certain Bootstrap features like dropdowns, modals, etc.) -->
  </body>
</html>


create_event.html: This HTML file creates an “Add Event” page in an Event Management System using Bootstrap. The form allows users to input details such as event name, category, start and end dates, priority, description, location, and organizer. Bootstrap styling enhances the visual presentation.

HTML




<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Add Event</title>
    <!-- Bootstrap CSS -->
</head>
<body>
    <div class="container mt-5">
        <h2  class="text-center">Add Event</h2>
        <br>
        <form method="post" action="{% url 'create_event' %}" onsubmit="return validateForm()">
            {% csrf_token %}
            <div class="form-group">
                <label for="eventName">Event Name:</label>
                <input type="text" class="form-control" id="eventName" name="name" placeholder="Enter event name" required>
            </div>
            <div class="form-group">
                <label for="eventCategory">Category:</label>
                <select class="form-control" id="eventCategory" name="category" required>
                    <option value="">Select category</option>
                    {% for category in categories %}
                        <option value="{{ category.id }}">{{ category.name }}</option>
                    {% endfor %}
                </select>
            </div>
            <div class="form-group">
                <label for="startDate">Start Date:</label>
                <input type="datetime-local" class="form-control" id="startDate" name="start_date" required>
            </div>
            <div class="form-group">
                <label for="endDate">End Date:</label>
                <input type="datetime-local" class="form-control" id="endDate" name="end_date" required>
            </div>
            <div class="form-group">
                <label for="priority">Priority:</label>
                <input type="number" class="form-control" id="priority" name="priority" min="1" value="1" required>
            </div>
            <div class="form-group">
                <label for="description">Description:</label>
                <textarea class="form-control" id="description" name="description" rows="3"></textarea>
            </div>
            <div class="form-group">
                <label for="location">Location:</label>
                <input type="text" class="form-control" id="location" name="location" placeholder="Enter event location">
            </div>
            <div class="form-group">
                <label for="organizer">Organizer:</label>
                <input type="text" class="form-control" id="organizer" name="organizer" placeholder="Enter event organizer">
            </div>
            <button type="submit" class="btn btn-primary">Submit</button>
        </form>
    </div>
 
    <!-- Bootstrap JS (Optional - for certain Bootstrap features like dropdowns, modals, etc.) -->
    <script>
        function validateForm() {
            var startDate = document.getElementById("startDate").value;
            var endDate = document.getElementById("endDate").value;
 
            if (new Date(startDate) >= new Date(endDate)) {
                alert("End date must be after the start date.");
                return false;
            }
            return true;
        }
    </script>
</body>
</html>


update_event.html: This HTML file presents an “Update Event” page for an Event Management System using Bootstrap. It features a form with pre-filled event details for updating, including validation to ensure the end date is after the start date

HTML




<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Update Event</title>
  </head>
  <body>
    <div class="container mt-5">
      <h2 class="text-center">Update Event</h2>
      <br>
      <form method="post" id="updateEventForm">
        {% csrf_token %}
        <div class="form-group">
          <label for="name">Name:</label>
          <input type="text" class="form-control" id="name" name="name" value="{{ event.name }}" required />
        </div>
        <div class="form-group">
          <label for="start_date">Start Date:</label>
          <input type="datetime-local" class="form-control" id="start_date" name="start_date" value="{{ event.start_date }}" required />
        </div>
        <div class="form-group">
          <label for="end_date">End Date:</label>
          <input type="datetime-local" class="form-control" id="end_date" name="end_date" value="{{ event.end_date }}" required />
          <small id="end_date_error" class="form-text text-danger"></small>
        </div>
        <div class="form-group">
          <label for="priority">Priority:</label>
          <input type="number" class="form-control" id="priority" name="priority" value="{{ event.priority }}" required />
        </div>
        <div class="form-group">
          <label for="description">Description:</label>
          <textarea class="form-control" id="description" name="description" required>{{ event.description }}</textarea>
        </div>
        <div class="form-group">
          <label for="location">Location:</label>
          <input type="text" class="form-control" id="location" name="location" value="{{ event.location }}" required />
        </div>
        <div class="form-group">
          <label for="organizer">Organizer:</label>
          <input type="text" class="form-control" id="organizer" name="organizer" value="{{ event.organizer }}" required />
        </div>
        <button type="submit" class="btn btn-primary">Save Event</button>
      </form>
    </div>
 
    <script>
      // Function to validate end date is after start date
      function validateEndDate() {
        var startDate = new Date(document.getElementById('start_date').value)
        var endDate = new Date(document.getElementById('end_date').value)
        if (endDate <= startDate) {
          document.getElementById('end_date_error').innerText = 'End date must be after start date'
          return false
        } else {
          document.getElementById('end_date_error').innerText = ''
          return true
        }
      }
       
      // Add event listener to form submission for validation
      document.getElementById('updateEventForm').addEventListener('submit', function (event) {
        if (!validateEndDate()) {
          event.preventDefault() // Prevent form submission if validation fails
        }
      })
    </script>
  </body>
</html>


event_chart.html: his HTML file uses Bootstrap and Chart.js to create a “Pending Events by Category” chart. It visualizes the count of pending events in each category. The Chart.js library is employed to generate a bar chart with colorful bars representing different categories and their corresponding pending event counts.

HTML




<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Event Pending Chart</title>
    <!-- Bootstrap CSS -->
  </head>
  <body>
    <div class="container">
      <h1 class="mt-5 text-center">Pending Events by Category</h1>
      <br />
      <div class="row">
        <div class="col-md-6">
          <canvas id="eventChart" width="400" height="400"></canvas>
        </div>
      </div>
    </div>
 
    <!-- Bootstrap JS (optional for components that require JS) -->
    <!-- Chart.js -->
    <script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
    <script>
    var ctx = document.getElementById('eventChart').getContext('2d');
    var data = {
      labels: [{% for category, count in pending_counts.items %}'{{ category }}',{% endfor %}],
      datasets: [{
        label: 'Pending Events',
        data: [{% for category, count in pending_counts.items %}{{ count }},{% endfor %}],
        backgroundColor: [
          'rgba(255, 99, 132, 0.2)',
          'rgba(54, 162, 235, 0.2)',
          'rgba(255, 206, 86, 0.2)',
          'rgba(75, 192, 192, 0.2)',
          'rgba(153, 102, 255, 0.2)',
          'rgba(255, 159, 64, 0.2)'
        ],
        borderColor: [
          'rgba(255, 99, 132, 1)',
          'rgba(54, 162, 235, 1)',
          'rgba(255, 206, 86, 1)',
          'rgba(75, 192, 192, 1)',
          'rgba(153, 102, 255, 1)',
          'rgba(255, 159, 64, 1)'
        ],
        borderWidth: 1
      }]
    };
    var options = {
      scales: {
        y: {
          beginAtZero: true
        }
      }
    };
    var myChart = new Chart(ctx, {
      type: 'bar',
      data: data,
      options: options
    });
  </script>
  </body>
</html>


admin.py:Here we are registering our models.

Python3




from django.contrib import admin
from .models import Category, Event
 
 
@admin.register(Category)
class CategoryAdmin(admin.ModelAdmin):
    list_display = ('name',)
    search_fields = ('name',)
 
@admin.register(Event)
class EventAdmin(admin.ModelAdmin):
    list_display = ('name', 'category', 'start_date', 'end_date', 'priority')
    list_filter = ('category', 'priority')
    search_fields = ('name', 'category__name', 'description', 'location', 'organizer')


Deployment of the Project

Run these commands to apply the migrations:

python3 manage.py makemigrations
python3 manage.py migrate

Run the server with the help of following command:

python3 manage.py runserver

Output:
Screenshot-2024-02-23-102615Screenshot-2024-02-23-102622

Screenshot-2024-02-23-102751

Screenshot-2024-02-23-104217

Video Demonstration



Like Article
Suggest improvement
Share your thoughts in the comments

Similar Reads