Skip to content

Commit b1edaa7

Browse files
committed
refactory: auth 로직 리팩토링
1 parent 4e91a55 commit b1edaa7

File tree

11 files changed

+172
-275
lines changed

11 files changed

+172
-275
lines changed

ProjectVG.Api/Controllers/OAuthController.cs

Lines changed: 2 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,6 @@
11
using Microsoft.AspNetCore.Mvc;
22
using ProjectVG.Application.Services.Auth;
3-
using ProjectVG.Application.Models.Auth;
43
using ProjectVG.Infrastructure.Auth;
5-
using System.Security.Cryptography;
6-
using System.Text;
74
using Microsoft.Extensions.Options;
85
using ProjectVG.Common.Configuration;
96

@@ -14,24 +11,16 @@ namespace ProjectVG.Api.Controllers
1411
public class OAuthController : ControllerBase
1512
{
1613
private readonly IOAuth2Service _oauth2Service;
17-
private readonly IAuthService _authService;
18-
private readonly OAuth2ProviderSettings _oauth2Settings;
1914

2015
public OAuthController(
21-
IHttpClientFactory httpClientFactory,
22-
JwtService jwtService,
2316
IOAuth2Service oauth2Service,
24-
IAuthService authService,
2517
IOptions<OAuth2ProviderSettings> oauth2Settings)
2618
{
2719
_oauth2Service = oauth2Service;
28-
_authService = authService;
29-
_oauth2Settings = oauth2Settings.Value;
3020
}
3121

3222
[HttpGet("oauth2/authorize")]
3323
public async Task<IActionResult> OAuth2Authorize(
34-
[FromQuery] string scope,
3524
[FromQuery] string state,
3625
[FromQuery] string code_challenge,
3726
[FromQuery] string code_challenge_method,
@@ -45,14 +34,12 @@ public async Task<IActionResult> OAuth2Authorize(
4534
return BadRequest("Invalid PKCE parameters");
4635
}
4736

48-
var googleAuthUrl = await _oauth2Service.BuildAuthorizationUrlAsync(scope, state, code_challenge, code_challenge_method, code_verifier, client_redirect_uri);
37+
var googleAuthUrl = await _oauth2Service.BuildAuthorizationUrlAsync(state, code_challenge, code_challenge_method, code_verifier, client_redirect_uri);
4938

5039
return Ok(new
5140
{
5241
success = true,
53-
auth_url = googleAuthUrl,
54-
state = state,
55-
message = "Redirect to this URL to start OAuth2 login"
42+
auth_url = googleAuthUrl
5643
});
5744
}
5845
catch (InvalidOperationException ex)

ProjectVG.Api/Filters/JwtAuthenticationFilter.cs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
using Microsoft.AspNetCore.Mvc;
22
using Microsoft.AspNetCore.Mvc.Filters;
33
using Microsoft.Extensions.Logging;
4-
using ProjectVG.Application.Services.Auth;
4+
using ProjectVG.Infrastructure.Auth;
55
using System.Security.Claims;
66

77
namespace ProjectVG.Api.Filters
@@ -12,7 +12,7 @@ public class JwtAuthenticationAttribute : Attribute, IAsyncAuthorizationFilter
1212
public async Task OnAuthorizationAsync(AuthorizationFilterContext context)
1313
{
1414
var logger = context.HttpContext.RequestServices.GetRequiredService<ILogger<JwtAuthenticationAttribute>>();
15-
var authService = context.HttpContext.RequestServices.GetRequiredService<IAuthService>();
15+
var tokenService = context.HttpContext.RequestServices.GetRequiredService<ITokenService>();
1616

1717
// 디버그: 모든 헤더 로깅
1818
logger.LogInformation("=== JWT 인증 디버그 시작 ===");
@@ -47,7 +47,7 @@ public async Task OnAuthorizationAsync(AuthorizationFilterContext context)
4747
logger.LogInformation("토큰 추출 성공. 토큰 길이: {TokenLength}", token.Length);
4848
logger.LogInformation("토큰 미리보기: {TokenPreview}", token.Length > 20 ? token.Substring(0, 20) + "..." : token);
4949

50-
var isValid = await authService.ValidateAccessTokenAsync(token);
50+
var isValid = await tokenService.ValidateAccessTokenAsync(token);
5151
logger.LogInformation("토큰 검증 결과: {IsValid}", isValid);
5252

5353
if (!isValid)
@@ -66,7 +66,7 @@ public async Task OnAuthorizationAsync(AuthorizationFilterContext context)
6666
return;
6767
}
6868

69-
var userId = await authService.GetCurrentUserIdAsync(token);
69+
var userId = await tokenService.GetUserIdFromTokenAsync(token);
7070
logger.LogInformation("추출된 사용자 ID: {UserId}", userId);
7171

7272
if (!userId.HasValue)

ProjectVG.Application/Services/Auth/AuthService.cs

Lines changed: 0 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -182,45 +182,5 @@ public async Task<bool> LogoutAsync(string refreshToken)
182182
return false;
183183
}
184184
}
185-
186-
public async Task<bool> ValidateAccessTokenAsync(string accessToken)
187-
{
188-
try
189-
{
190-
_logger.LogInformation("=== ValidateAccessTokenAsync 디버그 ===");
191-
192-
var userId = await _tokenService.GetUserIdFromTokenAsync(accessToken);
193-
_logger.LogInformation("추출된 UserId: {UserId}", userId);
194-
195-
if (!userId.HasValue)
196-
{
197-
_logger.LogWarning("UserId가 null이므로 검증 실패");
198-
return false;
199-
}
200-
201-
_logger.LogInformation("JWT 토큰 검증 성공 - UserId: {UserId}", userId.Value);
202-
return true;
203-
}
204-
catch (Exception ex)
205-
{
206-
_logger.LogError(ex, "Access token validation failed");
207-
return false;
208-
}
209-
}
210-
211-
public async Task<Guid?> GetCurrentUserIdAsync(string accessToken)
212-
{
213-
try
214-
{
215-
return await _tokenService.GetUserIdFromTokenAsync(accessToken);
216-
}
217-
catch (Exception ex)
218-
{
219-
_logger.LogError(ex, "Failed to get user ID from access token");
220-
return null;
221-
}
222-
}
223-
224-
225185
}
226186
}

