@ -11,6 +11,8 @@ use crate::{ 
			
		
	
		
			
				
					     mail ,   CONFIG ,  
			
		
	
		
			
				
					} ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					use   futures ::{ stream ,   stream ::StreamExt } ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					pub   fn  routes ( )   -> Vec < Route >   {  
			
		
	
		
			
				
					     routes ! [  
			
		
	
		
			
				
					         get_contacts ,  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -36,13 +38,17 @@ pub fn routes() -> Vec<Route> { 
			
		
	
		
			
				
					// region get
  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ get( " /emergency-access/trusted " ) ]  
			
		
	
		
			
				
					fn  get_contacts ( headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					async   fn  get_contacts ( headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					     check_emergency_access_allowed ( ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   emergency_access_list   =   EmergencyAccess ::find_all_by_grantor_uuid ( & headers . user . uuid ,   & conn ) ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   emergency_access_list_json : Vec < Value >   =  
			
		
	
		
			
				
					         emergency_access_list . iter ( ) . map ( | e |   e . to_json_grantee_details ( & conn ) ) . collect ( ) ;  
			
		
	
		
			
				
					     let   emergency_access_list_json   =  
			
		
	
		
			
				
					         stream ::iter ( EmergencyAccess ::find_all_by_grantor_uuid ( & headers . user . uuid ,   & conn ) . await )  
			
		
	
		
			
				
					             . then ( | e |   async   {  
			
		
	
		
			
				
					                 let   e   =   e ;   // Move out this single variable
  
			
		
	
		
			
				
					                 e . to_json_grantee_details ( & conn ) . await  
			
		
	
		
			
				
					             } )  
			
		
	
		
			
				
					             . collect ::< Vec < Value > > ( )  
			
		
	
		
			
				
					             . await ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     Ok ( Json ( json ! ( {  
			
		
	
		
			
				
					       "Data" : emergency_access_list_json ,  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -52,13 +58,17 @@ fn get_contacts(headers: Headers, conn: DbConn) -> JsonResult { 
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ get( " /emergency-access/granted " ) ]  
			
		
	
		
			
				
					fn  get_grantees ( headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					async   fn  get_grantees ( headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					     check_emergency_access_allowed ( ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   emergency_access_list   =   EmergencyAccess ::find_all_by_grantee_uuid ( & headers . user . uuid ,   & conn ) ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   emergency_access_list_json : Vec < Value >   =  
			
		
	
		
			
				
					         emergency_access_list . iter ( ) . map ( | e |   e . to_json_grantor_details ( & conn ) ) . collect ( ) ;  
			
		
	
		
			
				
					     let   emergency_access_list_json   =  
			
		
	
		
			
				
					         stream ::iter ( EmergencyAccess ::find_all_by_grantee_uuid ( & headers . user . uuid ,   & conn ) . await )  
			
		
	
		
			
				
					             . then ( | e |   async   {  
			
		
	
		
			
				
					                 let   e   =   e ;   // Move out this single variable
  
			
		
	
		
			
				
					                 e . to_json_grantor_details ( & conn ) . await  
			
		
	
		
			
				
					             } )  
			
		
	
		
			
				
					             . collect ::< Vec < Value > > ( )  
			
		
	
		
			
				
					             . await ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     Ok ( Json ( json ! ( {  
			
		
	
		
			
				
					       "Data" : emergency_access_list_json ,  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -68,11 +78,11 @@ fn get_grantees(headers: Headers, conn: DbConn) -> JsonResult { 
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ get( " /emergency-access/<emer_id> " ) ]  
			
		
	
		
			
				
					fn  get_emergency_access ( emer_id : String ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					async   fn  get_emergency_access ( emer_id : String ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					     check_emergency_access_allowed ( ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn )   {  
			
		
	
		
			
				
					         Some ( emergency_access )   = >   Ok ( Json ( emergency_access . to_json_grantee_details ( & conn ) ) ) ,  
			
		
	
		
			
				
					     match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( emergency_access )   = >   Ok ( Json ( emergency_access . to_json_grantee_details ( & conn ) . await ) ) ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Emergency access not valid." ) ,  
			
		
	
		
			
				
					     }  
			
		
	
		
			
				
					}  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -90,17 +100,25 @@ struct EmergencyAccessUpdateData { 
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ put( " /emergency-access/<emer_id> " , data =  " <data> " ) ]  
			
		
	
		
			
				
					fn  put_emergency_access ( emer_id : String ,   data : JsonUpcase < EmergencyAccessUpdateData > ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					     post_emergency_access ( emer_id ,   data ,   conn )  
			
		
	
		
			
				
					async   fn  put_emergency_access (  
			
		
	
		
			
				
					     emer_id : String ,  
			
		
	
		
			
				
					     data : JsonUpcase < EmergencyAccessUpdateData > ,  
			
		
	
		
			
				
					     conn : DbConn ,  
			
		
	
		
			
				
					)   -> JsonResult   {  
			
		
	
		
			
				
					     post_emergency_access ( emer_id ,   data ,   conn ) . await  
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ post( " /emergency-access/<emer_id> " , data =  " <data> " ) ]  
			
		
	
		
			
				
					fn  post_emergency_access ( emer_id : String ,   data : JsonUpcase < EmergencyAccessUpdateData > ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					async   fn  post_emergency_access (  
			
		
	
		
			
				
					     emer_id : String ,  
			
		
	
		
			
				
					     data : JsonUpcase < EmergencyAccessUpdateData > ,  
			
		
	
		
			
				
					     conn : DbConn ,  
			
		
	
		
			
				
					)   -> JsonResult   {  
			
		
	
		
			
				
					     check_emergency_access_allowed ( ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   data : EmergencyAccessUpdateData   =   data . into_inner ( ) . data ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   mut   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn )   {  
			
		
	
		
			
				
					     let   mut   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( emergency_access )   = >   emergency_access ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Emergency access not valid." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -114,7 +132,7 @@ fn post_emergency_access(emer_id: String, data: JsonUpcase<EmergencyAccessUpdate 
			
		
	
		
			
				
					     emergency_access . wait_time_days   =   data . WaitTimeDays ;  
			
		
	
		
			
				
					     emergency_access . key_encrypted   =   data . KeyEncrypted ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     emergency_access . save ( & conn ) ? ;  
			
		
	
		
			
				
					     emergency_access . save ( & conn ) . await ? ;  
			
		
	
		
			
				
					     Ok ( Json ( emergency_access . to_json ( ) ) )  
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -123,12 +141,12 @@ fn post_emergency_access(emer_id: String, data: JsonUpcase<EmergencyAccessUpdate 
			
		
	
		
			
				
					// region delete
  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ delete( " /emergency-access/<emer_id> " ) ]  
			
		
	
		
			
				
					fn  delete_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> EmptyResult   {  
			
		
	
		
			
				
					async   fn  delete_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> EmptyResult   {  
			
		
	
		
			
				
					     check_emergency_access_allowed ( ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   grantor_user   =   headers . user ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn )   {  
			
		
	
		
			
				
					     let   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( emer )   = >   {  
			
		
	
		
			
				
					             if   emer . grantor_uuid   ! =   grantor_user . uuid   & &   emer . grantee_uuid   ! =   Some ( grantor_user . uuid )   {  
			
		
	
		
			
				
					                 err ! ( "Emergency access not valid." )  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -137,13 +155,13 @@ fn delete_emergency_access(emer_id: String, headers: Headers, conn: DbConn) -> E 
			
		
	
		
			
				
					         }  
			
		
	
		
			
				
					         None   = >   err ! ( "Emergency access not valid." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
		
			
				
					     emergency_access . delete ( & conn ) ? ;  
			
		
	
		
			
				
					     emergency_access . delete ( & conn ) . await ? ;  
			
		
	
		
			
				
					     Ok ( ( ) )  
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ post( " /emergency-access/<emer_id>/delete " ) ]  
			
		
	
		
			
				
					fn  post_delete_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> EmptyResult   {  
			
		
	
		
			
				
					     delete_emergency_access ( emer_id ,   headers ,   conn )  
			
		
	
		
			
				
					async   fn  post_delete_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> EmptyResult   {  
			
		
	
		
			
				
					     delete_emergency_access ( emer_id ,   headers ,   conn ) . await  
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					// endregion
  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -159,7 +177,7 @@ struct EmergencyAccessInviteData { 
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ post( " /emergency-access/invite " , data =  " <data> " ) ]  
			
		
	
		
			
				
					fn  send_invite ( data : JsonUpcase < EmergencyAccessInviteData > ,   headers : Headers ,   conn : DbConn )   -> EmptyResult   {  
			
		
	
		
			
				
					async   fn  send_invite ( data : JsonUpcase < EmergencyAccessInviteData > ,   headers : Headers ,   conn : DbConn )   -> EmptyResult   {  
			
		
	
		
			
				
					     check_emergency_access_allowed ( ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   data : EmergencyAccessInviteData   =   data . into_inner ( ) . data ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -180,7 +198,7 @@ fn send_invite(data: JsonUpcase<EmergencyAccessInviteData>, headers: Headers, co 
			
		
	
		
			
				
					         err ! ( "You can not set yourself as an emergency contact." )  
			
		
	
		
			
				
					     }  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   grantee_user   =   match   User ::find_by_mail ( & email ,   & conn )   {  
			
		
	
		
			
				
					     let   grantee_user   =   match   User ::find_by_mail ( & email ,   & conn ) . await   {  
			
		
	
		
			
				
					         None   = >   {  
			
		
	
		
			
				
					             if   ! CONFIG . signups_allowed ( )   {  
			
		
	
		
			
				
					                 err ! ( format ! ( "Grantee user does not exist: {}" ,   email ) )  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -192,11 +210,11 @@ fn send_invite(data: JsonUpcase<EmergencyAccessInviteData>, headers: Headers, co 
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					             if   ! CONFIG . mail_enabled ( )   {  
			
		
	
		
			
				
					                 let   invitation   =   Invitation ::new ( email . clone ( ) ) ;  
			
		
	
		
			
				
					                 invitation . save ( & conn ) ? ;  
			
		
	
		
			
				
					                 invitation . save ( & conn ) . await ? ;  
			
		
	
		
			
				
					             }  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					             let   mut   user   =   User ::new ( email . clone ( ) ) ;  
			
		
	
		
			
				
					             user . save ( & conn ) ? ;  
			
		
	
		
			
				
					             user . save ( & conn ) . await ? ;  
			
		
	
		
			
				
					             user  
			
		
	
		
			
				
					         }  
			
		
	
		
			
				
					         Some ( user )   = >   user ,  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -208,6 +226,7 @@ fn send_invite(data: JsonUpcase<EmergencyAccessInviteData>, headers: Headers, co 
			
		
	
		
			
				
					         & grantee_user . email ,  
			
		
	
		
			
				
					         & conn ,  
			
		
	
		
			
				
					     )  
			
		
	
		
			
				
					     . await  
			
		
	
		
			
				
					     . is_some ( )  
			
		
	
		
			
				
					     {  
			
		
	
		
			
				
					         err ! ( format ! ( "Grantee user already invited: {}" ,   email ) )  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -220,7 +239,7 @@ fn send_invite(data: JsonUpcase<EmergencyAccessInviteData>, headers: Headers, co 
			
		
	
		
			
				
					         new_type ,  
			
		
	
		
			
				
					         wait_time_days ,  
			
		
	
		
			
				
					     ) ;  
			
		
	
		
			
				
					     new_emergency_access . save ( & conn ) ? ;  
			
		
	
		
			
				
					     new_emergency_access . save ( & conn ) . await ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     if   CONFIG . mail_enabled ( )   {  
			
		
	
		
			
				
					         mail ::send_emergency_access_invite (  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -232,9 +251,9 @@ fn send_invite(data: JsonUpcase<EmergencyAccessInviteData>, headers: Headers, co 
			
		
	
		
			
				
					         ) ? ;  
			
		
	
		
			
				
					     }   else   {  
			
		
	
		
			
				
					         // Automatically mark user as accepted if no email invites
  
			
		
	
		
			
				
					         match   User ::find_by_mail ( & email ,   & conn )   {  
			
		
	
		
			
				
					         match   User ::find_by_mail ( & email ,   & conn ) . await   {  
			
		
	
		
			
				
					             Some ( user )   = >   {  
			
		
	
		
			
				
					                 match   accept_invite_process ( user . uuid ,   new_emergency_access . uuid ,   Some ( email ) ,   conn . borrow ( ) )   {  
			
		
	
		
			
				
					                 match   accept_invite_process ( user . uuid ,   new_emergency_access . uuid ,   Some ( email ) ,   conn . borrow ( ) ) . await   {  
			
		
	
		
			
				
					                     Ok ( v )   = >   ( v ) ,  
			
		
	
		
			
				
					                     Err ( e )   = >   err ! ( e . to_string ( ) ) ,  
			
		
	
		
			
				
					                 }  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -247,10 +266,10 @@ fn send_invite(data: JsonUpcase<EmergencyAccessInviteData>, headers: Headers, co 
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ post( " /emergency-access/<emer_id>/reinvite " ) ]  
			
		
	
		
			
				
					fn  resend_invite ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> EmptyResult   {  
			
		
	
		
			
				
					async   fn  resend_invite ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> EmptyResult   {  
			
		
	
		
			
				
					     check_emergency_access_allowed ( ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn )   {  
			
		
	
		
			
				
					     let   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( emer )   = >   emer ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Emergency access not valid." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -268,7 +287,7 @@ fn resend_invite(emer_id: String, headers: Headers, conn: DbConn) -> EmptyResult 
			
		
	
		
			
				
					         None   = >   err ! ( "Email not valid." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   grantee_user   =   match   User ::find_by_mail ( & email ,   & conn )   {  
			
		
	
		
			
				
					     let   grantee_user   =   match   User ::find_by_mail ( & email ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( user )   = >   user ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Grantee user not found." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -284,13 +303,15 @@ fn resend_invite(emer_id: String, headers: Headers, conn: DbConn) -> EmptyResult 
			
		
	
		
			
				
					             Some ( grantor_user . email ) ,  
			
		
	
		
			
				
					         ) ? ;  
			
		
	
		
			
				
					     }   else   {  
			
		
	
		
			
				
					         if   Invitation ::find_by_mail ( & email ,   & conn ) . is_none ( )   {  
			
		
	
		
			
				
					         if   Invitation ::find_by_mail ( & email ,   & conn ) . await . is_none ( )   {  
			
		
	
		
			
				
					             let   invitation   =   Invitation ::new ( email ) ;  
			
		
	
		
			
				
					             invitation . save ( & conn ) ? ;  
			
		
	
		
			
				
					             invitation . save ( & conn ) . await ? ;  
			
		
	
		
			
				
					         }  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					         // Automatically mark user as accepted if no email invites
  
			
		
	
		
			
				
					         match   accept_invite_process ( grantee_user . uuid ,   emergency_access . uuid ,   emergency_access . email ,   conn . borrow ( ) )   {  
			
		
	
		
			
				
					         match   accept_invite_process ( grantee_user . uuid ,   emergency_access . uuid ,   emergency_access . email ,   conn . borrow ( ) )  
			
		
	
		
			
				
					             . await  
			
		
	
		
			
				
					         {  
			
		
	
		
			
				
					             Ok ( v )   = >   ( v ) ,  
			
		
	
		
			
				
					             Err ( e )   = >   err ! ( e . to_string ( ) ) ,  
			
		
	
		
			
				
					         }  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -306,28 +327,28 @@ struct AcceptData { 
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ post( " /emergency-access/<emer_id>/accept " , data =  " <data> " ) ]  
			
		
	
		
			
				
					fn  accept_invite ( emer_id : String ,   data : JsonUpcase < AcceptData > ,   conn : DbConn )   -> EmptyResult   {  
			
		
	
		
			
				
					async   fn  accept_invite ( emer_id : String ,   data : JsonUpcase < AcceptData > ,   conn : DbConn )   -> EmptyResult   {  
			
		
	
		
			
				
					     check_emergency_access_allowed ( ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   data : AcceptData   =   data . into_inner ( ) . data ;  
			
		
	
		
			
				
					     let   token   =   & data . Token ;  
			
		
	
		
			
				
					     let   claims   =   decode_emergency_access_invite ( token ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   grantee_user   =   match   User ::find_by_mail ( & claims . email ,   & conn )   {  
			
		
	
		
			
				
					     let   grantee_user   =   match   User ::find_by_mail ( & claims . email ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( user )   = >   {  
			
		
	
		
			
				
					             Invitation ::take ( & claims . email ,   & conn ) ;  
			
		
	
		
			
				
					             Invitation ::take ( & claims . email ,   & conn ) . await ;  
			
		
	
		
			
				
					             user  
			
		
	
		
			
				
					         }  
			
		
	
		
			
				
					         None   = >   err ! ( "Invited user not found" ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn )   {  
			
		
	
		
			
				
					     let   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( emer )   = >   emer ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Emergency access not valid." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     // get grantor user to send Accepted email
  
			
		
	
		
			
				
					     let   grantor_user   =   match   User ::find_by_uuid ( & emergency_access . grantor_uuid ,   & conn )   {  
			
		
	
		
			
				
					     let   grantor_user   =   match   User ::find_by_uuid ( & emergency_access . grantor_uuid ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( user )   = >   user ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Grantor user not found." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -336,7 +357,7 @@ fn accept_invite(emer_id: String, data: JsonUpcase<AcceptData>, conn: DbConn) -> 
			
		
	
		
			
				
					         & &   ( claims . grantor_name . is_some ( )   & &   grantor_user . name   = =   claims . grantor_name . unwrap ( ) )  
			
		
	
		
			
				
					         & &   ( claims . grantor_email . is_some ( )   & &   grantor_user . email   = =   claims . grantor_email . unwrap ( ) )  
			
		
	
		
			
				
					     {  
			
		
	
		
			
				
					         match   accept_invite_process ( grantee_user . uuid . clone ( ) ,   emer_id ,   Some ( grantee_user . email . clone ( ) ) ,   & conn )   {  
			
		
	
		
			
				
					         match   accept_invite_process ( grantee_user . uuid . clone ( ) ,   emer_id ,   Some ( grantee_user . email . clone ( ) ) ,   & conn ) . await   {  
			
		
	
		
			
				
					             Ok ( v )   = >   ( v ) ,  
			
		
	
		
			
				
					             Err ( e )   = >   err ! ( e . to_string ( ) ) ,  
			
		
	
		
			
				
					         }  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -351,8 +372,13 @@ fn accept_invite(emer_id: String, data: JsonUpcase<AcceptData>, conn: DbConn) -> 
			
		
	
		
			
				
					     }  
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					fn  accept_invite_process ( grantee_uuid : String ,   emer_id : String ,   email : Option < String > ,   conn : & DbConn )   -> EmptyResult   {  
			
		
	
		
			
				
					     let   mut   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   conn )   {  
			
		
	
		
			
				
					async   fn  accept_invite_process (  
			
		
	
		
			
				
					     grantee_uuid : String ,  
			
		
	
		
			
				
					     emer_id : String ,  
			
		
	
		
			
				
					     email : Option < String > ,  
			
		
	
		
			
				
					     conn : & DbConn ,  
			
		
	
		
			
				
					)   -> EmptyResult   {  
			
		
	
		
			
				
					     let   mut   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   conn ) . await   {  
			
		
	
		
			
				
					         Some ( emer )   = >   emer ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Emergency access not valid." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -369,7 +395,7 @@ fn accept_invite_process(grantee_uuid: String, emer_id: String, email: Option<St 
			
		
	
		
			
				
					     emergency_access . status   =   EmergencyAccessStatus ::Accepted   as   i32 ;  
			
		
	
		
			
				
					     emergency_access . grantee_uuid   =   Some ( grantee_uuid ) ;  
			
		
	
		
			
				
					     emergency_access . email   =   None ;  
			
		
	
		
			
				
					     emergency_access . save ( conn )  
			
		
	
		
			
				
					     emergency_access . save ( conn ) . await  
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ derive(Deserialize) ]  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -379,7 +405,7 @@ struct ConfirmData { 
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ post( " /emergency-access/<emer_id>/confirm " , data =  " <data> " ) ]  
			
		
	
		
			
				
					fn  confirm_emergency_access (  
			
		
	
		
			
				
					async   fn  confirm_emergency_access (  
			
		
	
		
			
				
					     emer_id : String ,  
			
		
	
		
			
				
					     data : JsonUpcase < ConfirmData > ,  
			
		
	
		
			
				
					     headers : Headers ,  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -391,7 +417,7 @@ fn confirm_emergency_access( 
			
		
	
		
			
				
					     let   data : ConfirmData   =   data . into_inner ( ) . data ;  
			
		
	
		
			
				
					     let   key   =   data . Key ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   mut   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn )   {  
			
		
	
		
			
				
					     let   mut   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( emer )   = >   emer ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Emergency access not valid." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -402,13 +428,13 @@ fn confirm_emergency_access( 
			
		
	
		
			
				
					         err ! ( "Emergency access not valid." )  
			
		
	
		
			
				
					     }  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   grantor_user   =   match   User ::find_by_uuid ( & confirming_user . uuid ,   & conn )   {  
			
		
	
		
			
				
					     let   grantor_user   =   match   User ::find_by_uuid ( & confirming_user . uuid ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( user )   = >   user ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Grantor user not found." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     if   let   Some ( grantee_uuid )   =   emergency_access . grantee_uuid . as_ref ( )   {  
			
		
	
		
			
				
					         let   grantee_user   =   match   User ::find_by_uuid ( grantee_uuid ,   & conn )   {  
			
		
	
		
			
				
					         let   grantee_user   =   match   User ::find_by_uuid ( grantee_uuid ,   & conn ) . await   {  
			
		
	
		
			
				
					             Some ( user )   = >   user ,  
			
		
	
		
			
				
					             None   = >   err ! ( "Grantee user not found." ) ,  
			
		
	
		
			
				
					         } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -417,7 +443,7 @@ fn confirm_emergency_access( 
			
		
	
		
			
				
					         emergency_access . key_encrypted   =   Some ( key ) ;  
			
		
	
		
			
				
					         emergency_access . email   =   None ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					         emergency_access . save ( & conn ) ? ;  
			
		
	
		
			
				
					         emergency_access . save ( & conn ) . await ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					         if   CONFIG . mail_enabled ( )   {  
			
		
	
		
			
				
					             mail ::send_emergency_access_invite_confirmed ( & grantee_user . email ,   & grantor_user . name ) ? ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -433,11 +459,11 @@ fn confirm_emergency_access( 
			
		
	
		
			
				
					// region access emergency access
  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ post( " /emergency-access/<emer_id>/initiate " ) ]  
			
		
	
		
			
				
					fn  initiate_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					async   fn  initiate_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					     check_emergency_access_allowed ( ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   initiating_user   =   headers . user ;  
			
		
	
		
			
				
					     let   mut   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn )   {  
			
		
	
		
			
				
					     let   mut   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( emer )   = >   emer ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Emergency access not valid." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -448,7 +474,7 @@ fn initiate_emergency_access(emer_id: String, headers: Headers, conn: DbConn) -> 
			
		
	
		
			
				
					         err ! ( "Emergency access not valid." )  
			
		
	
		
			
				
					     }  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   grantor_user   =   match   User ::find_by_uuid ( & emergency_access . grantor_uuid ,   & conn )   {  
			
		
	
		
			
				
					     let   grantor_user   =   match   User ::find_by_uuid ( & emergency_access . grantor_uuid ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( user )   = >   user ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Grantor user not found." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -458,7 +484,7 @@ fn initiate_emergency_access(emer_id: String, headers: Headers, conn: DbConn) -> 
			
		
	
		
			
				
					     emergency_access . updated_at   =   now ;  
			
		
	
		
			
				
					     emergency_access . recovery_initiated_at   =   Some ( now ) ;  
			
		
	
		
			
				
					     emergency_access . last_notification_at   =   Some ( now ) ;  
			
		
	
		
			
				
					     emergency_access . save ( & conn ) ? ;  
			
		
	
		
			
				
					     emergency_access . save ( & conn ) . await ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     if   CONFIG . mail_enabled ( )   {  
			
		
	
		
			
				
					         mail ::send_emergency_access_recovery_initiated (  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -472,11 +498,11 @@ fn initiate_emergency_access(emer_id: String, headers: Headers, conn: DbConn) -> 
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ post( " /emergency-access/<emer_id>/approve " ) ]  
			
		
	
		
			
				
					fn  approve_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					async   fn  approve_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					     check_emergency_access_allowed ( ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   approving_user   =   headers . user ;  
			
		
	
		
			
				
					     let   mut   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn )   {  
			
		
	
		
			
				
					     let   mut   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( emer )   = >   emer ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Emergency access not valid." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -487,19 +513,19 @@ fn approve_emergency_access(emer_id: String, headers: Headers, conn: DbConn) -> 
			
		
	
		
			
				
					         err ! ( "Emergency access not valid." )  
			
		
	
		
			
				
					     }  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   grantor_user   =   match   User ::find_by_uuid ( & approving_user . uuid ,   & conn )   {  
			
		
	
		
			
				
					     let   grantor_user   =   match   User ::find_by_uuid ( & approving_user . uuid ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( user )   = >   user ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Grantor user not found." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     if   let   Some ( grantee_uuid )   =   emergency_access . grantee_uuid . as_ref ( )   {  
			
		
	
		
			
				
					         let   grantee_user   =   match   User ::find_by_uuid ( grantee_uuid ,   & conn )   {  
			
		
	
		
			
				
					         let   grantee_user   =   match   User ::find_by_uuid ( grantee_uuid ,   & conn ) . await   {  
			
		
	
		
			
				
					             Some ( user )   = >   user ,  
			
		
	
		
			
				
					             None   = >   err ! ( "Grantee user not found." ) ,  
			
		
	
		
			
				
					         } ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					         emergency_access . status   =   EmergencyAccessStatus ::RecoveryApproved   as   i32 ;  
			
		
	
		
			
				
					         emergency_access . save ( & conn ) ? ;  
			
		
	
		
			
				
					         emergency_access . save ( & conn ) . await ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					         if   CONFIG . mail_enabled ( )   {  
			
		
	
		
			
				
					             mail ::send_emergency_access_recovery_approved ( & grantee_user . email ,   & grantor_user . name ) ? ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -511,11 +537,11 @@ fn approve_emergency_access(emer_id: String, headers: Headers, conn: DbConn) -> 
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ post( " /emergency-access/<emer_id>/reject " ) ]  
			
		
	
		
			
				
					fn  reject_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					async   fn  reject_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					     check_emergency_access_allowed ( ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   rejecting_user   =   headers . user ;  
			
		
	
		
			
				
					     let   mut   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn )   {  
			
		
	
		
			
				
					     let   mut   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( emer )   = >   emer ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Emergency access not valid." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -527,19 +553,19 @@ fn reject_emergency_access(emer_id: String, headers: Headers, conn: DbConn) -> J 
			
		
	
		
			
				
					         err ! ( "Emergency access not valid." )  
			
		
	
		
			
				
					     }  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   grantor_user   =   match   User ::find_by_uuid ( & rejecting_user . uuid ,   & conn )   {  
			
		
	
		
			
				
					     let   grantor_user   =   match   User ::find_by_uuid ( & rejecting_user . uuid ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( user )   = >   user ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Grantor user not found." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     if   let   Some ( grantee_uuid )   =   emergency_access . grantee_uuid . as_ref ( )   {  
			
		
	
		
			
				
					         let   grantee_user   =   match   User ::find_by_uuid ( grantee_uuid ,   & conn )   {  
			
		
	
		
			
				
					         let   grantee_user   =   match   User ::find_by_uuid ( grantee_uuid ,   & conn ) . await   {  
			
		
	
		
			
				
					             Some ( user )   = >   user ,  
			
		
	
		
			
				
					             None   = >   err ! ( "Grantee user not found." ) ,  
			
		
	
		
			
				
					         } ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					         emergency_access . status   =   EmergencyAccessStatus ::Confirmed   as   i32 ;  
			
		
	
		
			
				
					         emergency_access . save ( & conn ) ? ;  
			
		
	
		
			
				
					         emergency_access . save ( & conn ) . await ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					         if   CONFIG . mail_enabled ( )   {  
			
		
	
		
			
				
					             mail ::send_emergency_access_recovery_rejected ( & grantee_user . email ,   & grantor_user . name ) ? ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -555,12 +581,12 @@ fn reject_emergency_access(emer_id: String, headers: Headers, conn: DbConn) -> J 
			
		
	
		
			
				
					// region action
  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ post( " /emergency-access/<emer_id>/view " ) ]  
			
		
	
		
			
				
					fn  view_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					async   fn  view_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					     check_emergency_access_allowed ( ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   requesting_user   =   headers . user ;  
			
		
	
		
			
				
					     let   host   =   headers . host ;  
			
		
	
		
			
				
					     let   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn )   {  
			
		
	
		
			
				
					     let   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( emer )   = >   emer ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Emergency access not valid." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -569,10 +595,13 @@ fn view_emergency_access(emer_id: String, headers: Headers, conn: DbConn) -> Jso 
			
		
	
		
			
				
					         err ! ( "Emergency access not valid." )  
			
		
	
		
			
				
					     }  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   ciphers   =   Cipher ::find_owned_by_user ( & emergency_access . grantor_uuid ,   & conn ) ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   ciphers_json : Vec < Value >   =  
			
		
	
		
			
				
					         ciphers . iter ( ) . map ( | c |   c . to_json ( & host ,   & emergency_access . grantor_uuid ,   & conn ) ) . collect ( ) ;  
			
		
	
		
			
				
					     let   ciphers_json   =   stream ::iter ( Cipher ::find_owned_by_user ( & emergency_access . grantor_uuid ,   & conn ) . await )  
			
		
	
		
			
				
					         . then ( | c |   async   {  
			
		
	
		
			
				
					             let   c   =   c ;   // Move out this single variable
  
			
		
	
		
			
				
					             c . to_json ( & host ,   & emergency_access . grantor_uuid ,   & conn ) . await  
			
		
	
		
			
				
					         } )  
			
		
	
		
			
				
					         . collect ::< Vec < Value > > ( )  
			
		
	
		
			
				
					         . await ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     Ok ( Json ( json ! ( {  
			
		
	
		
			
				
					       "Ciphers" : ciphers_json ,  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -582,11 +611,11 @@ fn view_emergency_access(emer_id: String, headers: Headers, conn: DbConn) -> Jso 
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ post( " /emergency-access/<emer_id>/takeover " ) ]  
			
		
	
		
			
				
					fn  takeover_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					async   fn  takeover_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					     check_emergency_access_allowed ( ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   requesting_user   =   headers . user ;  
			
		
	
		
			
				
					     let   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn )   {  
			
		
	
		
			
				
					     let   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( emer )   = >   emer ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Emergency access not valid." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -595,7 +624,7 @@ fn takeover_emergency_access(emer_id: String, headers: Headers, conn: DbConn) -> 
			
		
	
		
			
				
					         err ! ( "Emergency access not valid." )  
			
		
	
		
			
				
					     }  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   grantor_user   =   match   User ::find_by_uuid ( & emergency_access . grantor_uuid ,   & conn )   {  
			
		
	
		
			
				
					     let   grantor_user   =   match   User ::find_by_uuid ( & emergency_access . grantor_uuid ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( user )   = >   user ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Grantor user not found." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -616,7 +645,7 @@ struct EmergencyAccessPasswordData { 
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ post( " /emergency-access/<emer_id>/password " , data =  " <data> " ) ]  
			
		
	
		
			
				
					fn  password_emergency_access (  
			
		
	
		
			
				
					async   fn  password_emergency_access (  
			
		
	
		
			
				
					     emer_id : String ,  
			
		
	
		
			
				
					     data : JsonUpcase < EmergencyAccessPasswordData > ,  
			
		
	
		
			
				
					     headers : Headers ,  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -629,7 +658,7 @@ fn password_emergency_access( 
			
		
	
		
			
				
					     let   key   =   data . Key ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   requesting_user   =   headers . user ;  
			
		
	
		
			
				
					     let   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn )   {  
			
		
	
		
			
				
					     let   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( emer )   = >   emer ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Emergency access not valid." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -638,7 +667,7 @@ fn password_emergency_access( 
			
		
	
		
			
				
					         err ! ( "Emergency access not valid." )  
			
		
	
		
			
				
					     }  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   mut   grantor_user   =   match   User ::find_by_uuid ( & emergency_access . grantor_uuid ,   & conn )   {  
			
		
	
		
			
				
					     let   mut   grantor_user   =   match   User ::find_by_uuid ( & emergency_access . grantor_uuid ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( user )   = >   user ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Grantor user not found." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -646,18 +675,15 @@ fn password_emergency_access( 
			
		
	
		
			
				
					     // change grantor_user password
  
			
		
	
		
			
				
					     grantor_user . set_password ( new_master_password_hash ,   None ) ;  
			
		
	
		
			
				
					     grantor_user . akey   =   key ;  
			
		
	
		
			
				
					     grantor_user . save ( & conn ) ? ;  
			
		
	
		
			
				
					     grantor_user . save ( & conn ) . await ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     // Disable TwoFactor providers since they will otherwise block logins
  
			
		
	
		
			
				
					     TwoFactor ::delete_all_by_user ( & grantor_user . uuid ,   & conn ) ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     // Removing owner, check that there are at least another owner
  
			
		
	
		
			
				
					     let   user_org_grantor   =   UserOrganization ::find_any_state_by_user ( & grantor_user . uuid ,   & conn ) ;  
			
		
	
		
			
				
					     TwoFactor ::delete_all_by_user ( & grantor_user . uuid ,   & conn ) . await ? ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     // Remove grantor from all organisations unless Owner
  
			
		
	
		
			
				
					     for   user_org   in   user_org_grantor   {  
			
		
	
		
			
				
					     for   user_org   in   UserOrganization ::find_any_state_by_user ( & grantor_user . uuid ,   & conn ) . await   {  
			
		
	
		
			
				
					         if   user_org . atype   ! =   UserOrgType ::Owner   as   i32   {  
			
		
	
		
			
				
					             user_org . delete ( & conn ) ? ;  
			
		
	
		
			
				
					             user_org . delete ( & conn ) . await ? ;  
			
		
	
		
			
				
					         }  
			
		
	
		
			
				
					     }  
			
		
	
		
			
				
					     Ok ( ( ) )  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -666,9 +692,9 @@ fn password_emergency_access( 
			
		
	
		
			
				
					// endregion
  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					#[ get( " /emergency-access/<emer_id>/policies " ) ]  
			
		
	
		
			
				
					fn  policies_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					async   fn  policies_emergency_access ( emer_id : String ,   headers : Headers ,   conn : DbConn )   -> JsonResult   {  
			
		
	
		
			
				
					     let   requesting_user   =   headers . user ;  
			
		
	
		
			
				
					     let   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn )   {  
			
		
	
		
			
				
					     let   emergency_access   =   match   EmergencyAccess ::find_by_uuid ( & emer_id ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( emer )   = >   emer ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Emergency access not valid." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -677,13 +703,13 @@ fn policies_emergency_access(emer_id: String, headers: Headers, conn: DbConn) -> 
			
		
	
		
			
				
					         err ! ( "Emergency access not valid." )  
			
		
	
		
			
				
					     }  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   grantor_user   =   match   User ::find_by_uuid ( & emergency_access . grantor_uuid ,   & conn )   {  
			
		
	
		
			
				
					     let   grantor_user   =   match   User ::find_by_uuid ( & emergency_access . grantor_uuid ,   & conn ) . await   {  
			
		
	
		
			
				
					         Some ( user )   = >   user ,  
			
		
	
		
			
				
					         None   = >   err ! ( "Grantor user not found." ) ,  
			
		
	
		
			
				
					     } ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     let   policies   =   OrgPolicy ::find_confirmed_by_user ( & grantor_user . uuid ,   & conn ) ;  
			
		
	
		
			
				
					     let   policies_json : Vec < Value >   =   policies . iter ( ) . map ( OrgPolicy ::to_json ) . collect ( ) ;  
			
		
	
		
			
				
					     let   policies_json : Vec < Value >   =   policies . await . iter ( ) . map ( OrgPolicy ::to_json ) . collect ( ) ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     Ok ( Json ( json ! ( {  
			
		
	
		
			
				
					         "Data" : policies_json ,  
			
		
	
	
		
			
				
					
						
							
								 
						
						
							
								 
						
						
					 
				
				@ -716,7 +742,7 @@ pub async fn emergency_request_timeout_job(pool: DbPool) { 
			
		
	
		
			
				
					     }  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     if   let   Ok ( conn )   =   pool . get ( ) . await   {  
			
		
	
		
			
				
					         let   emergency_access_list   =   EmergencyAccess ::find_all_recoveries ( & conn ) ;  
			
		
	
		
			
				
					         let   emergency_access_list   =   EmergencyAccess ::find_all_recoveries ( & conn ) . await ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					         if   emergency_access_list . is_empty ( )   {  
			
		
	
		
			
				
					             debug ! ( "No emergency request timeout to approve" ) ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -728,15 +754,17 @@ pub async fn emergency_request_timeout_job(pool: DbPool) { 
			
		
	
		
			
				
					                     > =   emer . recovery_initiated_at . unwrap ( )   +   Duration ::days ( emer . wait_time_days   as   i64 )  
			
		
	
		
			
				
					             {  
			
		
	
		
			
				
					                 emer . status   =   EmergencyAccessStatus ::RecoveryApproved   as   i32 ;  
			
		
	
		
			
				
					                 emer . save ( & conn ) . expect ( "Cannot save emergency access on job" ) ;  
			
		
	
		
			
				
					                 emer . save ( & conn ) . await . expect ( "Cannot save emergency access on job" ) ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					                 if   CONFIG . mail_enabled ( )   {  
			
		
	
		
			
				
					                     // get grantor user to send Accepted email
  
			
		
	
		
			
				
					                     let   grantor_user   =   User ::find_by_uuid ( & emer . grantor_uuid ,   & conn ) . expect ( "Grantor user not found." ) ;  
			
		
	
		
			
				
					                     let   grantor_user   =  
			
		
	
		
			
				
					                         User ::find_by_uuid ( & emer . grantor_uuid ,   & conn ) . await . expect ( "Grantor user not found." ) ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					                     // get grantee user to send Accepted email
  
			
		
	
		
			
				
					                     let   grantee_user   =  
			
		
	
		
			
				
					                         User ::find_by_uuid ( & emer . grantee_uuid . clone ( ) . expect ( "Grantee user invalid." ) ,   & conn )  
			
		
	
		
			
				
					                             . await  
			
		
	
		
			
				
					                             . expect ( "Grantee user not found." ) ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					                     mail ::send_emergency_access_recovery_timed_out (  
			
		
	
	
		
			
				
					
						
							
								 
						
						
							
								 
						
						
					 
				
				@ -763,7 +791,7 @@ pub async fn emergency_notification_reminder_job(pool: DbPool) { 
			
		
	
		
			
				
					     }  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					     if   let   Ok ( conn )   =   pool . get ( ) . await   {  
			
		
	
		
			
				
					         let   emergency_access_list   =   EmergencyAccess ::find_all_recoveries ( & conn ) ;  
			
		
	
		
			
				
					         let   emergency_access_list   =   EmergencyAccess ::find_all_recoveries ( & conn ) . await ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					         if   emergency_access_list . is_empty ( )   {  
			
		
	
		
			
				
					             debug ! ( "No emergency request reminder notification to send" ) ;  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -777,15 +805,17 @@ pub async fn emergency_notification_reminder_job(pool: DbPool) { 
			
		
	
		
			
				
					                     | |   ( emer . last_notification_at . is_some ( )  
			
		
	
		
			
				
					                         & &   Utc ::now ( ) . naive_utc ( )   > =   emer . last_notification_at . unwrap ( )   +   Duration ::days ( 1 ) ) )  
			
		
	
		
			
				
					             {  
			
		
	
		
			
				
					                 emer . save ( & conn ) . expect ( "Cannot save emergency access on job" ) ;  
			
		
	
		
			
				
					                 emer . save ( & conn ) . await . expect ( "Cannot save emergency access on job" ) ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					                 if   CONFIG . mail_enabled ( )   {  
			
		
	
		
			
				
					                     // get grantor user to send Accepted email
  
			
		
	
		
			
				
					                     let   grantor_user   =   User ::find_by_uuid ( & emer . grantor_uuid ,   & conn ) . expect ( "Grantor user not found." ) ;  
			
		
	
		
			
				
					                     let   grantor_user   =  
			
		
	
		
			
				
					                         User ::find_by_uuid ( & emer . grantor_uuid ,   & conn ) . await . expect ( "Grantor user not found." ) ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					                     // get grantee user to send Accepted email
  
			
		
	
		
			
				
					                     let   grantee_user   =  
			
		
	
		
			
				
					                         User ::find_by_uuid ( & emer . grantee_uuid . clone ( ) . expect ( "Grantee user invalid." ) ,   & conn )  
			
		
	
		
			
				
					                             . await  
			
		
	
		
			
				
					                             . expect ( "Grantee user not found." ) ;  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					                     mail ::send_emergency_access_recovery_reminder (