Add documentation for the new user-specific appointment statistics endpoint to the API root view. This endpoint provides authenticated users with their appointment analytics including total requests, pending reviews, scheduled, rejected, and completed appointments along with completion rate. The endpoint is available at /api/meetings/user/appointments/stats/ and requires authentication via GET request.
430 lines
20 KiB
Python
430 lines
20 KiB
Python
from rest_framework.decorators import api_view, permission_classes
|
|
from rest_framework.response import Response
|
|
from rest_framework.permissions import AllowAny
|
|
|
|
@api_view(['GET'])
|
|
@permission_classes([AllowAny])
|
|
def api_root(request, format=None):
|
|
base_url = request.build_absolute_uri('/api/')
|
|
|
|
endpoints = {
|
|
'authentication': {
|
|
'description': 'User authentication and management endpoints',
|
|
'base_path': '/api/auth/',
|
|
'endpoints': {
|
|
'register': {
|
|
'description': 'Register a new user and send verification OTP',
|
|
'url': request.build_absolute_uri('/api/auth/register/'),
|
|
'methods': ['POST'],
|
|
'required_fields': ['email', 'first_name', 'last_name', 'password', 'password2'],
|
|
'example_request': {
|
|
'email': 'user@example.com',
|
|
'first_name': 'John',
|
|
'last_name': 'Doe',
|
|
'phone_number': '+1234567890',
|
|
'password': 'SecurePassword123',
|
|
'password2': 'SecurePassword123'
|
|
}
|
|
},
|
|
'verify_otp': {
|
|
'description': 'Verify email address using OTP',
|
|
'url': request.build_absolute_uri('/api/auth/verify-otp/'),
|
|
'methods': ['POST'],
|
|
'required_fields': ['email', 'otp'],
|
|
'example_request': {
|
|
'email': 'user@example.com',
|
|
'otp': '123456'
|
|
}
|
|
},
|
|
'login': {
|
|
'description': 'Authenticate user and return JWT tokens',
|
|
'url': request.build_absolute_uri('/api/auth/login/'),
|
|
'methods': ['POST'],
|
|
'required_fields': ['email', 'password'],
|
|
'example_request': {
|
|
'email': 'user@example.com',
|
|
'password': 'SecurePassword123'
|
|
}
|
|
},
|
|
'resend_otp': {
|
|
'description': 'Resend OTP for email verification or password reset',
|
|
'url': request.build_absolute_uri('/api/auth/resend-otp/'),
|
|
'methods': ['POST'],
|
|
'required_fields': ['email'],
|
|
'optional_fields': ['context (registration/password_reset)'],
|
|
'example_request': {
|
|
'email': 'user@example.com',
|
|
'context': 'registration'
|
|
}
|
|
},
|
|
'forgot_password': {
|
|
'description': 'Initiate password reset process',
|
|
'url': request.build_absolute_uri('/api/auth/forgot-password/'),
|
|
'methods': ['POST'],
|
|
'required_fields': ['email'],
|
|
'example_request': {
|
|
'email': 'user@example.com'
|
|
}
|
|
},
|
|
'verify_password_reset_otp': {
|
|
'description': 'Verify OTP for password reset',
|
|
'url': request.build_absolute_uri('/api/auth/verify-password-reset-otp/'),
|
|
'methods': ['POST'],
|
|
'required_fields': ['email', 'otp'],
|
|
'example_request': {
|
|
'email': 'user@example.com',
|
|
'otp': '123456'
|
|
}
|
|
},
|
|
'reset_password': {
|
|
'description': 'Reset password after OTP verification',
|
|
'url': request.build_absolute_uri('/api/auth/reset-password/'),
|
|
'methods': ['POST'],
|
|
'required_fields': ['email', 'otp', 'new_password', 'confirm_password'],
|
|
'example_request': {
|
|
'email': 'user@example.com',
|
|
'otp': '123456',
|
|
'new_password': 'NewSecurePassword123',
|
|
'confirm_password': 'NewSecurePassword123'
|
|
}
|
|
},
|
|
'token_refresh': {
|
|
'description': 'Refresh access token using refresh token',
|
|
'url': request.build_absolute_uri('/api/auth/token/refresh/'),
|
|
'methods': ['POST'],
|
|
'required_fields': ['refresh'],
|
|
'example_request': {
|
|
'refresh': 'your_refresh_token_here'
|
|
}
|
|
},
|
|
"update_profile": {
|
|
"description": "Update user profile (Authenticated users only)",
|
|
"url": request.build_absolute_uri("/api/auth/profile/update/"),
|
|
"methods": ["PATCH"],
|
|
"authentication": "Required (Authenticated users only)",
|
|
"required_fields": ["first_name", "last_name", "phone_number"],
|
|
"example_request": {
|
|
"first_name": "John",
|
|
"last_name": "Doe",
|
|
"phone_number": "+1234567890"
|
|
}
|
|
},
|
|
"get_profile": {
|
|
"description": "Get user profile (Authenticated users only)",
|
|
"url": request.build_absolute_uri("/api/auth/profile/"),
|
|
"methods": ["GET"],
|
|
"authentication": "Required (Authenticated users only)",
|
|
"response_fields": {
|
|
"user": "User object"
|
|
}
|
|
},
|
|
"all-users": {
|
|
"description": "Get all users (Admin only)",
|
|
"url": request.build_absolute_uri("/api/auth/all-users/"),
|
|
"methods": ["GET"],
|
|
"authentication": "Required (Admin users only)",
|
|
"response_fields": {
|
|
"users": "List of user objects"
|
|
}
|
|
},
|
|
"activate-deactivate-user": {
|
|
"description": "Activate or deactivate a user (Admin only)",
|
|
"url": request.build_absolute_uri("/api/auth/activate-deactivate-user/<uuid:pk>/"),
|
|
"methods": ["GET"],
|
|
"authentication": "Required (Admin users only)",
|
|
"response_fields": {
|
|
"user": "User object"
|
|
}
|
|
},
|
|
"delete-user": {
|
|
"description": "Delete a user (Admin only)",
|
|
"url": request.build_absolute_uri("/api/auth/delete-user/<uuid:pk>/"),
|
|
"methods": ["GET"],
|
|
"authentication": "Required (Admin users only)",
|
|
"response_fields": {
|
|
"user": "User object"
|
|
}
|
|
}
|
|
}
|
|
},
|
|
"appointments": {
|
|
"description": "Appointment request and management system with Jitsi video meetings",
|
|
"base_path": "/api/meetings/",
|
|
"endpoints": {
|
|
"admin_availability": {
|
|
"description": "Get or update admin weekly availability (Admin only)",
|
|
"url": request.build_absolute_uri("/api/meetings/admin/availability/"),
|
|
"methods": ["GET", "PUT", "PATCH"],
|
|
"authentication": "Required (Staff users only)",
|
|
"response_fields": {
|
|
"available_days": "List of weekday numbers (0-6) when appointments are accepted",
|
|
"available_days_display": "Human-readable day names"
|
|
},
|
|
"example_request": {
|
|
"available_days": [0, 1, 2, 3, 4]
|
|
}
|
|
},
|
|
"available_dates": {
|
|
"description": "Get available appointment dates for the next 30 days (Public)",
|
|
"url": request.build_absolute_uri("/api/meetings/appointments/available-dates/"),
|
|
"methods": ["GET"],
|
|
"authentication": "None required",
|
|
"response": "List of available dates in YYYY-MM-DD format"
|
|
},
|
|
"create_appointment": {
|
|
"description": "Create a new appointment request (Public)",
|
|
"url": request.build_absolute_uri("/api/meetings/appointments/create/"),
|
|
"methods": ["POST"],
|
|
"authentication": "Required (User only)",
|
|
"required_fields": [
|
|
"first_name", "last_name", "email",
|
|
"preferred_dates", "preferred_time_slots"
|
|
],
|
|
"optional_fields": ["phone", "reason"],
|
|
"example_request": {
|
|
"first_name": "John",
|
|
"last_name": "Doe",
|
|
"email": "john@example.com",
|
|
"phone": "+1234567890",
|
|
"reason": "Initial consultation for anxiety",
|
|
"preferred_dates": ["2024-01-15", "2024-01-16"],
|
|
"preferred_time_slots": ["morning", "afternoon"]
|
|
},
|
|
"validation": "Preferred dates must be within admin available days"
|
|
},
|
|
"list_appointments": {
|
|
"description": "List appointment requests (Admin sees all, users see their own)",
|
|
"url": request.build_absolute_uri("/api/meetings/appointments/"),
|
|
"methods": ["GET"],
|
|
"authentication": "Required",
|
|
"query_parameters": {
|
|
"email": "For non-authenticated user lookup (simplified approach)"
|
|
},
|
|
"response_fields": {
|
|
"jitsi_meet_url": "Jitsi meeting URL (only for scheduled appointments)",
|
|
"jitsi_room_id": "Jitsi room ID",
|
|
"has_jitsi_meeting": "Boolean indicating if meeting is created",
|
|
"can_join_meeting": "Boolean indicating if meeting can be joined now",
|
|
"meeting_status": "Current meeting status"
|
|
}
|
|
},
|
|
"appointment_detail": {
|
|
"description": "Get detailed information about a specific appointment",
|
|
"url": request.build_absolute_uri("/api/meetings/appointments/<uuid:pk>/"),
|
|
"methods": ["GET"],
|
|
"authentication": "Required",
|
|
"url_parameter": "pk (UUID of the appointment)",
|
|
"response_includes": "Jitsi meeting information for scheduled appointments"
|
|
},
|
|
"user_appointments": {
|
|
"description": "Get appointments for the authenticated user",
|
|
"url": request.build_absolute_uri("/api/meetings/user/appointments/"),
|
|
"methods": ["GET"],
|
|
"authentication": "Required",
|
|
"response": "List of user's appointment requests with Jitsi meeting details"
|
|
},
|
|
"schedule_appointment": {
|
|
"description": "Schedule an appointment and automatically create Jitsi meeting (Admin only)",
|
|
"url": request.build_absolute_uri("/api/meetings/appointments/<uuid:pk>/schedule/"),
|
|
"methods": ["POST"],
|
|
"authentication": "Required (Staff users only)",
|
|
"required_fields": ["scheduled_datetime"],
|
|
"optional_fields": ["scheduled_duration"],
|
|
"prerequisites": "Appointment must be in 'pending_review' status",
|
|
"example_request": {
|
|
"scheduled_datetime": "2024-01-15T10:00:00Z",
|
|
"scheduled_duration": 60
|
|
},
|
|
"side_effects": [
|
|
"Updates status to 'scheduled'",
|
|
"Automatically generates Jitsi meeting room",
|
|
"Creates unique Jitsi room ID and URL",
|
|
"Sends confirmation email to user with meeting link",
|
|
"Clears rejection reason if any"
|
|
],
|
|
"response_includes": {
|
|
"jitsi_meet_url": "Generated Jitsi meeting URL",
|
|
"jitsi_room_id": "Unique Jitsi room ID",
|
|
"has_jitsi_meeting": "true"
|
|
}
|
|
},
|
|
"reject_appointment": {
|
|
"description": "Reject an appointment request (Admin only)",
|
|
"url": request.build_absolute_uri("/api/meetings/appointments/<uuid:pk>/reject/"),
|
|
"methods": ["POST"],
|
|
"authentication": "Required (Staff users only)",
|
|
"optional_fields": ["rejection_reason"],
|
|
"prerequisites": "Appointment must be in 'pending_review' status",
|
|
"example_request": {
|
|
"rejection_reason": "No availability for preferred dates"
|
|
},
|
|
"side_effects": [
|
|
"Updates status to 'rejected'",
|
|
"Clears Jitsi meeting information",
|
|
"Sends rejection email to user",
|
|
"Clears scheduled datetime if any"
|
|
]
|
|
},
|
|
"jitsi_meeting_info": {
|
|
"description": "Get Jitsi meeting information for a scheduled appointment",
|
|
"url": request.build_absolute_uri("/api/meetings/appointments/<uuid:pk>/jitsi-meeting/"),
|
|
"methods": ["GET"],
|
|
"authentication": "Required",
|
|
"prerequisites": "Appointment must be in 'scheduled' status",
|
|
"response_fields": {
|
|
"meeting_url": "Jitsi meeting URL",
|
|
"room_id": "Jitsi room ID",
|
|
"scheduled_time": "Formatted scheduled datetime",
|
|
"duration": "Meeting duration display",
|
|
"can_join": "Boolean indicating if meeting can be joined now",
|
|
"meeting_status": "Current meeting status",
|
|
"join_instructions": "Instructions for joining the meeting"
|
|
}
|
|
},
|
|
"appointment_stats": {
|
|
"description": "Get appointment statistics and analytics (Admin only)",
|
|
"url": request.build_absolute_uri("/api/meetings/appointments/stats/"),
|
|
"methods": ["GET"],
|
|
"authentication": "Required (Staff users only)",
|
|
"response_fields": {
|
|
"total_requests": "Total number of appointment requests",
|
|
"pending_review": "Number of pending review requests",
|
|
"scheduled": "Number of scheduled appointments",
|
|
"rejected": "Number of rejected requests",
|
|
"completion_rate": "Percentage of requests that were scheduled"
|
|
}
|
|
},
|
|
"user_appointment_stats": {
|
|
"description": "Get appointment statistics and analytics for the authenticated user",
|
|
"url": request.build_absolute_uri("/api/meetings/user/appointments/stats/"),
|
|
"methods": ["GET"],
|
|
"authentication": "Required",
|
|
"response_fields": {
|
|
"total_requests": "Total number of appointment requests",
|
|
"pending_review": "Number of pending review requests",
|
|
"scheduled": "Number of scheduled appointments",
|
|
"rejected": "Number of rejected requests",
|
|
"completed": "Number of completed appointments",
|
|
"completion_rate": "Percentage of requests that were scheduled"
|
|
}
|
|
},
|
|
|
|
},
|
|
"jitsi_integration": {
|
|
"description": "Automatic Jitsi video meeting integration",
|
|
"features": [
|
|
"Automatic meeting room generation when appointment is scheduled",
|
|
"Unique room IDs for each therapy session",
|
|
"No setup required for clients - just click and join",
|
|
"Meeting availability based on scheduled time",
|
|
"Secure, encrypted video sessions"
|
|
],
|
|
"meeting_lifecycle": {
|
|
"pending": "No Jitsi meeting created",
|
|
"scheduled": "Jitsi meeting automatically generated with unique URL",
|
|
"active": "Meeting can be joined 10 minutes before scheduled time",
|
|
"completed": "Meeting ends 15 minutes after scheduled duration"
|
|
},
|
|
"join_conditions": [
|
|
"Appointment must be in 'scheduled' status",
|
|
"Current time must be within 10 minutes before to 15 minutes after scheduled end",
|
|
"Both client and therapist can join using the same URL"
|
|
]
|
|
}
|
|
}
|
|
}
|
|
|
|
return Response({
|
|
'message': 'Therapy Appointment API',
|
|
'version': '1.0.0',
|
|
'base_url': base_url,
|
|
'project_structure': {
|
|
'admin': '/admin/ - Django admin interface',
|
|
'authentication': '/api/auth/ - User authentication and management',
|
|
'appointments': '/api/meetings/ - Appointment booking system'
|
|
},
|
|
'endpoints': endpoints,
|
|
|
|
'appointment_workflows': {
|
|
'client_booking_flow': [
|
|
'1. GET /api/meetings/appointments/available-dates/ - Check available dates',
|
|
'2. POST /api/meetings/appointments/create/ - Submit appointment request',
|
|
'3. GET /api/meetings/user/appointments/ - Track request status',
|
|
'4. Receive email notification when scheduled/rejected'
|
|
],
|
|
'admin_management_flow': [
|
|
'1. PUT /api/meetings/admin/availability/ - Set weekly availability',
|
|
'2. GET /api/meetings/appointments/ - Review pending requests',
|
|
'3. POST /api/meetings/appointments/{id}/schedule/ - Schedule appointment OR',
|
|
'4. POST /api/meetings/appointments/{id}/reject/ - Reject with reason',
|
|
'5. GET /api/meetings/appointments/stats/ - Monitor performance'
|
|
],
|
|
'status_lifecycle': [
|
|
'pending_review → scheduled (with datetime)',
|
|
'pending_review → rejected (with optional reason)'
|
|
]
|
|
},
|
|
|
|
'authentication_flows': {
|
|
'registration_flow': [
|
|
'1. POST /api/auth/register/ - Register user and send OTP',
|
|
'2. POST /api/auth/verify-otp/ - Verify email with OTP',
|
|
'3. POST /api/auth/login/ - Login with credentials'
|
|
],
|
|
'password_reset_flow': [
|
|
'1. POST /api/auth/forgot-password/ - Request password reset OTP',
|
|
'2. POST /api/auth/verify-password-reset-otp/ - Verify OTP',
|
|
'3. POST /api/auth/reset-password/ - Set new password'
|
|
]
|
|
},
|
|
|
|
'quick_start': {
|
|
'for_users': [
|
|
'1. Register: POST /api/auth/register/',
|
|
'2. Verify email: POST /api/auth/verify-otp/',
|
|
'3. Login: POST /api/auth/login/',
|
|
'4. Check availability: GET /api/meetings/appointments/available-dates/',
|
|
'5. Book appointment: POST /api/meetings/appointments/create/'
|
|
],
|
|
'for_admins': [
|
|
'1. Login to Django admin: /admin/',
|
|
'2. Set availability: PUT /api/meetings/admin/availability/',
|
|
'3. Manage appointments: GET /api/meetings/appointments/',
|
|
'4. Schedule/Reject: Use specific appointment endpoints'
|
|
]
|
|
},
|
|
|
|
'data_specifications': {
|
|
'appointment': {
|
|
'status_choices': [
|
|
'pending_review - Initial state, awaiting admin action',
|
|
'scheduled - Approved with specific date/time',
|
|
'rejected - Not accepted, with optional reason'
|
|
],
|
|
'time_slot_choices': [
|
|
'morning - 9AM to 12PM',
|
|
'afternoon - 1PM to 5PM',
|
|
'evening - 6PM to 9PM'
|
|
],
|
|
'preferred_dates_format': 'YYYY-MM-DD (array of strings)',
|
|
'encrypted_fields': [
|
|
'first_name', 'last_name', 'email', 'phone',
|
|
'reason', 'rejection_reason'
|
|
]
|
|
},
|
|
'availability': {
|
|
'day_format': '0=Monday, 1=Tuesday, ..., 6=Sunday',
|
|
'example': '[0, 1, 2, 3, 4] for Monday-Friday'
|
|
}
|
|
},
|
|
|
|
'authentication_notes': {
|
|
'token_usage': 'Include JWT token in Authorization header: Bearer <token>',
|
|
'token_refresh': 'Use refresh token to get new access token when expired',
|
|
'permissions': {
|
|
'public_endpoints': 'No authentication required',
|
|
'user_endpoints': 'Valid JWT token required',
|
|
'admin_endpoints': 'Staff user with valid JWT token required'
|
|
}
|
|
}
|
|
}) |