ProjectVG.Application/Services/Auth/IAuthService.cs

Lines changed: 32 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -3,24 +3,50 @@
33

44
namespace ProjectVG.Application.Services.Auth
55
{
6+
/// <summary>
7+
/// 인증 및 토큰 관리 서비스
8+
/// JWT 토큰 생성, 검증, 갱신 및 OAuth 로그인 처리를 담당
9+
/// </summary>
610
public interface IAuthService
711
{
8-
// 로그인을 실행 (provider Id와 )
9-
10-
11-
12+
/// <summary>
13+
/// OAuth 제공자를 통한 로그인 처리 (Google, GitHub, Microsoft, 게스트 등)
14+
/// </summary>
15+
/// <param name="provider">인증 제공자 (google, github, microsoft, guest, test)</param>
16+
/// <param name="providerUserId">제공자별 사용자 ID</param>
17+
/// <returns>로그인 결과 (토큰, 사용자 정보 포함)</returns>
1218
Task<AuthResult> LoginWithOAuthAsync(string provider, string providerUserId);
19+
20+
/// <summary>
21+
/// 리프레시 토큰을 사용하여 새로운 액세스 토큰 발급
22+
/// </summary>
23+
/// <param name="refreshToken">유효한 리프레시 토큰</param>
24+
/// <returns>새로운 토큰 쌍과 사용자 정보</returns>
1325
Task<AuthResult> RefreshTokenAsync(string refreshToken);
26+
27+
/// <summary>
28+
/// 사용자 로그아웃 처리 (리프레시 토큰 무효화)
29+
/// </summary>
30+
/// <param name="refreshToken">무효화할 리프레시 토큰</param>
31+
/// <returns>로그아웃 성공 여부</returns>
1432
Task<bool> LogoutAsync(string refreshToken);
15-
Task<bool> ValidateAccessTokenAsync(string accessToken);
16-
Task<Guid?> GetCurrentUserIdAsync(string accessToken);
1733
}
1834

35+
/// <summary>
36+
/// 인증 처리 결과를 담는 클래스
37+
/// </summary>
1938
public class AuthResult
2039
{
40+
/// <summary>인증 성공 여부</summary>
2141
public bool IsSuccess { get; set; }
42+
43+
/// <summary>실패시 오류 메시지</summary>
2244
public string? ErrorMessage { get; set; }
45+
46+
/// <summary>성공시 JWT 토큰 정보</summary>
2347
public TokenResponse? Tokens { get; set; }
48+
49+
/// <summary>성공시 사용자 정보</summary>
2450
public UserDto? User { get; set; }
2551
}
2652
}

ProjectVG.Application/Services/Auth/ILoginService.cs

Lines changed: 0 additions & 30 deletions
This file was deleted.

ProjectVG.Application/Services/Auth/IOAuth2Service.cs

Lines changed: 75 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2,26 +2,98 @@
22

