Skip to content

Commit c599a5f

Browse files
committed
feat: Implementación del panel de administración (Dashboard)
Se ha implementado un completo panel de administración con las siguientes características: Archivos añadidos: - Templates HTML: * dashboard_base.html: Estructura base del panel con navegación lateral * msg_stats.html: Estadísticas detalladas de mensajes * report_stats.html: Visualización y gestión de reportes de usuarios * ride_management.html: CRUD de viajes con filtrado avanzado * trip_stats.html: Análisis de viajes con gráficos * user_management.html: Gestión de usuarios (ver, eliminar) * user_stats.html: Métricas de usuarios registrados - Archivos CSS: * dashboard.css: Estilos específicos para el panel principal * dashboard_shared.css: Sistema de componentes y variables compartidas - Archivos JavaScript: * dashboard.js: Funcionalidad general del panel * msg_stats.js: Generación de gráficos para estadísticas de mensajes - Python: * urls.py: Configuración de rutas para el panel y APIs * views.py: Controladores para generar los datos del panel - Scripts: * generate_demo_data.sh: Generación de datos de prueba para demostración El panel permite: - Visualizar métricas de la plataforma con gráficos interactivos - Gestionar viajes (filtrar, buscar, eliminar) - Analizar mensajes entre usuarios - Gestionar reportes de usuarios - Administrar usuarios - Visualizar datos por diferentes periodos (hoy, semana, mes, año, todo) También añadido/modificado: - Funciones de interfaz pública añadidas a las aplicaciones existentes: * chat.public: delete_chat(), get_messages_for_chat(), get_messages_count(), get_messages_in_period(), get_all_chats_with_stats(), filter_chats_by_criteria(), get_chat_stats() * accounts.public: get_active_users(), delete_user(), get_user_count(), get_users_in_period(), filter_users_by_criteria(), get_recently_registered_users() * rides.public: get_rides_published_in_period(), delete_ride(), get_active_rides_today(), get_seats_available(), get_ride_stats(), filter_rides_by_criteria(), get_Termporal_ride_data(), get_popular_locations(), get_basic_ride_data() get ride_stats_for_dashboard(), get_completed_rides), get_recently_publissed_rides, get_Active_Rides_today() * reports.public: get_report_by_id(), update_report_status() * payments.public: get_recent_payments(), get_payments_Stats(), get_payments_in_period(), get_recent_payments() - Utilidades del panel de control: * Utils.py: Funciones de ayuda para el tratamiento de datos, la generación de gráficos y la preparación del contexto * constants.py: Constantes para rutas de plantillas, claves de contexto y nombres de URL.
1 parent 5e9f4c0 commit c599a5f

83 files changed

Lines changed: 7992 additions & 31 deletions

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

