from email import message
from django.shortcuts import render
from rest_framework.views import APIView
from rest_framework.response import Response
from rest_framework import status
from .models import *
from datetime import datetime, timedelta, date
from django.conf import settings
from .authentication import authenticated
from django.contrib.auth.models import User
from rest_framework_simplejwt.tokens import RefreshToken
from passlib.hash import django_pbkdf2_sha256 as handler
from django.template.loader import render_to_string
from django.core import mail
from django.core.mail import EmailMultiAlternatives
import math, random, pytz, string
from django.contrib import messages
import jwt
from django.core.files.storage import FileSystemStorage
import os
import ast
from django.db.models import Q 
from pyfcm import FCMNotification
from .serializers import *
from django.views.generic import TemplateView
from admin_panel.models import ContentManagement,OnBoardingData,AdminNotifications,Exercisetimer
from trainer.models import *
from trainer.serializers import *
from .functions import *
from django.utils.timesince import timesince
from twilio.rest import Client
from django.conf import settings
import json
from twilio.jwt.access_token.grants import (
	SyncGrant,
	ChatGrant,
	VideoGrant
)
from twilio.rest import Client
from twilio.jwt.access_token import AccessToken
import stripe
from firebase_admin import messaging
from decouple import config
from django.utils import timezone
from datetime import timedelta
# Create your views here.
import ast
stripe.api_key = config('STRIPE_API_KEY')

account_sid= settings.TWILIO_ACCOUNT_SID
auth_token = settings.TWILIO_AUTH_TOKEN
chat_service_sid = settings.TWILIO_CHAT_SID
sync_service_sid = settings.TWILIO_SYNC_SID
api_sid = settings.TWILIO_API_SID
api_secret= settings.TWILIO_API_SECRET
client = Client(account_sid, auth_token)
def send_push_notification(registration_id, title, body):
	message = messaging.Message(
		notification=messaging.Notification(
			title=title,
			body=body
		),
		token=registration_id  # Specify the registration token here
	)
	response = messaging.send(message)
	return response
# Create your views here.
def generateTranscationsId():
	lastObj= UserTranscations.objects.all().last()
	if lastObj:
		if not lastObj.transcation_id:
			return 'TRANS000001'

		theId=lastObj.transcation_id
		theId=theId[5:]
		theId=int(theId)+1
		theId=str(theId)
		theId=theId.zfill(5)
		return "TRANS"+str(theId)
	else:
		return 'TRANS000001'

