
    2|f                    6   d dl mZmZ d dlmZmZ d dlmZ d dlm	Z	 d dl
mZ d dlmZmZ d dlmZ d dlmZ d	d
l d	d
l d dlmZ d dlmZmZmZ d dlmZmZ d dlmZ d dlm Z  d dl!m"Z" d dl#m$Z$ d dl%m&Z& d dl%m'Z' d dl(m)Z) d dl*m+Z+ d	d
l, d dl-Z-d dl.Z.d dl/m0Z0  G d dejb                        Z2 G d dejf                        Z4 G d de	      Z5 G d de	      Z6 G d  d!e	      Z7 G d" d#e	      Z8 G d$ d%e	      Z9 G d& d'e	      Z: G d( d)e	      Z; G d* d+e	      Z< G d, d-e	      Z= G d. d/e	      Z> G d0 d1e	      Z? G d2 d3e	      Z@ G d4 d5e	      ZA G d6 d7e	      ZB G d8 d9e	      ZC G d: d;e	      ZD G d< d=e	      ZE G d> d?e	      ZF G d@ dAej                        ZH G dB dCe	      ZI G dD dEe	      ZJ G dF dGe	      ZK G dH dIe	      ZL G dJ dKe	      ZM G dL dMe	      ZN G dN dOe	      ZO G dP dQe	      ZP G dR dSe	      ZQ G dT dUe	      ZR G dV dWe	      ZSy)X    )DecimalROUND_UP)genericspermissions)JSONWebTokenAuthentication)APIView)TokenAuthentication)IsAuthenticatedIsAdminUser)Responsestatus   )*)geodesic)VehicleTypeVehicleVehicleAssignment)DriverLocationDevice)VehicleTypeSerializer)ValidationError)Distance)D)fromstr)Point)timezone)	timedeltaN)transactionc                   d    e Zd Zej                  j                         ZeZe	gZ
ej                  gZy)LocationListCreateAPIViewN__name__
__module____qualname__LocationobjectsallquerysetLocationSerializerserializer_classr   authentication_classesr   r
   permission_classes     5C:\Users\user\Documents\project_loop\booking\views.pyr!   r!      4    ##%H)89%556r/   r!   c                   d    e Zd Zej                  j                         ZeZe	gZ
ej                  gZy)$LocationRetrieveUpdateDestroyAPIViewNr"   r.   r/   r0   r3   r3   #   r1   r/   r3   c                   "    e Zd ZdZegZegZd Zy)NearbyLocationsViewz_
    View to get a list of locations within a 30 km radius of the user's current location.
    c                 &   |j                   j                  d      }|j                   j                  d      }||t        dddt        j                        S t        |      }t        |      }||f}g }t        j                  j                         D ]G  }|j                  |j                  f}t        ||      j                  }|dk  s7|j                  |       I t        |d	      }	t        d
d|	j                   dt        j                        S )Nlatitude	longituder   $Latitude and longitude are required.r   messager      Tmanyr   z(Nearby locations retrieved successfully.r   r;   data)r@   getr   r   HTTP_400_BAD_REQUESTfloatr&   r'   r(   r7   r8   r   
kilometersappendr*   HTTP_200_OK)
selfrequestuser_latitudeuser_longitudeuser_locationnearby_locationslocationlocation_coordsdistance
serializers
             r0   rA   zNearbyLocationsView.get2   s   ((4 ))+6 N$:)OP22  m,~.&7  !((,,. 	2H'00(2D2DEO?JJH 2~ ''1	2 ((8tD
E"
 %%
 	
r/   N)	r#   r$   r%   __doc__r	   r,   r
   r-   rA   r.   r/   r0   r5   r5   *   s      22)*%
r/   r5   c                       e Zd ZegZegZd Zy)AvailableVehicleTypesViewc           
         |j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|r|r|st        dddt        j                        S 	 |d   }|d	   }|d   }|d	   }	 t        j                  j                  |d      }	 t        ||||      }	t        d| d| dd      }t        j                         t!        d      z
  }||cxk  r|t!        d      z   k  rn nt"        j$                  j'                  t)        d|            j+                  d      d d }t,        j$                  j/                  d|D cg c]  }|j0                   c}dd      j3                         }n,t,        j$                  j5                         j3                         }g }|D ]y  }|	|j6                  z  }|j9                  t;        d      t<              }|j?                  |j@                  |jB                  |jD                  |j6                  tG        |      d       { t        dd |d!t        jH                        S # t
        t        f$ r! t        dd
dt        j                        cY S w xY w# t        $ r! t        dddt        j                        cY S w xY w# t        $ r1}
t        dt        |
      dt        j                        cY d }
~
S d }
~
ww xY wc c}w )"Nfrom_address
to_address	ride_timer   z=From address, to address, and ride time details are required.r:   r   r7   r8   [Invalid address format. Latitude and longitude are required for both from and to addresses.%Y-%m-%dT%H:%M:%S%zzDInvalid ride time format. Use ISO format: YYYY-MM-DDTHH:MM:SS+HH:MM.POINT( )  srid   minutes   last_known_location)rO   rO      TF)vehicle__status vehicle__assignments__driver__invehicle__assignments__activevehicle__assignments__on_ride0.01rounding)idvehicle_typeseating_capacityper_km_chargeestimated_farer   zDAvailable vehicle types with estimated fares retrieved successfully.r?   )%r@   rA   r   r   rB   	TypeErrorKeyErrorr   datetimestrptime
ValueErrorcalculate_distancer   strr   nowr   r   r'   annotater   order_byr   filterdriverdistinctr(   rp   quantizer   r   rE   rm   rn   ro   rC   rF   )rG   rH   rU   rV   rW   from_latitudefrom_longitudeto_latitudeto_longituderO   e
from_pointadjusted_current_timenearest_driversr}   available_vehicle_typesvehicle_types_with_faresrn   rq   rounded_fares                       r0   postzAvailableVehicleTypesView.post^   s
   ||''7\\%%l3
