feat: 관리자 전용 API에 사용할 새로운 Interceptor 및 어노테이션 추가

This commit is contained in:
이상진 2025-09-11 16:58:05 +09:00
parent 39da28d3f1
commit e02086680b
2 changed files with 63 additions and 1 deletions

View File

@ -1,5 +1,7 @@
package roomescape.auth.web.support
import roomescape.admin.infrastructure.persistence.Privilege
@Target(AnnotationTarget.FUNCTION)
@Retention(AnnotationRetention.RUNTIME)
annotation class Admin
@ -10,4 +12,10 @@ annotation class LoginRequired
@Target(AnnotationTarget.VALUE_PARAMETER)
@Retention(AnnotationRetention.RUNTIME)
annotation class MemberId
annotation class MemberId
@Target(AnnotationTarget.FUNCTION)
@Retention(AnnotationRetention.RUNTIME)
annotation class AdminOnly(
val privilege: Privilege
)

View File

@ -0,0 +1,54 @@
package roomescape.auth.web.support.interceptors
import io.github.oshai.kotlinlogging.KLogger
import io.github.oshai.kotlinlogging.KotlinLogging
import jakarta.servlet.http.HttpServletRequest
import jakarta.servlet.http.HttpServletResponse
import org.slf4j.MDC
import org.springframework.stereotype.Component
import org.springframework.web.method.HandlerMethod
import org.springframework.web.servlet.HandlerInterceptor
import roomescape.admin.infrastructure.persistence.AdminPermissionLevel
import roomescape.auth.business.CLAIM_PERMISSION_KEY
import roomescape.auth.exception.AuthErrorCode
import roomescape.auth.exception.AuthException
import roomescape.auth.infrastructure.jwt.JwtUtils
import roomescape.auth.web.support.AdminOnly
import roomescape.auth.web.support.MDC_MEMBER_ID_KEY
import roomescape.auth.web.support.accessToken
private val log: KLogger = KotlinLogging.logger {}
@Component
class AdminInterceptor(
private val jwtUtils: JwtUtils
) : HandlerInterceptor {
override fun preHandle(
request: HttpServletRequest,
response: HttpServletResponse,
handler: Any
): Boolean {
if (handler !is HandlerMethod) {
return true
}
val annotation: AdminOnly = handler.getMethodAnnotation(AdminOnly::class.java) ?: return true
val token: String? = request.accessToken()
val adminId = jwtUtils.extractSubject(token).also { MDC.put(MDC_MEMBER_ID_KEY, it) }
jwtUtils.extractClaim(
token = token, key = CLAIM_PERMISSION_KEY
).also {
val permission = AdminPermissionLevel.valueOf(it)
if (!permission.hasPrivilege(annotation.privilege)) {
log.warn { "[AuthInterceptor] 관리자 권한 부족: required=${annotation.privilege} / current=${permission}" }
throw AuthException(AuthErrorCode.ACCESS_DENIED)
}
log.info { "[AuthInterceptor] 인증 완료. adminId=$adminId, permission=${permission}" }
}
return true
}
}