README.md

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -117,6 +117,43 @@ Para ejecutar un método de test específico:
117117
python manage.py test nombre_app.tests.test_module.NombreClaseTest.test_metodo
118118
```
119119

120+
# Generador de Datos de Prueba para CharlaCar
121+
122+
Este comando de gestión de Django genera datos de prueba aleatorios.
123+
## Uso
124+
125+
Para generar datos de prueba, ejecute:
126+
127+
```bash
128+
python manage.py generate_test_data
129+
```
130+
131+
### Opciones disponibles
132+
133+
- `--users NUMBER`: Número de usuarios a crear (por defecto: 20)
134+
- `--rides NUMBER`: Número de viajes a crear (por defecto: 50)
135+
- `--chats NUMBER`: Número de chats a crear (por defecto: 30)
136+
- `--messages NUMBER`: Número de mensajes a crear (por defecto: 200)
137+
- `--reports NUMBER`: Número de reportes a crear (por defecto: 25)
138+
- `--payments NUMBER`: Número de pagos a crear (por defecto: 40)
139+
- `--clean`: Elimina todos los datos existentes antes de generar nuevos datos
140+
141+
### Ejemplos
142+
143+
Generar datos con los valores predeterminados:
144+
```bash
145+
python manage.py generate_test_data
146+
```
147+
148+
Generar un conjunto más grande de datos:
149+
```bash
150+
python manage.py generate_test_data --users 100 --rides 200 --messages 1000
151+
```
152+
153+
Limpiar la base de datos y generar un pequeño conjunto de datos:
154+
```bash
155+
python manage.py generate_test_data --clean --users 10 --rides 20
156+
```
120157

121158
## Estructura del proyecto
122159

codigo/accounts/__init__.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
# ==========================================
2+
# Autor: Alejandro Gasca Mediel
3+
# ==========================================

codigo/accounts/_utils.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,6 @@
1+
# ==========================================
2+
# Autor: Alejandro Gasca Mediel
3+
# ==========================================
14
"""
25
Funciones de utilidad interna para la aplicación de cuentas (accounts).
36
"""

codigo/accounts/admin.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,6 @@
1+
# ==========================================
2+
# Autor: Alejandro Gasca Mediel
3+
# ==========================================
14
from django.contrib import admin
25
from .models import UserProfile
36
from django.contrib.auth.models import User

codigo/accounts/apps.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,6 @@
1+
# ==========================================
2+
# Autor: Alejandro Gasca Mediel
3+
# ==========================================
14
from django.apps import AppConfig
25

36

codigo/accounts/constants.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,6 @@
1+
# ==========================================
2+
# Autor: Alejandro Gasca Mediel
3+
# ==========================================
14
# Descripción: Constantes utilizadas en la aplicación de cuentas de usuario.
25
# Tipos de configuraciones
36
ACCOUNT_SETTINGS = 'account'

codigo/accounts/forms.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,6 @@
1+
# ==========================================
2+
# Autor: Alejandro Gasca Mediel
3+
# ==========================================
14
from django import forms
25
from django.contrib.auth.forms import UserCreationForm
36
from django.contrib.auth.models import User

codigo/accounts/models.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,6 @@
1+
# ==========================================
2+
# Autor: Alejandro Gasca Mediel
3+
# ==========================================
14
from django.db import models
25
from django.contrib.auth.models import User
36
from django.utils import timezone

codigo/accounts/public.py

Lines changed: 109 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,12 @@
1+
# ==========================================
2+
# Autor: Alejandro Gasca Mediel
3+
# ==========================================
14
"""
25
API pública de la aplicación de cuentas (accounts).
36
"""
47
from django.contrib.auth.models import User
58
from django.utils import timezone
6-
from datetime import date
9+
from datetime import date, timedelta
710

811
from .models import UserProfile
912
from .constants import (
@@ -23,6 +26,49 @@ def get_user_profile(user):
2326
return profile
2427

2528

29+
def get_user_count():
30+
"""
31+
Obtiene el número total de usuarios en el sistema.
32+
"""
33+
return User.objects.count()
34+
35+
36+
def get_users_in_period(start_date=None, end_date=None):
37+
"""
38+
Obtiene los usuarios registrados en un período específico.
39+
"""
40+
users = User.objects.all()
41+
42+
if start_date:
43+
users = users.filter(date_joined__date__gte=start_date)
44+
45+
if end_date:
46+
users = users.filter(date_joined__date__lte=end_date)
47+
48+
return users
49+
50+
51+
def get_active_users(minutes=30):
52+
"""
53+
Obtiene los usuarios que han estado activos en los últimos minutos especificados.
54+
"""
55+
threshold_time = timezone.now() - timedelta(minutes=minutes)
56+
active_profiles = UserProfile.objects.filter(last_active__gte=threshold_time)
57+
user_ids = active_profiles.values_list('user_id', flat=True)
58+
59+
return User.objects.filter(id__in=user_ids)
60+
61+
62+
def get_recently_registered_users(days=7, limit=5):
63+
"""
64+
Obtiene los usuarios registrados recientemente.
65+
"""
66+
recent_date = timezone.now() - timedelta(days=days)
67+
return User.objects.filter(
68+
date_joined__gte=recent_date
69+
).order_by('-date_joined')[:limit]
70+
71+
2672
def get_user_by_username(username):
2773
"""
2874
Busca un usuario por su nombre de usuario.
@@ -153,7 +199,7 @@ def profile_is_visible(user):
153199
profile = get_user_profile(user)
154200
return profile.profile_visible
155201

156-
#TODO HAY Q EVITAR DUPLICIDAD ENTRE PUBLIC Y PRIVATE
202+
157203
def update_last_activity(user):
158204
"""
159205
Actualiza la marca de tiempo de última actividad del usuario.
@@ -162,6 +208,7 @@ def update_last_activity(user):
162208
profile.last_active = timezone.now()
163209
profile.save(update_fields=[LAST_ACTIVE_FIELD])
164210

211+
165212
def update_notification_preference(user, notification_type, value):
166213
"""
167214
Actualiza una preferencia de notificación específica.
@@ -178,4 +225,63 @@ def update_notification_preference(user, notification_type, value):
178225
return False
179226

180227
profile.save(update_fields=[f'{notification_type}_notifications'])
181-
return True
228+
return True
229+
230+
231+
def delete_user(user_id):
232+
"""
233+
Elimina un usuario por su ID.
234+
"""
235+
try:
236+
user = User.objects.get(id=user_id)
237+
user.delete()
238+
return True
239+
except User.DoesNotExist:
240+
return False
241+
242+
243+
def filter_users_by_criteria(search='', status='all', from_date='', to_date=''):
244+
"""
245+
Filtra usuarios según múltiples criterios para el panel de administración.
246+
"""
247+
from django.db.models import Q
248+
import datetime
249+
250+
users = User.objects.all().order_by('-date_joined')
251+
252+
if search:
253+
users = users.filter(
254+
Q(username__icontains=search) |
255+
Q(email__icontains=search) |
256+
Q(first_name__icontains=search) |
257+
Q(last_name__icontains=search)
258+
)
259+
260+
if status == 'active':
261+
active_threshold = timezone.now() - timedelta(minutes=30)
262+
user_ids = UserProfile.objects.filter(last_active__gte=active_threshold).values_list('user_id', flat=True)
263+
users = users.filter(id__in=user_ids)
264+
elif status == 'inactive':
265+
active_threshold = timezone.now() - timedelta(minutes=30)
266+
user_ids = UserProfile.objects.filter(
267+
Q(last_active__lt=active_threshold) | Q(last_active__isnull=True)
268+
).values_list('user_id', flat=True)
269+
users = users.filter(id__in=user_ids)
270+
elif status == 'staff':
271+
users = users.filter(is_staff=True)
272+
273+
if from_date:
274+
try:
275+
from_date_obj = datetime.datetime.strptime(from_date, '%Y-%m-%d').date()
276+
users = users.filter(date_joined__date__gte=from_date_obj)
277+
except ValueError:
278+
pass
279+
280+
if to_date:
281+
try:
282+
to_date_obj = datetime.datetime.strptime(to_date, '%Y-%m-%d').date()
283+
users = users.filter(date_joined__date__lte=to_date_obj)
284+
except ValueError:
285+
pass
286+
287+
return users

codigo/accounts/tests/__init__.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
# ==========================================
2+
# Autor: Alejandro Gasca Mediel
3+
# ==========================================

0 commit comments

Comments
 (0)