From 1c8a1cd56f7cfd656f5e9dc18d37d247fa8ad3cf Mon Sep 17 00:00:00 2001 From: Flatlogic Bot Date: Sun, 1 Mar 2026 13:05:50 +0000 Subject: [PATCH] Autosave: 20260301-130550 --- core/__pycache__/urls.cpython-311.pyc | Bin 2996 -> 3211 bytes core/__pycache__/views.cpython-311.pyc | Bin 46553 -> 49843 bytes core/templates/core/blood_request_list.html | 8 +- core/templates/core/chat.html | 17 ++++- core/templates/core/donation_history.html | 2 +- core/templates/core/donor_list.html | 4 +- core/templates/core/inbox.html | 54 ++++++++------ core/templates/core/index.html | 74 ------------------- core/templates/core/lives_saved.html | 2 +- core/templates/core/profile.html | 10 ++- core/templates/core/register.html | 2 +- core/urls.py | 2 + core/views.py | 77 ++++++++++++++++++-- 13 files changed, 139 insertions(+), 113 deletions(-) diff --git a/core/__pycache__/urls.cpython-311.pyc b/core/__pycache__/urls.cpython-311.pyc index 384084cc0e7a3749eabb44af6d87d508c5884e57..198b087ed654275d8e5685483e14ed357bf45857 100644 GIT binary patch delta 292 zcmdlY-Yu!VoR^o20SH`=F3fc2WMFs<;=q6sl<_%gqdG6k#0{+cwyDfn3NYyuyNL@# zHSK{yif|!^HEhe685mXrF$AQ`MJc5?1~X_nZMI|4WDJr|NzF+uN!86wEiO(>Pc7EB zDK06pDlJYe%1g{mwbQ@F4^a>gQ&0sJ&`nHE&M(a?(Z9t9RRI;)oW|S8k)Mwm$lWP&9fIp)KKT`uY2o`ArWdU>{ B7x4f9 diff --git a/core/__pycache__/views.cpython-311.pyc b/core/__pycache__/views.cpython-311.pyc index 50e031b61e378dd748992069c183c080ed640d67..6abdf0f26bbcb0c902e65effba6f19fe0a8cc38a 100644 GIT binary patch delta 6746 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 RIVu2**CC^U6~6NF{{xR?&#M3c delta 4343 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 diff --git a/core/templates/core/blood_request_list.html b/core/templates/core/blood_request_list.html index a128447..86d24d8 100644 --- a/core/templates/core/blood_request_list.html +++ b/core/templates/core/blood_request_list.html @@ -76,7 +76,13 @@ {% endif %} {% if user.is_authenticated and user.donor_profile and req.user != user %} - Volunteer + {% if can_volunteer %} + Volunteer + {% else %} + + {% endif %} {% endif %} Call diff --git a/core/templates/core/chat.html b/core/templates/core/chat.html index d6b7d29..e868a41 100644 --- a/core/templates/core/chat.html +++ b/core/templates/core/chat.html @@ -115,13 +115,28 @@ Online -
+
+
diff --git a/core/templates/core/donation_history.html b/core/templates/core/donation_history.html index 775b4af..9756377 100644 --- a/core/templates/core/donation_history.html +++ b/core/templates/core/donation_history.html @@ -84,7 +84,7 @@
{{ donation.donor_user.username }}
-
Verified Hero
+
Verified Champion
diff --git a/core/templates/core/donor_list.html b/core/templates/core/donor_list.html index a8c4345..b7caea6 100644 --- a/core/templates/core/donor_list.html +++ b/core/templates/core/donor_list.html @@ -78,8 +78,8 @@
- - {% if donor.is_available %}Available{% else %}Unavailable{% endif %} + + {% if donor.on_break %}On Break ({{ donor.days_remaining }}d){% elif donor.is_available %}Available{% else %}Unavailable{% endif %}

Phone: {{ donor.phone }}

diff --git a/core/templates/core/inbox.html b/core/templates/core/inbox.html index 025d72a..6de5e22 100644 --- a/core/templates/core/inbox.html +++ b/core/templates/core/inbox.html @@ -13,30 +13,40 @@ {% if conversations %}
{% for conv in conversations %} - -
- {% if conv.user.profile.profile_pic %} - {{ conv.user.username }} - {% else %} -
- -
- {% endif %} -
-
- {% else %} diff --git a/core/templates/core/index.html b/core/templates/core/index.html index d16a1a1..d7a3b4b 100644 --- a/core/templates/core/index.html +++ b/core/templates/core/index.html @@ -111,50 +111,6 @@ border-radius: 10px; } - .hero-section { - background: linear-gradient(135deg, #1a1a1a, #2d1b1b); - border: 1px solid rgba(255, 215, 0, 0.3); - border-radius: 16px; - padding: 12px 16px; - margin-bottom: 20px; - position: relative; - } - .hero-item { - background: rgba(255, 255, 255, 0.05); - border-radius: 12px; - padding: 8px 12px; - margin-right: 10px; - border: 1px solid rgba(255, 215, 0, 0.1); - display: inline-flex; - align-items: center; - gap: 10px; - min-width: 180px; - } - .live-pulse { - width: 8px; - height: 8px; - background: #FF4D4D; - border-radius: 50%; - display: inline-block; - margin-right: 5px; - box-shadow: 0 0 0 rgba(255, 77, 77, 0.4); - animation: pulse 2s infinite; - } - @keyframes pulse { - 0% { box-shadow: 0 0 0 0 rgba(255, 77, 77, 0.7); } - 70% { box-shadow: 0 0 0 10px rgba(255, 77, 77, 0); } - 100% { box-shadow: 0 0 0 0 rgba(255, 77, 77, 0); } - } - .heroes-scroll { - display: flex; - overflow-x: auto; - padding: 5px 0; - scrollbar-width: none; - } - .heroes-scroll::-webkit-scrollbar { - display: none; - } - .filter-btn { background: #ffffff; border: 1px solid var(--border-color); @@ -292,7 +248,6 @@
-

Hero Community

@@ -300,35 +255,6 @@
- {% if recent_heroes %} -
-
- - - Live: Today's Heroes (Last 24h) - - {{ recent_heroes.count }} Active -
-
- {% for hero in recent_heroes %} -
- {% if hero.donor.user and hero.donor.user.profile.profile_pic %} - - {% else %} -
- {{ hero.donor.blood_group }} -
- {% endif %} -
-

{{ hero.donor.name }}

-

Saved Life {{ hero.date|timesince }} ago

-
-
- {% endfor %} -
-
- {% endif %} - diff --git a/core/templates/core/lives_saved.html b/core/templates/core/lives_saved.html index becbc6a..089f410 100644 --- a/core/templates/core/lives_saved.html +++ b/core/templates/core/lives_saved.html @@ -44,7 +44,7 @@ - + diff --git a/core/templates/core/profile.html b/core/templates/core/profile.html index 1ee9c72..82c6acd 100644 --- a/core/templates/core/profile.html +++ b/core/templates/core/profile.html @@ -174,12 +174,18 @@

Clearing personal info will remove your bio, location, phone number, and profile picture. Your account and donation history will remain intact.

-
+ {% csrf_token %} - +
+ {% csrf_token %} + +
diff --git a/core/templates/core/register.html b/core/templates/core/register.html index 002a541..93569b9 100644 --- a/core/templates/core/register.html +++ b/core/templates/core/register.html @@ -11,7 +11,7 @@

Join RaktaPulse

-

Be a hero. Start saving lives today.

+

Join our mission. Start saving lives today.

diff --git a/core/urls.py b/core/urls.py index 18c4bf7..bb63c67 100644 --- a/core/urls.py +++ b/core/urls.py @@ -18,6 +18,8 @@ urlpatterns = [ path("chat//", views.chat, name="chat"), path("notifications/", views.notifications_view, name="notifications"), path("delete-personal-info/", views.delete_personal_info, name="delete_personal_info"), + path("delete-messages//", views.delete_messages, name="delete_messages"), + path("delete-account/", views.delete_account, name="delete_account"), # Donor & Blood Management path("donors/", views.donor_list, name="donor_list"), diff --git a/core/views.py b/core/views.py index 9795189..56e8139 100644 --- a/core/views.py +++ b/core/views.py @@ -172,14 +172,40 @@ def delete_personal_info(request): profile.phone = "" profile.birth_date = None profile.profile_pic = None - # We keep blood_group as it's often essential for the app's functionality (blood donation) - # but we can clear it if the user really wants to. - # For now, let's just clear the "soft" personal info. profile.save() + # If they have a donor profile, clear that too (or keep it but mark unavailable) + if hasattr(user, 'donor_profile'): + donor = user.donor_profile + donor.phone = "" + donor.location = "" + donor.save() + messages.success(request, "Your non-essential personal information has been cleared.") return redirect('profile') +@login_required +@require_POST +def delete_messages(request, username): + """Delete all messages between the current user and another user.""" + other_user = User.objects.get(username=username) + Message.objects.filter( + (Q(sender=request.user) & Q(receiver=other_user)) | + (Q(sender=other_user) & Q(receiver=request.user)) + ).delete() + messages.success(request, f"Conversation with {username} has been deleted.") + return redirect('inbox') + +@login_required +@require_POST +def delete_account(request): + """Delete the user's account and all associated data.""" + user = request.user + logout(request) # Logout before deleting to clear session + user.delete() + messages.success(request, "Your account and all associated data have been permanently deleted.") + return redirect('welcome') + def haversine(lat1, lon1, lat2, lon2): # Radius of the Earth in km R = 6371.0 @@ -244,7 +270,7 @@ def home(request): # Ensure default badges exist if Badge.objects.count() == 0: Badge.objects.create(name='First-Time Donor', description='Completed your first donation!', icon_class='fas fa-award') - Badge.objects.create(name='Community Hero', description='Completed 5 donations!', icon_class='fas fa-medal') + Badge.objects.create(name='Community Champion', description='Completed 5 donations!', icon_class='fas fa-medal') Badge.objects.create(name='Life Saver', description='Completed 10+ donations!', icon_class='fas fa-heart') donors = Donor.objects.all() @@ -285,9 +311,9 @@ def home(request): actual_completed = DonationEvent.objects.filter(is_completed=True).count() completed_donations = actual_completed + demo_donations - # Find Recent Heroes (Last 24 Hours) + # Find Recent Contributions (Last 24 Hours) last_24_hours = timezone.now() - timezone.timedelta(hours=24) - recent_heroes = DonationEvent.objects.filter( + recent_contributions = DonationEvent.objects.filter( is_completed=True, date__gte=last_24_hours ).select_related('donor').order_by('-date') @@ -327,7 +353,7 @@ def home(request): "blood_banks": blood_banks, "blood_groups": [g[0] for g in BLOOD_GROUPS], "stats": stats, - "recent_heroes": recent_heroes, + "recent_contributions": recent_contributions, "project_name": "RaktaPulse", "current_time": timezone.now(), "myths_vs_facts": myths_vs_facts, @@ -378,6 +404,15 @@ def donor_list(request): else: donor_list_data.sort(key=lambda x: (-x.is_verified, x.name)) + # Check 90-day availability + for d in donor_list_data: + if d.last_donation_date: + days_since = (timezone.now().date() - d.last_donation_date).days + if days_since < 90: + d.is_available = False + d.on_break = True + d.days_remaining = 90 - days_since + context = { 'donors': donor_list_data, 'blood_groups': [g[0] for g in BLOOD_GROUPS], @@ -391,9 +426,22 @@ def blood_request_list(request): requests = requests.filter(status=status) requests = requests.order_by('-created_at') + + can_volunteer = True + days_until_eligible = 0 + if request.user.is_authenticated: + donor_profile = getattr(request.user, 'donor_profile', None) + if donor_profile and donor_profile.last_donation_date: + days_since = (timezone.now().date() - donor_profile.last_donation_date).days + if days_since < 90: + can_volunteer = False + days_until_eligible = 90 - days_since + context = { 'requests': requests, 'current_status': status, + 'can_volunteer': can_volunteer, + 'days_until_eligible': days_until_eligible, } return render(request, 'core/blood_request_list.html', context) @@ -604,6 +652,14 @@ def volunteer_for_request(request, request_id): messages.error(request, "You need to be registered as a donor to volunteer.") return redirect('donor_list') + # Check for 3-month (90 days) restriction + if donor_profile.last_donation_date: + days_since_last_donation = (timezone.now().date() - donor_profile.last_donation_date).days + if days_since_last_donation < 90: + remaining_days = 90 - days_since_last_donation + messages.error(request, f"For your safety, you must wait 3 months (90 days) between donations. You can volunteer again in {remaining_days} days.") + return redirect('blood_request_list') + # Prevent requester from volunteering for their own request if blood_request.user == request.user: messages.error(request, "You cannot volunteer for your own blood request.") @@ -642,6 +698,11 @@ def complete_donation(request, event_id): event.is_completed = True event.save() + # Update donor's last donation date + if event.donor: + event.donor.last_donation_date = timezone.now().date() + event.donor.save() + # Award Badges Logic donor_profile = event.donor_user.profile completed_count = DonationEvent.objects.filter(donor_user=event.donor_user, is_completed=True).count() @@ -652,7 +713,7 @@ def complete_donation(request, event_id): donor_profile.badges.add(badge) if completed_count >= 5: - badge = Badge.objects.filter(name='Community Hero').first() + badge = Badge.objects.filter(name='Community Champion').first() if badge: donor_profile.badges.add(badge)
HeroChampion Impact Location Date