LL$$[1		^ 22 	(4M)+6N$Z0K%k2L		 ))229>STI	)~{LH vn%5Q}oQGdS
 (11E E!=$y'<<= -44==!"7D > hz"2A'O '2&9&9&@&@ $0?2&,FMM2 .2.3 'A ' hj $ '2&9&9&=&=&?&H&H&J##% 3 	L%(B(BBN)2276?X2VL$++&//$0$=$=(4(E(E%1%?%?&+L&9	 a0
 %%
 	
} 8$ 	| 22 	  	e 22 	  	Q022 	$2sH   7I  J -J< %K9
-JJ'J98J9<	K6&K1+K61K6Nr#   r$   r%   r	   r,   r
   r-   r   r.   r/   r0   rS   rS   Z   s    12)*X
r/   rS   c                       e Zd ZegZegZd Zy)FareEstimationViewc           
         t        d       |j                  j                  d      }|j                  j                  d      }|j                  j                  d      }|j                  j                  d      }|r|r|r|s)t        d       t        ddd	t        j
                  
      S 	 t        d       |d   }|d   }|d   }|d   }		 t        d       t        ||||	      }
	 t        d       t        j                  j                  |      }t        d       |
|j                  z  }|j!                  t#        d      t$              }t        d       t        ddd|j                  |
t'        |      dt        j(                  
      S # t        t        f$ r, t        d       t        ddd	t        j
                  
      cY S w xY w# t        $ r<}t        d       t        dt        |      d	t        j
                  
      cY d }~S d }~ww xY w# t        j                  $ r, t        d       t        ddd	t        j                  
      cY S w xY w)NzStep 1: Retrieving request datavehicle_type_idrU   rV   rW   z0Step 2: Checking if all required data is presentr   z6Vehicle type, address details, ride time are required.r:   r   z6Step 3: Extracting latitude and longitude from addressr7   r8   z'Step 4: Handling invalid address formatrX   zStep 5: Calculating distancez!Step 6: Handling validation errorzStep 7: Retrieving vehicle typerm   z-Step 8: Handling vehicle type not found errorVehicle type not found.z"Step 9: Calculating estimated farerj   rk   zStep 13: Returning responser   'Estimated fare calculated successfully.20)r   r;   	base_farerate_per_kmtotal_kmrq   )printr@   rA   r   r   rB   rr   rs   rw   r   rx   r   r'   DoesNotExistHTTP_404_NOT_FOUNDrp   r   r   r   rC   rF   )rG   rH   r   rU   rV   rW   r   r   r   r   rO   r   rn   rq   r   s                  r0   r   zFareEstimationView.post   sC   /0!,,**+<=||''7\\%%l3
LL$$[1	LZIDEW 22 	JK(4M)+6N$Z0K%k2L
	01)~{LH	34&..22o2FL 	23!L$>$>>%..wv.R+,D!+99$"'"5 %%

 
	
K 8$ 	;<| 22 	  	56Q022 	 '' 	AB)BC00 	sB   *F	 
G $+H 	8GG	H1HHH<IINr   r.   r/   r0   r   r      s    12)*E
r/   r   c                       e Zd ZegZegZd Zy)ConfirmRideViewc                    |j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }t        |||||g      st        dd	d
t        j
                        S t        j                  j                  |j                  d|i      \  }	}
t        j                  j                  |j                  |	|t        d|d    d|d    dd      t        d|d    d|d    dd      ||t        j                  j                  |d      d	      }t!        t"        |       t        dd|j$                  dt        j&                        S )Nr   pickup_namedropoff_namepickup_locationdropoff_locationrW   device_tokenr   zeAll fields  vehicle_type_id, pickup_location, dropoff_location, ride_time, device_token are required.r:   r   userdefaultsrZ   r8   r[   r7   r\   r]   r^   rY   pending)	r   user_devicer   r   r   r   r   rW   r   r   zRide confirmed successfully.)r   r;   ride_id)r@   rA   r(   r   r   rB   r   r'   get_or_creater   Ridecreater   r   rt   ru   setup_async_tasksprocess_new_riderm   rF   )rG   rH   r   r   r   r   r   rW   r   r   _new_rides               r0   r   zConfirmRideView.post	  s   !,,**+<=ll&&}5||''7!,,**+<="<<++,>?LL$$[1	||''7 
   G 22   55(F 6 
Q
 <<&&#+#56a
8S7TTUV %)+67q9I*9U8VVWX $%''00<QR ' 
$ 	*H59#;;
 %%
 	
r/   Nr   r.   r/   r0   r   r     s    12)*:
r/   r   c                       e Zd ZegZegZd Zy)DriverRideDetailViewc                    	 t         j                  j                  |      }t	        dd|j                  j                   d|j                  j                   |j                  |j                  |j                  j                  |j                  j                  d	|j                  j                  |j                  j                  d	|j                   rt#        |j                         nd |j$                  rt#        |j$                        nd d
dt
        j&                        S # t         j                  $ r! t	        dddt
        j                        cY S w xY w)Nr   r   Ride not found.r:   r   r   $Ride details retrieved successfully.r[   r7   r8   )	user_namer   r   pickup_coordinatesdropoff_coordinatesrO   rq   r   r;   ride_details)r   r'   rA   r   r   r   r   r   
first_name	last_namer   r   r   yxr   rO   rC   rq   rF   )rG   rH   r   rides       r0   rA   zDriverRideDetailView.getJ  s*   	<<##w#/D A$(II$8$8#9499;N;N:O!P#'#3#3$($5$5$($8$8$:$:%)%9%9%;%;+
 %)$9$9$;$;%)%:%:%<%<, 9=dmm 446:6I6Id112t!* %%-
 	
    	):;00 	s    D" "1EENr#   r$   r%   r	   r,   r
   r-   rA   r.   r/   r0   r   r   F  s    12)* 
