diff --git a/src/api/core/accounts.rs b/src/api/core/accounts.rs
index b2afe9050508cee8d773ca78334dbb3d547b98f7..5b947b85ac486855e8be68516aa7fd0edea08e26 100644
--- a/src/api/core/accounts.rs
+++ b/src/api/core/accounts.rs
@@ -166,7 +166,8 @@ pub async fn _register(data: JsonUpcase<RegisterData>, mut conn: DbConn) -> Json
                 }
                 user
             } else if CONFIG.is_signup_allowed(&email)
-                || EmergencyAccess::find_invited_by_grantee_email(&email, &mut conn).await.is_some()
+                || (CONFIG.emergency_access_allowed()
+                    && EmergencyAccess::find_invited_by_grantee_email(&email, &mut conn).await.is_some())
             {
                 user
             } else {
@@ -217,7 +218,6 @@ pub async fn _register(data: JsonUpcase<RegisterData>, mut conn: DbConn) -> Json
             if let Err(e) = mail::send_welcome_must_verify(&user.email, &user.uuid).await {
                 error!("Error sending welcome email: {:#?}", e);
             }
-
             user.last_verifying_at = Some(user.created_at);
         } else if let Err(e) = mail::send_welcome(&user.email).await {
             error!("Error sending welcome email: {:#?}", e);
@@ -229,6 +229,14 @@ pub async fn _register(data: JsonUpcase<RegisterData>, mut conn: DbConn) -> Json
     }
 
     user.save(&mut conn).await?;