33
namespace ProjectVG.Application.Services.Auth
44
{
5+
/// <summary>
6+
/// OAuth2 인증 플로우 관리 서비스
7+
/// Google, GitHub, Microsoft 등의 외부 OAuth2 제공자와의 인증 처리를 담당
8+
/// </summary>
59
public interface IOAuth2Service
610
{
7-
Task<string> BuildAuthorizationUrlAsync(string scope, string state, string codeChallenge, string codeChallengeMethod, string codeVerifier, string clientRedirectUri);
11+
/// <summary>
12+
/// OAuth2 인증 URL 생성 (PKCE 플로우 지원)
13+
/// </summary>
14+
/// <param name="state">CSRF 보호를 위한 상태값</param>
15+
/// <param name="codeChallenge">PKCE code challenge</param>
16+
/// <param name="codeChallengeMethod">PKCE challenge 방법 (S256)</param>
17+
/// <param name="codeVerifier">PKCE code verifier</param>
18+
/// <param name="clientRedirectUri">클라이언트 리다이렉트 URI</param>
19+
/// <returns>OAuth2 인증 URL</returns>
20+
Task<string> BuildAuthorizationUrlAsync(string state, string codeChallenge, string codeChallengeMethod, string codeVerifier, string clientRedirectUri);
21+
22+
/// <summary>
23+
/// OAuth2 콜백 처리 (인증 코드를 토큰으로 교환하고 사용자 로그인 처리)
24+
/// </summary>
25+
/// <param name="code">인증 코드</param>
26+
/// <param name="state">상태값</param>
27+
/// <returns>콜백 처리 결과</returns>
828
Task<OAuth2CallbackResult> HandleOAuth2CallbackAsync(string code, string state);
29+
30+
/// <summary>
31+
/// 상태값으로 저장된 OAuth2 토큰 데이터 조회
32+
/// </summary>
33+
/// <param name="state">상태값</param>
34+
/// <returns>토큰 데이터 (없으면 null)</returns>
935
Task<OAuth2TokenData?> GetTokenDataAsync(string state);
36+
37+
/// <summary>
38+
/// OAuth2 토큰 데이터 삭제 (사용 후 정리)
39+
/// </summary>
40+
/// <param name="state">삭제할 토큰 데이터의 상태값</param>
1041
Task DeleteTokenDataAsync(string state);
42+
43+
/// <summary>
44+
/// OAuth2 인증 코드를 액세스 토큰으로 교환
45+
/// </summary>
46+
/// <param name="code">인증 코드</param>
47+
/// <param name="clientId">클라이언트 ID</param>
48+
/// <param name="redirectUri">리다이렉트 URI</param>
49+
/// <param name="codeVerifier">PKCE code verifier (선택적)</param>
50+
/// <returns>토큰 교환 결과</returns>
1151
Task<TokenResponse> ExchangeAuthorizationCodeAsync(string code, string clientId, string redirectUri, string codeVerifier = "");
52+
53+
/// <summary>
54+
/// OAuth2 제공자에서 사용자 정보 조회
55+
/// </summary>
56+
/// <param name="accessToken">OAuth2 액세스 토큰</param>
57+
/// <param name="provider">제공자명 (google, github, microsoft)</param>
58+
/// <returns>사용자 정보</returns>
1259
Task<OAuth2UserInfo> GetUserInfoAsync(string accessToken, string provider);
60+
61+
/// <summary>
62+
/// OAuth2 요청 정보 저장 (임시 저장소)
63+
/// </summary>
64+
/// <param name="state">상태값</param>
65+
/// <param name="request">OAuth2 요청 정보</param>
66+
/// <returns>저장된 요청 정보</returns>
1367
Task<OAuth2AuthRequest> StoreOAuth2RequestAsync(string state, OAuth2AuthRequest request);
68+
69+
/// <summary>
70+
/// 저장된 OAuth2 요청 정보 조회
71+
/// </summary>
72+
/// <param name="state">상태값</param>
73+
/// <returns>요청 정보 (없으면 null)</returns>
1474
Task<OAuth2AuthRequest?> GetOAuth2RequestAsync(string state);
75+
76+
/// <summary>
77+
/// OAuth2 요청 정보 삭제 (사용 후 정리)
78+
/// </summary>
79+
/// <param name="state">삭제할 요청의 상태값</param>
1580
Task DeleteOAuth2RequestAsync(string state);
81+
82+
/// <summary>
83+
/// 토큰 데이터를 상태값과 함께 임시 저장
84+
/// </summary>
85+
/// <param name="state">상태값</param>
86+
/// <param name="tokenData">저장할 토큰 데이터</param>
1687
Task StoreTokenDataAsync(string state, object tokenData);
1788
}
1889

90+
/// <summary>
91+
/// OAuth2 제공자에서 가져온 사용자 정보
92+
/// </summary>
1993
public class OAuth2UserInfo
2094
{
2195
public string Id { get; set; } = string.Empty;
2296
public string Email { get; set; } = string.Empty;
23-
public string Name { get; set; } = string.Empty;
24-
public string? Picture { get; set; }
2597
public string Provider { get; set; } = string.Empty;
2698
}
2799
}

ProjectVG.Application/Services/Auth/LoginService.cs

Lines changed: 0 additions & 39 deletions
This file was deleted.

0 commit comments

Comments
 (0)