r/   r   c                       e Zd ZegZegZd Zy)UpdateDriverLocationViewc           
         |j                   j                  d      }|j                   j                  d      }||t        dddt        j                        S 	 t
        j                  j                  |j                  dt        t        |      t        |            i      \  }}t        d	d
dt        j                        S # t        $ r! t        dddt        j                        cY S w xY w)Nr7   r8   errorr9   r:   r   rd   )r}   r   successzLocation updated successfully.zInvalid latitude or longitude.)r@   rA   r   r   rB   r   r'   update_or_creater   r   rC   rF   rv   )rG   rH   r7   r8   driver_locationcreateds         r0   r   zUpdateDriverLocationView.postq  s    <<##J/LL$$[1	y0"/UV22 
	'5'='='N'N||)5y1A5?+S (O ($OW $1QR))   	"/OP22 	s   A)C 'C.-C.Nr   r.   r/   r0   r   r   m      12)*r/   r   c                       e Zd ZegZegZd Zy)AcceptRideViewc                    |j                   }|j                  st        dddt        j                        S 	 t
        j                  j                  |      }t        j                  j                  |d      j                         }|rd|_        ||_        |j                  |_        |j                          d|_        |j                          t        j                  j!                  ||d	       t#        |j                   |       nt        dd
dt        j$                        S 	 t        dddt        j*                        S # t
        j&                  $ r! t        dddt        j(                        cY S w xY w)Nr   zOnly drivers can accept rides.r:   r   r   T)r}   activeaccepted)r   r}   responsez.No active vehicle assignment found for driver.,Ride request not found or already processed.r   zRide accepted successfully.)r   	is_driverr   r   HTTP_403_FORBIDDENr   r'   rA   r   r|   firstr}   vehiclesaveon_rideDriverResponseLogr   notify_user_ride_acceptedrB   r   r   rF   rG   rH   r   r}   r   vehicle_assignments         r0   r   zAcceptRideView.post  sm   )IJ00 
#	<<##w#/D!2!:!:!A!Ad "B "eg  "($199		-1"*"'')!))00!' 1  *$))T:"##S "66  ;& %BC%%
 	
    	M 00 	s   C-E 1E98E9Nr   r.   r/   r0   r   r     s    12)*1
r/   r   c                       e Zd ZegZegZd Zy)RejectRideViewc                    |j                   }|j                  j                  d      }|j                  st	        dddt
        j                        S 	 t        j                  j                  |      }d|_        |j                          t        j                  j                  ||d|       t	        d
ddt
        j                        S # t        j                  $ r! t	        dd	dt
        j                        cY S w xY w)Nreasonr   zOnly drivers can reject rides.r:   r   r   rejected)r   r}   r   r   r   r   zRide rejected successfully.)r   r@   rA   r   r   r   r   r   r'   r   r   r   r   r   rF   )rG   rH   r   r}   r   r   s         r0   r   zRejectRideView.post  s    !!(+)IJ00 
	<<##w#/D$DKIIK%%,,&:f -  %BC%%
 	
    	M 00 	s   AC 1C?>C?Nr   r.   r/   r0   r   r     s    12)*
r/   r   c                       e Zd ZegZegZd Zy)DriverLocationViewc                    |j                   }	 t        j                  j                  ||dg      }t        j                  j                  |j
                        }t        dd|j                  j                  |j                  j                  ddt        j                        S # t        j                  $ r! t        d	d
dt        j                        cY S t        j                  $ r! t        d	ddt        j                        cY S w xY w)Nr   )rm   r   
status__inr}   r   z'Driver location retrieved successfully.r   )r   r;   r   r   r   zRide not found or not active.r:   zDriver location not available.)r   r   r'   rA   r   r}   r   rd   r   r   r   rF   r   r   )rG   rH   r   r   r   r   s         r0   rA   zDriverLocationView.get  s    ||	<<##wTzl#SD,44888LOH$3$G$G$I$I%4%H%H%J%J( ))
 
    	)HI00  ** 	)IJ00 	s   BB% %1D0D
DNr   r.   r/   r0   r   r     r   r/   r   c                       e Zd ZegZegZd Zy)StartRideViewc                    |j                   j                  d      }|j                  }|st        dddt        j
                        S 	 t        j                  j                  ||d      }t        |j                        t        |      k(  rdt        j                         |_        d|_        |j                          t        |j                  |       t        d	d
dt        j                        S t        dddt        j
                        S # t        j                   $ r! t        dddt        j"                        cY S w xY w)Notpr   z"OTP is required to start the ride.r:   r   r   rm   r}   r   startedr   zRide started successfully.zInvalid OTP.z&Ride not found or already in progress.)r@   rA   r   r   r   rB   r   r'   rx   r   r   ry   
start_timer   notify_user_ride_startedrF   r   r   )rG   rH   r   r   r}   r   s         r0   r   zStartRideView.post  s   llu%)MN22 
	<<##wvj#QD488}C("*,,.'		(D9 -IJ!-- 
   ^<!66     	)QR00 	s   	B&D 0D 1EENr   r.   r/   r0   r   r     s    12)*r/   r   c                       e Zd ZegZegZd Zy)EndRideViewc                    |j                   }	 t        j                  j                  ||d      }d|_        t        j                         |_        |j                          t        |j                   |       t        j                  j                  |      }d|_        |j                          t        dddt        j                  	      S # t        j                  $ r! t        d
ddt        j                  	      cY S w xY w)Nin_progressr   	completedr   Fr   zRide completed successfully.r:   r   r   z"Ride not found or not in progress.)r   r   r'   rA   r   r   ry   end_timer   notify_user_ride_finishedr   r   r   rF   r   r   r   s         r0   r   zEndRideView.post5  s    	<<##wvm#TD%DK$LLNDMIIK%dii6!2!:!:!>!>f!>!M).&##%)GH))     	)MN00 	s   B<C 1C?>C?Nr   r.   r/   r0   r   r   1  s    12)*r/   r   c                       e Zd ZegZegZd Zy)RideDetailViewc           
         |j                   }	 t        j                  j                  ||      }t	        dd|j
                  j
                  |j                  j                  |j                  j                  |j                  |j                  ddt        j                        S # t        j                  $ r! t	        ddd	t        j                        cY S w xY w)
