This commit is contained in:
2026-06-05 23:41:24 +08:00
parent 27b30f974b
commit 7140ac72b5
9 changed files with 69 additions and 10 deletions

View File

@@ -64,6 +64,8 @@ pub struct AuthUser {
pub binding_status: AuthBindingStatus,
pub wechat_bound: bool,
#[serde(default)]
pub wechat_display_name: Option<String>,
#[serde(default)]
pub wechat_account: Option<String>,
pub token_version: u64,
#[serde(default)]

View File

@@ -105,12 +105,21 @@ fn hydrate_private_auth_fields(
if hydrated.user.phone_number.is_none() {
hydrated.user.phone_number = hydrated.phone_number.clone();
}
let hydrated_wechat_identity = state
.wechat_identity_by_provider_uid
.values()
.find(|identity| identity.user_id == hydrated.user.id);
if hydrated.user.wechat_display_name.is_none() {
hydrated.user.wechat_display_name = hydrated_wechat_identity
.and_then(|identity| identity.display_name.clone())
.or_else(|| {
(hydrated.user.login_method == AuthLoginMethod::Wechat)
.then(|| hydrated.user.display_name.clone())
});
}
if hydrated.user.wechat_account.is_none() {
hydrated.user.wechat_account = state
.wechat_identity_by_provider_uid
.values()
.find(|identity| identity.user_id == hydrated.user.id)
.map(|identity| identity.provider_uid.clone());
hydrated.user.wechat_account =
hydrated_wechat_identity.map(|identity| identity.provider_uid.clone());
}
hydrated
}
@@ -1100,6 +1109,7 @@ impl InMemoryAuthStore {
login_method: AuthLoginMethod::Password,
binding_status: AuthBindingStatus::Active,
wechat_bound: false,
wechat_display_name: None,
wechat_account: None,
token_version: 1,
created_at,
@@ -1242,6 +1252,7 @@ impl InMemoryAuthStore {
login_method: AuthLoginMethod::Phone,
binding_status: AuthBindingStatus::Active,
wechat_bound: false,
wechat_display_name: None,
wechat_account: None,
token_version: 1,
created_at,
@@ -1303,6 +1314,7 @@ impl InMemoryAuthStore {
login_method: AuthLoginMethod::Password,
binding_status: AuthBindingStatus::Active,
wechat_bound: false,
wechat_display_name: None,
wechat_account: None,
token_version: 1,
created_at,
@@ -1349,6 +1361,8 @@ impl InMemoryAuthStore {
.filter(|value| !value.is_empty())
.unwrap_or("微信旅人")
.to_string();
let wechat_display_name = normalize_optional_string(profile.display_name.clone())
.or_else(|| Some(display_name.clone()));
let username = build_wechat_username(&display_name, &profile.provider_uid);
let provider_uid = normalize_required_string(&profile.provider_uid).unwrap_or_default();
let user = AuthUser {
@@ -1362,6 +1376,7 @@ impl InMemoryAuthStore {
login_method: AuthLoginMethod::Wechat,
binding_status: AuthBindingStatus::PendingBindPhone,
wechat_bound: true,
wechat_display_name,
wechat_account: Some(provider_uid.clone()),
token_version: 1,
created_at,
@@ -1518,6 +1533,9 @@ impl InMemoryAuthStore {
stored_user.user.display_name = display_name.to_string();
}
stored_user.user.wechat_account = Some(next_provider_uid.clone());
if let Some(display_name) = next_display_name.clone() {
stored_user.user.wechat_display_name = Some(display_name);
}
stored_user.user.clone()
};
self.persist_wechat_state(&state)?;
@@ -1753,6 +1771,7 @@ impl InMemoryAuthStore {
.cloned()
.ok_or(PhoneAuthError::UserStateMismatch)?;
let pending_wechat_account = pending_wechat_identity.provider_uid.clone();
let pending_wechat_display_name = pending_wechat_identity.display_name.clone();
let pending_username = state
.users_by_username
@@ -1782,6 +1801,7 @@ impl InMemoryAuthStore {
.ok_or(PhoneAuthError::UserNotFound)?;
target_user.user.wechat_bound = true;
target_user.user.wechat_account = Some(pending_wechat_account);
target_user.user.wechat_display_name = pending_wechat_display_name;
if target_user.user.phone_number.is_none() {
target_user.user.phone_number = target_user.phone_number.clone();
}
@@ -1799,6 +1819,11 @@ impl InMemoryAuthStore {
.values()
.find(|identity| identity.user_id == pending_user_id)
.map(|identity| identity.provider_uid.clone());
let bound_wechat_display_name = state
.wechat_identity_by_provider_uid
.values()
.find(|identity| identity.user_id == pending_user_id)
.and_then(|identity| identity.display_name.clone());
let stored_user = state
.users_by_username
@@ -1812,6 +1837,9 @@ impl InMemoryAuthStore {
if stored_user.user.wechat_account.is_none() {
stored_user.user.wechat_account = bound_wechat_account;
}
if stored_user.user.wechat_display_name.is_none() {
stored_user.user.wechat_display_name = bound_wechat_display_name;
}
stored_user.phone_number = Some(phone_number.e164);
let next_user = stored_user.user.clone();
self.persist_phone_state(&state)?;
@@ -3368,6 +3396,10 @@ mod tests {
AuthBindingStatus::PendingBindPhone
);
assert_eq!(first_wechat.user.username, "微信旅人甲_wx-openid-first");
assert_eq!(
first_wechat.user.wechat_display_name.as_deref(),
Some("微信旅人甲")
);
assert!(first_wechat.user.id.starts_with("user_"));
assert!(!first_wechat.user.id.ends_with("00000001"));
@@ -3389,6 +3421,10 @@ mod tests {
assert_ne!(second_wechat.user.id, phone_user.id);
assert_eq!(second_wechat.user.login_method, AuthLoginMethod::Wechat);
assert_eq!(second_wechat.user.username, first_wechat.user.username);
assert_eq!(
second_wechat.user.wechat_display_name.as_deref(),
Some("微信旅人乙")
);
}
#[tokio::test]
@@ -3438,6 +3474,10 @@ mod tests {
wechat_user.binding_status,
AuthBindingStatus::PendingBindPhone
);
assert_eq!(
wechat_user.wechat_display_name.as_deref(),
Some("待绑定微信用户")
);
assert_ne!(wechat_user.id, phone_user.id);
phone_service
@@ -3465,6 +3505,10 @@ mod tests {
assert_eq!(merged.user.id, phone_user.id);
assert_eq!(merged.user.binding_status, AuthBindingStatus::Active);
assert!(merged.user.wechat_bound);
assert_eq!(
merged.user.wechat_display_name.as_deref(),
Some("待绑定微信用户")
);
let reused_wechat_user = wechat_service
.resolve_login(ResolveWechatLoginInput {
@@ -3482,5 +3526,9 @@ mod tests {
assert!(!reused_wechat_user.created);
assert_eq!(reused_wechat_user.user.id, phone_user.id);
assert!(reused_wechat_user.user.wechat_bound);
assert_eq!(
reused_wechat_user.user.wechat_display_name.as_deref(),
Some("已归并微信用户")
);
}
}