class Register(APIView):
	def post(self, request):
		try:
			data = request.data
			full_name = data.get('full_name')
			email = data.get('email')
			email=email.lower()
			password = data.get('password')
			address=data.get('address')
			latitude=data.get('latitude')
			longitude = data.get('longitude')


			# Input validation
			if not email or not full_name or not password:
				return Response({"message": 'All required fields must be provided'}, status=status.HTTP_400_BAD_REQUEST)

			# Password hashing
			new_password = handler.hash(password)

			# Check if the email is already registered
			app_user_obj = AppUser.objects.filter(email=email,end_date__isnull=True).first()
			if app_user_obj:
				return Response({"message": "The email is already registered"}, status=status.HTTP_409_CONFLICT)
			else:
				the_otp=random.randrange(1000, 9999, 5)
				app_user_obj = AppUser.objects.create(
					full_name=full_name,
					email=email,
					password=new_password,
					otp=the_otp,
					address=address,
					latitude=latitude,
					longitude=longitude,
				)

				# AppUserNotifications.objects.create(message="You have received your referral bonus successfully", notification_type="referral_bonus", app_user=app_user_obj)

				# Email verification
				app_user_obj.otp = the_otp
				app_user_obj.save()
				subject = "Verify Account"
				html_message = render_to_string('email_verification.html', {'otp': the_otp})
				plain_message = html_message
				from_email = settings.EMAIL_HOST_USER
				print(from_email)
				to = email
				# mail.send_mail(subject, plain_message, from_email, [to], html_message=html_message)

				try:
					mail.send_mail(subject, plain_message, from_email, [to], html_message=html_message)
				except Exception as email_error:
					print(email_error)
					return Response({"message": "Your account has been created, but we encountered an issue sending the verification email. Please contact support for assistance."}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

				# Admin notification
				# AdminNotifications.objects.create(message=full_name + ' has been successfully registered with us.', type='app_user_register')

			return Response({"message": 'You have been successfully registered with us. Please verify your email.'})
		except Exception as e:
			return Response({"message": str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class UserResendEmailOtp(APIView):
	def post(self, request):
		try:
			data = request.data
			email = data.get('email')
			email=email.lower()


			# Input validation
			if not email:
				return Response({"message": 'All required fields must be provided'}, status=status.HTTP_400_BAD_REQUEST)

			# Password hashing
			# Check if the email is already registered
			app_user_obj = AppUser.objects.filter(email=email).last()
			if not app_user_obj:
				return Response({"message": "Email not found"}, status=status.HTTP_409_CONFLICT)
			else:
				the_otp=random.randrange(1000, 9999, 5)
				app_user_obj.otp = the_otp
				app_user_obj.save()

				# AppUserNotifications.objects.create(message="You have received your referral bonus successfully", notification_type="referral_bonus", app_user=app_user_obj)

				# Email verificatio)
				subject = "Verify Account"
				html_message = render_to_string('email_verification.html', {'otp': the_otp})
				plain_message = html_message
				from_email = settings.EMAIL_HOST_USER
				to = email
				# mail.send_mail(subject, plain_message, from_email, [to], html_message=html_message)

				try:
					mail.send_mail(subject, plain_message, from_email, [to], html_message=html_message)
				except Exception as email_error:
					return Response({"message": "Your account has been created, but we encountered an issue sending the verification email. Please contact support for assistance."}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

				# Admin notification
				# AdminNotifications.objects.create(message=full_name + ' has been successfully registered with us.', type='app_user_register')

			return Response({"message": 'You have been successfully registered with us. Please verify your email.'})
		except Exception as e:
			return Response({"message": str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class SocialLogin(APIView):
	def post(self, request):
		try:
			print("in social")
			data = request.data
			provider_id = data.get('provider_id')
			email = data.get('email')
			full_name = data.get('full_name')
			# social_id = data.get('social_id')
			device_type = data.get('device_type')
			fcm_token = data.get('fcm_token')
			print(fcm_token)

			if not provider_id :
				return Response({'message': 'provider_id is required.'}, status=status.HTTP_400_BAD_REQUEST)
			if not full_name:
				return Response({'message': 'full_name is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not email:
				return Response({'message': 'email is required'}, status=status.HTTP_400_BAD_REQUEST)
			# if not social_id:
			# 	return Response({'message': 'social_id is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not device_type:
				return Response({'message': 'device_type is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not fcm_token:
				return Response({'message': 'fcm_token is required'}, status=status.HTTP_400_BAD_REQUEST)

			# Check if social account already exists in the database
			app_user_obj = AppUser.objects.filter(provider_id=provider_id,end_date__isnull=True).first()
			if not app_user_obj:
				# If social account not found, create a new one
				app_user_obj = AppUser.objects.create(full_name=full_name,
					  provider_id=provider_id,email=email,device_type=device_type,fcm_token=fcm_token)

			# Issue tokens (refresh token and access token) for the authenticated user
			refresh_token = RefreshToken.for_user(app_user_obj)

			allData={'id':app_user_obj.id,
					'full_name':app_user_obj.full_name,
					'email':app_user_obj.email,
					'is_profile_completed':app_user_obj.is_profile_completed,
					'refresh': str(refresh_token),
					'access': str(refresh_token.access_token),
				   }

			return Response({'message': 'Success', 'data': allData})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)



class OtpVerification(APIView):
	def post(self,request):
		try:
			data=request.data
			email = data.get('email')
			otp = data.get('otp')
			fcm_token = data.get('fcm_token')

			if not email:
				return Response({"message":'email is required'},status=status.HTTP_400_BAD_REQUEST)
			if not otp:
				return Response({"message":'otp is required'},status=status.HTTP_400_BAD_REQUEST)
			try:
				app_user_obj = AppUser.objects.get(email=email,otp=otp)
			except Exception as e:
				return Response({"message":'Invalid otp','data':{}},status=status.HTTP_400_BAD_REQUEST)
			app_user_obj.email_verified = True
			app_user_obj.fcm_token = fcm_token
			app_user_obj.save()
			refresh_token = RefreshToken.for_user(app_user_obj)
			allData={'id':app_user_obj.id,
				'full_name':app_user_obj.full_name,
				'email':app_user_obj.email,
				'is_profile_completed':app_user_obj.is_profile_completed,
				'refresh': str(refresh_token),
				'access': str(refresh_token.access_token),
				}
			AdminNotifications.objects.create(message = "A new user "+ app_user_obj.full_name +" has been registered successfully with us.",type = "user_registered")
			return Response({"message":'Success','data':allData})
		except Exception as e:
			return Response({"message":str(e)},status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class RestoreAccount(APIView):
	def post(self, request):
		try:
			data = request.data
			
			email = data.get('email')
			email=email.lower()

			# Input validation
			if not email :
				return Response({"message": 'Email must be provided'}, status=status.HTTP_400_BAD_REQUEST)

			# Password hashing

			# Check if the email is already registered
			app_user_obj = AppUser.objects.filter(email=email,end_date__isnull=True).first()
			if app_user_obj:
				return Response({"message": "The email is already working"}, status=status.HTTP_409_CONFLICT)
			else:
				the_otp=random.randrange(1000, 9999, 5)
				app_user_obj = AppUser.objects.filter(email=email).update(
					otp=the_otp,
				)

				# AppUserNotifications.objects.create(message="You have received your referral bonus successfully", notification_type="referral_bonus", app_user=app_user_obj)

				# Email verification
				# app_user_obj.otp = the_otp
				# app_user_obj.save()
				subject = "Verify Account"
				html_message = render_to_string('email_verification.html', {'otp': the_otp})
				plain_message = html_message
				from_email = settings.EMAIL_HOST_USER
				to = email
				# mail.send_mail(subject, plain_message, from_email, [to], html_message=html_message)

				try:
					mail.send_mail(subject, plain_message, from_email, [to], html_message=html_message)
				except Exception as email_error:
					return Response({"message": "We encountered an issue sending the verification email. Please contact support for assistance."}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

				# Admin notification
				# AdminNotifications.objects.create(message=full_name + ' has been successfully registered with us.', type='app_user_register')

			return Response({"message": 'Otp sent successsfully','otp':the_otp})
		except Exception as e:
			return Response({"message": str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class RestoreAccountOtpVerification(APIView):
	def post(self,request):
		try:
			data=request.data
			email = data.get('email')
			otp = data.get('otp')

			if not email:
				return Response({"message":'email is required'},status=status.HTTP_400_BAD_REQUEST)
			if not otp:
				return Response({"message":'otp is required'},status=status.HTTP_400_BAD_REQUEST)
			try:
				app_user_obj = AppUser.objects.get(email=email,otp=otp)
			except Exception as e:
				return Response({"message":'Invalid otp','data':{}},status=status.HTTP_400_BAD_REQUEST)
			# app_user_obj.email_verified = True
			app_user_obj.end_date= None
			app_user_obj.save()
			
			AdminNotifications.objects.create(message = "The account with "+ app_user_obj.full_name +" has been restored successfully",type = "user_restored")
			return Response({"message":'Success'})
		except Exception as e:
			return Response({"message":str(e)},status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class LoginUser(APIView):
	def post(self,request):
		try:
			data = request.data
			email = data.get('email')
			email=email.lower()
			password = data.get('password')
			fcm_token = data.get('fcm_token')
			device_type = data.get('deviceType')
			if not email:
				return Response({"message":'Invalid credentials'},status=status.HTTP_400_BAD_REQUEST)
			if not password:
				return Response({"message":'Invalid credentials'},status=status.HTTP_400_BAD_REQUEST)
			user  = AppUser.objects.filter(email=email).count()
			if user == 0:
				return Response({"message":'This email does not exist in our database, please register'},status=status.HTTP_404_NOT_FOUND)
			app_user_obj  = AppUser.objects.filter(email=email,status=True,end_date__isnull=True).first()
			if not app_user_obj:
				return Response({"message":'Your account has not been activated, Please contact to admin.'},status=status.HTTP_401_UNAUTHORIZED)
			check_password = app_user_obj.password
			check = handler.verify(password,check_password)

			if check:
				if app_user_obj.email_verified == False:
					# Email verification
					the_otp=random.randrange(1000, 9999, 5)
					app_user_obj.otp = the_otp
					app_user_obj.save()
					subject = "Verify Account"
					html_message = render_to_string('email_verification.html', {'otp': the_otp})
					plain_message = html_message
					from_email = settings.EMAIL_HOST_USER
					to = email
					# mail.send_mail(subject, plain_message, from_email, [to], html_message=html_message)

					try:
						mail.send_mail(subject, plain_message, from_email, [to], html_message=html_message)
					except Exception as email_error:
						return Response({"message": "Failed to send the verification email. Please try again later."}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

					return Response({"message":'Please verify your email first'},status=status.HTTP_400_BAD_REQUEST)
				app_user_obj.fcm_token = fcm_token
				app_user_obj.device_type  =device_type
				app_user_obj.save()
				refresh_token = RefreshToken.for_user(app_user_obj)
				allData={'id':app_user_obj.id,
					'full_name':app_user_obj.full_name,
					'email':app_user_obj.email,
					'is_profile_completed':app_user_obj.is_profile_completed,
					'refresh': str(refresh_token),
					'access': str(refresh_token.access_token),
				   }
				return Response({"message":'Login Successfully','data':allData})
			else:
				return Response({"message":'Invalid password'},status=status.HTTP_401_UNAUTHORIZED)
		except Exception as e:
			return Response({"message":str(e)},status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class ForgetPassword(APIView):
	def post(self,request):
			try:
				data = request.data
				email = data.get('email')
				if not email:
					return Response({"message":'Email is required'})
				user  = AppUser.objects.filter(email=email,end_date__isnull=True).count()
				if user == 0:
					return Response({"message":'This email does not exist in our database, please enter the valid email address.'},status=status.HTTP_404_NOT_FOUND)
				app_user_obj  = AppUser.objects.filter(email=email,end_date__isnull=True).first()
				if app_user_obj:
					the_otp=random.randrange(1000, 9999, 5)
					app_user_obj.otp = the_otp
					app_user_obj.save()
					subject = 'Forgot Password'
					html_message = render_to_string('forget_password_email.html', {'otp': the_otp})
					plain_message = html_message
					from_email = settings.EMAIL_HOST_USER
					to = email
					# mail.send_mail(subject, plain_message, from_email, [to], html_message=html_message)

					try:
						mail.send_mail(subject, plain_message, from_email, [to], html_message=html_message)
					except Exception as email_error:
						return Response({"message": "Failed to send the verification email. Please try again later."}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

					return Response({"message":'Reset password otp has been sent to your email address.'})
				else:
					return Response({"message":'Email not exists'})

			except Exception as e:
				print(e)
				return Response({"message":str(e)},status=status.HTTP_500_INTERNAL_SERVER_ERROR)



class ForgetPasswordVerification(APIView):
	def post(self,request):
		try:
			data=request.data
			email = data.get('email')
			otp = data.get('otp')
			if not email:
				return Response({"message":'email is required'},status=status.HTTP_400_BAD_REQUEST)
			if not otp:
				return Response({"message":'otp is required'},status=status.HTTP_400_BAD_REQUEST)

			app_user_obj = AppUser.objects.filter(email=email,end_date__isnull=True,otp=otp).first()
			if not app_user_obj:
				return Response({"message":'Invalid otp','data':{}},status=status.HTTP_400_BAD_REQUEST)

			return Response({"message":'Success'})
		except Exception as e:
			return Response({"message":str(e)},status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class SetForgetPassword(APIView):
	def post(self,request):
		try:
			data=request.data
			email = data.get('email')
			new_password = data.get('new_password')
			otp = data.get('otp')
			if not new_password:
				return Response({"message":'new_password is required'},status=status.HTTP_400_BAD_REQUEST)
			if not email:
				return Response({"message":'email is required'},status=status.HTTP_400_BAD_REQUEST)
			if not otp:
				return Response({"message":'otp is required'},status=status.HTTP_400_BAD_REQUEST)

			app_user_obj = AppUser.objects.filter(email=email,otp=otp).first()
			encrypt_password = handler.hash(new_password)
			if app_user_obj:
				app_user_obj.password = encrypt_password
				app_user_obj.otp = None
				app_user_obj.save()
				return Response({"message":'Success'})
			else:
				return Response({"message":'Something went wrong'},status=status.HTTP_400_BAD_REQUEST)
		except Exception as e:
			return Response({"message":str(e)},status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class CompleteProfile(APIView):

	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)

			data = request.data
			full_name = data.get('full_name')
			# email = data.get('email')
			gender = data.get('gender')
			age = data.get('age')
			current_weight = data.get('current_weight')
			target_weight = data.get('target_weight')
			weight_unit = data.get('weight_unit')
			current_height = data.get('current_height')
			height_unit = data.get('height_unit')
			focus_area = data.get('focus_area')
			main_goal = data.get('main_goal')
			current_body_shape = data.get('current_body_shape')
			fitness_level = data.get('fitness_level')
			medical_condition = data.get('medical_condition')
			allergies_exclusions = data.get('allergies_exclusions')

			# check_email = AppUser.objects.filter(email=email).exclude(id=app_user_obj.id).first()
			# if check_email:
			# 	return Response({"message":"The email is already registered"},status=status.HTTP_409_CONFLICT)

			if not full_name:
				return Response({"message": 'full_name is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not gender:
				return Response({"message": 'gender is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not age:
				return Response({"message": 'age is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not current_weight:
				return Response({"message": 'current_weight is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not target_weight:
				return Response({"message": 'target_weight is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not weight_unit:
				return Response({"message": 'weight_unit is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not current_height:
				return Response({"message": 'current_height is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not height_unit:
				return Response({"message": 'height_unit is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not focus_area:
				return Response({"message": 'focus_area is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not main_goal:
				return Response({"message": 'main_goal is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not current_body_shape:
				return Response({"message": 'current_body_shape is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not fitness_level:
				return Response({"message": 'fitness_level is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not medical_condition:
				return Response({"message": 'medical_condition is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not allergies_exclusions:
				return Response({"message": 'allergies_exclusions is required'}, status=status.HTTP_400_BAD_REQUEST)

			app_user_obj.full_name = full_name
			app_user_obj.gender = gender
			app_user_obj.age = age
			app_user_obj.current_weight = current_weight
			app_user_obj.target_weight = target_weight
			app_user_obj.weight_unit = weight_unit
			app_user_obj.current_height = current_height
			app_user_obj.height_unit = height_unit
			app_user_obj.focus_area = focus_area
			app_user_obj.main_goal = main_goal
			app_user_obj.current_body_shape = current_body_shape
			app_user_obj.fitness_level = fitness_level
			app_user_obj.medical_condition = medical_condition
			app_user_obj.allergies_exclusions = allergies_exclusions
			app_user_obj.is_profile_completed = True
			app_user_obj.save()

			return Response({'message': 'Success'})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)



class GetCompleteProfileData(APIView):
	def get(self, request):
		try:
			main_goals = OnBoardingData.objects.filter(screen_type='main_goals',end_date__isnull=True)
			medical_conditions = OnBoardingData.objects.filter(screen_type='medical_conditions',end_date__isnull=True)
			allergies = OnBoardingData.objects.filter(screen_type='allergy_exclusion',end_date__isnull=True)

			main_goals_data = OnBoardingSerializer(main_goals, many=True).data
			medical_conditions_data = OnBoardingSerializer(medical_conditions, many=True).data
			allergies_data = OnBoardingSerializer(allergies, many=True).data

			fitness_levels_data = [
				{"id": 1, "title": "Beginner"},
				{"id": 2, "title": "Intermediate"},
				{"id": 3, "title": "Advance"}
			]


			response_data = {
				"message": "Success",
				"main_goals": main_goals_data,
				"fitness_level": fitness_levels_data,
				"medical_condition": medical_conditions_data,
				"allergies": allergies_data,
			}


			return Response(response_data)
		except Exception as e:
			return Response({"message": str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)




class GetProfile(APIView):
	def get(self,request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)
			allData=AppUserSerializer(app_user_obj).data
			return Response({'message':'Success','data':allData})
		except Exception as e:
			return Response({'message':str(e)},status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class EditProfile(APIView):

	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)

			data = request.data
			full_name = data.get('full_name')
			# email = data.get('email')
			gender = data.get('gender')
			age = data.get('age')
			current_weight = data.get('current_weight')
			target_weight = data.get('target_weight')
			weight_unit = data.get('weight_unit')
			current_height = data.get('current_height')
			height_unit = data.get('height_unit')
			focus_area = data.get('focus_area')
			main_goal = data.get('main_goal')
			current_body_shape = data.get('current_body_shape')
			fitness_level = data.get('fitness_level')
			medical_condition = data.get('medical_condition')
			allergies_exclusions = data.get('allergies_exclusions')
			image = data.get('image')

			# check_email = AppUser.objects.filter(email=email).exclude(id=app_user_obj.id).first()
			# if check_email:
			# 	return Response({"message":"The email is already registered"},status=status.HTTP_409_CONFLICT)

			if not full_name:
				return Response({"message": 'full_name is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not gender:
				return Response({"message": 'gender is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not age:
				return Response({"message": 'age is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not current_weight:
				return Response({"message": 'current_weight is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not target_weight:
				return Response({"message": 'target_weight is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not weight_unit:
				return Response({"message": 'weight_unit is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not current_height:
				return Response({"message": 'current_height is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not height_unit:
				return Response({"message": 'height_unit is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not focus_area:
				return Response({"message": 'focus_area is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not main_goal:
				return Response({"message": 'main_goal is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not current_body_shape:
				return Response({"message": 'current_body_shape is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not fitness_level:
				return Response({"message": 'fitness_level is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not medical_condition:
				return Response({"message": 'medical_condition is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not allergies_exclusions:
				return Response({"message": 'allergies_exclusions is required'}, status=status.HTTP_400_BAD_REQUEST)

			app_user_obj.full_name = full_name
			app_user_obj.gender = gender
			app_user_obj.age = age
			app_user_obj.current_weight = current_weight
			app_user_obj.target_weight = target_weight
			app_user_obj.weight_unit = weight_unit
			app_user_obj.current_height = current_height
			app_user_obj.height_unit = height_unit
			app_user_obj.focus_area = focus_area
			app_user_obj.main_goal = main_goal
			app_user_obj.current_body_shape = current_body_shape
			app_user_obj.fitness_level = fitness_level
			app_user_obj.medical_condition = medical_condition
			app_user_obj.allergies_exclusions = allergies_exclusions
			if image:
				app_user_obj.image = image
			app_user_obj.save()

			return Response({'message': 'Success'})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class UploadImages(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)

			data = request.data
			images = data.getlist('images')
			image_urls = []

			for image in images:
				image_path = uploadTheProfile(image)
				# image_url = settings.BASE_URL + image_path
				image_urls.append(image_path)
			# # image_urls_str = ','.join(image_urls)
			# if not trainer_obj.images:
			# 	trainer_obj.images = image_urls
			# 	trainer_obj.primary_image = image_urls[0]
			# 	trainer_obj.save()

			return Response({'message': 'Success','data':image_urls})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class GetUserFaq(APIView):
	def get(self,request):
		try:
			faq_obj = Faq.objects.filter(end_date__isnull =True,type="user").order_by('-id')
			all_data = FAQSerializer(faq_obj,many=True).data
			return Response({'message':'Success','data':all_data})
		except Exception as e:
			print(e)
			return Response({'message':str(e)},status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class GetUserPrivacyPolicy(APIView):
	def get(self,request):
		try:
			content_obj =  ContentManagement.objects.filter(page_type='Privacy Policy',user_type='user').first()
			allData=ContentSerializer(content_obj).data
			return Response({'message':'Success','data':allData})
		except Exception as e:
			return Response({'message':str(e)},status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class GetUserTerms(APIView):
	def get(self,request):
		try:
			content_obj =  ContentManagement.objects.filter(page_type='Terms & conditions',user_type='user').first()
			allData=ContentSerializer(content_obj).data
			return Response({'message':'Success','data':allData})
		except Exception as e:
			return Response({'message':str(e)},status=status.HTTP_500_INTERNAL_SERVER_ERROR)


# Exercise
class GetAdminExerciseList(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)
			# Read operation - Retrieve all exercise or a list of exercises
			exercise_obj = FitnessLevel.objects.filter(end_date__isnull=True)
			exercise_serializer = ExerciseLevelSerializer(exercise_obj, many=True).data
			return Response({'message':'Success','data':exercise_serializer})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


# Sub exercise
class GetAdminSubExerciseList(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)
			# Read operation - Retrieve all exercise or a list of exercises
			data = request.query_params
			exercise_id = data.get('exercise_id')
			if not exercise_id:
				return Response({"message": 'exercise_id is required'}, status=status.HTTP_400_BAD_REQUEST)
			exercise_obj = AdminExercise.objects.filter(id=exercise_id).first()
			exercise_serializer = AdminExerciseSerializer(exercise_obj).data
			sub_exercise_obj = AdminSubExercise.objects.filter(exercise=exercise_obj)
			sub_exercise_serializer = AdminSubExerciseSerializer(sub_exercise_obj, many=True).data

			all_data = {'exercise':exercise_serializer,
						'sub_exercise':	sub_exercise_serializer
			}
			return Response({'message':'Success','data':all_data})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


# Trainer List
class GetTrainerList(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)
			# Read operation - Retrieve all exercise or a list of exercises
			trainer_obj = Trainer.objects.filter(status=True,end_date__isnull=True)

			# trainer_serializer = TrainerSerializer(trainer_obj, many=True).data

			return Response({'message':'Success','data':trainer_obj.values()})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)



class GetTrainerDetail(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)
			data = request.query_params
			trainer_id = data.get('trainer_id')
			if not trainer_id:
				return Response({"message": 'trainer_id is required'}, status=status.HTTP_400_BAD_REQUEST)
			# Read operation - Retrieve all exercise or a list of exercises
			trainer_obj = Trainer.objects.filter(id=trainer_id).first()
			check_request =  Students.objects.filter(app_user_id = app_user_obj.id,trainer_id = trainer_id ).first()

			if not check_request:
				is_requested = None
			else:
				if check_request.follow_request_status == 0:
					is_requested = 'requested'
				else:
					is_requested = 'accepted'

			trainer_serializer = TrainerSerializer(trainer_obj,context={'is_requested': is_requested}).data

			return Response({'message':'Success','data':trainer_serializer})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)




class SendFollowRequest(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
			print("here")
			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)
			trainer_id = request.data.get('trainer_id')
			if not trainer_id:
				return Response({"message": 'trainer_id is required'}, status=status.HTTP_400_BAD_REQUEST)
			trainer = Trainer.objects.get(id=trainer_id)

			student_follow = Students.objects.filter(trainer=trainer, app_user=app_user_obj).first()
			if not student_follow:
				print("if not student_follow:")
				student_follow = Students.objects.create(trainer=trainer, app_user=app_user_obj,follow_request_status=False)
				print(student_follow.app_user.notification_status)
				if student_follow.app_user.notification_status:
					registration_id = student_follow.app_user.fcm_token
					server_key = str(settings.FIREBASE_SERVER_KEY)
					print(student_follow.app_user.device_type)
					if student_follow.app_user.device_type == 'Android':
						send_push_notification(registration_id, "FOLLOW REQUEST",'You got a new follow request')
					if student_follow.app_user.device_type == 'Ios':
						send_push_notification(registration_id, "FOLLOW REQUEST",'You got a new follow request')
				
			else:
				return Response({'message': 'Request already sent'})

			return Response({'message': 'Follow request sent successfully'})

		except Trainer.DoesNotExist:
			return Response({'message': 'Trainer not found'}, status=status.HTTP_404_NOT_FOUND)

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class getUserNotifications(APIView):
	def get(self,request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)
			if not app_user_obj:
				return Response({'status_code':status.HTTP_400_BAD_REQUEST,'status_message':'User does not exists.'},status=status.HTTP_400_BAD_REQUEST)
			notify_obj = AppUserNotification.objects.filter(user=app_user_obj.id,end_date__isnull = True).order_by('-id')
			notification_count=AppUserNotification.objects.filter(user=app_user_obj.id,end_date__isnull = True,is_read=False).count()
			allData=[]
			for notify in notify_obj:
				alldata = {
					'id':notify.id,
					'message': notify.message,
					'notification_type' : notify.notification_type,
					'start_date':timesince(notify.start_date)+' ago',
				}
				allData.append(alldata)
			return Response ({'status_code':status.HTTP_200_OK,'status_message':'','data':allData,'notification_count':notification_count})
		except Exception as e:
			return Response({'status_code':status.HTTP_500_INTERNAL_SERVER_ERROR,'status_message':str(e)},status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class deleteUserNotifications(APIView):
	def post(self,request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)
			notification_id =  request.data.get('notification_id')
			if not notification_id:
				return Response({'status_code':status.HTTP_400_BAD_REQUEST,'status_message':'Notification Id is required'},status=status.HTTP_400_BAD_REQUEST)
			AppUserNotification.objects.filter(id=notification_id).update(end_date=datetime.now())
			return Response({'status_code':status.HTTP_200_OK,'status_message':'Notification Deleted Successfully'})
		except Exception as e:
			return Response({'status_code':status.HTTP_500_INTERNAL_SERVER_ERROR,'status_message':str(e)},status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class userDeleteAccount(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)
			app_user_obj.is_account_deleted = True
			app_user_obj.end_date = datetime.now()
			app_user_obj.save()
			return Response({'status_code':status.HTTP_200_OK,'status_message':'Account Deleted Successfully'})
		except Exception as e:
			return Response({'status_code':status.HTTP_500_INTERNAL_SERVER_ERROR,'status_message':str(e)},status=status.HTTP_500_INTERNAL_SERVER_ERROR)



class AddFriend(APIView):
	def post(self,request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)
			data = request.data
			friend_id = data.get('friend_id')
			if not friend_id:
				return Response({'message':'friend_id is required'},status=status.HTTP_400_BAD_REQUEST)
			try:
				friend = AppUser.objects.get(id=friend_id)
			except AppUser.DoesNotExist:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			friendship_request = Friends.objects.filter(from_user=app_user_obj, to_user=friend).first()
			if not friendship_request:
				friendship_request = Friends.objects.create(from_user=app_user_obj, to_user=friend, accepted=False)


				# push notification
				if friend.notification_status:
					registration_id = friend.fcm_token
					server_key = str(settings.FIREBASE_SERVER_KEY)
					if friend.device_type == 'Android':
						print("=====================================")
						send_push_notification(registration_id, "NEW FOLLOW REQUEST RECEIVED",app_user_obj.full_name +' sent you a follow request.')
					if friend.device_type == 'Ios':
						print("111111111111111111111111111111111111111")
						send_push_notification(registration_id, "NEW FOLLOW REQUEST RECEIVED",app_user_obj.full_name +' sent you a follow request.')

				# end

				# system notification
				AppUserNotification.objects.create(message=app_user_obj.full_name+' sent you a follow request.',notification_type="friend_request_received",user=friend)

				return Response({'message': 'success'})
			else:
				return Response({'message': 'Request already sent'})
		except Exception as e:
				return Response({'message':str(e)},status=status.HTTP_500_INTERNAL_SERVER_ERROR)



class AcceptRejectRequest(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			data = request.data
			request_id = data.get('request_id')
			status_type = data.get('status')  # 'accept' or 'reject'
			if not request_id:
				return Response({'message': 'Request ID is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not status_type:
				return Response({'message': 'Status is required'}, status=status.HTTP_400_BAD_REQUEST)
			try:
				friendship_request = Friends.objects.get(id=request_id, accepted=False)
			except Friends.DoesNotExist:
				return Response({'message': 'Friendship request not found or already accepted'}, status=status.HTTP_404_NOT_FOUND)

			if status_type == 'accept':
				friendship_request.accepted = True
				friendship_request.save()
				if friendship_request.from_user.notification_status:
					registration_id = friendship_request.from_user.fcm_token
					server_key = str(settings.FIREBASE_SERVER_KEY)
					if friendship_request.from_user.device_type == 'Android':
						send_push_notification(registration_id, "Request Accepted",f"{app_user_obj.full_name} accepted your follow request.")
					elif friendship_request.from_user.device_type == 'Ios':
						send_push_notification(registration_id, "Request Accepted",f"{app_user_obj.full_name} accepted your follow request.")

				# end

				# system notification
				AppUserNotification.objects.create(message=f"{app_user_obj.full_name} accepted your follow request.", notification_type="friend_request_accepted", user=friendship_request.from_user)

				return Response({'message': 'Friend request accepted'})
			elif status_type == 'reject':
				friendship_request.delete()
				return Response({'message': 'Friend request rejected'})
			else:
				return Response({'message': 'Status type must be accept/reject'}, status=status.HTTP_400_BAD_REQUEST)
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class SentRequestsList(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			friendship_request = Friends.objects.filter(from_user=app_user_obj, accepted=False)
			all_data = SentUserFriendListSerializer(friendship_request, many=True).data
			return Response({'message': 'Success', 'data': all_data})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class ReceivedRequestsList(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			received_friendlist = Friends.objects.filter(to_user=app_user_obj, accepted=False)
			all_data = ReceivedUserFriendListSerializer(received_friendlist, many=True).data
			return Response({'message': 'Success', 'data': all_data})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)



class FriendList(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			friends = Friends.objects.filter(
				(Q(from_user=app_user_obj) | Q(to_user=app_user_obj)) & Q(accepted=True)
			).select_related('from_user', 'to_user')

			friend_list = []
			for friend in friends:
				friend_user = friend.to_user if friend.from_user == app_user_obj else friend.from_user
				friend_list.append(friend_user)

			all_data = AppUserFriendSerializer(friend_list, many=True).data
			return Response({'message': 'Success', 'data': all_data})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class SearchFriend(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			data = request.query_params
			search = data.get('search')
			if not search:
				return Response({'message': 'Search parameter is required'}, status=status.HTTP_400_BAD_REQUEST)

			search_friend = AppUser.objects.filter(Q(full_name__icontains=search) | Q(email__icontains=search), end_date__isnull=True).exclude(id=app_user_obj.id)
			user_data = AppUserFriendSerializer(search_friend, many=True, context={'login_user': app_user_obj}).data
			return Response({'message': 'Success', 'data': user_data})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class CancelSentRequest(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			data = request.data
			request_id = data.get('request_id')
			if not request_id:
				return Response({'message': 'Request ID is required'}, status=status.HTTP_400_BAD_REQUEST)

			try:
				friendship_request = Friends.objects.get(id=request_id, accepted=False)
			except Friends.DoesNotExist:
				return Response({'message': 'Friendship request not found or already accepted'}, status=status.HTTP_404_NOT_FOUND)

			friendship_request.delete()
			return Response({'message': 'Friend request cancelled'})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)



class AssessmentList(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)


			# try:
			# 	student = Students.objects.get(app_user=app_user_obj)
			# except Students.DoesNotExist:
			# 	return Response({'message': 'Student not found'}, status=status.HTTP_404_NOT_FOUND)

			# Create the StudentAssessment object
			student_assessment = StudentAssessment.objects.filter(
				student__app_user=app_user_obj
			).order_by('-id')
			student_serializer = StudentAssessmentSerializer(student_assessment,many=True).data

			return Response({'message': 'Success','data':student_serializer})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class AssessmentDetail(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			data = request.query_params

			assessment_id = data.get('assessment_id')
			if not assessment_id:
				return Response({'message': 'assessment_id is required'}, status=status.HTTP_400_BAD_REQUEST)


			# Create the StudentAssessment object
			student_assessment = StudentAssessment.objects.filter(
				id=assessment_id
			).first()
			if not student_assessment:
				return Response({'message': 'StudentAssessment not found'}, status=status.HTTP_404_NOT_FOUND)
			student_serializer = StudentAssessmentSerializer(student_assessment).data

			return Response({'message': 'Success','data':student_serializer})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class StartAssessmentProgress(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			data = request.data

			assessment_id = data.get('assessment_id')
			assessment_progress = data.get('assessment_progress')

			if not assessment_id:
				return Response({'message': 'assessment_id is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not assessment_progress:
				return Response({'message': 'assessment_progress is required'}, status=status.HTTP_400_BAD_REQUEST)

			try:
				student_assessment = StudentAssessment.objects.get(id=assessment_id)
			except StudentAssessment.DoesNotExist:
				return Response({'message': 'StudentAssessment not found'}, status=status.HTTP_404_NOT_FOUND)

			student_assessment.assessment_progress = assessment_progress
			student_assessment.total_attempt += 1
			student_assessment.save()

			# Get the last attempt number for the assessment
			last_attempt = AssessmentAttempt.objects.filter(assessment_id=assessment_id).order_by('-attempt_number').first()
			if last_attempt:
				next_attempt_number = last_attempt.attempt_number + 1 if last_attempt else 1
			else:
				next_attempt_number = 1
			attempt = AssessmentAttempt.objects.create(user=app_user_obj, assessment=student_assessment, attempt_number=next_attempt_number)
			return Response({'message': 'Success'})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class FinishAssessmentProgress(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			data = request.data

			assessment_id = data.get('assessment_id')
			completed_time = data.get('completed_time')
			assessment_progress = data.get('assessment_progress')
			repetitions = data.get('repetitions')
			print('repetitions',repetitions)
			sets = data.get('sets')
			weight = data.get('weight')

			if not assessment_id:
				return Response({'message': 'assessment_id is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not assessment_progress:
				return Response({'message': 'assessment_progress is required'}, status=status.HTTP_400_BAD_REQUEST)

			try:
				student_assessment = StudentAssessment.objects.get(id=assessment_id)
			except StudentAssessment.DoesNotExist:
				return Response({'message': 'StudentAssessment not found'}, status=status.HTTP_404_NOT_FOUND)

			student_assessment.assessment_progress = assessment_progress
			student_assessment.save()

			from datetime import datetime
			if completed_time:
				assessment_obj = Assesments.objects.get(id = student_assessment.assessment_id)
				# total_time = assessment_obj.completion_time
				# completed_time_str = str(completed_time)
				# total_time_str = str(total_time)
				# completed_time_new = datetime.strptime(completed_time_str, '%H:%M:%S')
				# total_time = datetime.strptime(total_time_str, '%H:%M:%S')
				# time_difference = total_time - completed_time_new
				# total_seconds_difference = (time_difference.days * 86400) + time_difference.seconds
				# total_seconds_total_time = (total_time.hour * 3600) + (total_time.minute * 60) + total_time.second
				# fraction_completion = total_seconds_difference / total_seconds_total_time
				# percentage_completed = fraction_completion * 100



				total_time = assessment_obj.completion_time
				completed_time_str = str(completed_time)
				print('completed_time_str',completed_time_str)
				total_time_str = str(total_time)
				print('total_time_str',total_time_str)

				completed_time_new = datetime.strptime(completed_time_str, '%H:%M:%S')
				print('completed_time_new',completed_time_new)

				total_time = datetime.strptime(total_time_str, '%H:%M:%S')
				print('total_time',total_time)

				time_difference = total_time - completed_time_new
				print('time_difference',time_difference)
				total_seconds_difference = (time_difference.days * 86400) + time_difference.seconds
				total_seconds_total_time = (total_time.hour * 3600) + (total_time.minute * 60) + total_time.second
				fraction_completion = total_seconds_difference / total_seconds_total_time
				percentage_completed = fraction_completion * 100

				# Ensure percentage_completed is within the range of 0 to 100
				if percentage_completed > 100:
					percentage_completed = 100
				elif percentage_completed < 0:
					percentage_completed = 0

			else:
				assessment_obj = Assesments.objects.get(id = student_assessment.assessment_id)
				completed_sets = int(sets)
				print("completed_sets",completed_sets)

				completed_reps = int(repetitions)
				print("completed_reps",completed_reps)

				total_sets_planned = int(assessment_obj.sets)
				print("total_sets_planned",total_sets_planned)

				reps_per_set_planned = int(assessment_obj.repetitions)
				print("reps_per_set_planned",reps_per_set_planned)

				total_reps_completed = (completed_sets * reps_per_set_planned) + completed_reps
				print("total_reps_completed",total_reps_completed)

				total_reps_planned = total_sets_planned * reps_per_set_planned
				print("total_reps_planned",total_reps_planned)

				percentage_completed = (total_reps_completed / total_reps_planned) * 100
				print("percentage_completed",percentage_completed)



				if percentage_completed > 100:
					percentage_completed = 100
				elif percentage_completed < 0:
					percentage_completed = 0


			last_attempt = AssessmentAttempt.objects.filter(assessment_id=assessment_id).order_by('-attempt_number').first()
			last_attempt.completion_time = completed_time
			last_attempt.repetitions = repetitions
			last_attempt.sets = sets
			last_attempt.weight = weight
			last_attempt.completed_date = date.today()
			last_attempt.complete_percent = percentage_completed
			last_attempt.save()
			return Response({'message': 'Success'})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)




class GetWorkoutTrainer(APIView):
	def get(self,request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)


			student_workout = StudentWorkOutPlan.objects.filter(
				student__app_user=app_user_obj
			).order_by('-id')

			all_data = []


			seen_trainer_ids = set()

			for workout in student_workout:
				trainer_id = workout.workout.trainer.id
				if trainer_id not in seen_trainer_ids:
					all_data.append({
						'trainer_id': trainer_id,
						'trainer_name': workout.workout.trainer.full_name,
						'trainer_image': workout.workout.trainer.image,
						'isFavourite': workout.workout.trainer.is_favourite,

					})
					seen_trainer_ids.add(trainer_id)

			return Response({'message': 'Success', 'data': all_data})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class WorkOutList(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			trainer_id=request.GET.get('trainer_id')
			if not trainer_id:
				return Response({'message': 'Trainer not found'}, status=status.HTTP_404_NOT_FOUND)
			get_trainer=Trainer.objects.filter(id=trainer_id,end_date__isnull=True).first()
			workout_plan=WorkoutPlan.objects.filter(trainer=get_trainer).order_by('-id')
			if not trainer_id:
				return Response({'message': 'workout_plan not found'}, status=status.HTTP_404_NOT_FOUND)
			all_Data = []
			for workout in workout_plan:
				student_workout = StudentWorkOutPlan.objects.filter(
					workout=workout
				).order_by('-id')


				for stuworkout in student_workout:
					all_data = {
						'id' :stuworkout.id,
						'workout_id' : stuworkout.workout.id,
						'name':stuworkout.workout.name,
						'image':stuworkout.workout.image,
						'description':stuworkout.workout.description,

					}
					all_Data.append(all_data)
			unique_workouts = {item['workout_id']: item for item in all_Data}
			unique_workouts_list = list(unique_workouts.values())

			return Response({'message': 'Success','data':unique_workouts_list})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
class LikecommentWorkout(APIView):
		def post(self,request):
			try:
				try:
					uid = authenticated(request)
				except Exception as e:
					return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

				app_user_obj = AppUser.objects.filter(id=uid).first()
				if not app_user_obj:
					return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
				data = request.data

				get_status = data.get('get_status')
				comment=data.get('comment')
				workout_id=data.get('workout_id')
				if not workout_id:
					return Response({'message': 'workout_id not found'}, status=status.HTTP_404_NOT_FOUND)
				workout_plan=WorkoutPlan.objects.all()
				if get_status=='like' and not comment:
					get_workout_plan=workout_plan.filter(id=workout_id).first()
					get_workout_plan.likes+=1
					WorkoutComments.objects.create(user=app_user_obj,workout=get_workout_plan,is_liked=True)
					get_workout_plan.save()
					return Response({'message': 'Liked succcessfully'})
				if get_status=='dislike' and not comment:
					get_workout_plan=workout_plan.filter(id=workout_id).first()
					if not get_workout_plan.likes==0:
						get_workout_plan.likes-=1
					WorkoutComments.objects.create(user=app_user_obj,workout=get_workout_plan,is_liked=False)
					get_workout_plan.save()
					return Response({'message': 'Disliked succcessfully'})
				if get_status=='like' and comment:
					get_workout_plan=workout_plan.filter(id=workout_id).first()
					get_workout_plan.likes+=1
					WorkoutComments.objects.create(user=app_user_obj,workout=get_workout_plan,is_liked=True,comment=comment)
					get_workout_plan.save()
					return Response({'message': 'Liked and commented succcessfully'})
				if get_status=='dislike' and comment:
					get_workout_plan=workout_plan.filter(id=workout_id).first()
					if not get_workout_plan.likes==0:
						get_workout_plan.likes-=1
					WorkoutComments.objects.create(user=app_user_obj,workout=get_workout_plan,is_liked=False,comment=comment)
					get_workout_plan.save()
					return Response({'message': 'Disliked and commented succcessfully'})
				if not get_status and comment:
					get_workout_plan=workout_plan.filter(id=workout_id).first()
					WorkoutComments.objects.create(user=app_user_obj,workout=get_workout_plan,comment=comment)
					get_workout_plan.save()
					return Response({'message': 'Commented succcessfully'})





			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class AllWorkoutLikesComments(APIView):
	def get(self, request):
			try:
				try:
					uid = authenticated(request)
				except Exception as e:
					return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

				app_user_obj = AppUser.objects.filter(id=uid).first()
				if not app_user_obj:
					return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

				data = request.query_params
				workout_id = data.get('workout_id')
				if not workout_id:
					return Response({'message': 'workout_id is required'}, status=status.HTTP_400_BAD_REQUEST)

				workout_plan = WorkoutPlan.objects.filter(id=workout_id).first()
				get_comments=WorkoutComments.objects.filter(workout=workout_plan)
				# if not get_comments:
				# 		return Response({'message': 'get_comments is required'}, status=status.HTTP_400_BAD_REQUEST)

				comments=get_comments.values('user__full_name','user__image','comment','created_at')
				all_comments=list(comments)
				get_like_status=WorkoutComments.objects.filter(user=app_user_obj,workout=workout_plan).last()

				if not get_like_status:
						get_like_status=None
				else:
						get_like_status=get_like_status.is_liked
				data={
					'workout_id':workout_plan.id,
					'is_liked': get_like_status,
					'total_likes':workout_plan.likes,
					'comments':all_comments
				}

				if not workout_plan:
					return Response({'message': 'Workout Plan not found'}, status=status.HTTP_404_NOT_FOUND)



				return Response({'message': 'Success','data':data})

			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
class WorkOutDetail(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			data = request.query_params

			workout_id = data.get('workout_id')
			if not workout_id:
				return Response({'message': 'workout_id is required'}, status=status.HTTP_400_BAD_REQUEST)


			# Create the StudentAssessment object
			student_workout = StudentWorkOutPlan.objects.filter(
				id=workout_id
			).first()
			if not student_workout:
				return Response({'message': 'student workout not found'}, status=status.HTTP_404_NOT_FOUND)

			workout_plan = WorkoutPlan.objects.filter(id=student_workout.workout.id).first()
			
			if not workout_plan:
				return Response({'message': 'Workout Plan not found'}, status=status.HTTP_404_NOT_FOUND)
			work_type='private'
			workout_plan_serializer = WorkoutPlanSerializer(workout_plan,context={'work_type': work_type}).data
			if 'weeks' in workout_plan_serializer:
				for index,week in enumerate(workout_plan_serializer['weeks'],start=1):
					week['week_number']=index
			return Response({'message': 'Success','data':workout_plan_serializer})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)




class StudentHomePage(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			# Fetch unique trainers associated with workout plans
			unique_trainer_ids = WorkoutPlan.objects.filter(end_date__isnull=True).values_list('trainer', flat=True).distinct()
			unique_trainers = Trainer.objects.filter(id__in=unique_trainer_ids,end_date__isnull=True)

			# Prepare trainer data
			trainer_Data = []
			for trainer in unique_trainers:
				all_data = {
					'id': trainer.id,
					'trainer_name': trainer.full_name,
					'email': trainer.email,
					'age':trainer.age,
					'total_experience': trainer.total_experience,
					'gender':trainer.gender,
					'trainer_image': trainer.image,
				}
				trainer_Data.append(all_data)

			day = request.GET.get('day')
			if not day:
				return Response({'message': 'Day not found'}, status=status.HTTP_404_NOT_FOUND)

			exercise_obj = AdminExercise.objects.filter(day=day).first()
			exercise_serializer = AdminExerciseSerializer(exercise_obj).data
			sub_exercise_obj = AdminSubExercise.objects.filter(exercise=exercise_obj)
			sub_exercise_serializer = AdminSubExerciseSerializer(sub_exercise_obj, many=True).data

			exercise_data = {'exercise':exercise_serializer,
						'sub_exercise':	sub_exercise_serializer
			}

			return Response({'message':'Success','trainer_data':trainer_Data,'exercise_data':exercise_data})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class GetTrainerPublicWorkout(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			trainer_id = request.GET.get('trainer_id')
			if not trainer_id:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			workout_plan_obj = WorkoutPlan.objects.filter(work_access = 'public',trainer_id=trainer_id)
			public_workout_data =  []
			for workout in workout_plan_obj:
				public_workout = {
					'id':workout.id,
					'name':workout.name,
					'goal':workout.goal,
					'description':workout.description,
					'notes':workout.notes,
					'image':workout.image,
					'duration_type':workout.duration_type,
					'duration_minutes':workout.duration_minutes,
					'duration_weeks':workout.duration_weeks,
					'work_access':workout.work_access,
					'created_at':workout.created_at,
					'isFavourite':workout.is_favourite
				}
				public_workout_data.append(public_workout)
			return Response({'message':'Success','all_data':public_workout_data})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)



class getTrainerPublicWorkoutDetails(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			data =  request.query_params
			workout_id = data.get('workout_id')

			if not workout_id:
				return Response({'message': 'workout_id is required'}, status=status.HTTP_400_BAD_REQUEST)

			workout_plan = WorkoutPlan.objects.filter(id=workout_id).first()

			if not workout_plan:
				return Response({'message': 'Workout Plan not found'}, status=status.HTTP_404_NOT_FOUND)
			work_type='public'
			workout_plan_serializer = WorkoutPlanSerializer(workout_plan, context={'work_type': work_type}).data

			return Response({'message': 'Success','data':workout_plan_serializer})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)



class startWorkout(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			data = request.data

			workout_id = data.get('workout_id')
			workout_progress = data.get('workout_progress')

			if not workout_id:
				return Response({'message': 'workout_id is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not workout_progress:
				return Response({'message': 'workout_progress is required'}, status=status.HTTP_400_BAD_REQUEST)

			try:
				student_workout = StudentWorkOutPlan.objects.get(id=workout_id)
			except student_workout.DoesNotExist:
				return Response({'message': 'student workout not found'}, status=status.HTTP_404_NOT_FOUND)

			student_workout.assessment_progress = workout_progress
			student_workout.total_attempt += 1
			student_workout.save()

			# Get the last attempt number for the assessment
			last_attempt = WorkoutAttempt.objects.filter(workout_id=workout_id).order_by('-attempt_number').first()
			if last_attempt:
				next_attempt_number = last_attempt.attempt_number + 1 if last_attempt else 1
			else:
				next_attempt_number = 1
			attempt = WorkoutAttempt.objects.create(user=app_user_obj, workout=student_workout, attempt_number=next_attempt_number)
			return Response({'message': 'Success'})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


# class endWorkout(APIView):
#     def post(self, request):
#         try:
#             try:
#                 uid = authenticated(request)
#             except Exception as e:
#                 return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

#             app_user_obj = AppUser.objects.filter(id=uid).first()
#             if not app_user_obj:
#                 return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

#             data = request.data

#             workout_id = data.get('workout_id')
#             print(workout_id)
#             completed_time = data.get('completed_time')
#             workout_progress = data.get('workout_progress')
#             repetitions = data.get('repetitions')
#             sets = data.get('sets')
#             weight = data.get('weight')
#             exercise_data=data.get('exercise_data')

#             if not workout_id:
#                 return Response({'message': 'workout_id is required'}, status=status.HTTP_400_BAD_REQUEST)
#             if not workout_progress:
#                 return Response({'message': 'workout_progress is required'}, status=status.HTTP_400_BAD_REQUEST)

#             try:
#                 student_workout = StudentWorkOutPlan.objects.get(id=workout_id)
#             except student_workout.DoesNotExist:
#                 return Response({'message': 'StudentAssessment not found'}, status=status.HTTP_404_NOT_FOUND)

#             student_workout.workout_progress = workout_progress
#             student_workout.save()
#             print("here")
#             from datetime import datetime
#             if completed_time:
#                 student_obj = StudentWorkOutPlan.objects.get(id = student_workout.workout_id)

#                 total_time = student_obj.completion_time
#                 completed_time_str = str(completed_time)
#                 total_time_str = str(total_time)

#                 completed_time_new = datetime.strptime(completed_time_str, '%H:%M:%S')

#                 total_time = datetime.strptime(total_time_str, '%H:%M:%S')

#                 time_difference = total_time - completed_time_new
#                 total_seconds_difference = (time_difference.days * 86400) + time_difference.seconds
#                 total_seconds_total_time = (total_time.hour * 3600) + (total_time.minute * 60) + total_time.second
#                 fraction_completion = total_seconds_difference / total_seconds_total_time
#                 percentage_completed = fraction_completion * 100

#                 # Ensure percentage_completed is within the range of 0 to 100
#                 if percentage_completed > 100:
#                     percentage_completed = 100
#                 elif percentage_completed < 0:
#                     percentage_completed = 0

#             else:
#                 assessment_obj = StudentWorkOutPlan.objects.get(id = student_workout.workout_id)
#                 completed_sets = int(sets)

#                 completed_reps = int(repetitions)

#                 total_sets_planned = int(assessment_obj.sets)

#                 reps_per_set_planned = int(assessment_obj.repetitions)

#                 total_reps_completed = (completed_sets * reps_per_set_planned) + completed_reps

#                 total_reps_planned = total_sets_planned * reps_per_set_planned

#                 percentage_completed = (total_reps_completed / total_reps_planned) * 100



#                 if percentage_completed > 100:
#                     percentage_completed = 100
#                 elif percentage_completed < 0:
#                     percentage_completed = 0


#             last_attempt = WorkoutAttempt.objects.filter(workout_id=workout_id).order_by('-attempt_number').first()
#             last_attempt.completion_time = completed_time
#             last_attempt.repetitions = repetitions
#             last_attempt.sets = sets
#             last_attempt.weight = weight
#             last_attempt.exercise_data=exercise_data

#             last_attempt.completed_date = date.today()
#             last_attempt.complete_percent = percentage_completed
#             last_attempt.save()
#             return Response({'message': 'Success'})

#         except Exception as e:
#             return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class endWorkout(APIView):
			def post(self,request):
				try :
					try:
						uid = authenticated(request)
					except Exception as e:
						return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
					app_user_obj = AppUser.objects.filter(id=uid).first()
					if not app_user_obj:
						return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

					data = request.data

					workout_id = data.get('workout_id')
					if not workout_id:
						return Response({'message': 'workout_id not found'}, status=status.HTTP_404_NOT_FOUND)
					exercise_data=data.get('exercise_data')


					
					workout_week=data.get('workout_week')
					if not workout_week:
						return Response({'message': 'workout_week not found'}, status=status.HTTP_404_NOT_FOUND)
					workout_day=data.get('workout_day')
					completion_time=data.get('completion_time')
					if not workout_day:
						return Response({'message': 'workout_day not found'}, status=status.HTTP_404_NOT_FOUND)
					if not completion_time:
						return Response({'message': 'completion_time not found'}, status=status.HTTP_404_NOT_FOUND)	
					get_workout=WorkoutPlan.objects.filter(id=workout_id).first()
					get_student_workout = StudentWorkOutPlan.objects.filter(workout=get_workout).first()
					if not get_workout:
						return Response({'message': 'get_workout not found'}, status=status.HTTP_404_NOT_FOUND)
					# request_id = data.get('request_id')
					today = timezone.now().date()
					workout_type='private'


					start_of_week = today - timedelta(days=today.weekday())

					# Calculate the end of the week (e.g., Sunday)
					end_of_week = start_of_week + timedelta(days=6)
					exercise_id=data.get('exercise_id')
					print(exercise_id)
					print(exercise_data)
					get_exercise=PlanExercise.objects.filter(id=exercise_id).first()
					print(exercise_data)
					print(type(exercise_data))
					if exercise_data:
						list_data=json.loads(exercise_data)

						for data in list_data:
							print(data)
							get_id=data["exercise_id"]
							get_sub_exercise=SubExercise.objects.filter(id=get_id).first()
							check_completed=UserIsExerciseWorkout.objects.filter(user=app_user_obj,exercise=get_exercise,sub_exercise=get_sub_exercise,workout=get_workout,
														workout_week=workout_week,
														workout_day=workout_day,workout_type=workout_type,is_completed=True).first()
							if not check_completed:
								UserIsExerciseWorkout.objects.create(user=app_user_obj,exercise=get_exercise,				sub_exercise=get_sub_exercise,workout=get_workout,workout_type=workout_type,
															workout_week=workout_week,
															workout_day=workout_day,is_completed=True)

						
						
				
					last_attempt = WorkoutAttempt.objects.filter(user=app_user_obj,created_at__date__range=[start_of_week, end_of_week],workout=get_student_workout,workout_week=workout_week,workout_day=workout_day).order_by('-attempt_number').first()
					if last_attempt:

						last_attempt.exercise_data=exercise_data
						last_attempt.completed_date = date.today()
						last_attempt.workout_week=workout_week
						last_attempt.workout_day=workout_day
						last_attempt.completion_time=completion_time
						last_attempt.save()
						return Response({'message': 'Success'})
					else:
						WorkoutAttempt.objects.create(user=app_user_obj,workout=get_student_workout,
													exercise_data=exercise_data,
													completed_date = date.today(),
													workout_week=workout_week,
													workout_day=workout_day,completion_time=completion_time)

						return Response({'message': 'Success'})
				except Exception as e:
					return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class startPublicWorkout(APIView):
	def post(self, request):
		# try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			data = request.data

			workout_id = data.get('workout_id')
			workout_progress = data.get('workout_progress')

			if not workout_id:
				return Response({'message': 'workout_id is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not workout_progress:
				return Response({'message': 'workout_progress is required'}, status=status.HTTP_400_BAD_REQUEST)

			
			workout = WorkoutPlan.objects.filter(id=workout_id).first()
			if workout:
				workout.assessment_progress = workout_progress
				workout.total_attempt += 1
				workout.save()
			else:
				return Response({'message': 'workout not found'}, status=status.HTTP_400_BAD_REQUEST)

			
			# Get the last attempt number for the assessment
			last_attempt = PublicWorkoutAttempt.objects.filter(workout_id=workout_id).order_by('-attempt_number').first()
			if last_attempt:
				next_attempt_number = last_attempt.attempt_number + 1 if last_attempt else 1
			else:
				next_attempt_number = 1
			attempt = PublicWorkoutAttempt.objects.create(user=app_user_obj, workout=workout, attempt_number=next_attempt_number)
			return Response({'message': 'Success'})

		# except Exception as e:
		# 	return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class endPublicWorkout(APIView):
		# try:
			def post(self,request):
				try:
					uid = authenticated(request)
				except Exception as e:
					return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
				app_user_obj = AppUser.objects.filter(id=uid).first()
				if not app_user_obj:
					return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

				data = request.data

				workout_id = data.get('workout_id')
				if not workout_id:
					return Response({'message': 'workout_id not found'}, status=status.HTTP_404_NOT_FOUND)
				exercise_data=data.get('exercise_data')
				workout_week=data.get('workout_week')
				if not workout_week:
					return Response({'message': 'workout_week not found'}, status=status.HTTP_404_NOT_FOUND)
				workout_day=data.get('workout_day')
				completion_time=data.get('completion_time')
				if not workout_day:
					return Response({'message': 'workout_day not found'}, status=status.HTTP_404_NOT_FOUND)
				if not completion_time:
					return Response({'message': 'completion_time not found'}, status=status.HTTP_404_NOT_FOUND)
				get_workout=WorkoutPlan.objects.filter(id=workout_id).first()
				# get_student_workout = StudentWorkOutPlan.objects.filter(workout=get_workout).first()
				if not get_workout:
					return Response({'message': 'get_workout not found'}, status=status.HTTP_404_NOT_FOUND)
				today = timezone.now().date()
				workout_type='public'

				start_of_week = today - timedelta(days=today.weekday())

				# Calculate the end of the week (e.g., Sunday)
				end_of_week = start_of_week + timedelta(days=6)
				exercise_id=data.get('exercise_id')
				print(exercise_id)
				print(exercise_data)
				get_exercise=PlanExercise.objects.filter(id=exercise_id).first()
				print(exercise_data)
				print(type(exercise_data))
				if exercise_data:
					list_data=json.loads(exercise_data)

					for data in list_data:
						print(data)
						get_id=data["exercise_id"]
						get_sub_exercise=SubExercise.objects.filter(id=get_id).first()
						check_completed=UserIsExerciseWorkout.objects.filter(user=app_user_obj,exercise=get_exercise,sub_exercise=get_sub_exercise,workout=get_workout,
													workout_week=workout_week,workout_type=workout_type,
													workout_day=workout_day,is_completed=True).first()
						if not check_completed:
							UserIsExerciseWorkout.objects.create(user=app_user_obj,exercise=get_exercise,				sub_exercise=get_sub_exercise,workout=get_workout,
														workout_week=workout_week,workout_type=workout_type,
														workout_day=workout_day,is_completed=True)

					
					
			   
				last_attempt = PublicWorkoutAttempt.objects.filter(user=app_user_obj,workout=get_workout).order_by('-attempt_number').first()
				if last_attempt:

					last_attempt.exercise_data=exercise_data
					last_attempt.completed_date = date.today()
					last_attempt.workout_week=workout_week
					last_attempt.workout_day=workout_day
					last_attempt.save()
					return Response({'message': 'Success'})
				else:
					PublicWorkoutAttempt.objects.create(user=app_user_obj,workout=get_workout,
												exercise_data=exercise_data,
												completed_date = date.today(),
												workout_week=workout_week,
												workout_day=workout_day)

					return Response({'message': 'Success'})
class GetEndWorkoutdetails(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			workout_id = request.GET.get('workout_id')
			if not workout_id:
				return Response({'message': 'workout_id not found'}, status=status.HTTP_404_NOT_FOUND)
			get_workout=StudentWorkOutPlan.objects.filter(id=workout_id).first()
			if not get_workout:
				return Response({'message': 'get_workout not found'}, status=status.HTTP_404_NOT_FOUND)
			workoutattempt=WorkoutAttempt.objects.filter(user=app_user_obj,workout=get_workout)
			if not workoutattempt:
				return Response({'message': 'workoutattempt not found'}, status=status.HTTP_404_NOT_FOUND)
			return Response({'message':'Success','all_data':workoutattempt.values()})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)




class GetDiscoverData(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			category_obj =  DiscoverMainCategory.objects.filter(end_date__isnull = True)
			category_serialize_data = MainCategorySerializer(category_obj,many = True)
			return Response({'message':'Success','all_data':category_serialize_data.data})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class GetDiscoverExercise(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			subcategory_id=request.GET.get('subcategory_id')
			if not subcategory_id:
					return Response({'message': 'Subcategory id is required'}, status=status.HTTP_404_NOT_FOUND)

			category_obj =  DiscoverSubCategory.objects.get(id=subcategory_id)
			category_serialize_data = GetSubCategoryExercisesSerializer(category_obj)
			all_data=category_serialize_data.data
			fav_obj  = FavouriteDiscoverSubCategory.objects.filter(discover_sub_category=category_obj.id,user = app_user_obj).first()
			if fav_obj:
				all_data['is_favourite'] = True
				return Response({'message':'Success','all_data':all_data})
			else:
				all_data['is_favourite'] = False
				return Response({'message':'Success','all_data':all_data})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)






class CreateConversationwithTrainer(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message':str(e)},status=status.HTTP_401_UNAUTHORIZED)
			app_user_obj = AppUser.objects.filter(id=uid).first()
			# student_obj = Students.objects.get(app_user=user)

			trainer_id=request.data.get('trainer_id')
			if not trainer_id:
				return Response({'status_code': status.HTTP_400_BAD_REQUEST, 'status_message': 'trainer_id is required.'})

			trainer_obj = Trainer.objects.filter(id=trainer_id).first()
			if not trainer_obj:
				return Response({'status_code': status.HTTP_400_BAD_REQUEST, 'status_message': 'No trainer found'})

			existing_conversation = Conversation.objects.filter(student=app_user_obj, trainer=trainer_obj).first()
			if existing_conversation:
				twilio_channel_sid = existing_conversation.conversation_room_id
			else:
				concatinate_names= str(trainer_obj.full_name) + str(app_user_obj.full_name) + str(app_user_obj.id) + str(trainer_obj.id)
				suffle_string = list(concatinate_names)
				random.shuffle(suffle_string)
				conversation_name = ''.join(suffle_string)
				account_sid = settings.TWILIO_ACCOUNT_SID
				# print(account_sid)
				auth_token = settings.TWILIO_AUTH_TOKEN
				client = Client(account_sid, auth_token)
				# Create Conversation chat
				conversation = client.conversations \
						.v1 \
						.conversations \
						.create(friendly_name=conversation_name)


				conversation_obj = Conversation.objects.create(student=app_user_obj,trainer_id=trainer_obj.id )
				conversation_obj.conversation_room_id = conversation.sid
				conversation_obj.last_message = datetime.now()
				conversation_obj.save()

				student_attributes= {"id":str(app_user_obj.id),"name":str(app_user_obj.full_name),
					"image":str(app_user_obj.image)
				}
				student_json_attributes = json.dumps(student_attributes)

				student_participant = client.conversations \
					.v1 \
					.conversations(conversation.sid) \
					.participants \
					.create(identity=str(app_user_obj.id),attributes=student_json_attributes)


				trainer_attributes= {"id":str(trainer_obj.id),"name":str(trainer_obj.full_name),
					"image":str(trainer_obj.image)
				}
				trainer_attributes_json_attributes = json.dumps(trainer_attributes)

				trainer_attributes_participant = client.conversations \
					.v1 \
					.conversations(conversation.sid) \
					.participants \
					.create(identity=str(trainer_obj.id),attributes=trainer_attributes_json_attributes)

				conversation_obj.student_twilio_id = student_participant.sid
				conversation_obj.trainer_twilio_id = trainer_attributes_participant.sid
				conversation_obj.save()

				twilio_channel_sid = conversation_obj.conversation_room_id


			return Response ({'status_code':status.HTTP_200_OK,'status_message':'success','twilio_channel_sid':twilio_channel_sid})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class CreateFavourateSubCategory(APIView):
	def post(self,request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': "User not found"})
			discover_subcategory_id=request.data.get('discover_subcategory_id')

			if not discover_subcategory_id:
				return Response({'message': 'discover_subcategory_id is required'}, status=status.HTTP_404_NOT_FOUND)


			discover_subcategory_obj=DiscoverSubCategory.objects.filter(id=discover_subcategory_id).first()
			if not discover_subcategory_obj:
					return Response({'message': 'No subcategory found'}, status=status.HTTP_404_NOT_FOUND)

			favourite_post, created = FavouriteDiscoverSubCategory.objects.get_or_create(discover_sub_category=discover_subcategory_obj,user=app_user_obj,is_deleted=True)
			if not created:
				favourite_post.delete()
				return Response({'status_code':status.HTTP_200_OK,'status_message':'Removed from favourite list'})
			else:
				favourite_post.save()
				return Response({'status_code':status.HTTP_200_OK,'status_message':'Added to favourite list.'})

		except Exception as e:
		   return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class GetFavouriteSubCategory(APIView):
	def get(self,request):
				try:
					try:
						uid = authenticated(request)
					except Exception as e:
						return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

					app_user_obj = AppUser.objects.filter(id=uid).first()
					# student_obj = Students.objects.get(app_user=user)
					# student_obj = Students.objects.filter( app_user=app_user_obj).first()
					if not app_user_obj:
						return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)


					get_favourite_subcategory =  FavouriteDiscoverSubCategory.objects.filter(user=app_user_obj).values('user','discover_sub_category','is_deleted','created_at','updated_at',
													  'discover_sub_category__main_category',
													 'discover_sub_category__title',
													  'discover_sub_category__description',
													   'discover_sub_category__image',
														'discover_sub_category__start_date',
														'discover_sub_category__end_date',
														  ).order_by('id')

					all_data=[]
					for favourite in get_favourite_subcategory:
						favourite['discover_sub_main_category']=favourite.pop('discover_sub_category__main_category')
						favourite['discover_sub_category_title']=favourite.pop('discover_sub_category__title')
						favourite['discover_sub_category_description']=favourite.pop('discover_sub_category__description')
						favourite['discover_sub_category_image']=favourite.pop('discover_sub_category__image')
						favourite['discover_sub_category_start_date']=favourite.pop('discover_sub_category__start_date')
						favourite['discover_sub_category_end_date']=favourite.pop('discover_sub_category__end_date')
						all_data.append(favourite)
					return Response({'message':'Success','all_data':all_data})
				except Exception as e:
					return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class CreateUserAccessToken(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			identity = app_user_obj.id
			token = AccessToken(account_sid,api_sid,api_secret,identity=identity)

			if chat_service_sid:
				chat_grant = ChatGrant(service_sid=chat_service_sid)
				token.add_grant(chat_grant)

			notification = client.conversations \
			.v1 \
			.services(chat_service_sid) \
			.configuration \
			.notifications() \
			.update(
				new_message_enabled=True,
				new_message_sound='default',
				new_message_template="You have a new message in ${CONVERSATION}: ${MESSAGE}"
			)

			alldata = {
			'identity':identity,
			'token':token.to_jwt(),
			}
			return Response ({'status_code':status.HTTP_200_OK,'status_message':'Token Created Successfully','data':alldata})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)



class GetConverstationListing(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message':str(e)},status=status.HTTP_401_UNAUTHORIZED)
			app_user_obj = AppUser.objects.filter(id=uid).first()
					# student_obj = Students.objects.get(app_user=user)

			conversations = Conversation.objects.filter(student = app_user_obj)
			account_sid = settings.TWILIO_ACCOUNT_SID
			auth_token = settings.TWILIO_AUTH_TOKEN
			client = Client(account_sid, auth_token)
			conversation_list = []
			for conversation in conversations:
				messages = client.conversations \
				  .v1 \
				  .conversations(conversation.conversation_room_id) \
				  .messages \
				  .list(order='desc', limit=1)
				last_message = ''
				time = ''
				message_date = ''
				for record in messages:
					if record.body:
						last_message = record.body
						time = timesince(record.date_created)+' ago'
						message_date = record.date_created
					elif record.media:

						last_message = 'file'
						time = timesince(record.date_created)+' ago'
						message_date = record.date_created

				conversation_data = {
					"id": conversation.id,
					"twilio_channel_sid": conversation.conversation_room_id,
					"customer_name": conversation.student.full_name,
					"customer_image": conversation.student.image,
					"customer_id":conversation.student.id,
					"trainer_name": conversation.trainer.full_name,
					"trainer_image": conversation.trainer.image,
					"trainer_id": conversation.trainer.id,
					"last_message":last_message,
					"time":time,
					"message_date":message_date,
				}
				conversation_list.append(conversation_data)
			return Response ({'status_code':status.HTTP_200_OK,'status_message':'success','data':conversation_list})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class saveWeightReport(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			weight = request.data.get('weight')
			if not weight:
				return Response({'message': 'weight is required'}, status=status.HTTP_404_NOT_FOUND)

			date = request.data.get('date')
			if not date:
				return Response({'message': 'date is required'}, status=status.HTTP_404_NOT_FOUND)
			weight_obj =  WeightReport.objects.filter(date = date,user = app_user_obj.id).first()
			if weight_obj:
				weight_obj.weight = weight
				weight_obj.date = date
				weight_obj.save()
			else:
				WeightReport.objects.create(date = date,user = app_user_obj,weight = weight)
			return Response ({'status_code':status.HTTP_200_OK,'status_message':'success'})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class saveBmiReport(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			weight = request.data.get('weight')
			if not weight:
				return Response({'message': 'weight is required'}, status=status.HTTP_404_NOT_FOUND)

			height = request.data.get('height')
			if not height:
				return Response({'message': 'height is required'}, status=status.HTTP_404_NOT_FOUND)

			total_height=float(height)*float(height)
			# print(type(total_height),total_height)
			# print(type(weight),weight)


			x = float(weight)/total_height;
			if float(x) < 18.5:
				bmi =  'Underweight'
			if float(x)>=18.5 and x<25:
				bmi =  'Normal'
			if float(x) >= 25 and x < 30:
				bmi =  'Overweight'
			if float(x) >= 30:
				bmi = 'Obesity'

			bmi_report = BmiReport.objects.filter(user = app_user_obj.id).first()
			if bmi_report:
				bmi_report.weight = weight
				bmi_report.height = height
				bmi_report.bmi = bmi
				bmi_report.bmi_value = float(x)
				bmi_report.save()
			else:
				BmiReport.objects.create(user = app_user_obj,weight = weight,height =height,bmi = bmi,bmi_value=float(x))

			return Response ({'status_code':status.HTTP_200_OK,'status_message':'success','bmi_value':x})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class getUserHealthReport(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			weight_report = WeightReport.objects.filter(user_id = app_user_obj.id )
			weight_Data = []
			for weight in weight_report:
				all_data = {
					'id':weight.id,
					'weight':weight.weight,
					'date':weight.date,
				}
				weight_Data.append(all_data)

			bmi_obj = BmiReport.objects.filter(user =app_user_obj.id).first()
			if bmi_obj:
				bmi_value=bmi_obj.bmi_value
				bmi_type=bmi_obj.bmi
			else:
				bmi_value=None
				bmi_type=None

			bmi_data = {
				'bmi_value':bmi_value,
				'bmi_type':bmi_type,
			}

			get_workout=WorkoutAttempt.objects.filter(user=app_user_obj)
			total_calories = 0
			total_minutes=0
			for attempt in get_workout:
				# Simple calculation: 5 calories per minute of workout
				if attempt.completion_time:
					minutes = attempt.completion_time.total_seconds() / 60
					calories = int(minutes * 5)
					total_calories+=int(calories)
					total_minutes += int(minutes)
			calorie_data={
				'total_workout':get_workout.count(),
				'total_calories':total_calories,
				'total_minutes':total_minutes
			}
			return Response ({'status_code':status.HTTP_200_OK,'status_message':'success','weight_Data':weight_Data,'bmi_data':bmi_data,'calorie_data':calorie_data,'total_calories':0})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class GetStudentWorkOutPlanByWeek(APIView):
	def get(self,request):
		try:
				try:
					uid = authenticated(request)
				except Exception as e:
					return Response({'message':str(e)},status=status.HTTP_401_UNAUTHORIZED)
				app_user_obj = AppUser.objects.filter(id=uid).first()
						# student_obj = Students.objects.get(app_user=user)
				student_obj = Students.objects.filter( app_user=app_user_obj).first()
				if not student_obj:
					return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)
				date_num=request.GET.get('date_num')
				current_date = date.today()

				# Find the first day (Monday) of the current week
				start_of_week = current_date - timedelta(days=current_date.weekday())

				# Find the last day (Sunday) of the current week
				end_of_week = start_of_week + timedelta(days=6)

				all_dates_in_week = []

				# Iterate through each day of the week
				for day_offset in range(7):
					current_day = start_of_week + timedelta(days=day_offset)
					all_dates_in_week.append(current_day)

				# Ensure the current date (25th) is included if it lies within the current week
				if start_of_week <= current_date <= end_of_week:
					if current_date.day == date_num:
						all_dates_in_week.append(current_date)

				get_workout_plan=StudentWorkOutPlan.objects.filter(student=student_obj,created_at__date__in=all_dates_in_week,end_date__isnull = True).values(
					"student__app_user__full_name","workout__id","workout__name","workout__image","workout_progress","created_at")
				all_data=[]
				for favourite in get_workout_plan:
					favourite['student_full_name']=favourite.pop('student__app_user__full_name')
					favourite['workout_id']=favourite.pop('workout__id')
					favourite['workout_name']=favourite.pop('workout__name')
					favourite['workout_image']=favourite.pop('workout__image')
					favourite['workout_progress']=favourite.pop('workout_progress')
					favourite['created_at']=favourite.pop('created_at')

					all_data.append(favourite)
				return Response ({'status_code':status.HTTP_200_OK,'data':all_data})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class  GetNearestUserTrainer(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)

			user_lat=request.GET.get('user_lat')
			user_long=request.GET.get('user_long')
			user_lat= float(user_lat)
			user_long= float(user_long)
			# if not app_user_obj.latitude or not app_user_obj.longitude:
			# 	user_lat = 0.1
			# 	user_long = 0.1
			# else:
			# 	user_lat = float(app_user_obj.latitude)
			# 	user_long = float(app_user_obj.longitude)

			if not user_lat:
				return Response({'message': 'user latitude not found','user_lat':user_lat}, status=status.HTTP_404_NOT_FOUND)
			if not user_long:
				return Response({'message': 'user longitude not found'}, status=status.HTTP_404_NOT_FOUND)


			kmrange = 30
			users_within_30km = AppUser.objects.filter(
				Q(latitude__gte=(user_lat - kmrange / 111.1),
				  latitude__lte=(user_lat + kmrange / 111.1),
				  longitude__gte=(user_long - kmrange / 111.1),
				  longitude__lte=(user_long + kmrange / 111.1))
			)

			user_data = []
			for user in users_within_30km:
				user_data.append({
					'id': user.id,
					'full_name': user.full_name,
					'email': user.email,
					'image': user.image,
					"latitude": user.latitude,
					"longitude": user.longitude,
				})

			trainers_within_10km = Trainer.objects.filter(
				Q(latitude__gte=(user_lat - kmrange / 111.1),
				  latitude__lte=(user_lat + kmrange / 111.1),
				  longitude__gte=(user_long - kmrange / 111.1),
				  longitude__lte=(user_long + kmrange / 111.1))
			)

			trainer_data = []
			for trainer in trainers_within_10km:
				trainer_data.append({
					'id': trainer.id,
					'full_name': trainer.full_name,
					'email': trainer.email,
					'image': trainer.image,
					"latitude": trainer.latitude,
					"longitude": trainer.longitude,
				})

			return Response({
				'status_code': status.HTTP_200_OK,
				'user_data': user_data,
				'trainer_data': trainer_data
			})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class StudentFeedback(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			student_obj = Students.objects.filter( app_user=app_user_obj).first()
			if not student_obj:
				return Response({'message': 'user not found'}, status=status.HTTP_404_NOT_FOUND)


			workout_id=request.data.get('workout_id')
			feedback=request.data.get('feedback')

			if not workout_id:
				return Response({'message': 'workout_id is required'}, status=status.HTTP_400_BAD_REQUEST)


			# Create the StudentAssessment object
			workout = WorkoutPlan.objects.filter(
				id=workout_id
			).first()
			if not workout:
				return Response({'message': 'workout not found'}, status=status.HTTP_404_NOT_FOUND)

			get_trainer=Trainer.objects.filter(id=workout.trainer.id).first()
			if not get_trainer:
				return Response({'message': 'workout not found'}, status=status.HTTP_404_NOT_FOUND)
			try:
				CreateStudentFeedback.objects.create(
						student = student_obj,
						trainer = get_trainer,
						workout= workout,
						feedback=feedback)
				return Response({'message': 'Saved successfully'}, status=status.HTTP_404_NOT_FOUND)

			except Exception as e:
				return Response({'message': f'{e}'}, status=status.HTTP_404_NOT_FOUND)

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class SaveCaloriesData(APIView):
			def post(self,request):
				try:
					uid = authenticated(request)
				except Exception as e:
					return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
				app_user_obj = AppUser.objects.filter(id=uid).first()
				if not app_user_obj:
					return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

				data = request.data
				total_calories=data.get('total_calories')
				if not total_calories:
					return Response({'message': 'total_calories not found'}, status=status.HTTP_404_NOT_FOUND)
				try:
					CaloriesData.objects.create(user=app_user_obj,total_calories=total_calories)
					return Response({'message': 'calories data saved successfully'}, status=status.HTTP_201_CREATED)
				except Exception as e:
					print(e)
					return Response({'message': 'something went wrong while saving data'}, status=status.HTTP_404_NOT_FOUND)

class GetCaloriesData(APIView):
			def get(self,request):
				try:
					uid = authenticated(request)
				except Exception as e:
					return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
				app_user_obj = AppUser.objects.filter(id=uid).first()
				if not app_user_obj:
					return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

				data = request.GET
				get_date=data.get('get_date')
				if not get_date:
					return Response({'message': 'get_date not found'}, status=status.HTTP_404_NOT_FOUND)
				date_str = get_date
				date_obj = datetime.strptime(date_str, "%d/%m/%Y").date()

				try:
					all_data=CaloriesData.objects.filter(user=app_user_obj,created_at__date=date_obj)
					return Response({'status_code':status.HTTP_200_OK,'data':all_data.values()})
				except Exception as e:

					 return Response({e}, status=status.HTTP_404_NOT_FOUND)


class GenerateCards(APIView):
	def post(self, request):
		try:
			uid = authenticated(request)
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

		app_user_obj = AppUser.objects.filter(id=uid).first()
		if not app_user_obj:
			return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

		data = request.data
		card_digits = data.get('card_digits')
		exp_month = data.get('exp_month')
		exp_year = data.get('exp_year')
		source_id=data.get('source_id')

		if not card_digits or not exp_month or not exp_year:
			return Response({'message': 'Invalid card data provided'}, status=status.HTTP_400_BAD_REQUEST)


		try:


			# Create a source for the customer
			card_details = stripe.Customer.create_source(
				f"{app_user_obj.stripe_id}",
				source=source_id
			)

			# Create UserCards entry
			if not UserCards.objects.filter(user=app_user_obj,card_id=card_details['id']).exists():
				UserCards.objects.create(
					user=app_user_obj,
					card_id=card_details['id'],
					the_user_stripe=app_user_obj.stripe_id,
					last_digits=card_digits,
					exp_month=exp_month,
					exp_year=exp_year
				)

			return Response({'message': 'Card data saved successfully'}, status=status.HTTP_201_CREATED)

		except stripe.error.StripeError as e:
			return Response({'message': str(e)}, status=status.HTTP_400_BAD_REQUEST)

		except Exception as e:
			return Response({'message': 'Internal server error'}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class ListallCards(APIView):
	def get(self,request):
				try:
					uid = authenticated(request)
				except Exception as e:
					return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
				app_user_obj = AppUser.objects.filter(id=uid).first()
				if not app_user_obj:
					return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

				try:
					all_data=UserCards.objects.filter(user=app_user_obj,end_date__isnull = True)
					return Response({'status_code':status.HTTP_200_OK,'data':all_data.values()})
				except Exception as e:
					 return Response({e}, status=status.HTTP_404_NOT_FOUND)


class DeleteCards(APIView):
	def post(self,request):
				try:
					uid = authenticated(request)
				except Exception as e:
					return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
				app_user_obj = AppUser.objects.filter(id=uid).first()
				if not app_user_obj:
					return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

				data = request.data
				id = data.get('card_id')
				all_data=UserCards.objects.filter(id=id)
				all_data.update(end_date=datetime.today())
				data=all_data.first()
				data.card_id

				try:
					stripe.Customer.delete_source(
						data.user.stripe_id,
						data.card_id,
					)
					return Response({'message:deleted successfully'})
				except stripe.StripeError as e:
					# Handle specific Stripe errors
					error_message = str(e)
					# Optionally log the error
					# logger.error(f"Stripe error: {error_message}")
					return Response({'error': error_message}, status=status.HTTP_404_NOT_FOUND)
				except Exception as e:
					# Handle other unexpected exceptions
					error_message = str(e)
					# Optionally log the error
					# logger.error(f"Unexpected error: {error_message}")
					return Response({'error': error_message}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class CreatePayment(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			data = request.data
			trainer_id = data.get('trainer_id')
			source_id = data.get('source_id')
			amount = data.get('amount')

			payment = stripe.Charge.create(
				amount=int(amount) * 100,
				currency='usd',
				description='Payment',
				source=source_id,
			)

			payment_check = {
				'txn_id': payment.balance_transaction,
				'recipet_url': payment.receipt_url,
				'payment_mode': payment.payment_method_details.type,
			}

			get_trainer = Trainer.objects.filter(id=trainer_id, end_date__isnull=True).first()
			if not get_trainer:
				return Response({'message': 'Trainer not found'}, status=status.HTTP_404_NOT_FOUND)

			try:
				UserTranscations.objects.create(
					transcation_id=generateTranscationsId(),
					trainer=get_trainer,
					user=app_user_obj,
					amount=str(amount),
					txn_id=payment_check['txn_id'],
					recipet_url=payment_check['recipet_url'],
					payment_mode=payment_check['payment_mode'],
					transcation_type="pay"
				)

				get_wallet = TrainerWallet.objects.filter(trainer=get_trainer).first()
				if get_wallet:
					old_amount = int(get_wallet.amount)
					new_amount = old_amount + int(amount)
					get_wallet.amount = new_amount
					get_wallet.save()

				return Response({'message': 'Payment created successfully', 'status_code': status.HTTP_200_OK})
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class GetWorkoutFeedback(APIView):
	 def get(self, request):
	   try:
		   try:
			   uid = authenticated(request)
		   except Exception as e:
			   return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
		   trainer_obj = AppUser.objects.filter(id=uid).first()
		   if not trainer_obj:
			   return Response({'message': 'Trainer not found'}, status=status.HTTP_404_NOT_FOUND)
		   workout_id=request.GET.get('workout_id')
		   if not workout_id:
			   return Response({'message': 'workout_id not found'}, status=status.HTTP_404_NOT_FOUND)
		   workout_obj=WorkoutPlan.objects.filter(id=workout_id).first()
		   if not workout_obj:
			   return Response({'message': 'workout_obj not found'}, status=status.HTTP_404_NOT_FOUND)

		   feedback = CreateStudentFeedback.objects.filter(workout=workout_obj).values("student__app_user__full_name","student__app_user__image","feedback","created_at")

		   return Response({'message':'Success','data':feedback})
	   except Exception as e:
		   return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class EditSubExercise(APIView):
	def get(self, request ):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			user_obj = AppUser.objects.filter(id=uid).first()
			if not user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			data = request.query_params
			exercise_id = data.get('exercise_id')
			if not exercise_id:
				return Response({"message": 'exercise_id is required'}, status=status.HTTP_400_BAD_REQUEST)
			sub_exercise_obj = SubExercise.objects.filter(id=exercise_id).first()
			sub_exercise_serializer = SubExerciseSerializer(sub_exercise_obj).data
			return Response({'message':'Success','data':sub_exercise_serializer})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
	def post(self, request):
		try:
			# Update operation - Update an existing exercise
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			user_obj = AppUser.objects.filter(id=uid).first()
			if not user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)

			data = request.data
			exercise_id = data.get('exercise_id')
			name = data.get('name')
			description = data.get('description')
			comments = data.get('comments')
			note = data.get('note')
			focus_area = data.get('focus_area')
			sets = data.get('sets')
			reps = data.get('reps')
			weight = data.get('weight')
			youtube_link = data.get('youtube_link')
			images = data.get('images')
			videos = data.get('videos')

			if not name:
				return Response({"message": 'name is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not description:
				return Response({"message": 'description is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not exercise_id:
				return Response({"message": 'exercise_id is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not comments:
				return Response({"message": 'comments is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not note:
				return Response({"message": 'note is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not focus_area:
				return Response({"message": 'focus_area is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not sets:
				return Response({"message": 'sets is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not weight:
				return Response({"message": 'weight is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not reps:
				return Response({"message": 'reps is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not youtube_link:
				return Response({"message": 'youtube_link is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not images:
				return Response({"message": 'images is required'}, status=status.HTTP_400_BAD_REQUEST)
			if not videos:
				return Response({"message": 'videos is required'}, status=status.HTTP_400_BAD_REQUEST)

			sub_exercise_obj = SubExercise.objects.filter(id=exercise_id).first()
			if not sub_exercise_obj:
				return Response({'message': 'Exercise not found'}, status=status.HTTP_404_NOT_FOUND)

			sub_exercise_obj.name=name
			sub_exercise_obj.description=description
			sub_exercise_obj.comments = comments
			sub_exercise_obj.note = note
			sub_exercise_obj.focus_area = focus_area
			sub_exercise_obj.sets = sets
			sub_exercise_obj.weight = weight
			sub_exercise_obj.reps = reps
			sub_exercise_obj.youtube_link = youtube_link
			sub_exercise_obj.images=images
			sub_exercise_obj.videos = videos
			sub_exercise_obj.save()
			return Response({'message':'Success'})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class GetSubExerciseList(APIView):
	def get(self, request ):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			user_obj = AppUser.objects.filter(id=uid).first()
			if not user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			data = request.query_params
			exercise_id = data.get('exercise_id')
			if not exercise_id:
				return Response({"message": 'exercise_id is required'}, status=status.HTTP_400_BAD_REQUEST)
			exercise_obj = Exercise.objects.filter(id=exercise_id,end_date__isnull=True).first()
			subexercise_obj=SubExercise.objects.filter(exercise=exercise_obj,end_date__isnull=True)
			total_data=[]
			for exercise in subexercise_obj:
				focus_area = exercise.focus_area.strip("[]").replace("'", "").split(", ")
				videos = exercise.videos.strip("[]").replace("'", "").split(", ")
				images = exercise.images.strip("[]").replace("'", "").split(", ")
				# Convert to list of strings
				focus_area_result = [item.strip() for item in focus_area]
				videos_result = [item.strip() for item in videos]
				images_result = [item.strip() for item in images]
				data={
				"id": exercise.id,
				"exercise_id": exercise.exercise_id,
				"name": exercise.name,
				"description": exercise.description,
				"note":  exercise.note,
				"focus_area":focus_area_result,
				"sets":  exercise.sets,
				"reps":  exercise.reps,
				"weight":  exercise.weight,
				"youtube_link":  exercise.youtube_link,
				"video_link":  exercise.video_link,
				"images": images_result,
				"videos":  videos_result,
				"created_at":  exercise.created_at,
				"updated_at": exercise.updated_at,
				"end_date":  exercise.end_date,
			}
			total_data.append(data)
			return Response({'message':'Success','data':total_data})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class GetSubExerciseDetails(APIView):
	def get(self, request ):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			user_obj = AppUser.objects.filter(id=uid).first()
			if not user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			data = request.query_params
			sub_exercise_id = data.get('sub_exercise_id')
			if not sub_exercise_id:
				return Response({"message": 'sub_exercise_id is required'}, status=status.HTTP_400_BAD_REQUEST)

			subexercise_obj=SubExercise.objects.filter(id=sub_exercise_id,end_date__isnull=True).first()
			total_data=[]

			focus_area = subexercise_obj.focus_area.strip("[]").replace("'", "").split(", ")
			videos = subexercise_obj.videos.strip("[]").replace("'", "").split(", ")
			images = subexercise_obj.images.strip("[]").replace("'", "").split(", ")
			# Convert to list of strings
			focus_area_result = [item.strip() for item in focus_area]
			videos_result = [item.strip() for item in videos]
			images_result = [item.strip() for item in images]
			data={
			"id": subexercise_obj.id,
			"exercise_id": subexercise_obj.exercise_id,
			"name": subexercise_obj.name,
			"description": subexercise_obj.description,
			"note":  subexercise_obj.note,
			"focus_area":focus_area_result,
			"sets":  subexercise_obj.sets,
			"reps":  subexercise_obj.reps,
			"weight":  subexercise_obj.weight,
			"youtube_link":  subexercise_obj.youtube_link,
			"video_link":  subexercise_obj.video_link,
			"images": images_result,
			"videos":  videos_result,
			"created_at":  subexercise_obj.created_at,
			"updated_at": subexercise_obj.updated_at,
			"end_date":  subexercise_obj.end_date,
		}
			total_data.append(data)
			return Response({'message':'Success','data':total_data})





		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class ReadNotifications(APIView):
		def post(self,request):
			try :
				try:
					uid = authenticated(request)
				except Exception as e:
					return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

				app_user_obj = AppUser.objects.filter(id=uid).first()
				if not app_user_obj:
					return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
				notification=AppUserNotification.objects.update(is_read=True)
				return Response({'message': 'notification read successfully'}, status=status.HTTP_404_NOT_FOUND)


			except Exception as e:
				return Response({e}, status=status.HTTP_404_NOT_FOUND)


class ChangeisFavWorkoutTrainerStatus(APIView):
	def post(self,request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			data = request.data
			trainer_id=data.get('trainer_id')
			if not trainer_id:
				return Response({'message': 'trainer_id not found'}, status=status.HTTP_404_NOT_FOUND)
			isFavourite = data.get('isFavourite')
			if not isFavourite:
				return Response({'message': 'isFavourite not found'}, status=status.HTTP_404_NOT_FOUND)

			trainer_obj=Trainer.objects.filter(id=trainer_id,end_date__isnull=True).first()
			if isFavourite=='true':
				trainer_obj.is_favourite=True
			else:
				trainer_obj.is_favourite=False
			trainer_obj.save()
			all_data={
						'trainer_id': trainer_obj.id,
						'trainer_name': trainer_obj.full_name,
						'trainer_image': trainer_obj.image,
						'isFavourite':trainer_obj.is_favourite
					}
			return Response({'message': 'is_favourate status changed', 'data': all_data})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class  GetIsFavouriteTrainers(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			trainer_obj=Trainer.objects.filter(is_favourite=True,end_date__isnull=True)
			all_data = []

			for trainer in trainer_obj:

					all_data.append({
						'trainer_id': trainer.id,
						'trainer_name': trainer.full_name,
						'trainer_image': trainer.image,
						'isFavourite':trainer.is_favourite
					})

			return Response({'message': 'Success','data':all_data})

		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class ChangeFavWorkoutStatus(APIView):
	def post(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)



			data = request.data
			workout_id=data.get('workout_id')
			if not workout_id:
				return Response({'message': 'workout_id not found'}, status=status.HTTP_404_NOT_FOUND)
			isFavourite = data.get('isFavourite')
			if not isFavourite:
				return Response({'message': 'isFavourite not found'}, status=status.HTTP_404_NOT_FOUND)

			workout_plan_obj = WorkoutPlan.objects.filter(work_access = 'public',id=workout_id).first()
			if not workout_plan_obj:
				return Response({'message': 'workout_plan_obj not found'}, status=status.HTTP_404_NOT_FOUND)
			
			if isFavourite=='true':
				workout_plan_obj.is_favourite=True
			else:
				workout_plan_obj.is_favourite=False
			workout_plan_obj.save()


			public_workout = {
				'id':workout_plan_obj.id,
				'name':workout_plan_obj.name,
				'goal':workout_plan_obj.goal,
				'description':workout_plan_obj.description,
				'notes':workout_plan_obj.notes,
				'image':workout_plan_obj.image,
				'duration_type':workout_plan_obj.duration_type,
				'duration_minutes':workout_plan_obj.duration_minutes,
				'duration_weeks':workout_plan_obj.duration_weeks,
				'work_access':workout_plan_obj.work_access,
				'created_at':workout_plan_obj.created_at,
				'isFavourite':workout_plan_obj.is_favourite
			}

			return Response({'message':'Success','all_data':public_workout})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)


class GetIsFavouriteWorkouts(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			workout_plan_obj = WorkoutPlan.objects.filter(work_access = 'public',is_favourite=True,end_date__isnull=True)
			all_data=[]
			for workout in workout_plan_obj:
				public_workout = {
					'id':workout.id,
					'name':workout.name,
					'goal':workout.goal,
					'description':workout.description,
					'notes':workout.notes,
					'image':workout.image,
					'duration_type':workout.duration_type,
					'duration_minutes':workout.duration_minutes,
					'duration_weeks':workout.duration_weeks,
					'work_access':workout.work_access,
					'created_at':workout.created_at,
					'isFavourite':workout.is_favourite
				}
				all_data.append(public_workout)
			return Response({'message':'Success','all_data':all_data})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
		
class GetExercisetimer(APIView):
	def get(self, request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			all_data = Exercisetimer.objects.values().last()
			
			return Response({'message':'Success','all_data':all_data})
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
		
class Getuserprivateworkoutperformance(APIView):
	def get(self,request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			workout_id=request.GET.get('workout_id')
			if not workout_id:
				return Response({'message': 'workout_id not found'}, status=status.HTTP_404_NOT_FOUND)
			get_workout=StudentWorkOutPlan.objects.filter(id=workout_id,end_date__isnull=True).first()

			if not get_workout:
				return Response({'message': 'workout with workout_id not found'}, status=status.HTTP_404_NOT_FOUND)
			today = timezone.now().date()


			start_of_week = today - timedelta(days=today.weekday())

			# Calculate the end of the week (e.g., Sunday)
			end_of_week = start_of_week + timedelta(days=6)


			attempt = WorkoutAttempt.objects.filter(user=app_user_obj, workout=get_workout,created_at__date__range=[start_of_week, end_of_week]).values()

# Initialize list to store complete data
			complete_data = []

			# Loop through each attempt entry
			for att in attempt:
				# Initialize dictionary for each attempt
				entry_data = {}
				entry_data["user_id"] = att["user_id"]
				entry_data["workout_id"] = att["workout_id"]
				entry_data["workout_day"] = att["workout_day"]

				# Parse exercise_data string into a list of dictionaries
				try:
					exercises = json.loads(att["exercise_data"].replace("'", '"'))
				except json.JSONDecodeError:
					exercises = []

				# Calculate total training volume for all exercises in this attempt
				training_volume = sum(float(ex['weight']) * int(ex['reps']) * int(ex['sets']) for ex in exercises)

				# Add training volume to the entry data
				entry_data["training_volume"] = training_volume

				# Append each entry's data to the complete data list
				complete_data.append(entry_data)

			# Print result
			print(complete_data)
			return Response({'data':complete_data }, status=status.HTTP_200_OK)
			
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR) 

class Getuserpublicworkoutperformance(APIView):
	def get(self,request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			workout_id=request.GET.get('workout_id')
			
			if not workout_id:
				return Response({'message': 'workout_id not found'}, status=status.HTTP_404_NOT_FOUND)
			
			
			get_workout=WorkoutPlan.objects.filter(id=workout_id,end_date__isnull=True).first()

			
			if not get_workout:
				return Response({'message': 'workout with workout_id not found'}, status=status.HTTP_404_NOT_FOUND)
			today = timezone.now().date()


			start_of_week = today - timedelta(days=today.weekday())

			# Calculate the end of the week (e.g., Sunday)
			end_of_week = start_of_week + timedelta(days=6)


			attempt = PublicWorkoutAttempt.objects.filter(user=app_user_obj, workout=get_workout,created_at__date__range=[start_of_week, end_of_week]).values()

# Initialize list to store complete data
			complete_data = []

			# Loop through each attempt entry
			for att in attempt:
				# Initialize dictionary for each attempt
				entry_data = {}
				entry_data["user_id"] = att["user_id"]
				entry_data["workout_id"] = att["workout_id"]
				entry_data["workout_day"] = att["workout_day"]

				# Parse exercise_data string into a list of dictionaries
				try:
					exercises = json.loads(att["exercise_data"].replace("'", '"'))
				except json.JSONDecodeError:
					exercises = []

				# Calculate total training volume for all exercises in this attempt
				training_volume = sum(float(ex['weight']) * int(ex['reps']) * int(ex['sets']) for ex in exercises)

				# Add training volume to the entry data
				entry_data["training_volume"] = training_volume

				# Append each entry's data to the complete data list
				complete_data.append(entry_data)

			# Print result
			print(complete_data)
			return Response({'data':complete_data }, status=status.HTTP_200_OK)
			
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR) 
		

class ChangeexerciseStatus(APIView):
	def post(self,request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			data = request.data
			exercise_id=data.get('exercise_id')
			is_completed=data.get('is_completed')
			
			if not exercise_id:
				return Response({'message': 'exercise_id not found'}, status=status.HTTP_404_NOT_FOUND)
			
			print(exercise_id)
			get_exercise=SubExercise.objects.filter(id=exercise_id,end_date__isnull=True).first()

			
			if not get_exercise:
				return Response({'message': 'exercise not found'}, status=status.HTTP_404_NOT_FOUND)
			
			get_exercise.is_completed=is_completed
			get_exercise.save()

			return Response({'message':'status changed successfully' }, status=status.HTTP_200_OK)
			
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR) 

class GetUserWeeklyPrivateworkouts(APIView):
	def get(self,request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
			
			user_obj = AppUser.objects.filter(id=uid).first()
			if not user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			today = timezone.now().date()


			start_of_week = today - timedelta(days=today.weekday())

			# Calculate the end of the week (e.g., Sunday)
			end_of_week = start_of_week + timedelta(days=6)
			all_data=[]
			time_values = []

			# Convert time strings to seconds
			

			# Convert total seconds to minutes and seconds
			
			attempt = WorkoutAttempt.objects.filter(user=user_obj,created_at__date__range=[start_of_week, end_of_week])
			completed_workouts=0
			for att in attempt:
				# exercise_data=att.exercise_data
				# exercise_data = exercise_data.replace("'", '"')
				# exercise_data_list = json.loads(exercise_data)
				if att.exercise_data:
					data=json.loads(att.exercise_data)
					for exercise in data:
						exercise['sets'] = int(float(exercise['sets'])) if exercise['sets'] else 0
						exercise['reps'] = int(float(exercise['reps'])) if exercise['reps'] else 0
						exercise['weight'] = str(float(exercise['weight'])) if exercise['weight'] else 0
				all_data.append({ 
					"id": att.id,
					"user_id": att.user.id,
					"workout_id": att.workout.id,
					"workout_name": att.workout.workout.name,
					"workout_image": att.workout.workout.image,
					"exercise_data": data if data else None,
					"workout_week": att.workout_week,
					"workout_day": att.workout_day,
					"completion_time": att.completion_time}
	
					)  
				if att.exercise_data:
					completed_workouts+=len(json.loads(att.exercise_data))
				if att.completion_time:
					print(att.completion_time)
					time_values.append(f"{att.completion_time}")
			total_seconds = sum(
				int(h) * 3600 + int(m) * 60 + int(s)
				for h, m, s in (time.split(":") for time in time_values)
			)

			total_time = timedelta(seconds=total_seconds)
			total_seconds = total_time.total_seconds()
			minutes, remaining_seconds = divmod(total_seconds, 60)
			total_days=len(all_data)
			# print(time_values)   
			week_order = ['Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday', 'Sunday']

# Sort the `all_data` list based on the day name
			all_data.sort(key=lambda x: week_order.index(x['workout_day'])) 

			return Response({'status':True,'workout_minutes':f"{int(minutes)}:{int(remaining_seconds)}",'total_days':total_days,'completed_workouts':completed_workouts,'message':'success','data':all_data }, status=status.HTTP_200_OK)
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR) 
		
class GetUserPrivateworkoutdetail(APIView):
	def get(self,request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
			
			user_obj = AppUser.objects.filter(id=uid).first()
			if not user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			workout_day=request.GET.get('workout_day')
			if not workout_day:
				return Response({'message': 'workout_day not found'}, status=status.HTTP_404_NOT_FOUND)
			today = timezone.now().date()


			start_of_week = today - timedelta(days=today.weekday())

			# Calculate the end of the week (e.g., Sunday)
			end_of_week = start_of_week + timedelta(days=6)
			attempt = WorkoutAttempt.objects.filter(workout_day=workout_day,user=user_obj,created_at__date__range=[start_of_week, end_of_week])
			all_data=[]

			# Convert time strings to seconds
			# Convert total seconds to minutes and seconds
		   
			for att in attempt:
				# exercise_data=att.exercise_data
				# exercise_data = exercise_data.replace("'", '"')
				# exercise_data_list = json.loads(exercise_data)
				all_data.append({
					"id": att.id,
					"user_id": att.user.id,
					"workout_id": att.workout.id,
					"exercise_data": ast.literal_eval(att.exercise_data),
					"workout_week": att.workout_week,
					"workout_day": att.workout_day,
				})
			week_order = ['Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday', 'Sunday']

# Sort the `all_data` list based on the day name
			all_data.sort(key=lambda x: week_order.index(x['workout_day']))
			return Response({'data':all_data }, status=status.HTTP_200_OK)
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)

class ResetWorkout(APIView):
		def post(self,request):
			try:
				try:
					uid = authenticated(request)
				except Exception as e:
					return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)

				app_user_obj = AppUser.objects.filter(id=uid).first()
				if not app_user_obj:
					return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
				data = request.data
				workout_id=data.get('workout_id')
				get_workout=WorkoutPlan.objects.filter(id=workout_id).first()
				workout_day=data.get('workout_day')
				if not get_workout:
					return Response({'message': 'get_workout not found'}, status=status.HTTP_404_NOT_FOUND)
				if not workout_day:
					return Response({'message': 'workout_day not found'}, status=status.HTTP_404_NOT_FOUND)
				get_exercise=UserIsExerciseWorkout.objects.filter(workout=get_workout,workout_day=workout_day,end_date__isnull=True)

				
				if not get_exercise:
					return Response({'message': 'exercise not found'}, status=status.HTTP_404_NOT_FOUND)
				for obj in get_exercise:
					obj.is_completed=False
					obj.save()

				return Response({'message':'status changed successfully' }, status=status.HTTP_200_OK)
				
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR) 

class Calculateworkoutperformance(APIView):
	def get(self,request):
		try:
			try:
				uid = authenticated(request)
			except Exception as e:
				return Response({'message': str(e)}, status=status.HTTP_401_UNAUTHORIZED)
			
			app_user_obj = AppUser.objects.filter(id=uid).first()
			if not app_user_obj:
				return Response({'message': 'User not found'}, status=status.HTTP_404_NOT_FOUND)
			workout_id=request.GET.get('workout_id')
			workout_week=request.GET.get('workout_week')
			if not workout_id:
				return Response({'message': 'workout_id not found'}, status=status.HTTP_404_NOT_FOUND)
			if not workout_week:
				return Response({'message': 'workout_week not found'}, status=status.HTTP_404_NOT_FOUND)
			# get_workout=WorkoutPlan.objects.filter(id=workout_id).first()
			get_student_workout = StudentWorkOutPlan.objects.filter(id=workout_id).first()
			if not get_student_workout:
				return Response({'message': 'workout with workout_id not found'}, status=status.HTTP_404_NOT_FOUND)
			today = timezone.now().date()


			start_of_week = today - timedelta(days=today.weekday())

			# Calculate the end of the week (e.g., Sunday)
			end_of_week = start_of_week + timedelta(days=6)


			attempt = WorkoutAttempt.objects.filter(user=app_user_obj, workout=get_student_workout,created_at__date__range=[start_of_week, end_of_week],workout_week=str(workout_week).strip('"')).values()

# Initialize list to store complete data
			complete_data = []

			# Loop through each attempt entry
			for att in attempt:
				# Initialize dictionary for each attempt
				entry_data = {}
				entry_data["user_id"] = att["user_id"]
				entry_data["workout_id"] = att["workout_id"]
				entry_data["workout_day"] = att["workout_day"]
				entry_data["workout_week"] = int(str(att["workout_week"]).strip('"'))
				# Parse exercise_data string into a list of dictionaries
				try:
					exercises = json.loads(att["exercise_data"].replace("'", '"'))
				except json.JSONDecodeError:
					exercises = []

				# Calculate total training volume for all exercises in this attempt
				training_volume = sum(float(ex['weight']) * int(ex['reps']) * int(ex['sets']) for ex in exercises)

				# Constants (estimated based on average exertion)
				calories_per_pound_lifted = 0.0015  # ~0.0015 calories per pound lifted

				# Calculate total weight lifted
				total_weight_lifted = [float(ex['weight']) * int(ex['reps']) * int(ex['sets']) for ex in exercises]

				# Estimate calories burned
				calories_burned = total_weight_lifted[0] * calories_per_pound_lifted

				# Output results
				
				# Add training volume to the entry data
				entry_data["training_volume"] = training_volume
				entry_data["total_calories_count"] = calories_burned

				# Append each entry's data to the complete data list
				complete_data.append(entry_data)

			# Print result
			print(complete_data)
			return Response({'data':complete_data }, status=status.HTTP_200_OK)
			
		except Exception as e:
			return Response({'message': str(e)}, status=status.HTTP_500_INTERNAL_SERVER_ERROR) 
		