N)rm   r   r   r   )rn   r   driver_namer   r   r   r   r   r   r:   )r   r   r'   rA   r   rn   r   plate_numberr}   r   r   r   rF   r   r   )rG   rH   r   r   r   s        r0   rA   zRideDetailView.getP  s    ||	<<##wT#:DE(,(9(9(F(F#'<<#<#<'+{{'='=#xx"&++%
 ))     	):;00 	s   BB$ $1CCNr   r.   r/   r0   r   r   L  s    12)*r/   r   c                       e Zd ZegZegZd Zy)DriverApproachingViewc                    |j                   }|j                  st        dddt        j                        S 	 t
        j                  j                  ||d      }t        |j                   |       t        dd	dt        j                        S # t
        j                  $ r! t        dddt        j                        cY S w xY w)
Nr   z0Only drivers can send approaching notifications.r:   r   r   r   +Ride not found or not in an accepted state.r   z2Driver approaching notification sent successfully.)r   r   r   r   r   r   r'   rA   notify_user_driver_reachingr   r   rF   rG   rH   r   r}   r   s        r0   r   zDriverApproachingView.postn  s    Q 00 	<<##wvj#QD'		48 O %%
 	
    	)VW00 	   8B 1CCNr   r.   r/   r0   r   r   j  s    12)*
r/   r   c                       e Zd ZegZegZd Zy)DriverArrivedViewc                    |j                   }|j                  st        dddt        j                        S 	 t
        j                  j                  ||d      }t        |j                   |       t        dd	dt        j                        S # t
        j                  $ r! t        dddt        j                        cY S w xY w)
Nr   z,Only drivers can send arrived notifications.r:   r   r   r   r   r   z.Driver arrived notification sent successfully.)r   r   r   r   r   r   r'   rA   notify_user_driver_arrivedr   r   rF   r   s        r0   r   zDriverArrivedView.post  s    M 00 	<<##wvj#QD&tyy$7 %UV%%
 	
    	)VW00 	r   Nr   r.   r/   r0   r  r    s    12)*
r/   r  c                   "    e Zd ZdZegZegZd Zy)RideListViewz5
    View to list users with optional filtering.
    c                 .   	 |j                   }t        j                  j                  d
i |}t	        |d      }t        dd|j                   dt        j                        S # t        $ r(}t        ddd	t        j                        cY d }~S d }~ww xY w)NTr=   r   zRides retrieved successfullyr?   r   r   zAn unexpected error occurredr:   r.   )
r@   r   r'   r|   RideSerializerr   r   rF   	ExceptionHTTP_500_INTERNAL_SERVER_ERROR)rG   rH   filter_paramsridesrP   r   s         r0   r   zRideListView.post  s    	#LLMLL''8-8E'D9J=&OO
 ))   	)GH<< 	s   A A# #	B,B	BBN	r#   r$   r%   rQ   r   r,   r   r-   r   r.   r/   r0   r  r    s     99%r/   r  c                       e Zd ZegZegZd Zy)CreateSharedRideViewc                    |j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }	t        ||||||	g      st        d	d
dt        j
                        S t        |	      d	k  rt        d	ddt        j
                        S 	 t        j                  j                  |      }
t        j                  j                  |j                  d|i      \  }}t        j                  j                  |j                  |
t!        d|d    d|d    dd      t!        d|d    d|d    dd      t"        j$                  j'                  |d      |
j(                  t        |	      t        |	      d|||      }t        dd|j*                  dt        j,                        S # t        j                  $ r! t        d	ddt        j                        cY S w xY w)Nr   r   r   r   r   rW   r   seats_requiredr   zuAll fields are required: vehicle_type_id, pickup_location, dropoff_location, ride_time, device_token, seats_required.r:   r   7The number of seats required must be greater than zero.r   zInvalid vehicle type ID.r   rZ   r8   r[   r7   r\   r]   r^   rY   r   )primary_userrn   primary_pickup_locationprimary_dropoff_locationrW   seats_totalseats_occupiedr  r   r   r   r   r   z!Shared ride created successfully.r   r;   shared_ride_id)r@   rA   r(   r   r   rB   intr   r'   r   r   r   r   r   
SharedRider   r   r   rt   ru   ro   rm   HTTP_201_CREATED)rG   rH   r   r   r   r   r   rW   r   r  rn   r   r   shared_rides                 r0   r   zCreateSharedRideView.post  s   !,,**+<=ll&&}5||''7!,,**+<="<<++,>?LL$$[1	||''7 ))*:;  	
   W 22  ~!#X 22 	&..22o2FL  55(F 6 
Q
 !((// %$+56a
8S7TTUV% &-)+67q9I*9U8VVWX& ''00<QR$55~.~.##%% 0 
* >"-..
 **
 	
C '' 	)CD00 	s   5 I 1J JNr   r.   r/   r0   r  r    s    12)*Q
r/   r  c                       e Zd ZegZegZd Zy)ListAvailableSharedRidesViewc                 4   |j                   j                  d      }|j                   j                  d      }|j                   j                  d      }t        |||g      st        dddt        j
                        S t        t        |d         t        |d	         d
      }t        t        |d         t        |d	         d
      }t        j                  j                  |d      }|t        j                  d      z
  }|t        j                  d      z   }	t        j                  j                  ||	f|t        d      f|t        d      fd      }