+
+    // accept any open emergency access invitations
+    if !CONFIG.mail_enabled() && CONFIG.emergency_access_allowed() {
+        for mut emergency_invite in EmergencyAccess::find_all_invited_by_grantee_email(&user.email, &mut conn).await {
+            let _ = emergency_invite.accept_invite(&user.uuid, &user.email, &mut conn).await;
+        }
+    }
+
     Ok(Json(json!({
       "Object": "register",
       "CaptchaBypassToken": "",
diff --git a/src/api/core/emergency_access.rs b/src/api/core/emergency_access.rs
index 5f64cde099de69b67cbb050eb3b9b014464b5176..5d522c61c214b918b6ee191847d638dc422596ab 100644
--- a/src/api/core/emergency_access.rs
+++ b/src/api/core/emergency_access.rs
@@ -61,7 +61,9 @@ async fn get_contacts(headers: Headers, mut conn: DbConn) -> Json<Value> {
     let emergency_access_list = EmergencyAccess::find_all_by_grantor_uuid(&headers.user.uuid, &mut conn).await;
     let mut emergency_access_list_json = Vec::with_capacity(emergency_access_list.len());
     for ea in emergency_access_list {
-        emergency_access_list_json.push(ea.to_json_grantee_details(&mut conn).await);
+        if let Some(grantee) = ea.to_json_grantee_details(&mut conn).await {
+            emergency_access_list_json.push(grantee)
+        }
     }
 
     Json(json!({
@@ -95,7 +97,9 @@ async fn get_emergency_access(emer_id: &str, mut conn: DbConn) -> JsonResult {
     check_emergency_access_enabled()?;
 
     match EmergencyAccess::find_by_uuid(emer_id, &mut conn).await {
-        Some(emergency_access) => Ok(Json(emergency_access.to_json_grantee_details(&mut conn).await)),
+        Some(emergency_access) => Ok(Json(
+            emergency_access.to_json_grantee_details(&mut conn).await.expect("Grantee user should exist but does not!"),
+        )),
         None => err!("Emergency access not valid."),
     }
 }
@@ -209,7 +213,7 @@ async fn send_invite(data: JsonUpcase<EmergencyAccessInviteData>, headers: Heade
         err!("You can not set yourself as an emergency contact.")
     }
 
-    let grantee_user = match User::find_by_mail(&email, &mut conn).await {
+    let (grantee_user, new_user) = match User::find_by_mail(&email, &mut conn).await {
         None => {
             if !CONFIG.invitations_allowed() {
                 err!(format!("Grantee user does not exist: {}", &email))
@@ -226,9 +230,10 @@ async fn send_invite(data: JsonUpcase<EmergencyAccessInviteData>, headers: Heade
 
             let mut user = User::new(email.clone());
             user.save(&mut conn).await?;
-            user
+            (user, true)
         }
-        Some(user) => user,
+        Some(user) if user.password_hash.is_empty() => (user, true),
+        Some(user) => (user, false),
     };
 
     if EmergencyAccess::find_by_grantor_uuid_and_grantee_uuid_or_email(
@@ -256,15 +261,9 @@ async fn send_invite(data: JsonUpcase<EmergencyAccessInviteData>, headers: Heade
             &grantor_user.email,
         )
         .await?;
-    } else {
-        // Automatically mark user as accepted if no email invites
-        match User::find_by_mail(&email, &mut conn).await {
-            Some(user) => match accept_invite_process(&user.uuid, &mut new_emergency_access, &email, &mut conn).await {
-                Ok(v) => v,
-                Err(e) => err!(e.to_string()),
-            },
-            None => err!("Grantee user not found."),
-        }
+    } else if !new_user {
+        // if mail is not enabled immediately accept the invitation for existing users
+        new_emergency_access.accept_invite(&grantee_user.uuid, &email, &mut conn).await?;
     }
 
     Ok(())
@@ -308,17 +307,12 @@ async fn resend_invite(emer_id: &str, headers: Headers, mut conn: DbConn) -> Emp
             &grantor_user.email,
         )
         .await?;
-    } else {
-        if Invitation::find_by_mail(&email, &mut conn).await.is_none() {
-            let invitation = Invitation::new(&email);
-            invitation.save(&mut conn).await?;
-        }
-
-        // Automatically mark user as accepted if no email invites
-        match accept_invite_process(&grantee_user.uuid, &mut emergency_access, &email, &mut conn).await {
-            Ok(v) => v,
-            Err(e) => err!(e.to_string()),
-        }
+    } else if !grantee_user.password_hash.is_empty() {
+        // accept the invitation for existing user
+        emergency_access.accept_invite(&grantee_user.uuid, &email, &mut conn).await?;
+    } else if CONFIG.invitations_allowed() && Invitation::find_by_mail(&email, &mut conn).await.is_none() {
+        let invitation = Invitation::new(&email);
+        invitation.save(&mut conn).await?;
     }
 
     Ok(())
@@ -367,10 +361,7 @@ async fn accept_invite(emer_id: &str, data: JsonUpcase<AcceptData>, headers: Hea
         && grantor_user.name == claims.grantor_name
         && grantor_user.email == claims.grantor_email
     {
-        match accept_invite_process(&grantee_user.uuid, &mut emergency_access, &grantee_user.email, &mut conn).await {
-            Ok(v) => v,
-            Err(e) => err!(e.to_string()),
-        }
+        emergency_access.accept_invite(&grantee_user.uuid, &grantee_user.email, &mut conn).await?;
 
         if CONFIG.mail_enabled() {
             mail::send_emergency_access_invite_accepted(&grantor_user.email, &grantee_user.email).await?;
@@ -382,26 +373,6 @@ async fn accept_invite(emer_id: &str, data: JsonUpcase<AcceptData>, headers: Hea
     }
 }
 
-async fn accept_invite_process(
-    grantee_uuid: &str,
-    emergency_access: &mut EmergencyAccess,
-    grantee_email: &str,
-    conn: &mut DbConn,
-) -> EmptyResult {
-    if emergency_access.email.is_none() || emergency_access.email.as_ref().unwrap() != grantee_email {
-        err!("User email does not match invite.");
-    }
-
-    if emergency_access.status == EmergencyAccessStatus::Accepted as i32 {
-        err!("Emergency contact already accepted.");
-    }
-
-    emergency_access.status = EmergencyAccessStatus::Accepted as i32;
-    emergency_access.grantee_uuid = Some(String::from(grantee_uuid));
-    emergency_access.email = None;
-    emergency_access.save(conn).await
-}
-
 #[derive(Deserialize)]
 #[allow(non_snake_case)]
 struct ConfirmData {
diff --git a/src/db/models/emergency_access.rs b/src/db/models/emergency_access.rs
index c3682920433fc827687ccd57f23260a5848fa4da..a0f07e7fa8b30eb354f7d6226477a934de1f7269 100644
--- a/src/db/models/emergency_access.rs
+++ b/src/db/models/emergency_access.rs
@@ -81,25 +81,32 @@ impl EmergencyAccess {
         })
     }
 
-    pub async fn to_json_grantee_details(&self, conn: &mut DbConn) -> Value {
+    pub async fn to_json_grantee_details(&self, conn: &mut DbConn) -> Option<Value> {
         let grantee_user = if let Some(grantee_uuid) = self.grantee_uuid.as_deref() {
-            Some(User::find_by_uuid(grantee_uuid, conn).await.expect("Grantee user not found."))
+            User::find_by_uuid(grantee_uuid, conn).await.expect("Grantee user not found.")
         } else if let Some(email) = self.email.as_deref() {
-            Some(User::find_by_mail(email, conn).await.expect("Grantee user not found."))
+            match User::find_by_mail(email, conn).await {
+                Some(user) => user,
+                None => {
+                    // remove outstanding invitations which should not exist
+                    let _ = Self::delete_all_by_grantee_email(email, conn).await;
+                    return None;
+                }
+            }
         } else {
-            None
+            return None;
         };
 
-        json!({
+        Some(json!({
             "Id": self.uuid,
             "Status": self.status,
             "Type": self.atype,
             "WaitTimeDays": self.wait_time_days,
-            "GranteeId": grantee_user.as_ref().map_or("", |u| &u.uuid),
-            "Email": grantee_user.as_ref().map_or("", |u| &u.email),
-            "Name": grantee_user.as_ref().map_or("", |u| &u.name),
+            "GranteeId": grantee_user.uuid,
+            "Email": grantee_user.email,
+            "Name": grantee_user.name,
             "Object": "emergencyAccessGranteeDetails",
-        })
+        }))
     }
 }
 
@@ -214,6 +221,13 @@ impl EmergencyAccess {
         Ok(())
     }
 
+    pub async fn delete_all_by_grantee_email(grantee_email: &str, conn: &mut DbConn) -> EmptyResult {
+        for ea in Self::find_all_invited_by_grantee_email(grantee_email, conn).await {
+            ea.delete(conn).await?;
+        }
+        Ok(())
+    }
+
     pub async fn delete(self, conn: &mut DbConn) -> EmptyResult {
         User::update_uuid_revision(&self.grantor_uuid, conn).await;
 
@@ -285,6 +299,15 @@ impl EmergencyAccess {
         }}
     }
 
+    pub async fn find_all_invited_by_grantee_email(grantee_email: &str, conn: &mut DbConn) -> Vec<Self> {
+        db_run! { conn: {
+            emergency_access::table
+                .filter(emergency_access::email.eq(grantee_email))
+                .filter(emergency_access::status.eq(EmergencyAccessStatus::Invited as i32))
+                .load::<EmergencyAccessDb>(conn).expect("Error loading emergency_access").from_db()
+        }}
+    }
+
     pub async fn find_all_by_grantor_uuid(grantor_uuid: &str, conn: &mut DbConn) -> Vec<Self> {
         db_run! { conn: {
             emergency_access::table
@@ -292,6 +315,21 @@ impl EmergencyAccess {
                 .load::<EmergencyAccessDb>(conn).expect("Error loading emergency_access").from_db()
         }}
     }
+
+    pub async fn accept_invite(&mut self, grantee_uuid: &str, grantee_email: &str, conn: &mut DbConn) -> EmptyResult {
+        if self.email.is_none() || self.email.as_ref().unwrap() != grantee_email {
+            err!("User email does not match invite.");
+        }
+
+        if self.status == EmergencyAccessStatus::Accepted as i32 {
+            err!("Emergency contact already accepted.");
+        }
+
+        self.status = EmergencyAccessStatus::Accepted as i32;
+        self.grantee_uuid = Some(String::from(grantee_uuid));
+        self.email = None;
+        self.save(conn).await
+    }
 }
 
 // endregion
diff --git a/src/db/models/user.rs b/src/db/models/user.rs
index feb094389277174d7c80e0674ca659a37c6b8249..bf7dad328c6712f6dc32bf752ffcf33126492f4b 100644
--- a/src/db/models/user.rs
+++ b/src/db/models/user.rs
@@ -311,6 +311,7 @@ impl User {
 
         Send::delete_all_by_user(&self.uuid, conn).await?;
         EmergencyAccess::delete_all_by_user(&self.uuid, conn).await?;
+        EmergencyAccess::delete_all_by_grantee_email(&self.email, conn).await?;
         UserOrganization::delete_all_by_user(&self.uuid, conn).await?;
         Cipher::delete_all_by_user(&self.uuid, conn).await?;
         Favorite::delete_all_by_user(&self.uuid, conn).await?;