-
Notifications
You must be signed in to change notification settings - Fork 1
Fix/#350 자동로그인 오류 해결 #355
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
The head ref may contain hidden characters: "fix/#350-\uC790\uB3D9\uB85C\uADF8\uC778-\uC624\uB958-\uD574\uACB0"
Fix/#350 자동로그인 오류 해결 #355
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -9,20 +9,37 @@ import Foundation | |
|
|
||
| import Alamofire | ||
|
|
||
| protocol TokenService { | ||
| protocol TokenService: Sendable { | ||
| func reissue() async throws | ||
| } | ||
|
|
||
| final class DefaultTokenService: TokenService { | ||
|
|
||
| actor DefaultTokenService: TokenService { | ||
| private var tokenTask: Task<Void, Error>? | ||
| private let keychainService: KeychainService | ||
|
|
||
| init( | ||
| keychainService: KeychainService | ||
| ) { | ||
|
|
||
| init(keychainService: KeychainService) { | ||
| self.keychainService = keychainService | ||
| } | ||
|
|
||
| func reissue() async throws { | ||
|
|
||
| if let task = tokenTask { | ||
| return try await task.value | ||
| } | ||
|
|
||
| let task = Task { | ||
| try await fetchAuthReissue() | ||
| } | ||
|
|
||
| tokenTask = task | ||
| defer { tokenTask = nil } | ||
|
|
||
| return try await task.value | ||
| } | ||
|
|
||
| private func fetchAuthReissue() async throws { | ||
| let header: HeaderType = .withAuth(acessToken: keychainService.load(key: .refreshToken)) | ||
| ByeBooLogger.debug("토큰 재발급 시작") | ||
|
|
||
|
|
@@ -39,46 +56,53 @@ final class DefaultTokenService: TokenService { | |
| .validate() | ||
| .responseDecodable(of: BaseResponse<TokenReissueResponseDTO>.self) { [weak self] response in | ||
| guard let self else { return } | ||
| ByeBooLogger.debug("💡Reissue \(response)") | ||
|
|
||
| switch response.result { | ||
| case .success(let data): | ||
| guard let data = data.data else { | ||
| ByeBooLogger.error(ByeBooError.noData) | ||
| continuation.resume(throwing: ByeBooError.noData) | ||
| return | ||
| } | ||
| ByeBooLogger.debug("토큰 재발급 완료") | ||
| self.keychainService.save(key: .accessToken, token: data.accessToken) | ||
| self.keychainService.save(key: .refreshToken, token: data.refreshToken) | ||
| continuation.resume(returning: ()) | ||
| case .failure(let error): | ||
| ByeBooLogger.debug("토큰 재발급 실패, 키체인 삭제 후 로그인으로 이동") | ||
| self.clearKeychain() | ||
| DispatchQueue.main.async { | ||
| NotificationCenter.default.post(name: .navigateLoginViewController, object: nil) | ||
|
|
||
| Task { | ||
| await self.debugTokenReissueSuccess(data) | ||
|
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 이 친구가 하는 역할이 단순 디버그가 아니라면 함수명을 더 직관적으로 바꿔주면 좋을 것 같아요! |
||
| continuation.resume(returning: ()) | ||
| } | ||
| if let data = response.data, | ||
| let statusCode = response.response?.statusCode, | ||
| let errorResponse = try? JSONDecoder().decode(EmptyResponse.self, from: data) { | ||
| ByeBooLogger.error(error) | ||
|
|
||
| case .failure(let error): | ||
| Task { | ||
| await self.debugTokenReissueFailure() | ||
|
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 이 친구 또한 ~ |
||
| continuation.resume(throwing: error) | ||
| } else { | ||
| ByeBooLogger.error(ByeBooError.decodingError) | ||
| continuation.resume(throwing: ByeBooError.decodingError) | ||
| } | ||
| } | ||
| } | ||
| } | ||
| } | ||
| } | ||
|
|
||
| extension DefaultTokenService { | ||
|
|
||
| private func debugTokenReissueSuccess(_ data: TokenReissueResponseDTO) { | ||
| ByeBooLogger.debug("토큰 재발급 완료") | ||
| self.keychainService.save(key: .accessToken, token: data.accessToken) | ||
| self.keychainService.save(key: .refreshToken, token: data.refreshToken) | ||
| } | ||
|
|
||
| private func debugTokenReissueFailure() { | ||
| ByeBooLogger.debug("토큰 재발급 실패, 키체인 삭제 후 로그인으로 이동") | ||
| clearKeychain() | ||
| DispatchQueue.main.async { | ||
| NotificationCenter.default.post(name: .navigateLoginViewController, object: nil) | ||
| } | ||
|
Comment on lines
+93
to
+95
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 이 친구만 concurrency를 사용하지 않은 이유가 궁금해요 !
Collaborator
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 그냥 메인스레드에서 해주면 되겠지 ~ 라는 생각으로 썼는데 바꿔주면 좋을 것 같아서 반영했습니다 !! |
||
| } | ||
|
|
||
| private func clearKeychain() { | ||
| for key in KeyType.allCases { | ||
| let token = keychainService.load(key: key) | ||
| if !token.isEmpty { | ||
| keychainService.delete(key: key) | ||
| ByeBooLogger.debug("\(key) 삭제") | ||
| if !token.isEmpty { | ||
| keychainService.delete(key: key) | ||
| ByeBooLogger.debug("\(key) 삭제") | ||
| } | ||
| } | ||
| } | ||
|
|
||
| } | ||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
여기서 continuation resume이 안되고 있어요 ! 누수가 발생할 가능성이 있어보입니다