g }|
D ]  }|j!                  |j"                  |j$                  j$                  |j$                  j"                  |j&                  |j(                  |j&                  z
  |j*                  |j,                  |j.                  j1                         d        t        dd|dt        j2                        S )Nr   r   rW   r   zFAll fields are required: pickup_location, dropoff_location, ride_time.r:   r   r8   r7   r]   r^   rY   r<   ra   g      ?)kmr   )ride_time__range%primary_pickup_location__distance_lte&primary_dropoff_location__distance_lter   )r  rn   r   r  seats_remainingr   r   rW   r   z+Available shared rides listed successfully.)r   r;   r  )r@   rA   r(   r   r   rB   r   rC   r   rt   ru   r   r  r'   r|   r   rE   rm   rn   r  r  r   r   rW   	isoformatrF   )rG   rH   r   r   rW   user_pickup_pointuser_dropoff_pointuser_ride_timetime_window_starttime_window_endavailable_rides
rides_listr   s                r0   r   z!ListAvailableSharedRidesView.post#  s   !,,**+<="<<++,>?LL$$[1	 O%5yABg 22  "/+.//*-.

 #";/0":./
 "**33I?TU*X-?-?-KK(8+=+=b+II %,,33/A3Da3i2P4FS	3R	 4 
 
# 	D&*gg$($5$5$B$B'+'8'8';';&*&9&9'+'7'7$:M:M'M#'#3#3$($5$5!%!9!9!;		 H#
 %%
 	
r/   Nr   r.   r/   r0   r  r    s    12)*?
r/   r  c                       e Zd ZegZegZd Zy)JoinSharedRideViewc           	      2   |j                   j                  d      }|j                   j                  d      }|j                   j                  d      }t        |||g      st        dddt        j
                        S t        |      dk  rt        dddt        j
                        S 	 t        j                  j                  |d	
      }|j                  t        |      z   |j                  kD  rt        dddt        j
                        S t        j                  j                  |j                  d|i      \  }}t         j                  j#                  ||j                  |j$                  |j&                  t        |      |       |xj                  t        |      z  c_        |j)                          t        dd|j*                  dt        j,                        S # t        j                  $ r! t        dddt        j                        cY S w xY w)Nr  r   r  r   zFAll fields are required: shared_ride_id, device_token, seats_required.r:   r   r  r   rm   r   z'Shared ride not found or not available.zNot enough seats available.r   )r  participant_userr   r   r  r   r   z$Successfully joined the shared ride.r  )r@   rA   r(   r   r   rB   r  r  r'   r   r   r  r  r   r   r   SharedRideParticipantr   r  r  r   rm   rF   )rG   rH   r  r   r  r  r   r   s           r0   r   zJoinSharedRideView.posti  s    ))*:;||''7 ))*:; NL.ABg 22  ~!#X 22 	$,,00N90UK %%N(;;k>U>UU)FG22   55(F 6 
Q
 	%%,,#$\\'??(AA~.$ 	- 	
 	""c.&99"A"-..
 %%
 	
A && 	)RS00 	s   +!G" "1HHNr   r.   r/   r0   r.  r.  e  s    12)*C
r/   r.  c                   .    e Zd ZdZegZegZd Zd Z	d Z
y)SharedRideListViewz<
    View to list shared rides with optional filtering.
    c                 >    t         j                  j                         S N)r  r'   r(   rG   s    r0   get_querysetzSharedRideListView.get_queryset  s    !!%%''r/   c                 8   g }|D ]  }||j                   j                         D cg c]S  }||j                  |j                  |j                  |j
                  |j                  |j                  |j                  dU c}d}|j                  |        |S c c}w )N)participantr   r   r   r   r   r  	joined_at)r   participants)
r<  r(   r   r   r   r   r   r  r;  rE   )rG   r)   combined_datar   r:  	ride_datas         r0   perform_querysetz#SharedRideListView.perform_queryset  s     	,D (,'8'8'<'<'>! $ (3(3(@(@+6+F+F,7,H,H'2'>'>(3(@(@*5*D*D%0%:%:	!I    +#	,$ !s   ABc                     t         S r6  )SharedRideSerializerr7  s    r0   get_serializer_classz'SharedRideListView.get_serializer_class  s    ##r/   N)r#   r$   r%   rQ   r   r,   r   r-   r8  r?  rB  r.   r/   r0   r4  r4    s)     99%(,$r/   r4  c                   "    e Zd ZdZegZegZd Zy)RouteCreateViewz4
    View to add a new route and its sequences.
    c                 B   	 |j                   j                  d      }|j                   j                  d      }|j                   j                  d      }t        j                  j	                  |d   |d   |d   d      \  }}t        j                  j	                  |d   |d   |d   d      \  }}g }|D ]W  }	|	j                  d	      }
t        j                  j	                  |	d   |	d   |	d   d      \  }}|j                  ||
d
       Y t        j                  j                  |j                   j                  d      |j                   j                  d      ||      }t        |d       D ]*  }t        j                  j                  ||d   |d	          , t        |      }t        |j                   t        j                        S # t        $ rD}t        dt        |      t!        j"                         dt        j$                        cY d }~S d }~ww xY w)Npickup_pointdropoff_pointintermediate_pointsnamer7   r8   r   rI  r   orderpointrK  description)rI  rN  rF  rG  c                     | d   S NrK  r.   r   s    r0   <lambda>z&RouteCreateView.post.<locals>.<lambda>	  s
    1W: r/   keyrM  routerM  rK  r   r   r   r;   t)r@   rA   
