Skip to content

Commit 5cca7af

Browse files
authored
#A04 - As Admin, I would like to delete existing Hackathon events (#100)
1 parent cd718cc commit 5cca7af

9 files changed

Lines changed: 156 additions & 14 deletions

File tree

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
# Generated by Django 3.1.1 on 2020-10-24 13:31
2+
3+
from django.conf import settings
4+
from django.db import migrations, models
5+
import django.db.models.deletion
6+
7+
8+
class Migration(migrations.Migration):
9+
10+
dependencies = [
11+
migrations.swappable_dependency(settings.AUTH_USER_MODEL),
12+
('hackathon', '0016_merge_20201024_1240'),
13+
]
14+
15+
operations = [
16+
migrations.AlterField(
17+
model_name='hackproject',
18+
name='created_by',
19+
field=models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.SET_NULL, related_name='hackproject', to=settings.AUTH_USER_MODEL),
20+
),
21+
migrations.AlterField(
22+
model_name='hackprojectscore',
23+
name='created_by',
24+
field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='hackprojectscores', to=settings.AUTH_USER_MODEL),
25+
),
26+
]
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
# Generated by Django 3.1.1 on 2020-10-24 13:49
2+
3+
from django.db import migrations, models
4+
5+
6+
class Migration(migrations.Migration):
7+
8+
dependencies = [
9+
('hackathon', '0017_auto_20201024_1431'),
10+
]
11+
12+
operations = [
13+
migrations.AddField(
14+
model_name='hackathon',
15+
name='status',
16+
field=models.CharField(blank=True, max_length=50, null=True),
17+
),
18+
]
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
# Generated by Django 3.1.1 on 2020-10-25 20:22
2+
3+
from django.db import migrations, models
4+
5+
6+
class Migration(migrations.Migration):
7+
8+
dependencies = [
9+
('hackathon', '0018_hackathon_status'),
10+
]
11+
12+
operations = [
13+
migrations.AlterField(
14+
model_name='hackathon',
15+
name='status',
16+
field=models.CharField(blank=True, default='', max_length=50),
17+
),
18+
]
Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
# Generated by Django 3.1.1 on 2020-10-26 20:56
2+
3+
from django.db import migrations
4+
5+
6+
class Migration(migrations.Migration):
7+
8+
dependencies = [
9+
('hackathon', '0018_merge_20201026_1722'),
10+
('hackathon', '0019_auto_20201025_2022'),
11+
]
12+
13+
operations = [
14+
]

hackathon/templates/hackathon/hackathon_list.html

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,9 @@
22
{% load static %}
33
{% block content %}
44
<section class="h-100">
5-
{% if page_obj %}
5+
{% if hackathons %}
66
<h2 class="p-orange text-center mb-4">Hackathons</h2>
7-
{% for hackathon in page_obj %}
7+
{% for hackathon in hackathons %}
88
{% include 'hackathon/includes/hackathon_card.html' %}
99
<hr>
1010
{% endfor %}
Lines changed: 43 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,45 @@
11
<article class="card shadow">
2-
<div class="card-body">
3-
<h5 class="p-orange card-title">{{ hackathon.display_name }}</h5>
4-
<h6 class="card-subtitle mb-2 text-muted">{{ hackathon.start_date }} - {{ hackathon.end_date }}</h6>
5-
<p class="card-text">{{ hackathon.description }}</p>
6-
{% if hackathon.organiser %}
7-
<p>Organiser: <a href="#" class="p-blue card-link">{{ hackathon.organiser }}</a></p>
2+
<div class="card-body">
3+
<h5 class="p-orange card-title">{{ hackathon.display_name }}</h5>
4+
<h6 class="card-subtitle mb-2 text-muted">{{ hackathon.start_date }} - {{ hackathon.end_date }}</h6>
5+
<p class="card-text">{{ hackathon.description }}</p>
6+
{% if hackathon.organiser %}
7+
<p>Organiser: <a href="#" class="p-blue card-link">{{ hackathon.organiser }}</a></p>
8+
{% endif %}
9+
<a href="#" class="btn btn-ci mr-3">Read More</a>
10+
11+
<!-- Delete button, only visible for admin users -->
12+
{% if user.is_authenticated and user.is_superuser %}
13+
<button class="btn btn-ci" type="button" data-toggle="modal" data-target="#delete-modal-{{ hackathon.id }}">
14+
Delete Event
15+
</button>
16+
{% endif %}
17+
</div>
18+
</article>
19+
20+
<!-- Modal - pass in hackathon id to modal id to enable rendering details and deleting correct hackathon event -->
21+
<div class="modal fade" id="delete-modal-{{ hackathon.id }}" tabindex="-1" aria-labelledby="delete-modal"
22+
aria-hidden="true">
23+
<div class="modal-dialog">
24+
<div class="modal-content">
25+
<div class="modal-header">
26+
<h4 class="modal-title">Delete Hackathon</h4>
27+
<button type="button" class="close" data-dismiss="modal" aria-label="Close">
28+
<span aria-hidden="true">&times;</span>
29+
</button>
30+
</div>
31+
<div class="modal-body">
32+
<!-- Warn user if hackathon has started and is in progress - dates need to be formatted to work correctly -->
33+
{% if hackathon.start_date|date:"jS F Y H:i" <= today|date:"jS F Y H:i" and hackathon.end_date|date:"jS F Y H:i" >= today|date:"jS F Y H:i" %}
34+
{{ hackathon.display_name }} is currently ongoing, do you really want to delete it?
35+
{% else %}
36+
Do you really want to delete {{ hackathon.display_name }}?
837
{% endif %}
9-
<a href="#" class="btn btn-ci">Read More</a>
10-
</div>
11-
</article>
38+
</div>
39+
<div class="modal-footer">
40+
<button type="button" class="btn btn-ci mr-3" data-dismiss="modal">No</button>
41+
<a href="{% url 'hackathon:delete_hackathon' hackathon.id %}" type="button" class="btn btn-ci">Yes</a>
42+
</div>
43+
</div>
44+
</div>
45+
</div>

