我正在用Spring MVC設計web應用程序。Java中服務層的多線程
我在安全更新電子郵件和註冊新用戶時遇到了一些問題。 電子郵件對每個用戶都是唯一的。
這是我的方法,它是由控制器用於註冊用戶調用:
@Override
public void registerUser(Client newUser) throws DuplicateEmailException {
if(!isEmailUnique(newUser.getEmail())){
throw new DuplicateEmailException("User with the same email is registered"
+ " in system already");
}
newUser.setPassword(encodePassword(newUser.getPassword()));
newUser.setRole(UserRole.ROLE_CLIENT);
newUser.setStatus(UserStatus.ACTIVE);
newUser.setEmailStatus(EmailStatus.NOTCONFIRMED);
newUser.setRegistrationTime(LocalDateTime.now());
clientDao.save(newUser);
}
這是更新的電子郵件方法:
@Override
public void updateUserEmail(String email, String newEmail, String password)
throws InvalidPasswordException, DuplicateEmailException {
Client client = getClientByEmail(email);
if(!isPasswordRight(password, client.getPassword())){
throw new InvalidPasswordException("Password doesn't match to real");
}
if(email.equals(newEmail)){
return;
}
if(!isEmailUnique(newEmail)){
throw new DuplicateEmailException(
"Such email is registered in system already");
}
client.setEmail(newEmail);
client.setEmailStatus(EmailStatus.NOTCONFIRMED);
}
有可能的情況下,當某些用戶點擊按鈕對於註冊,registerUser(Client newUser)
方法檢查電子郵件的唯一性,同時第二個用戶想要更新電子郵件,並且在clientDao.save(newUser)
被調用之前,updateUserEmail(String email, String newEmail, String password)
檢查電子郵件的唯一性,如果兩個用戶的電子郵件是平等的,我會g等兩個相同的電子郵件在db - 這是不可接受的。
我的服務層都標有@Translactional
註解,會話自動關閉交易之前沖刷和用戶保存在數據庫整理registerUser(..)
方法
所以以後只,請告訴我,我可以使用哪些工具在Java中的多線程爲了解決這個問題?
但在我更新的電子郵件方法中,我沒有使用save方法,我從db獲取Client實例並在此持久實例上設置字段。 – Yuriy
處理唯一性問題是您真正想避免在應用程序中執行的事情,如果您可以管理它。這是因爲即使您在一個JVM中解決了併發問題,如果您橫向擴展到應用程序的多個實例,您現在需要管理多個應用程序之間的併發性,這可能是一個非常難以解決的問題。我強烈建議你在DB端處理這個問題。 –
因此,我捕獲異常,如果我嘗試保存具有重複電子郵件的對象,則會調用異常。謝謝:) – Yuriy