RoutePointr'   r   rE   Router   sortedSequenceRouteSerializerr   r   r  r  rx   	traceback
format_excrB   )rG   rH   pickup_point_datadropoff_point_dataintermediate_points_datarF  r   rG  rH  
point_datarK  rM  rV  sequence_datarP   r   s                   r0   r   zRouteCreateView.post  s+   ;	 ' 0 0 @!(!1!1/!B'.||'7'78M'N$ %/$6$6$G$G&v. 1* =!2;!? %H %!L' &0%7%7%H%H'/ 2: >!3K!@ &I &"M7 #%6 	M
"w/!+!3!3!D!D#F+$.z$:%/%< "E "w $**UU+KL	M MM((\\%%f-#LL,,];)+	 ) E "((;AU!V   '''0'0 (  )/JJOOF4K4KLL 	Qi6J6J6LM22 	s   GG 	H9HHHNr  r.   r/   r0   rD  rD    s     99%<r/   rD  c                   "    e Zd ZdZegZegZd Zy)RouteUpdateViewz=
    View to update an existing route and its sequences.
    c                    	 t         j                  j                  |      }|j                  j                  d      }|j                  j                  d      }|j                  j                  d      }|r7t        j                  j                  |d   |d   |d   d	      \  }}||_        |r7t        j                  j                  |d   |d   |d   d	      \  }	}|	|_        |rg }
|D ]W  }|j                  d
      }t        j                  j                  |d   |d   |d   d	      \  }}|
j                  ||d       Y |j                  j                         j                          t        |
d       D ]*  }t        j                  j                  ||d   |d
          , |j                  j                  d|j                        |_        |j                  j                  d|j                         |_        |j#                          t%        |      }t'        |j                  t(        j*                        S # t         j,                  $ r! t'        dddt(        j.                        cY S t0        $ rD}t'        dt3        |      t5        j6                         dt(        j8                        cY d }~S d }~ww xY w)Nr   rF  rG  rH  rI  r7   r8   r   rJ  rK  rL  c                     | d   S rP  r.   rQ  s    r0   rR  z%RouteUpdateView.put.<locals>.<lambda>V  s
    qz r/   rS  rM  rU  rN  r   r   Route not foundr:   rW  )rZ  r'   rA   r@   rY  r   rF  rG  rE   	sequencesr(   deleter[  r\  r   rI  rN  r   r]  r   r   rF   r   r   r  rx   r^  r_  rB   )rG   rH   route_idrV  r`  ra  rb  rF  r   rG  rH  rc  rK  rM  rd  rP   r   s                    r0   putzRouteUpdateView.put#  s   M	MM%%%2E !( 0 0 @!(!1!1/!B'.||'7'78M'N$ !(2(:(:(K(K*62$5j$A%6{%C )L )%g &2" ")3););)L)L+F3$6z$B%7%D *M *&w '4# (&(#": 	QJ&NN73E%/%7%7%H%H'/(2:(>)3K)@" &I &NE7 (../OP	Q ##%,,. &,'-A& M $$++#+G4+G4 ,  !))&%**=EJ ' 0 0@Q@Q REJJL )/JJOOF4F4FGG!! 	):;00 
  	Qi6J6J6LM22 	s$   H;H> >1J=1J=99J82J=8J=N)	r#   r$   r%   rQ   r   r,   r   r-   rm  r.   r/   r0   rf  rf    s      99%Nr/   rf  c                   "    e Zd ZdZegZegZd Zy)RouteListViewz"
    View to list all routes.
    c                    	 t         j                  j                         }t        |d      }t	        |j
                  t        j                        S # t        $ r1}t	        dt        |      dt        j                        cY d }~S d }~ww xY wNTr=   r   r   r:   )rZ  r'   r(   r]  r   r@   r   rF   r  rx   rB   )rG   rH   routesrP   r   s        r0   rA   zRouteListView.get|  sq    	]]&&(F )d;J JOOF4F4FGG 	Q09T9T 	   AA 	B&BBBN)	r#   r$   r%   rQ   r   r,   r   r-   rA   r.   r/   r0   ro  ro  t  s     99%r/   ro  c                   "    e Zd ZdZegZegZd Zy)RouteDeleteViewz!
    View to delete a route.
    c                 z   	 t         j                  j                  |      }|j                          t	        ddit
        j                        S # t         j                  $ r! t	        dddt
        j                        cY S t        $ r1}t	        dt        |      dt
        j                        cY d }~S d }~ww xY w)Nr   zRoute deleted successfullyr   r   ri  r:   )rZ  r'   rA   rk  r   r   HTTP_204_NO_CONTENTr   r   r  rx   rB   )rG   rH   rl  rV  r   s        r0   rk  zRouteDeleteView.delete  s    	MM%%h/E LLN7811 
 !! 	):;00 
  	Q09T9T 	s$   AA 1B:B:	&B5/B:5B:N)	r#   r$   r%   rQ   r   r,   r   r-   rk  r.   r/   r0   ru  ru    s     99%r/   ru  c                       e Zd ZegZegZd Zy)ScheduledRideMasterCreateViewc           	      d   	 |j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }t        ||||||g      st        ddd	t        j
                  
      S t        j                  j                  |      }t        j                  j                  |      }	t        j                         5  t        j                  j                  |||||	|      }
d d d        t        
      }t        |j                   t        j                  
      S # 1 sw Y   9xY w# t        j                  $ r! t        ddd	t        j                   
      cY S t        j                  $ r! t        ddd	t        j                   
      cY S t"        $ r1}t        dt%        |      d	t        j
                  
      cY d }~S d }~ww xY w)NrI  starting_timeending_timerV  r   r   r   All fields are required.r:   r   r   )rI  r{  r|  rV  r   r   Route not found.Vehicle not found.)r@   rA   r(   r   r   rB   rZ  r'   r   r   atomicScheduledRideMasterr   ScheduledRideMasterSerializerr  r   r   r  rx   )rG   rH   rI  r{  r|  rl  
vehicle_idmaster_statusrV  r   scheduled_ride_masterrP   r   s                r0   r   z"ScheduledRideMasterCreateView.postp  s   -	<<##F+D#LL,,_=M!,,**=9K||''0H )))4J#LL,,X6M}k8ZW   -GH!66 
 MM%%%2Eoo))Z)8G##% (;(C(C(J(J"/ +#( )K )% 77LMJJOOF4K4KLL  !! 	);<00  ## 	)=>00   	Q09T9T 	sI   CF AF '&F7F F
F 1H/0H/6H/>&H*$H/*H/N)r#   r$   r%   r   r,   r   r-   r   r.   r/   r0   ry  ry  l  s    89%.r/   ry  c                       e Zd ZegZegZd Zy)ScheduledRideMasterUpdateViewc                    	 |j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  d      }t        ||||||g      st        ddd	t        j
                  
      S t        j                  j                  |      }	t        j                  j                  |      }
t        j                  j                  |      }||_
        ||_        ||_        |	|_        |
|_        ||_        |j                          t!        |      }t        |j                   t        j"                  
      S # t        j$                  $ r! t        ddd	t        j&                  
      cY S t        j$                  $ r! t        ddd	t        j&                  
      cY S t        j$                  $ r! t        ddd	t        j&                  
      cY S t(        $ r1}t        dt+        |      d	t        j
                  
      cY d }~S d }~ww xY w)NrI  r{  r|  rV  r   r   r   r}  r:   r   r   r~  r   Scheduled Ride Master not found.)r@   rA   r(   r   r   rB   rZ  r'   r   r  rI  r{  r|  rV  r   r   r  rF   r   r   r  rx   )rG   rH   rm   rI  r{  r|  rl  r  r  rV  r   r  rP   r   s                 r0   rm  z!ScheduledRideMasterUpdateView.put  s$   1	<<##F+D#LL,,_=M!,,**=9K||''0H )))4J#LL,,X6M}k8ZW   -GH!66 
 MM%%%2Eoo))Z)8G$7$?$?$C$Cr$C$J!)-!&2?!/0;!-*/!',3!)+8!(!&&(67LMJJOOF4F4FGG!! 	);<00  ## 	)=>00  #// 	)KL00   	Q09T9T 	s7   CF C	F 1I-0I-0I-4I-<&I("I-(I-N)r#   r$   r%   r   r,   r   r-   rm  r.   r/   r0   r  r    s    89%2r/   r  c                       e Zd ZegZegZd Zy)ScheduledRideMasterDeleteViewc                 ~   	 t         j                  j                  |      }|j                          t	        dddt
        j                        S # t         j                  $ r! t	        dddt
        j                        cY S t        $ r1}t	        dt        |      dt
        j                        cY d }~S d }~ww xY w)Nr   r   z+Scheduled Ride Master deleted successfully.r:   r   r   r  )r  r'   rA   rk  r   r   rw  r   r   r  rx   rB   )rG   rH   rm   r  r   s        r0   rk  z$ScheduledRideMasterDeleteView.delete  s    	$7$?$?$C$Cr$C$J!!((*)VW11  #// 	)KL00   	Q09T9T 	s$   AA 1B<B<&B71B<7B<N)r#   r$   r%   r   r,   r   r-   rk  r.   r/   r0   r  r    s    89%r/   r  c                       e Zd ZegZegZd Zy)ScheduledRideMasterListViewc                    	 t         j                  j                         }t        |d      }t	        |j
                  t        j                        S # t        $ r1}t	        dt        |      dt        j                        cY d }~S d }~ww xY wrq  )r  r'   r(   r  r   r@   r   rF   r  rx   rB   )rG   rH   scheduled_ridesrP   r   s        r0   rA   zScheduledRideMasterListView.get  so    	199==?O6TRJJOOF4F4FGG 	Q09T9T 	rs  N)r#   r$   r%   r   r,   r   r-   rA   r.   r/   r0   r  r    s    89%r/   r  c                       e Zd ZegZegZd Zy)ScheduledRideMobileListViewc                    	 t        |j                  j                  d            }t        |j                  j                  d            }||f}t        j                         j                         }	 t        j                  j                  d      }|j                         st        dd	dt        j                        S g }|D ]  }	 t         j                  j                  |t        j                         j#                         
      }	|	j                  dk(  r4|	j$                  |	j&                  z
  }
|
dkD  r||
d}|j)                  |        |st        dd	dt        j                        S g }|D ]  }|d   }|j2                  }|j4                  gt7        |j8                  j;                               z   }|D ]  }|j<                  |j>                  f}tA        ||      jB                  }|dk  s7tA        ||j4                  j<                  |j4                  j>                  f      jB                  |_"        |j)                  |          |jG                  d        g }|D ]5  }tI        |d         }|j                  }|d   |d<   |j)                  |       7 t        dd|dt        j                        S # t        t        f$ r! t        dddt        j                        cY S w xY w# t         j*                  $ r8 ||j,                  j.                  j0                  d}|j)                  |       Y rw xY w# tJ        $ r2}t        ddtM        |      dt        jN                        cY d }~S d }~ww xY w)Nr7   r8   r   z'Invalid latitude or longitude provided.r:   r   r   r   zNo rides available.scheduled_ridedater   )r   available_seatsr      c                      | d   j                   S )Nr   )distance_to_start)entrys    r0   rR  z1ScheduledRideMobileListView.get.<locals>.<lambda>  s    uV}/N/N r/   rS  r  z%Scheduled Rides Fetched successfully.)r   r;   RideszUnexpected error)r   r;   	exception)(rC   r@   rA   rr   rv   r   r   rB   r   ry   timer  r'   r|   existsrF   ScheduledRideDayr  total_seatsbooked_seatsrE   r   r   rn   ro   rV  rF  listrH  r(   r7   r8   r   r   r  sortScheduledRideMobileSerializerr  rx   r	  )rG   rH   rI   rJ   rK   current_timer  filtered_ridesr   scheduled_ride_dayr  
ride_entryfinal_ridesr  rV  pointsrM  point_locationrO   response_dataride_serializerr>  r   s                          r0   rA   zScheduledRideMobileListView.getb  sn   	!',,"2"2:">?M"7<<#3#3K#@AN '7||~**,H	199@@@QO"))+ -BC!-- 
  N' 66)9)A)A)E)E'+(,,.2E2E2G *F *& *00I=.::=O=\=\\ ( +Q.26?)[J*11*=6& " -BC!-- 
 K' V}

,,-U5N5N5R5R5T0UU# 	E&+nneoo%FN'~FIIH2~19)"//88%:L:L:V:VW2 " . $**51		 !NOM$ 0"?f"N+00	/45F/G	+,$$Y/	0 F*
 )) K :& 	)RS22 	> (44 6 $+/<<+D+D+U+U"J #))*56\  	);#a&Q<< 	sk   AJ8 1AL9 ?L9 BK+!L9 -BL9 /CL9 8-K('K(+AL62L9 5L66L9 9	M4'M/)M4/M4Nr   r.   r/   r0   r  r  ^  s    12)*Ur/   r  c                       e Zd ZegZegZd Zy)ScheduledFareEstimationViewc                    |j                   j                  d      }|j                   j                  d      }|j                   j                  d      }|j                   j                  dd      }|j                   j                  d      }|r|r|r|st        ddd	t        j                  
      S 	 |d   }|d   }|d   }	|d   }
	 t        |||	|
      }	 t        j                  j                  |      }||j                  z  |z  }|j                  t!        d      t"              }t        dd|j$                  |j                  ||t'        |      dt        j(                  
      S # t
        t        f$ r! t        ddd	t        j                  
      cY S w xY w# t        $ r1}t        dt        |      d	t        j                  
      cY d }~S d }~ww xY w# t        j                  $ r! t        ddd	t        j                  
      cY S w xY w)Nr   rU   rV   r  r   rW   r   zKVehicle type, address details, ride time, and seats required are mandatory.r:   r   r7   r8   rX   r   r   rj   rk   r   )r   r;   r   rate_per_km_per_seatr   r  rq   )r@   rA   r   r   rB   rr   rs   rw   r   rx   r   r'   r   r   fare_per_km_per_seatr   r   r   r   rC   rF   )rG   rH   r   rU   rV   r  rW   r   r   r   r   rO   r   rn   rq   r   s                   r0   r   z ScheduledFareEstimationView.post  s   !,,**+<=||''7\\%%l3
 ))*:A>LL$$[1	LZIl 22 	(4M)+6N$Z0K%k2L	)-VbcH	&..22o2FL "L$E$EEV%..wv.RD)33(4(I(I$"0"'"5 %%
 	
9 8$ 	| 22 	  	Q022 	 '' 	)BC00 	sB   0E& F  G &-FF	G"&GGG1H
	H
Nr   r.   r/   r0   r  r    s    12)*<
r/   r  c                       e Zd ZegZegZd Zy)JoinScheduledRideViewc           	         |j                   j                  d      }|j                   j                  dd      }|j                   j                  d      }|j                   j                  d      }|r|r|st        dddt        j                  	      S 	 |d
   }|d   }|d
   }|d   }	|j                  }
	 t        j                  j                  |d      }t        j                         j                         }	 t        j                  j                  ||      }|j                  dk7  rt        dddt        j                  	      S 	 |j(                  |j*                  z
  }||kD  rt        dddt        j                  	      S |xj*                  |z  c_        |j-                          t.        j                  j!                  ||
t1        ||      t1        ||	      |       t        dddt        j2                  	      S # t
        t        f$ r! t        dddt        j                  	      cY S w xY w# t        j                  $ r! t        dddt        j                  	      cY S w xY w# t        j                  $ rE t        j                  j!                  |||j"                  j$                  j&                  d      }Y xw xY w)Nr   r  r   
join_point	end_pointr   z0Ride ID, join point, and end point are required.r:   r   r7   r8   zWInvalid point format. Latitude and longitude are required for both join and end points.r   r0  zRide not found or inactive.r  r   z"Ride is not available for joining.)r  r  r  r  zNot enough available seats.)r  r   r  r  r  zSuccessfully joined the ride.)r@   rA   r   r   rB   rr   rs   r   r  r'   r   r   r   ry   r  r  r   r   rn   ro   r  r  r   ScheduledRideParticipantr   rF   )rG   rH   r   r  r  r  join_latitudejoin_longitudeend_latitudeend_longituder   r   todayr  r  s                  r0   r   zJoinScheduledRideView.post  s   ,,""9- ))*:A>\\%%l3
LL$$[1	J9)[\22 
		&z2M'4N$Z0L%k2M ||	&..22gh2OD ##%	!1!9!9!=!=TX]!=!^!((I5 -QR!66  6 -88;M;Z;ZZO+)FG22 
 	''>9'! ((//1]N;L-8) 	0 	
 %DE%%
 	
e 8$ 	  *C  D22 	 #// 	)FG00 	  ,, 	!1!9!9!@!@# LL55FF	 "A "	s8   G> 4!H1 8AI( >-H.-H.11I%$I%(AK ?K Nr   r.   r/   r0   r  r    s    12)*F
r/   r  )Tdecimalr   r   rest_frameworkr   r   !rest_framework_jwt.authenticationr   rest_framework.viewsr   rest_framework.authenticationr	   rest_framework.permissionsr
   r   rest_framework.responser   r   modelsserializersgeopy.distancer   vehiclehub.modelsr   r   r   accounts.modelsr   r   vehiclehub.serializersr   rest_framework.exceptionsr   &django.contrib.gis.db.models.functionsr   django.contrib.gis.measurer   django.contrib.gis.geosr   r   django.utilsr   rt   r   processasyncior^  	django.dbr   ListCreateAPIViewr!   RetrieveUpdateDestroyAPIViewr3   r5   rS   r   r   r   r   r   r   r   r   r   r   r   r  r  r  r  r.  ListAPIViewr4  rD  rf  ro  ru  ry  r  r  r  r  r  r  r.   r/   r0   <module>r     s   % 0 H ( = C , !   # E E 2 8 5 ; ( + ) !     !7 : : 778+P+P 7-
' -
`\
 \
~I
 I
X>
g >
B$
7 $
Nw B5
W 5
p"
W "
J B"G "J' 6W <
G 
D
 
>7 8U
7 U
pC
7 C
LG
 G
T"$-- "$JDg DNVg VrG 2g ~2G 2j6G 6rG .' ZY' Yv@
' @
DJ
G J
r/   