hackathon/urls.py

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,9 @@
11
from django.urls import path
22

3-
from .views import HackathonListView, create_hackathon
3+
from .views import HackathonListView, create_hackathon, delete_hackathon
44

55
urlpatterns = [
66
path('', HackathonListView.as_view(), name='hackathon-list'),
7-
path("create_hackathon", create_hackathon, name='create_hackathon')
7+
path("create_hackathon", create_hackathon, name='create_hackathon'),
8+
path("<int:hackathon_id>/delete_hackathon", delete_hackathon, name="delete_hackathon"),
89
]

hackathon/views.py

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,19 @@ class HackathonListView(ListView):
1515
ordering = ['-created']
1616
paginate_by = 8
1717

18+
def get_context_data(self, **kwargs):
19+
"""
20+
Pass in the following context to the template:
21+
hackathons - filter out deleted hackathons and order by newest first
22+
today - needed to compare dates to display delete alert for hackathons
23+
in progress (needed because using built in template 'now' date didn't
24+
work correctly for the comparison)
25+
"""
26+
context = super().get_context_data(**kwargs)
27+
context['hackathons'] = Hackathon.objects.order_by('-created').exclude(status='deleted')
28+
context['today'] = datetime.now()
29+
return context
30+
1831

1932
@login_required
2033
def create_hackathon(request):
@@ -55,3 +68,21 @@ def create_hackathon(request):
5568
return redirect("hackathon:hackathon-list")
5669

5770
pass
71+
72+
73+
@login_required
74+
def delete_hackathon(request, hackathon_id):
75+
""" Allow users to 'soft delete' hackathon event - set status to 'deleted'
76+
to remove from frontend list """
77+
78+
# Redirect user if they are not admin
79+
if not request.user.is_superuser:
80+
return redirect("hackathon:hackathon-list")
81+
82+
# Get selected hackathon and set status to deleted to remove from frontend list
83+
hackathon = get_object_or_404(Hackathon, pk=hackathon_id)
84+
hackathon.status = 'deleted'
85+
hackathon.save()
86+
87+
messages.success(request, f'{hackathon.display_name} has been successfully deleted!')
88+
return redirect("hackathon:hackathon-list")

static/js/datetimepicker.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ $(document).ready(function () {
2525
step: 30,
2626
minDate: defaultEndDate,
2727
defaultDate: defaultEndDate,
28-
defaultTime: '08:00',
28+
defaultTime: '17:00',
2929
minTime: '08:00',
3030
maxTime: '18:30',
3131
yearStart: today.getFullYear(),

0 commit comments

Comments
 (0)