From 0df35f0dd8c4cf45b7174c179fa5d2c5756e7aff Mon Sep 17 00:00:00 2001 From: felixncheng Date: Wed, 11 Oct 2023 10:57:00 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20fs-server=E6=94=AF=E6=8C=81token?= =?UTF-8?q?=E5=88=B7=E6=96=B0=20#1247?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../fs/server/config/RouteConfiguration.kt | 1 + .../server/filter/PermissionFilterFunction.kt | 9 +++++--- .../bkrepo/fs/server/handler/LoginHandler.kt | 22 ++++++++++++++++--- 3 files changed, 26 insertions(+), 6 deletions(-) diff --git a/src/backend/fs/boot-fs-server/src/main/kotlin/com/tencent/bkrepo/fs/server/config/RouteConfiguration.kt b/src/backend/fs/boot-fs-server/src/main/kotlin/com/tencent/bkrepo/fs/server/config/RouteConfiguration.kt index 36eedc019b..8994bde941 100644 --- a/src/backend/fs/boot-fs-server/src/main/kotlin/com/tencent/bkrepo/fs/server/config/RouteConfiguration.kt +++ b/src/backend/fs/boot-fs-server/src/main/kotlin/com/tencent/bkrepo/fs/server/config/RouteConfiguration.kt @@ -74,6 +74,7 @@ class RouteConfiguration( before(RouteConfiguration::initArtifactContext) filter(permissionFilterFunction::filter) POST("/login/{projectId}/{repoName}", loginHandler::login) + POST("/token/refresh/{projectId}/{repoName}", loginHandler::refresh) "/service/block".nest { GET("/list$DEFAULT_MAPPING_URI", fsNodeHandler::listBlocks) diff --git a/src/backend/fs/boot-fs-server/src/main/kotlin/com/tencent/bkrepo/fs/server/filter/PermissionFilterFunction.kt b/src/backend/fs/boot-fs-server/src/main/kotlin/com/tencent/bkrepo/fs/server/filter/PermissionFilterFunction.kt index c447ee4edc..5552359ce1 100644 --- a/src/backend/fs/boot-fs-server/src/main/kotlin/com/tencent/bkrepo/fs/server/filter/PermissionFilterFunction.kt +++ b/src/backend/fs/boot-fs-server/src/main/kotlin/com/tencent/bkrepo/fs/server/filter/PermissionFilterFunction.kt @@ -44,9 +44,12 @@ class PermissionFilterFunction(private val securityManager: SecurityManager) : C private val matcher = AntPathMatcher() override suspend fun filter( request: ServerRequest, - next: suspend (ServerRequest) -> ServerResponse + next: suspend (ServerRequest) -> ServerResponse, ): ServerResponse { - if (request.path().startsWith("/login") || request.path().startsWith("/service")) { + if (request.path().startsWith("/login") || + request.path().startsWith("/service") || + request.path().startsWith("/token") + ) { return next(request) } val action = request.getAction() @@ -92,7 +95,7 @@ class PermissionFilterFunction(private val securityManager: SecurityManager) : C "/node/delete/**", "/node/mkdir/**", "/node/set-length/**", - "/block/**" + "/block/**", ) } } diff --git a/src/backend/fs/boot-fs-server/src/main/kotlin/com/tencent/bkrepo/fs/server/handler/LoginHandler.kt b/src/backend/fs/boot-fs-server/src/main/kotlin/com/tencent/bkrepo/fs/server/handler/LoginHandler.kt index 896efe307c..be8b1191c9 100644 --- a/src/backend/fs/boot-fs-server/src/main/kotlin/com/tencent/bkrepo/fs/server/handler/LoginHandler.kt +++ b/src/backend/fs/boot-fs-server/src/main/kotlin/com/tencent/bkrepo/fs/server/handler/LoginHandler.kt @@ -50,7 +50,7 @@ import org.springframework.web.reactive.function.server.ServerResponse class LoginHandler( private val permissionService: PermissionService, private val securityManager: SecurityManager, - private val rAuthClient: RAuthClient + private val rAuthClient: RAuthClient, ) { /** @@ -70,7 +70,11 @@ class LoginHandler( if (tokenRes.data != true) { throw AuthenticationException() } + val token = createToken(projectId, repoName, username) + return ReactiveResponseBuilder.success(token) + } + private suspend fun createToken(projectId: String, repoName: String, username: String): String { val claims = mutableMapOf(JWT_CLAIMS_REPOSITORY to "$projectId/$repoName") val writePermit = permissionService.checkPermission(projectId, repoName, PermissionAction.WRITE, username) if (writePermit) { @@ -83,8 +87,20 @@ class LoginHandler( } val token = securityManager.generateToken( subject = username, - claims = claims + claims = claims, ) - return ReactiveResponseBuilder.success(token) + return token + } + + suspend fun refresh(request: ServerRequest): ServerResponse { + val token = request.headers().header(HttpHeaders.AUTHORIZATION).firstOrNull().orEmpty() + val jws = securityManager.validateToken(token) + val claims = jws.body + val username = claims.subject + val parts = claims[JWT_CLAIMS_REPOSITORY].toString().split("/") + val projectId = parts[0] + val repoName = parts[1] + val newToken = createToken(projectId, repoName, username) + return ReactiveResponseBuilder.success(newToken) } }