반응형
OAuth 2.0 인증 시스템에서 Refresh Token 전략을 구현하고, 사용자 로그아웃 시 Access Token과 Refresh Token을 무효화하는 방법을 학습합니다. 이 작업은 인증 프로세스의 보안과 사용자 경험을 향상시키는 데 중요합니다.
1. Refresh Token 개념 이해
1-1. Refresh Token의 역할
- Refresh Token은 Access Token이 만료된 경우 새로운 Access Token을 발급받기 위해 사용됩니다.
- Access Token은 짧은 수명을 가지며 보안을 강화하기 위해 주기적으로 갱신됩니다.
1-2. Refresh Token 동작 흐름
- 사용자 인증 시, 권한 서버는 Access Token과 Refresh Token을 발급합니다.
- Access Token이 만료되면 클라이언트는 Refresh Token을 사용하여 새 Access Token을 요청합니다.
- 권한 서버는 Refresh Token의 유효성을 확인한 후 새 Access Token을 반환합니다.
2. Refresh Token 전략 구현
2-1. Refresh Token 요청 구현
다음 코드는 Refresh Token을 사용하여 새 Access Token을 요청하는 방법을 보여줍니다.
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.ResponseEntity;
import org.springframework.web.client.RestTemplate;
public class TokenService {
private static final String TOKEN_REFRESH_URL = "https://oauth2.googleapis.com/token";
public String refreshAccessToken(String clientId, String clientSecret, String refreshToken) {
RestTemplate restTemplate = new RestTemplate();
// HTTP 요청 본문 구성
HttpHeaders headers = new HttpHeaders();
headers.set("Content-Type", "application/x-www-form-urlencoded");
String body = String.format(
"client_id=%s&client_secret=%s&refresh_token=%s&grant_type=refresh_token",
clientId, clientSecret, refreshToken
);
HttpEntity entity = new HttpEntity<>(body, headers);
// Refresh Token 요청
ResponseEntity response = restTemplate.postForEntity(TOKEN_REFRESH_URL, entity, Map.class);
// 새 Access Token 반환
return (String) response.getBody().get("access_token");
}
}
2-2. Access Token 및 Refresh Token 저장
사용자의 Access Token 및 Refresh Token은 안전하게 저장되어야 합니다. DB 또는 암호화된 세션에 저장할 수 있습니다.
사용자 토큰 저장 SQL 예:
CREATE TABLE user_tokens (
user_id BIGINT NOT NULL,
access_token TEXT,
refresh_token TEXT,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
PRIMARY KEY (user_id)
);
2-3. 토큰 갱신 프로세스 구현
public String getAccessToken(String userId) {
// DB에서 사용자 토큰 가져오기
String accessToken = getAccessTokenFromDB(userId);
String refreshToken = getRefreshTokenFromDB(userId);
// Access Token 만료 시 Refresh Token으로 갱신
if (isAccessTokenExpired(accessToken)) {
accessToken = refreshAccessToken(CLIENT_ID, CLIENT_SECRET, refreshToken);
saveAccessTokenToDB(userId, accessToken);
}
return accessToken;
}
3. 로그아웃 구현
3-1. Access Token과 Refresh Token 무효화
사용자가 로그아웃하면, 기존의 Access Token과 Refresh Token을 무효화하여 보안을 강화합니다.
Google 로그아웃 API 호출:
import org.springframework.web.client.RestTemplate;
public class LogoutService {
private static final String LOGOUT_URL = "https://accounts.google.com/o/oauth2/revoke?token=";
public void revokeToken(String token) {
RestTemplate restTemplate = new RestTemplate();
restTemplate.getForObject(LOGOUT_URL + token, String.class);
}
}
3-2. 로그아웃 컨트롤러 구현
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
@Controller
public class LogoutController {
private final LogoutService logoutService;
public LogoutController(LogoutService logoutService) {
this.logoutService = logoutService;
}
@GetMapping("/logout")
public String logout(String accessToken, String refreshToken) {
logoutService.revokeToken(accessToken);
logoutService.revokeToken(refreshToken);
// 세션 무효화
return "redirect:/login";
}
}
4. 보안 고려 사항
- Refresh Token 보안:
- Refresh Token은 장기적으로 사용되므로 암호화된 저장소에 저장하거나 DB에서 안전하게 관리해야 합니다.
- HTTPS 사용:
- 토큰 교환 및 API 호출 시 HTTPS를 사용하여 데이터 보안을 강화합니다.
- 사용자별 로그아웃:
- 특정 사용자가 로그아웃 시 해당 사용자의 모든 토큰을 무효화합니다.
5. 테스트
- Access Token 갱신:
- Access Token 만료 시 Refresh Token으로 새 Access Token을 요청합니다.
- 로그아웃 테스트:
- /logout URL로 접근하여 토큰 무효화를 확인합니다.
6. 마무리
이번 학습에서는 Refresh Token 전략과 로그아웃 구현을 통해 OAuth 2.0 인증 시스템을 더욱 완성했습니다. 다음에서는 OAuth 2.0의 커스텀 인증 필터 구현에 대해 학습합니다.
반응형
'개발 > 전자정부프레임워크' 카테고리의 다른 글
다중 인증 방식 통합 구현 (JWT와 OAuth 2.0) (0) | 2024.12.26 |
---|---|
OAuth 2.0 커스텀 인증 필터 구현 (0) | 2024.12.26 |
OAuth 2.0 기반 API 요청 및 Access Token 검증 (0) | 2024.12.26 |
OAuth 2.0을 이용한 소셜 로그인 구현 (0) | 2024.12.26 |
API 서버와 클라이언트 간의 데이터 암호화 및 보안 (0) | 2024.12.26 |