From cb5e0b63f0527cc5b94ad1fb6ea742622a06c163 Mon Sep 17 00:00:00 2001 From: ybelMekk Date: Mon, 3 Jul 2023 11:01:51 +0200 Subject: [PATCH 1/5] update(mock): gradle --- build.gradle.kts | 7 +-- gradle/wrapper/gradle-wrapper.properties | 2 +- .../security/mock/oauth2/MockOAuth2Server.kt | 18 +++---- .../nav/security/mock/oauth2/OAuth2Config.kt | 16 +++--- .../mock/oauth2/StandaloneMockOAuth2Server.kt | 4 +- .../security/mock/oauth2/debugger/Client.kt | 12 ++--- .../oauth2/debugger/DebuggerRequestHandler.kt | 10 ++-- .../mock/oauth2/debugger/SessionManager.kt | 6 +-- .../oauth2/extensions/HttpUrlExtensions.kt | 2 +- .../oauth2/extensions/NimbusExtensions.kt | 4 +- .../oauth2/grant/AuthorizationCodeHandler.kt | 10 ++-- .../grant/ClientCredentialsGrantHandler.kt | 8 +-- .../mock/oauth2/grant/GrantHandler.kt | 2 +- .../oauth2/grant/JwtBearerGrantHandler.kt | 6 +-- .../mock/oauth2/grant/PasswordGrantHandler.kt | 8 +-- .../oauth2/grant/RefreshTokenGrantHandler.kt | 6 +-- .../mock/oauth2/grant/RefreshTokenManager.kt | 8 +-- .../mock/oauth2/grant/TokenExchangeGrant.kt | 6 +-- .../oauth2/grant/TokenExchangeGrantHandler.kt | 6 +-- .../mock/oauth2/http/CorsInterceptor.kt | 2 +- .../mock/oauth2/http/OAuth2HttpRequest.kt | 8 +-- .../oauth2/http/OAuth2HttpRequestHandler.kt | 2 +- .../mock/oauth2/http/OAuth2HttpResponse.kt | 26 +++++----- .../mock/oauth2/http/OAuth2HttpRouter.kt | 2 +- .../mock/oauth2/http/OAuth2HttpServer.kt | 24 ++++----- .../no/nav/security/mock/oauth2/http/Ssl.kt | 40 +++++++------- .../mock/oauth2/introspect/Introspect.kt | 6 +-- .../mock/oauth2/login/LoginRequestHandler.kt | 2 +- .../mock/oauth2/templates/TemplateMapper.kt | 34 ++++++------ .../mock/oauth2/token/KeyGenerator.kt | 10 ++-- .../security/mock/oauth2/token/KeyProvider.kt | 2 +- .../mock/oauth2/token/OAuth2TokenCallback.kt | 10 ++-- .../mock/oauth2/token/OAuth2TokenProvider.kt | 18 +++---- .../security/mock/oauth2/userinfo/UserInfo.kt | 4 +- .../kotlin/ktor/client/OAuth2Client.kt | 26 +++++----- .../kotlin/ktor/client/OAuth2ClientTest.kt | 6 +-- .../kotlin/ktor/login/OAuth2LoginApp.kt | 14 ++--- .../kotlin/ktor/login/OAuth2LoginAppTest.kt | 12 ++--- .../resourceserver/OAuth2ResourceServerApp.kt | 14 ++--- .../OAuth2ResourceServerAppTest.kt | 12 ++--- .../mock/oauth2/MockOAuth2ServerTest.kt | 4 +- .../security/mock/oauth2/OAuth2ConfigTest.kt | 2 +- .../StandaloneMockOAuth2ServerKtTest.kt | 2 +- .../oauth2/e2e/CorsHeadersIntegrationTest.kt | 12 ++--- .../e2e/InteractiveLoginIntegrationTest.kt | 24 ++++----- .../e2e/JwtBearerGrantIntegrationTest.kt | 20 +++---- .../oauth2/e2e/LoginPageIntegrationTest.kt | 8 +-- .../e2e/MockOAuth2ServerIntegrationTest.kt | 26 +++++----- ...dcAuthorizationCodeGrantIntegrationTest.kt | 20 +++---- .../e2e/PasswordGrantIntegrationTest.kt | 4 +- .../e2e/RefreshTokenGrantIntegrationTest.kt | 18 +++---- .../e2e/TokenExchangeGrantIntegrationTest.kt | 22 ++++---- .../oauth2/e2e/UserInfoIntegrationTest.kt | 12 ++--- .../oauth2/examples/AbstractExampleApp.kt | 8 +-- .../ExampleAppWithClientCredentialsClient.kt | 4 +- ...ampleAppWithClientCredentialsClientTest.kt | 2 +- .../ExampleAppWithOpenIdConnect.kt | 8 +-- .../ExampleAppWithOpenIdConnectTest.kt | 4 +- .../ExampleAppWithSecuredApiTest.kt | 4 +- .../grant/AuthorizationCodeHandlerTest.kt | 14 ++--- .../http/OAuth2HttpRequestHandlerTest.kt | 14 ++--- .../mock/oauth2/http/OAuth2HttpRequestTest.kt | 52 +++++++++---------- .../mock/oauth2/http/OAuth2HttpRouterTest.kt | 12 ++--- .../mock/oauth2/introspect/IntrospectTest.kt | 10 ++-- .../oauth2/login/LoginRequestHandlerTest.kt | 2 +- .../oauth2/server/OAuth2HttpServerTest.kt | 8 +-- .../security/mock/oauth2/testutils/Grant.kt | 4 +- .../security/mock/oauth2/testutils/Http.kt | 32 ++++++------ .../security/mock/oauth2/testutils/Token.kt | 20 +++---- .../mock/oauth2/token/KeyGeneratorTest.kt | 2 +- .../mock/oauth2/token/KeyProviderTest.kt | 2 +- .../oauth2/token/OAuth2TokenCallbackTest.kt | 18 +++---- .../oauth2/token/OAuth2TokenProviderECTest.kt | 20 +++---- .../token/OAuth2TokenProviderRSATest.kt | 16 +++--- .../mock/oauth2/userinfo/UserInfoTest.kt | 6 +-- 75 files changed, 426 insertions(+), 425 deletions(-) diff --git a/build.gradle.kts b/build.gradle.kts index d627a82e..d63b3fa1 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -37,7 +37,7 @@ plugins { } application { - mainClassName = mainClassKt + mainClass.set(mainClassKt) } java { @@ -200,7 +200,7 @@ jib { } fun isNonStable(version: String): Boolean { - val stableKeyword = listOf("RELEASE", "FINAL", "GA").any { version.toUpperCase().contains(it) } + val stableKeyword = listOf("RELEASE", "FINAL", "GA").any { version.uppercase().contains(it) } val regex = "^[0-9,.v-]+(-r)?$".toRegex() val isStable = stableKeyword || regex.matches(version) return isStable.not() @@ -259,6 +259,7 @@ tasks { } withType { + jvmArgs("--add-opens=java.base/java.util=ALL-UNNAMED") useJUnitPlatform() } @@ -273,6 +274,6 @@ tasks { } withType { - gradleVersion = "7.4.2" + gradleVersion = "8.2" } } diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index aa991fce..15de9024 100644 --- a/gradle/wrapper/gradle-wrapper.properties +++ b/gradle/wrapper/gradle-wrapper.properties @@ -1,5 +1,5 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-7.4.2-bin.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-8.2-bin.zip zipStoreBase=GRADLE_USER_HOME zipStorePath=wrapper/dists diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/MockOAuth2Server.kt b/src/main/kotlin/no/nav/security/mock/oauth2/MockOAuth2Server.kt index e5193c6b..b403a023 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/MockOAuth2Server.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/MockOAuth2Server.kt @@ -42,7 +42,7 @@ private val log = KotlinLogging.logger { } @Suppress("unused", "MemberVisibilityCanBePrivate") open class MockOAuth2Server( val config: OAuth2Config = OAuth2Config(), - vararg additionalRoutes: Route + vararg additionalRoutes: Route, ) { constructor(vararg additionalRoutes: Route) : this(config = OAuth2Config(), additionalRoutes = additionalRoutes) constructor(config: OAuth2Config) : this(config = config, additionalRoutes = emptyArray()) @@ -51,7 +51,7 @@ open class MockOAuth2Server( private val defaultRequestHandler: OAuth2HttpRequestHandler = OAuth2HttpRequestHandler(config) private val router: RequestHandler = routes( *additionalRoutes, - defaultRequestHandler.authorizationServer + defaultRequestHandler.authorizationServer, ) /** @@ -221,7 +221,7 @@ open class MockOAuth2Server( val tokenRequest = TokenRequest( uri.toUri(), ClientSecretBasic(ClientID(clientId), Secret("secret")), - AuthorizationCodeGrant(AuthorizationCode("123"), URI.create("http://localhost")) + AuthorizationCodeGrant(AuthorizationCode("123"), URI.create("http://localhost")), ) return config.tokenProvider.accessToken(tokenRequest, issuerUrl, tokenCallback, null) } @@ -237,7 +237,7 @@ open class MockOAuth2Server( subject: String = UUID.randomUUID().toString(), audience: String? = "default", claims: Map = emptyMap(), - expiry: Long = 3600 + expiry: Long = 3600, ): SignedJWT = issueToken( issuerId, "default", @@ -247,8 +247,8 @@ open class MockOAuth2Server( JOSEObjectType.JWT.type, audience?.let { listOf(it) }, claims, - expiry - ) + expiry, + ), ) /** @@ -267,8 +267,8 @@ open class MockOAuth2Server( jwtClaimsSet, DefaultOAuth2TokenCallback( audience = jwtClaimsSet.audience, - expiry = expiry.toMillis() - ) + expiry = expiry.toMillis(), + ), ) } @@ -306,7 +306,7 @@ internal fun Map.toJwtClaimsSet(): JWTClaimsSet = fun withMockOAuth2Server( config: OAuth2Config = OAuth2Config(), - test: MockOAuth2Server.() -> R + test: MockOAuth2Server.() -> R, ): R { val server = MockOAuth2Server(config) server.start() diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/OAuth2Config.kt b/src/main/kotlin/no/nav/security/mock/oauth2/OAuth2Config.kt index 53e53fe2..600391a9 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/OAuth2Config.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/OAuth2Config.kt @@ -28,18 +28,18 @@ data class OAuth2Config @JvmOverloads constructor( @JsonDeserialize(contentAs = RequestMappingTokenCallback::class) val tokenCallbacks: Set = emptySet(), @JsonDeserialize(using = OAuth2HttpServerDeserializer::class) - val httpServer: OAuth2HttpServer = MockWebServerWrapper() + val httpServer: OAuth2HttpServer = MockWebServerWrapper(), ) { class OAuth2TokenProviderDeserializer : JsonDeserializer() { data class ProviderConfig( - val keyProvider: KeyProviderConfig? + val keyProvider: KeyProviderConfig?, ) data class KeyProviderConfig( val initialKeys: String?, - val algorithm: String + val algorithm: String, ) override fun deserialize(p: JsonParser, ctxt: DeserializationContext?): OAuth2TokenProvider { @@ -56,8 +56,8 @@ data class OAuth2Config @JvmOverloads constructor( return OAuth2TokenProvider( KeyProvider( jwks, - config.keyProvider?.algorithm ?: JWSAlgorithm.RS256.name - ) + config.keyProvider?.algorithm ?: JWSAlgorithm.RS256.name, + ), ) } } @@ -65,19 +65,19 @@ data class OAuth2Config @JvmOverloads constructor( class OAuth2HttpServerDeserializer : JsonDeserializer() { enum class ServerType { MockWebServerWrapper, - NettyWrapper + NettyWrapper, } data class ServerConfig( val type: ServerType, - val ssl: SslConfig? = null + val ssl: SslConfig? = null, ) data class SslConfig( val keyPassword: String = "", val keystoreFile: File? = null, val keystoreType: SslKeystore.KeyStoreType = SslKeystore.KeyStoreType.PKCS12, - val keystorePassword: String = "" + val keystorePassword: String = "", ) { fun ssl() = Ssl(sslKeyStore()) diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/StandaloneMockOAuth2Server.kt b/src/main/kotlin/no/nav/security/mock/oauth2/StandaloneMockOAuth2Server.kt index 181ee80c..4e0afc43 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/StandaloneMockOAuth2Server.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/StandaloneMockOAuth2Server.kt @@ -29,7 +29,7 @@ object StandaloneConfig { } else { OAuth2Config( interactiveLogin = true, - httpServer = NettyWrapper() + httpServer = NettyWrapper(), ) } } @@ -49,7 +49,7 @@ fun main() { oauth2Config(), route("/isalive") { OAuth2HttpResponse(status = 200, body = "alive and well") - } + }, ).apply { start(hostname(), port()) } diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/debugger/Client.kt b/src/main/kotlin/no/nav/security/mock/oauth2/debugger/Client.kt index 70a0b359..58bbab08 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/debugger/Client.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/debugger/Client.kt @@ -2,6 +2,7 @@ package no.nav.security.mock.oauth2.debugger import com.nimbusds.oauth2.sdk.OAuth2Error import no.nav.security.mock.oauth2.OAuth2Exception +import no.nav.security.mock.oauth2.http.Ssl import okhttp3.Credentials import okhttp3.Headers import okhttp3.HttpUrl @@ -15,12 +16,11 @@ import java.nio.charset.StandardCharsets import javax.net.ssl.SSLContext import javax.net.ssl.TrustManagerFactory import javax.net.ssl.X509TrustManager -import no.nav.security.mock.oauth2.http.Ssl internal class TokenRequest( val url: HttpUrl, clientAuthentication: ClientAuthentication, - parameters: Map + parameters: Map, ) { val headers = when (clientAuthentication.clientAuthMethod) { ClientAuthentication.Method.CLIENT_SECRET_BASIC -> Headers.headersOf("Authorization", clientAuthentication.basic()) @@ -49,7 +49,7 @@ internal class TokenRequest( internal data class ClientAuthentication( val clientId: String, val clientSecret: String, - val clientAuthMethod: Method + val clientAuthMethod: Method, ) { fun form(): String = "client_id=${clientId.urlEncode()}&client_secret=${clientSecret.urlEncode()}" fun basic(): String = Credentials.basic(clientId, clientSecret, StandardCharsets.UTF_8) @@ -59,7 +59,7 @@ internal data class ClientAuthentication( ClientAuthentication( map.require("client_id"), map.require("client_secret"), - Method.valueOf(map.require("client_auth_method")) + Method.valueOf(map.require("client_auth_method")), ) private fun Map.require(key: String): String = @@ -68,7 +68,7 @@ internal data class ClientAuthentication( enum class Method { CLIENT_SECRET_POST, - CLIENT_SECRET_BASIC + CLIENT_SECRET_BASIC, } } @@ -80,7 +80,7 @@ internal fun OkHttpClient.post(tokenRequest: TokenRequest): String = .headers(tokenRequest.headers) .url(tokenRequest.url) .post(tokenRequest.body.toRequestBody("application/x-www-form-urlencoded".toMediaType())) - .build() + .build(), ).execute().body?.string() ?: throw RuntimeException("could not get response body from url=${tokenRequest.url}") fun OkHttpClient.withSsl(ssl: Ssl, followRedirects: Boolean = false): OkHttpClient = diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/debugger/DebuggerRequestHandler.kt b/src/main/kotlin/no/nav/security/mock/oauth2/debugger/DebuggerRequestHandler.kt index 5760300f..a3bfc0b0 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/debugger/DebuggerRequestHandler.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/debugger/DebuggerRequestHandler.kt @@ -32,14 +32,14 @@ class DebuggerRequestHandler( exceptionHandler(handle(sessionManager)) debuggerForm(sessionManager) debuggerCallback(sessionManager, ssl) - } + }, ) : Route by route private fun handle(sessionManager: SessionManager): ExceptionHandler = { request, error -> OAuth2HttpResponse( status = 500, headers = Headers.headersOf("Content-Type", "text/html", "Set-Cookie", sessionManager.session(request).asCookie()), - body = templateMapper.debuggerErrorHtml(request.url.toDebuggerUrl(), error.stackTraceToString()) + body = templateMapper.debuggerErrorHtml(request.url.toDebuggerUrl(), error.stackTraceToString()), ).also { log.error("received exception when handling url=${request.url}", error) } @@ -55,7 +55,7 @@ private fun Route.Builder.debuggerForm(sessionManager: SessionManager) = apply { "&response_mode=query" + "&scope=openid+somescope" + "&state=1234" + - "&nonce=5678" + "&nonce=5678", ).build() html(templateMapper.debuggerFormHtml(url, "CLIENT_SECRET_BASIC")) } @@ -90,8 +90,8 @@ private fun Route.Builder.debuggerCallback(sessionManager: SessionManager, ssl: "grant_type" to "authorization_code", "code" to code, "scope" to session["scope"].urlEncode(), - "redirect_uri" to session["redirect_uri"].urlEncode() - ) + "redirect_uri" to session["redirect_uri"].urlEncode(), + ), ) val response = if (ssl != null) { client.withSsl(ssl).post(request) diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/debugger/SessionManager.kt b/src/main/kotlin/no/nav/security/mock/oauth2/debugger/SessionManager.kt index 713f23f8..ca1a7e02 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/debugger/SessionManager.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/debugger/SessionManager.kt @@ -25,7 +25,7 @@ class SessionManager { class Session( private val encryptionKey: SecretKey, - val request: OAuth2HttpRequest + val request: OAuth2HttpRequest, ) { val parameters: MutableMap = getSessionCookie() ?.let { objectMapper.readValue(it) } ?: mutableMapOf() @@ -41,7 +41,7 @@ class SessionManager { private fun String.encrypt(key: SecretKey): String = JWEObject( JWEHeader(JWEAlgorithm.DIR, EncryptionMethod.A128GCM), - Payload(this) + Payload(this), ).also { it.encrypt(DirectEncrypter(key)) }.serialize() @@ -59,7 +59,7 @@ class SessionManager { onFailure = { error -> log.error("received exception when decrypting cookie", error) null - } + }, ) companion object { const val DEBUGGER_SESSION_COOKIE = "debugger-session" diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/extensions/HttpUrlExtensions.kt b/src/main/kotlin/no/nav/security/mock/oauth2/extensions/HttpUrlExtensions.kt index 024eb137..ff5f295b 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/extensions/HttpUrlExtensions.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/extensions/HttpUrlExtensions.kt @@ -36,7 +36,7 @@ object OAuth2Endpoints { USER_INFO, INTROSPECT, DEBUGGER, - DEBUGGER_CALLBACK + DEBUGGER_CALLBACK, ) } diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/extensions/NimbusExtensions.kt b/src/main/kotlin/no/nav/security/mock/oauth2/extensions/NimbusExtensions.kt index a9780b68..809a2174 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/extensions/NimbusExtensions.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/extensions/NimbusExtensions.kt @@ -87,12 +87,12 @@ fun SignedJWT.verifySignatureAndIssuer(issuer: Issuer, jwkSet: JWKSet, jwsAlgori jwtProcessor.jwsTypeVerifier = DefaultJOSEObjectTypeVerifier(JOSEObjectType("JWT")) val keySelector: JWSKeySelector = JWSVerificationKeySelector( jwsAlgorithm, - ImmutableJWKSet(jwkSet) + ImmutableJWKSet(jwkSet), ) jwtProcessor.jwsKeySelector = keySelector jwtProcessor.jwtClaimsSetVerifier = DefaultJWTClaimsVerifier( JWTClaimsSet.Builder().issuer(issuer.toString()).build(), - HashSet(listOf("sub", "iat", "exp")) + HashSet(listOf("sub", "iat", "exp")), ) return jwtProcessor.process(this, null) } diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/grant/AuthorizationCodeHandler.kt b/src/main/kotlin/no/nav/security/mock/oauth2/grant/AuthorizationCodeHandler.kt index 360fdf2e..6e29caef 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/grant/AuthorizationCodeHandler.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/grant/AuthorizationCodeHandler.kt @@ -28,7 +28,7 @@ private val jsonMapper: ObjectMapper = jacksonObjectMapper() internal class AuthorizationCodeHandler( private val tokenProvider: OAuth2TokenProvider, - private val refreshTokenManager: RefreshTokenManager + private val refreshTokenManager: RefreshTokenManager, ) : GrantHandler { private val codeToAuthRequestCache: MutableMap = HashMap() @@ -51,12 +51,12 @@ internal class AuthorizationCodeHandler( null, authenticationRequest.state, null, - authenticationRequest.responseMode + authenticationRequest.responseMode, ) } else -> throw OAuth2Exception( OAuth2Error.INVALID_GRANT, - "hybrid og implicit flow not supported (yet)." + "hybrid og implicit flow not supported (yet).", ) } } @@ -64,7 +64,7 @@ internal class AuthorizationCodeHandler( override fun tokenResponse( request: OAuth2HttpRequest, issuerUrl: HttpUrl, - oAuth2TokenCallback: OAuth2TokenCallback + oAuth2TokenCallback: OAuth2TokenCallback, ): OAuth2TokenResponse { val tokenRequest = request.asNimbusTokenRequest() val code = tokenRequest.authorizationCode() @@ -84,7 +84,7 @@ internal class AuthorizationCodeHandler( accessToken = accessToken.serialize(), refreshToken = refreshToken, expiresIn = idToken.expiresIn(), - scope = scope + scope = scope, ) } diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/grant/ClientCredentialsGrantHandler.kt b/src/main/kotlin/no/nav/security/mock/oauth2/grant/ClientCredentialsGrantHandler.kt index 9f9c3300..c947903b 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/grant/ClientCredentialsGrantHandler.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/grant/ClientCredentialsGrantHandler.kt @@ -8,25 +8,25 @@ import no.nav.security.mock.oauth2.token.OAuth2TokenProvider import okhttp3.HttpUrl internal class ClientCredentialsGrantHandler( - private val tokenProvider: OAuth2TokenProvider + private val tokenProvider: OAuth2TokenProvider, ) : GrantHandler { override fun tokenResponse( request: OAuth2HttpRequest, issuerUrl: HttpUrl, - oAuth2TokenCallback: OAuth2TokenCallback + oAuth2TokenCallback: OAuth2TokenCallback, ): OAuth2TokenResponse { val tokenRequest = request.asNimbusTokenRequest() val accessToken = tokenProvider.accessToken( tokenRequest, issuerUrl, - oAuth2TokenCallback + oAuth2TokenCallback, ) return OAuth2TokenResponse( tokenType = "Bearer", accessToken = accessToken.serialize(), expiresIn = accessToken.expiresIn(), - scope = tokenRequest.scope?.toString() + scope = tokenRequest.scope?.toString(), ) } } diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/grant/GrantHandler.kt b/src/main/kotlin/no/nav/security/mock/oauth2/grant/GrantHandler.kt index 695e6110..a0c9115b 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/grant/GrantHandler.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/grant/GrantHandler.kt @@ -9,6 +9,6 @@ interface GrantHandler { fun tokenResponse( request: OAuth2HttpRequest, issuerUrl: HttpUrl, - oAuth2TokenCallback: OAuth2TokenCallback + oAuth2TokenCallback: OAuth2TokenCallback, ): OAuth2TokenResponse } diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/grant/JwtBearerGrantHandler.kt b/src/main/kotlin/no/nav/security/mock/oauth2/grant/JwtBearerGrantHandler.kt index ec1fe98d..fa0b8558 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/grant/JwtBearerGrantHandler.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/grant/JwtBearerGrantHandler.kt @@ -18,7 +18,7 @@ internal class JwtBearerGrantHandler(private val tokenProvider: OAuth2TokenProvi override fun tokenResponse( request: OAuth2HttpRequest, issuerUrl: HttpUrl, - oAuth2TokenCallback: OAuth2TokenCallback + oAuth2TokenCallback: OAuth2TokenCallback, ): OAuth2TokenResponse { val tokenRequest = request.asNimbusTokenRequest() val receivedClaimsSet = tokenRequest.assertion() @@ -26,13 +26,13 @@ internal class JwtBearerGrantHandler(private val tokenProvider: OAuth2TokenProvi tokenRequest, issuerUrl, receivedClaimsSet, - oAuth2TokenCallback + oAuth2TokenCallback, ) return OAuth2TokenResponse( tokenType = "Bearer", accessToken = accessToken.serialize(), expiresIn = accessToken.expiresIn(), - scope = tokenRequest.responseScope() + scope = tokenRequest.responseScope(), ) } diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/grant/PasswordGrantHandler.kt b/src/main/kotlin/no/nav/security/mock/oauth2/grant/PasswordGrantHandler.kt index 0d08d5a6..87d50bee 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/grant/PasswordGrantHandler.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/grant/PasswordGrantHandler.kt @@ -11,13 +11,13 @@ import no.nav.security.mock.oauth2.token.OAuth2TokenProvider import okhttp3.HttpUrl internal class PasswordGrantHandler( - private val tokenProvider: OAuth2TokenProvider + private val tokenProvider: OAuth2TokenProvider, ) : GrantHandler { override fun tokenResponse( request: OAuth2HttpRequest, issuerUrl: HttpUrl, - oAuth2TokenCallback: OAuth2TokenCallback + oAuth2TokenCallback: OAuth2TokenCallback, ): OAuth2TokenResponse { val tokenRequest = request.asNimbusTokenRequest() val scope: String? = tokenRequest.scope?.toString() @@ -28,12 +28,12 @@ internal class PasswordGrantHandler( tokenType = "Bearer", accessToken = accessToken.serialize(), expiresIn = accessToken.expiresIn(), - scope = scope + scope = scope, ) } private class PasswordGrantTokenCallback( - private val tokenCallback: OAuth2TokenCallback + private val tokenCallback: OAuth2TokenCallback, ) : OAuth2TokenCallback by tokenCallback { override fun subject(tokenRequest: TokenRequest) = diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/grant/RefreshTokenGrantHandler.kt b/src/main/kotlin/no/nav/security/mock/oauth2/grant/RefreshTokenGrantHandler.kt index 995b71b0..df333d33 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/grant/RefreshTokenGrantHandler.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/grant/RefreshTokenGrantHandler.kt @@ -17,13 +17,13 @@ private val log = KotlinLogging.logger {} internal class RefreshTokenGrantHandler( private val tokenProvider: OAuth2TokenProvider, - private val refreshTokenManager: RefreshTokenManager + private val refreshTokenManager: RefreshTokenManager, ) : GrantHandler { override fun tokenResponse( request: OAuth2HttpRequest, issuerUrl: HttpUrl, - oAuth2TokenCallback: OAuth2TokenCallback + oAuth2TokenCallback: OAuth2TokenCallback, ): OAuth2TokenResponse { val tokenRequest = request.asNimbusTokenRequest() val refreshToken = tokenRequest.refreshTokenGrant().refreshToken.value @@ -39,7 +39,7 @@ internal class RefreshTokenGrantHandler( accessToken = accessToken.serialize(), refreshToken = refreshToken, expiresIn = idToken.expiresIn(), - scope = scope + scope = scope, ) } diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/grant/RefreshTokenManager.kt b/src/main/kotlin/no/nav/security/mock/oauth2/grant/RefreshTokenManager.kt index cbe48723..c02b750b 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/grant/RefreshTokenManager.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/grant/RefreshTokenManager.kt @@ -8,7 +8,7 @@ import java.util.UUID typealias RefreshToken = String internal data class RefreshTokenManager( - private val cache: MutableMap = HashMap() + private val cache: MutableMap = HashMap(), ) { operator fun get(refreshToken: RefreshToken) = cache[refreshToken] @@ -25,8 +25,8 @@ internal data class RefreshTokenManager( JWTClaimsSet.parse( mapOf( "jti" to jti, - "nonce" to nonce - ) - ) + "nonce" to nonce, + ), + ), ).serialize() } diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/grant/TokenExchangeGrant.kt b/src/main/kotlin/no/nav/security/mock/oauth2/grant/TokenExchangeGrant.kt index cfabd772..81b553d4 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/grant/TokenExchangeGrant.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/grant/TokenExchangeGrant.kt @@ -10,7 +10,7 @@ val TOKEN_EXCHANGE = GrantType("urn:ietf:params:oauth:grant-type:token-exchange" class TokenExchangeGrant( val subjectTokenType: String, val subjectToken: String, - val audience: MutableList + val audience: MutableList, ) : AuthorizationGrant(TOKEN_EXCHANGE) { override fun toParameters(): MutableMap> = @@ -18,7 +18,7 @@ class TokenExchangeGrant( "grant_type" to mutableListOf(TOKEN_EXCHANGE.value), "subject_token_type" to mutableListOf(subjectTokenType), "subject_token" to mutableListOf(subjectToken), - "audience" to audience + "audience" to audience, ) companion object { @@ -28,7 +28,7 @@ class TokenExchangeGrant( parameters.require("subject_token"), parameters.require("audience") .split(" ") - .toMutableList() + .toMutableList(), ) } } diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/grant/TokenExchangeGrantHandler.kt b/src/main/kotlin/no/nav/security/mock/oauth2/grant/TokenExchangeGrantHandler.kt index 2dff5791..65db1890 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/grant/TokenExchangeGrantHandler.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/grant/TokenExchangeGrantHandler.kt @@ -15,7 +15,7 @@ internal class TokenExchangeGrantHandler(private val tokenProvider: OAuth2TokenP override fun tokenResponse( request: OAuth2HttpRequest, issuerUrl: HttpUrl, - oAuth2TokenCallback: OAuth2TokenCallback + oAuth2TokenCallback: OAuth2TokenCallback, ): OAuth2TokenResponse { val tokenRequest = request.asTokenExchangeRequest() val receivedClaimsSet = tokenRequest.subjectToken().jwtClaimsSet @@ -23,13 +23,13 @@ internal class TokenExchangeGrantHandler(private val tokenProvider: OAuth2TokenP tokenRequest, issuerUrl, receivedClaimsSet, - oAuth2TokenCallback + oAuth2TokenCallback, ) return OAuth2TokenResponse( tokenType = "Bearer", issuedTokenType = "urn:ietf:params:oauth:token-type:access_token", accessToken = accessToken.serialize(), - expiresIn = accessToken.expiresIn() + expiresIn = accessToken.expiresIn(), ) } } diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/http/CorsInterceptor.kt b/src/main/kotlin/no/nav/security/mock/oauth2/http/CorsInterceptor.kt index 2217e0c0..65ad0e6e 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/http/CorsInterceptor.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/http/CorsInterceptor.kt @@ -5,7 +5,7 @@ import mu.KotlinLogging private val log = KotlinLogging.logger {} class CorsInterceptor( - private val allowedMethods: List = listOf("POST", "GET", "OPTIONS") + private val allowedMethods: List = listOf("POST", "GET", "OPTIONS"), ) : ResponseInterceptor { companion object HeaderNames { diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequest.kt b/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequest.kt index dab551a2..49a61185 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequest.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequest.kt @@ -23,7 +23,7 @@ data class OAuth2HttpRequest( val headers: Headers, val method: String, val originalUrl: HttpUrl, - val body: String? = null + val body: String? = null, ) { val url: HttpUrl get() = proxyAwareUrl() val formParameters: Parameters = Parameters(body) @@ -41,7 +41,7 @@ data class OAuth2HttpRequest( tokenExchangeGrant, null, emptyList(), - formParameters.map.mapValues { mutableListOf(it.value) } + formParameters.map.mapValues { mutableListOf(it.value) }, ) } @@ -56,7 +56,7 @@ data class OAuth2HttpRequest( fun asNimbusTokenRequest(): TokenRequest = TokenRequest.parse( - this.asNimbusHTTPRequest() + this.asNimbusHTTPRequest(), ) fun asAuthenticationRequest(): AuthenticationRequest = AuthenticationRequest.parse(this.url.toUri()) @@ -75,7 +75,7 @@ data class OAuth2HttpRequest( endSessionEndpoint = this.proxyAwareUrl().toEndSessionEndpointUrl().toString(), introspectionEndpoint = this.proxyAwareUrl().toIntrospectUrl().toString(), jwksUri = this.proxyAwareUrl().toJwksUrl().toString(), - userInfoEndpoint = this.proxyAwareUrl().toUserInfoUrl().toString() + userInfoEndpoint = this.proxyAwareUrl().toUserInfoUrl().toString(), ) internal fun proxyAwareUrl(): HttpUrl = HttpUrl.Builder() diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequestHandler.kt b/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequestHandler.kt index c5a8ab98..4ee7b0bf 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequestHandler.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequestHandler.kt @@ -60,7 +60,7 @@ class OAuth2HttpRequestHandler(private val config: OAuth2Config) { JWT_BEARER to JwtBearerGrantHandler(config.tokenProvider), TOKEN_EXCHANGE to TokenExchangeGrantHandler(config.tokenProvider), REFRESH_TOKEN to RefreshTokenGrantHandler(config.tokenProvider, refreshTokenManager), - PASSWORD to PasswordGrantHandler(config.tokenProvider) + PASSWORD to PasswordGrantHandler(config.tokenProvider), ) private val exceptionHandler: ExceptionHandler = { request, error -> diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpResponse.kt b/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpResponse.kt index f57d078f..c9836498 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpResponse.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpResponse.kt @@ -19,7 +19,7 @@ val templateMapper: TemplateMapper = TemplateMapper.create {} data class OAuth2HttpResponse( val headers: Headers = Headers.headersOf(), val status: Int, - val body: String? = null + val body: String? = null, ) data class WellKnown( @@ -41,7 +41,7 @@ data class WellKnown( @JsonProperty("subject_types_supported") val subjectTypesSupported: List = listOf("public"), @JsonProperty("id_token_signing_alg_values_supported") - val idTokenSigningAlgValuesSupported: List = (KeyGenerator.ecAlgorithmFamily + KeyGenerator.rsaAlgorithmFamily).map { it.name }.toList() + val idTokenSigningAlgValuesSupported: List = (KeyGenerator.ecAlgorithmFamily + KeyGenerator.rsaAlgorithmFamily).map { it.name }.toList(), ) @JsonInclude(JsonInclude.Include.NON_NULL) @@ -59,13 +59,13 @@ data class OAuth2TokenResponse( @JsonProperty("expires_in") val expiresIn: Int = 0, @JsonProperty("scope") - val scope: String? = null + val scope: String? = null, ) fun json(anyObject: Any): OAuth2HttpResponse = OAuth2HttpResponse( headers = Headers.headersOf( HttpHeaderNames.CONTENT_TYPE.toString(), - "application/json;charset=UTF-8" + "application/json;charset=UTF-8", ), status = 200, body = when (anyObject) { @@ -74,21 +74,21 @@ fun json(anyObject: Any): OAuth2HttpResponse = OAuth2HttpResponse( objectMapper .enable(SerializationFeature.INDENT_OUTPUT) .writeValueAsString(anyObject) - } + }, ) fun html(content: String): OAuth2HttpResponse = OAuth2HttpResponse( headers = Headers.headersOf( HttpHeaderNames.CONTENT_TYPE.toString(), - "text/html;charset=UTF-8" + "text/html;charset=UTF-8", ), status = 200, - body = content + body = content, ) fun redirect(location: String, headers: Headers = Headers.headersOf()): OAuth2HttpResponse = OAuth2HttpResponse( headers = Headers.headersOf(HttpHeaderNames.LOCATION.toString(), location).newBuilder().addAll(headers).build(), - status = 302 + status = 302, ) fun notFound(body: String? = null): OAuth2HttpResponse = OAuth2HttpResponse(status = 404, body = body) @@ -102,13 +102,13 @@ fun authenticationSuccess(authenticationSuccessResponse: AuthenticationSuccessRe body = templateMapper.authorizationCodeResponseHtml( authenticationSuccessResponse.redirectionURI.toString(), authenticationSuccessResponse.authorizationCode.value, - authenticationSuccessResponse.state.value - ) + authenticationSuccessResponse.state.value, + ), ) } else -> OAuth2HttpResponse( headers = Headers.headersOf(HttpHeaderNames.LOCATION.toString(), authenticationSuccessResponse.toURI().toString()), - status = 302 + status = 302, ) } } @@ -118,12 +118,12 @@ fun oauth2Error(error: ErrorObject): OAuth2HttpResponse { return OAuth2HttpResponse( headers = Headers.headersOf( HttpHeaderNames.CONTENT_TYPE.toString(), - "application/json;charset=UTF-8" + "application/json;charset=UTF-8", ), status = responseCode, body = objectMapper .enable(SerializationFeature.INDENT_OUTPUT) .writeValueAsString(error.toJSONObject()) - .lowercase() + .lowercase(), ) } diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRouter.kt b/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRouter.kt index 81822f32..41649f8b 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRouter.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRouter.kt @@ -86,7 +86,7 @@ internal interface PathRoute : Route { internal class PathRouter( private val routes: MutableList, private val interceptors: MutableList, - private val exceptionHandler: ExceptionHandler + private val exceptionHandler: ExceptionHandler, ) : PathRoute { override fun matchPath(request: OAuth2HttpRequest): Boolean = routes.any { it.matchPath(request) } diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpServer.kt b/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpServer.kt index 2a6ebdbe..58fd8bf5 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpServer.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpServer.kt @@ -26,12 +26,6 @@ import io.netty.handler.ssl.SslHandler import io.netty.handler.stream.ChunkedStream import io.netty.handler.stream.ChunkedWriteHandler import io.netty.util.CharsetUtil -import java.net.InetAddress -import java.net.InetSocketAddress -import java.util.concurrent.BlockingQueue -import java.util.concurrent.LinkedBlockingQueue -import javax.net.ssl.SSLHandshakeException -import kotlin.properties.Delegates import mu.KotlinLogging import no.nav.security.mock.oauth2.extensions.asOAuth2HttpRequest import okhttp3.Headers @@ -40,6 +34,12 @@ import okhttp3.mockwebserver.Dispatcher import okhttp3.mockwebserver.MockResponse import okhttp3.mockwebserver.MockWebServer import okhttp3.mockwebserver.RecordedRequest +import java.net.InetAddress +import java.net.InetSocketAddress +import java.util.concurrent.BlockingQueue +import java.util.concurrent.LinkedBlockingQueue +import javax.net.ssl.SSLHandshakeException +import kotlin.properties.Delegates private val log = KotlinLogging.logger { } @@ -60,7 +60,7 @@ interface OAuth2HttpServer : AutoCloseable { } class MockWebServerWrapper@JvmOverloads constructor( - val ssl: Ssl? = null + val ssl: Ssl? = null, ) : OAuth2HttpServer { val mockWebServer: MockWebServer = MockWebServer() @@ -84,7 +84,7 @@ class MockWebServerWrapper@JvmOverloads constructor( internal class MockWebServerDispatcher( private val requestHandler: RequestHandler, - private val responseQueue: BlockingQueue = LinkedBlockingQueue() + private val responseQueue: BlockingQueue = LinkedBlockingQueue(), ) : Dispatcher() { override fun dispatch(request: RecordedRequest): MockResponse = @@ -103,7 +103,7 @@ class MockWebServerWrapper@JvmOverloads constructor( } class NettyWrapper @JvmOverloads constructor( - val ssl: Ssl? = null + val ssl: Ssl? = null, ) : OAuth2HttpServer { private val masterGroup = NioEventLoopGroup() private val workerGroup = NioEventLoopGroup() @@ -128,7 +128,7 @@ class NettyWrapper @JvmOverloads constructor( ch.pipeline().addLast("streamer", ChunkedWriteHandler()) ch.pipeline().addLast("routes", RouterChannelHandler(requestHandler)) } - } + }, ) .option(ChannelOption.SO_BACKLOG, 1000) .childOption(ChannelOption.SO_KEEPALIVE, true) @@ -196,7 +196,7 @@ class NettyWrapper @JvmOverloads constructor( private fun OAuth2HttpResponse.asNettyResponse(): Pair = DefaultHttpResponse( HttpVersion.HTTP_1_1, - HttpResponseStatus(this.status, "") + HttpResponseStatus(this.status, ""), ).apply { this@asNettyResponse.headers.forEach { (key, values) -> headers().set(key, values) } } to ChunkedStream(this.body?.byteInputStream() ?: "".byteInputStream()) @@ -206,7 +206,7 @@ class NettyWrapper @JvmOverloads constructor( this.headers().toOkHttpHeaders(), this.method().name(), this.requestUrl(scheme, address, port), - content().toString(CharsetUtil.UTF_8) + content().toString(CharsetUtil.UTF_8), ) private fun FullHttpRequest.requestUrl(scheme: String, address: InetSocketAddress, port: Int): HttpUrl = diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/http/Ssl.kt b/src/main/kotlin/no/nav/security/mock/oauth2/http/Ssl.kt index f87b9262..28d649bf 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/http/Ssl.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/http/Ssl.kt @@ -1,18 +1,5 @@ package no.nav.security.mock.oauth2.http -import java.io.File -import java.math.BigInteger -import java.security.KeyPair -import java.security.KeyPairGenerator -import java.security.KeyStore -import java.security.PublicKey -import java.security.cert.X509Certificate -import java.time.Duration -import java.time.Instant -import java.util.Date -import javax.net.ssl.KeyManagerFactory -import javax.net.ssl.SSLContext -import javax.net.ssl.SSLEngine import org.bouncycastle.asn1.oiw.OIWObjectIdentifiers import org.bouncycastle.asn1.x500.X500Name import org.bouncycastle.asn1.x509.AlgorithmIdentifier @@ -34,9 +21,22 @@ import org.bouncycastle.jce.provider.BouncyCastleProvider import org.bouncycastle.operator.ContentSigner import org.bouncycastle.operator.bc.BcDigestCalculatorProvider import org.bouncycastle.operator.jcajce.JcaContentSignerBuilder +import java.io.File +import java.math.BigInteger +import java.security.KeyPair +import java.security.KeyPairGenerator +import java.security.KeyStore +import java.security.PublicKey +import java.security.cert.X509Certificate +import java.time.Duration +import java.time.Instant +import java.util.Date +import javax.net.ssl.KeyManagerFactory +import javax.net.ssl.SSLContext +import javax.net.ssl.SSLEngine class Ssl @JvmOverloads constructor( - val sslKeystore: SslKeystore = SslKeystore() + val sslKeystore: SslKeystore = SslKeystore(), ) { fun sslEngine(): SSLEngine = sslContext().createSSLEngine().apply { useClientMode = false @@ -55,19 +55,19 @@ class Ssl @JvmOverloads constructor( class SslKeystore @JvmOverloads constructor( val keyPassword: String = "", - val keyStore: KeyStore = generate("localhost", keyPassword) + val keyStore: KeyStore = generate("localhost", keyPassword), ) { @JvmOverloads constructor( keyPassword: String, keystoreFile: File, keystoreType: KeyStoreType = KeyStoreType.PKCS12, - keystorePassword: String = "" + keystorePassword: String = "", ) : this(keyPassword, keyStore(keystoreFile, keystoreType, keystorePassword)) enum class KeyStoreType { PKCS12, - JKS + JKS, } companion object { @@ -87,7 +87,7 @@ class SslKeystore @JvmOverloads constructor( private fun keyStore( keystoreFile: File, keystoreType: KeyStoreType = KeyStoreType.PKCS12, - keystorePassword: String = "" + keystorePassword: String = "", ) = KeyStore.getInstance(keystoreType.name).apply { keystoreFile.inputStream().use { load(it, keystorePassword.toCharArray()) @@ -104,14 +104,14 @@ class SslKeystore @JvmOverloads constructor( Date.from(now), Date.from(now.plus(expiry)), x500Name, - this.public + this.public, ).addExtensions(cn, this.public).build(contentSigner) return JcaX509CertificateConverter().setProvider(BouncyCastleProvider()).getCertificate(certificateHolder) } private fun X509v3CertificateBuilder.addExtensions(cn: String, publicKey: PublicKey) = apply { val san: MutableList = mutableListOf( - GeneralName(GeneralName.dNSName, cn) + GeneralName(GeneralName.dNSName, cn), ) if (cn == "localhost") { diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/introspect/Introspect.kt b/src/main/kotlin/no/nav/security/mock/oauth2/introspect/Introspect.kt index d509d171..49b79a75 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/introspect/Introspect.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/introspect/Introspect.kt @@ -44,8 +44,8 @@ internal fun Route.Builder.introspect(tokenProvider: OAuth2TokenProvider) = claims["sub"].toString(), claims["aud"].toString(), claims["iss"].toString(), - claims["jti"].toString() - ) + claims["jti"].toString(), + ), ) } ?: json(IntrospectResponse(false)) } @@ -102,5 +102,5 @@ data class IntrospectResponse( @JsonProperty("iss") val iss: String? = null, @JsonProperty("jti") - val jti: String? = null + val jti: String? = null, ) diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/login/LoginRequestHandler.kt b/src/main/kotlin/no/nav/security/mock/oauth2/login/LoginRequestHandler.kt index 5aa18652..ff7eb5c3 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/login/LoginRequestHandler.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/login/LoginRequestHandler.kt @@ -30,5 +30,5 @@ class LoginRequestHandler(private val templateMapper: TemplateMapper, private va data class Login( val username: String, - val claims: String? = null + val claims: String? = null, ) diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/templates/TemplateMapper.kt b/src/main/kotlin/no/nav/security/mock/oauth2/templates/TemplateMapper.kt index e7a7a925..748f7083 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/templates/TemplateMapper.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/templates/TemplateMapper.kt @@ -9,11 +9,11 @@ import java.io.StringWriter data class HtmlContent( val template: String, - val model: Any? + val model: Any?, ) class TemplateMapper( - private val config: Configuration + private val config: Configuration, ) { fun loginHtml(oAuth2HttpRequest: OAuth2HttpRequest): String = @@ -22,9 +22,9 @@ class TemplateMapper( "login.ftl", mapOf( "request_url" to oAuth2HttpRequest.url.newBuilder().query(null).build().toString(), - "query" to OAuth2HttpRequest.Parameters(oAuth2HttpRequest.url.query).map - ) - ) + "query" to OAuth2HttpRequest.Parameters(oAuth2HttpRequest.url.query).map, + ), + ), ) fun debuggerCallbackHtml(tokenRequest: String, tokenResponse: String): String { @@ -33,9 +33,9 @@ class TemplateMapper( "debugger_callback.ftl", mapOf( "token_request" to tokenRequest, - "token_response" to tokenResponse - ) - ) + "token_response" to tokenResponse, + ), + ), ) } @@ -45,9 +45,9 @@ class TemplateMapper( "error.ftl", mapOf( "debugger_url" to debuggerUrl, - "stacktrace" to stacktrace - ) - ) + "stacktrace" to stacktrace, + ), + ), ) fun debuggerFormHtml(url: HttpUrl, clientAuthMethod: String): String { @@ -59,9 +59,9 @@ class TemplateMapper( "url" to urlWithoutQuery, "token_url" to url.toTokenEndpointUrl(), "query" to OAuth2HttpRequest.Parameters(url.query).map, - "client_auth_method" to clientAuthMethod - ) - ) + "client_auth_method" to clientAuthMethod, + ), + ), ) } @@ -72,9 +72,9 @@ class TemplateMapper( mapOf( "redirect_uri" to redirectUri, "code" to code, - "state" to state - ) - ) + "state" to state, + ), + ), ) private fun asString(htmlContent: HtmlContent): String = diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/token/KeyGenerator.kt b/src/main/kotlin/no/nav/security/mock/oauth2/token/KeyGenerator.kt index 053fc34e..2a9af24d 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/token/KeyGenerator.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/token/KeyGenerator.kt @@ -17,7 +17,7 @@ import java.security.interfaces.RSAPublicKey data class KeyGenerator( val algorithm: JWSAlgorithm = JWSAlgorithm.RS256, - var keyGenerator: KeyPairGenerator = generate(algorithm.name) + var keyGenerator: KeyPairGenerator = generate(algorithm.name), ) { fun generateKey(keyId: String): JWK { if (keyGenerator.algorithm != KeyType.RSA.value) { @@ -39,7 +39,7 @@ data class KeyGenerator( private fun toCurve(algorithm: JWSAlgorithm): Curve { return requireNotNull( - Curve.forJWSAlgorithm(algorithm).single() + Curve.forJWSAlgorithm(algorithm).single(), ) { throw OAuth2Exception("Unsupported: $algorithm") } @@ -67,7 +67,7 @@ data class KeyGenerator( private val supportedAlgorithms = listOf( Algorithm(rsaAlgorithmFamily, KeyType.RSA), - Algorithm(ecAlgorithmFamily, KeyType.EC) + Algorithm(ecAlgorithmFamily, KeyType.EC), ) fun isSupported(algorithm: JWSAlgorithm) = supportedAlgorithms.flatMap { it.family }.contains(algorithm) @@ -84,7 +84,7 @@ data class KeyGenerator( } else { this.initialize(RSAKeyGenerator.MIN_KEY_SIZE_BITS) } - } + }, ).keyGenerator } else { null @@ -94,7 +94,7 @@ data class KeyGenerator( data class Algorithm( val family: List, - val keyType: KeyType + val keyType: KeyType, ) } } diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/token/KeyProvider.kt b/src/main/kotlin/no/nav/security/mock/oauth2/token/KeyProvider.kt index 44a76542..35ebc254 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/token/KeyProvider.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/token/KeyProvider.kt @@ -12,7 +12,7 @@ import java.util.concurrent.LinkedBlockingDeque open class KeyProvider @JvmOverloads constructor( private val initialKeys: List = keysFromFile(INITIAL_KEYS_FILE), - private val algorithm: String = JWSAlgorithm.RS256.name + private val algorithm: String = JWSAlgorithm.RS256.name, ) { private val signingKeys: ConcurrentHashMap = ConcurrentHashMap() diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenCallback.kt b/src/main/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenCallback.kt index 3b06620a..e0a383fa 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenCallback.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenCallback.kt @@ -27,7 +27,7 @@ open class DefaultOAuth2TokenCallback @JvmOverloads constructor( // needs to be nullable in order to know if a list has explicitly been set, empty list should be a allowable value private val audience: List? = null, private val claims: Map = emptyMap(), - private val expiry: Long = 3600 + private val expiry: Long = 3600, ) : OAuth2TokenCallback { override fun issuerId(): String = issuerId @@ -58,8 +58,8 @@ open class DefaultOAuth2TokenCallback @JvmOverloads constructor( putAll( mapOf( "azp" to tokenRequest.clientIdAsString(), - "tid" to issuerId - ) + "tid" to issuerId, + ), ) } @@ -69,7 +69,7 @@ open class DefaultOAuth2TokenCallback @JvmOverloads constructor( data class RequestMappingTokenCallback( val issuerId: String, val requestMappings: Set, - val tokenExpiry: Long = Duration.ofHours(1).toSeconds() + val tokenExpiry: Long = Duration.ofHours(1).toSeconds(), ) : OAuth2TokenCallback { override fun issuerId(): String = issuerId @@ -101,7 +101,7 @@ data class RequestMapping( private val requestParam: String, private val match: String = "*", val claims: Map = emptyMap(), - val typeHeader: String = JOSEObjectType.JWT.type + val typeHeader: String = JOSEObjectType.JWT.type, ) { fun isMatch(tokenRequest: TokenRequest): Boolean = tokenRequest.toHTTPRequest().queryParameters[requestParam]?.any { diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenProvider.kt b/src/main/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenProvider.kt index a8dd50e0..8f8399d4 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenProvider.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenProvider.kt @@ -20,7 +20,7 @@ import java.util.Date import java.util.UUID class OAuth2TokenProvider @JvmOverloads constructor( - private val keyProvider: KeyProvider = KeyProvider() + private val keyProvider: KeyProvider = KeyProvider(), ) { @JvmOverloads fun publicJwkSet(issuerId: String = "default"): JWKSet { @@ -35,35 +35,35 @@ class OAuth2TokenProvider @JvmOverloads constructor( tokenRequest: TokenRequest, issuerUrl: HttpUrl, oAuth2TokenCallback: OAuth2TokenCallback, - nonce: String? = null + nonce: String? = null, ) = defaultClaims( issuerUrl, oAuth2TokenCallback.subject(tokenRequest), listOf(tokenRequest.clientIdAsString()), nonce, oAuth2TokenCallback.addClaims(tokenRequest), - oAuth2TokenCallback.tokenExpiry() + oAuth2TokenCallback.tokenExpiry(), ).sign(issuerUrl.issuerId(), oAuth2TokenCallback.typeHeader(tokenRequest)) fun accessToken( tokenRequest: TokenRequest, issuerUrl: HttpUrl, oAuth2TokenCallback: OAuth2TokenCallback, - nonce: String? = null + nonce: String? = null, ) = defaultClaims( issuerUrl, oAuth2TokenCallback.subject(tokenRequest), oAuth2TokenCallback.audience(tokenRequest), nonce, oAuth2TokenCallback.addClaims(tokenRequest), - oAuth2TokenCallback.tokenExpiry() + oAuth2TokenCallback.tokenExpiry(), ).sign(issuerUrl.issuerId(), oAuth2TokenCallback.typeHeader(tokenRequest)) fun exchangeAccessToken( tokenRequest: TokenRequest, issuerUrl: HttpUrl, claimsSet: JWTClaimsSet, - oAuth2TokenCallback: OAuth2TokenCallback + oAuth2TokenCallback: OAuth2TokenCallback, ) = Instant.now().let { now -> JWTClaimsSet.Builder(claimsSet) .issuer(issuerUrl.toString()) @@ -99,7 +99,7 @@ class OAuth2TokenProvider @JvmOverloads constructor( supported && keyType == KeyType.RSA.value -> { SignedJWT( jwsHeader(key.keyID, type, algorithm), - this + this, ).apply { sign(RSASSASigner(key.toRSAKey().toPrivateKey())) } @@ -107,7 +107,7 @@ class OAuth2TokenProvider @JvmOverloads constructor( supported && keyType == KeyType.EC.value -> { SignedJWT( jwsHeader(key.keyID, type, algorithm), - this + this, ).apply { sign(ECDSASigner(key.toECKey().toECPrivateKey())) } @@ -134,7 +134,7 @@ class OAuth2TokenProvider @JvmOverloads constructor( audience: List, nonce: String?, additionalClaims: Map, - expiry: Long + expiry: Long, ) = JWTClaimsSet.Builder().let { builder -> val now = Instant.now() builder.subject(subject) diff --git a/src/main/kotlin/no/nav/security/mock/oauth2/userinfo/UserInfo.kt b/src/main/kotlin/no/nav/security/mock/oauth2/userinfo/UserInfo.kt index bccf1375..6545bb94 100644 --- a/src/main/kotlin/no/nav/security/mock/oauth2/userinfo/UserInfo.kt +++ b/src/main/kotlin/no/nav/security/mock/oauth2/userinfo/UserInfo.kt @@ -50,7 +50,7 @@ private fun invalidToken(msg: String) = OAuth2Exception( ErrorObject( "invalid_token", msg, - HTTPResponse.SC_UNAUTHORIZED + HTTPResponse.SC_UNAUTHORIZED, ), - msg + msg, ) diff --git a/src/test/kotlin/examples/kotlin/ktor/client/OAuth2Client.kt b/src/test/kotlin/examples/kotlin/ktor/client/OAuth2Client.kt index 7b89d61a..9b559e11 100644 --- a/src/test/kotlin/examples/kotlin/ktor/client/OAuth2Client.kt +++ b/src/test/kotlin/examples/kotlin/ktor/client/OAuth2Client.kt @@ -43,7 +43,7 @@ suspend fun HttpClient.tokenRequest(url: String, auth: Auth, params: Map header(s, list.first()) } } @@ -54,8 +54,8 @@ suspend fun HttpClient.clientCredentialsGrant(url: String, auth: Auth, scope: St auth = auth, params = mapOf( "grant_type" to "client_credentials", - "scope" to scope - ) + "scope" to scope, + ), ) suspend fun HttpClient.onBehalfOfGrant(url: String, auth: Auth, token: String, scope: String) = @@ -66,13 +66,13 @@ suspend fun HttpClient.onBehalfOfGrant(url: String, auth: Auth, token: String, s "scope" to scope, "grant_type" to "urn:ietf:params:oauth:grant-type:jwt-bearer", "requested_token_use" to "on_behalf_of", - "assertion" to token - ) + "assertion" to token, + ), ) class Auth internal constructor( val parameters: Map = emptyMap(), - val headers: Headers = Headers.Empty + val headers: Headers = Headers.Empty, ) { companion object { private const val CLIENT_ASSERTION_TYPE = "urn:ietf:params:oauth:client-assertion-type:jwt-bearer" @@ -85,26 +85,26 @@ class Auth internal constructor( fun PrivateKeyJwt(jwt: String): Auth = Auth( parameters = mapOf( "client_assertion_type" to CLIENT_ASSERTION_TYPE, - "client_assertion" to jwt - ) + "client_assertion" to jwt, + ), ) fun PrivateKeyJwt( keyPair: KeyPair, clientId: String, tokenEndpoint: String, - expiry: Duration = Duration.ofSeconds(120) + expiry: Duration = Duration.ofSeconds(120), ): Auth = Auth( parameters = mapOf( "client_assertion_type" to CLIENT_ASSERTION_TYPE, - "client_assertion" to keyPair.clientAssertion(clientId, tokenEndpoint, expiry) - ) + "client_assertion" to keyPair.clientAssertion(clientId, tokenEndpoint, expiry), + ), ) private fun KeyPair.clientAssertion( clientId: String, tokenEndpoint: String, - expiry: Duration = Duration.ofSeconds(120) + expiry: Duration = Duration.ofSeconds(120), ): String { val now = Instant.now() return JWT.create() @@ -126,5 +126,5 @@ data class TokenResponse( @JsonProperty("expires_in") val expiresIn: Int, @JsonProperty("token_type") - val tokenType: String + val tokenType: String, ) diff --git a/src/test/kotlin/examples/kotlin/ktor/client/OAuth2ClientTest.kt b/src/test/kotlin/examples/kotlin/ktor/client/OAuth2ClientTest.kt index b96581b1..fa4af2bd 100644 --- a/src/test/kotlin/examples/kotlin/ktor/client/OAuth2ClientTest.kt +++ b/src/test/kotlin/examples/kotlin/ktor/client/OAuth2ClientTest.kt @@ -30,7 +30,7 @@ internal class OAuth2ClientTest { val tokenResponse = httpClient.clientCredentialsGrant( url = server.tokenEndpointUrl("default").toString(), auth = Auth.ClientSecretBasic("client1", "secret"), - scope = "targetScope" + scope = "targetScope", ) tokenResponse.asClue { @@ -50,10 +50,10 @@ internal class OAuth2ClientTest { auth = Auth.PrivateKeyJwt( keyPair = KeyPairGenerator.getInstance("RSA").apply { initialize(2048) }.generateKeyPair(), clientId = "client1", - tokenEndpoint = tokenEndpointUrl + tokenEndpoint = tokenEndpointUrl, ), token = initialToken.serialize(), - scope = "targetScope" + scope = "targetScope", ) tokenResponse.asClue { diff --git a/src/test/kotlin/examples/kotlin/ktor/login/OAuth2LoginApp.kt b/src/test/kotlin/examples/kotlin/ktor/login/OAuth2LoginApp.kt index 5b4a110d..b77e151c 100644 --- a/src/test/kotlin/examples/kotlin/ktor/login/OAuth2LoginApp.kt +++ b/src/test/kotlin/examples/kotlin/ktor/login/OAuth2LoginApp.kt @@ -41,15 +41,15 @@ fun main() { AuthConfig.IdProvider( name = "google", authorizationEndpoint = "https://accounts.google.com/o/oauth2/v2/auth", - tokenEndpoint = "https://oauth2.googleapis.com/token" + tokenEndpoint = "https://oauth2.googleapis.com/token", ), AuthConfig.IdProvider( name = "github", authorizationEndpoint = "https://github.com/login/oauth/authorize", - tokenEndpoint = "https://github.com/login/oauth/access_token" - ) - ) - ) + tokenEndpoint = "https://github.com/login/oauth/access_token", + ), + ), + ), ) }.start(true) } @@ -97,7 +97,7 @@ fun Application.module(authConfig: AuthConfig) { class Login(val type: String = "") class AuthConfig( - val providers: List = emptyList() + val providers: List = emptyList(), ) { class IdProvider(val name: String, authorizationEndpoint: String, tokenEndpoint: String) { val settings = OAuthServerSettings.OAuth2ServerSettings( @@ -107,7 +107,7 @@ class AuthConfig( requestMethod = HttpMethod.Post, clientId = "***", clientSecret = "***", - defaultScopes = listOf("openid") + defaultScopes = listOf("openid"), ) } } diff --git a/src/test/kotlin/examples/kotlin/ktor/login/OAuth2LoginAppTest.kt b/src/test/kotlin/examples/kotlin/ktor/login/OAuth2LoginAppTest.kt index 37569ddc..eef227ee 100644 --- a/src/test/kotlin/examples/kotlin/ktor/login/OAuth2LoginAppTest.kt +++ b/src/test/kotlin/examples/kotlin/ktor/login/OAuth2LoginAppTest.kt @@ -35,7 +35,7 @@ internal class OAuth2LoginAppTest { withEmbeddedServer( { module(authConfig()) }, - port + port, ) { get("http://localhost:$port/login/google").asClue { it shouldBe "welcome googleSubject" @@ -51,7 +51,7 @@ internal class OAuth2LoginAppTest { private fun withEmbeddedServer( moduleFunction: Application.() -> Unit, port: Int, - test: ApplicationEngine.() -> R + test: ApplicationEngine.() -> R, ): R { val engine = embeddedServer(Netty, port = port) { moduleFunction(this) @@ -75,13 +75,13 @@ internal class OAuth2LoginAppTest { AuthConfig.IdProvider( name = "google", authorizationEndpoint = mockOAuth2Server.authorizationEndpointUrl("google").toString(), - tokenEndpoint = mockOAuth2Server.tokenEndpointUrl("google").toString() + tokenEndpoint = mockOAuth2Server.tokenEndpointUrl("google").toString(), ), AuthConfig.IdProvider( name = "github", authorizationEndpoint = mockOAuth2Server.authorizationEndpointUrl("github").toString(), - tokenEndpoint = mockOAuth2Server.tokenEndpointUrl("github").toString() - ) - ) + tokenEndpoint = mockOAuth2Server.tokenEndpointUrl("github").toString(), + ), + ), ) } diff --git a/src/test/kotlin/examples/kotlin/ktor/resourceserver/OAuth2ResourceServerApp.kt b/src/test/kotlin/examples/kotlin/ktor/resourceserver/OAuth2ResourceServerApp.kt index 8712c14e..af7094c4 100644 --- a/src/test/kotlin/examples/kotlin/ktor/resourceserver/OAuth2ResourceServerApp.kt +++ b/src/test/kotlin/examples/kotlin/ktor/resourceserver/OAuth2ResourceServerApp.kt @@ -39,14 +39,14 @@ fun main() { "provider1" to AuthConfig.TokenProvider( wellKnownUrl = "https://provider1/.well-known/openid-configuration", acceptedAudience = "thisAppClientId", - requiredClaims = mapOf("groups" to listOf("group1")) + requiredClaims = mapOf("groups" to listOf("group1")), ), "provider2" to AuthConfig.TokenProvider( wellKnownUrl = "https://provider2/.well-known/openid-configuration", acceptedAudience = "thisAppClientId", - requiredClaims = mapOf("someClaim" to "someClaim1") - ) - ) + requiredClaims = mapOf("someClaim" to "someClaim1"), + ), + ), ) embeddedServer(Netty, port = 8080) { @@ -91,12 +91,12 @@ fun Application.module(authConfig: AuthConfig) { // just to show how the MockOAuth2Server can support multiple "token providers"/issuers at the same time class AuthConfig( - val providers: Map = emptyMap() + val providers: Map = emptyMap(), ) { class TokenProvider( val wellKnownUrl: String, val acceptedAudience: String, - val requiredClaims: Map = emptyMap() + val requiredClaims: Map = emptyMap(), ) { private val httpClient = HttpClient(CIO) { install(ContentNegotiation) { @@ -116,7 +116,7 @@ class AuthConfig( data class WellKnown( val issuer: String, @JsonProperty("jwks_uri") - val jwksUri: String + val jwksUri: String, ) } } diff --git a/src/test/kotlin/examples/kotlin/ktor/resourceserver/OAuth2ResourceServerAppTest.kt b/src/test/kotlin/examples/kotlin/ktor/resourceserver/OAuth2ResourceServerAppTest.kt index a88c6c68..5c2dde6f 100644 --- a/src/test/kotlin/examples/kotlin/ktor/resourceserver/OAuth2ResourceServerAppTest.kt +++ b/src/test/kotlin/examples/kotlin/ktor/resourceserver/OAuth2ResourceServerAppTest.kt @@ -70,7 +70,7 @@ class OAuth2ResourceServerAppTest { "provider1", "foo", "scopeFromProvider1", - mapOf("groups" to listOf("group1", "group2")) + mapOf("groups" to listOf("group1", "group2")), ).serialize() private fun MockOAuth2Server.tokenFromProvider2() = @@ -78,7 +78,7 @@ class OAuth2ResourceServerAppTest { "provider2", "foo", "scopeFromProvider2", - mapOf("stringClaim" to "1") + mapOf("stringClaim" to "1"), ).serialize() private fun MockOAuth2Server.authConfig() = @@ -87,13 +87,13 @@ class OAuth2ResourceServerAppTest { "provider1" to AuthConfig.TokenProvider( wellKnownUrl = wellKnownUrl("provider1").toString(), acceptedAudience = "scopeFromProvider1", - requiredClaims = mapOf("groups" to listOf("group2")) + requiredClaims = mapOf("groups" to listOf("group2")), ), "provider2" to AuthConfig.TokenProvider( wellKnownUrl = wellKnownUrl("provider2").toString(), acceptedAudience = "scopeFromProvider2", - requiredClaims = mapOf("stringClaim" to "1") - ) - ) + requiredClaims = mapOf("stringClaim" to "1"), + ), + ), ) } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/MockOAuth2ServerTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/MockOAuth2ServerTest.kt index 39cd0bf5..ccb7b281 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/MockOAuth2ServerTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/MockOAuth2ServerTest.kt @@ -29,8 +29,8 @@ class MockOAuth2ServerTest { "client_id" to "client", "client_secret" to "sec", "grant_type" to "client_credentials", - "scope" to "scope1" - ) + "scope" to "scope1", + ), ).body?.close() this.takeRequest().asClue { diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/OAuth2ConfigTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/OAuth2ConfigTest.kt index 826ec0d9..db04e2b3 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/OAuth2ConfigTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/OAuth2ConfigTest.kt @@ -118,7 +118,7 @@ internal class OAuth2ConfigTest { { "Date $withSkew should be after $now" }, { "Date $withSkew should not be after $now" - } + }, ) } } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/StandaloneMockOAuth2ServerKtTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/StandaloneMockOAuth2ServerKtTest.kt index a9e55e32..5282634c 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/StandaloneMockOAuth2ServerKtTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/StandaloneMockOAuth2ServerKtTest.kt @@ -9,8 +9,8 @@ import io.kotest.matchers.shouldBe import io.kotest.matchers.types.beInstanceOf import no.nav.security.mock.oauth2.StandaloneConfig.JSON_CONFIG import no.nav.security.mock.oauth2.StandaloneConfig.JSON_CONFIG_PATH -import no.nav.security.mock.oauth2.StandaloneConfig.SERVER_PORT import no.nav.security.mock.oauth2.StandaloneConfig.PORT +import no.nav.security.mock.oauth2.StandaloneConfig.SERVER_PORT import no.nav.security.mock.oauth2.StandaloneConfig.hostname import no.nav.security.mock.oauth2.StandaloneConfig.oauth2Config import no.nav.security.mock.oauth2.StandaloneConfig.port diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/CorsHeadersIntegrationTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/CorsHeadersIntegrationTest.kt index 1e3a8e28..8046ca7f 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/CorsHeadersIntegrationTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/CorsHeadersIntegrationTest.kt @@ -31,8 +31,8 @@ class CorsHeadersIntegrationTest { "origin", origin, ACCESS_CONTROL_REQUEST_HEADERS, - "X-MY-HEADER" - ) + "X-MY-HEADER", + ), ).asClue { it.code shouldBe 204 it.headers[ACCESS_CONTROL_ALLOW_ORIGIN] shouldBe origin @@ -48,7 +48,7 @@ class CorsHeadersIntegrationTest { withMockOAuth2Server { client.get( this.wellKnownUrl("issuer"), - Headers.headersOf("origin", origin) + Headers.headersOf("origin", origin), ).asClue { it.code shouldBe 200 it.headers[ACCESS_CONTROL_ALLOW_ORIGIN] shouldBe origin @@ -62,7 +62,7 @@ class CorsHeadersIntegrationTest { withMockOAuth2Server { client.get( this.jwksUrl("issuer"), - Headers.headersOf("origin", origin) + Headers.headersOf("origin", origin), ).asClue { it.code shouldBe 200 it.headers[ACCESS_CONTROL_ALLOW_ORIGIN] shouldBe origin @@ -85,8 +85,8 @@ class CorsHeadersIntegrationTest { "grant_type" to GrantType.REFRESH_TOKEN.value, "refresh_token" to "canbewhatever", "client_id" to "id", - "client_secret" to "secret" - ) + "client_secret" to "secret", + ), ) response.code shouldBe 200 diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/InteractiveLoginIntegrationTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/InteractiveLoginIntegrationTest.kt index 9f14fcd1..7940417c 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/InteractiveLoginIntegrationTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/InteractiveLoginIntegrationTest.kt @@ -47,19 +47,19 @@ class InteractiveLoginIntegrationTest { User( username = "user1", claims = mapOf( - "claim1" to "claim1value" - ) - ) + "claim1" to "claim1value", + ), + ), ), Arguments.of( User( username = "user2", claims = mapOf( - "claim2" to "claim2value" - ) - ) - ) + "claim2" to "claim2value", + ), + ), + ), ) } @@ -74,8 +74,8 @@ class InteractiveLoginIntegrationTest { loginUrl, mapOf( "username" to user.username, - "claims" to user.claimsAsJson() - ) + "claims" to user.claimsAsJson(), + ), ).let { authResponse -> val code = authResponse.headers["location"]?.toHttpUrl()?.queryParameter("code") code.shouldNotBeNull() @@ -91,13 +91,13 @@ class InteractiveLoginIntegrationTest { "grant_type" to "authorization_code", "scope" to "openid scope1", "redirect_uri" to "http://mycallback", - "code" to authCode - ) + "code" to authCode, + ), ).toTokenResponse() internal data class User( val username: String, - val claims: Map = emptyMap() + val claims: Map = emptyMap(), ) { fun claimsAsJson(): String = jacksonObjectMapper().writeValueAsString(claims) } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/JwtBearerGrantIntegrationTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/JwtBearerGrantIntegrationTest.kt index 256219e8..acccc7df 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/JwtBearerGrantIntegrationTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/JwtBearerGrantIntegrationTest.kt @@ -36,9 +36,9 @@ class JwtBearerGrantIntegrationTest { subject = initialSubject, claims = mapOf( "claim1" to "value1", - "claim2" to "value2" - ) - ) + "claim2" to "value2", + ), + ), ) val issuerId = "aad" val response: ParsedTokenResponse = client.tokenRequest( @@ -47,8 +47,8 @@ class JwtBearerGrantIntegrationTest { parameters = mapOf( "grant_type" to GrantType.JWT_BEARER.value, "scope" to "scope1", - "assertion" to initialToken.serialize() - ) + "assertion" to initialToken.serialize(), + ), ).toTokenResponse() response shouldBeValidFor GrantType.JWT_BEARER @@ -78,9 +78,9 @@ class JwtBearerGrantIntegrationTest { "claim1" to "value1", "claim2" to "value2", "scope" to "ascope", - "resource" to "aud1" - ) - ) + "resource" to "aud1", + ), + ), ) initialToken.audience.shouldBeEmpty() @@ -94,8 +94,8 @@ class JwtBearerGrantIntegrationTest { basicAuth = Pair("client1", "secret"), parameters = mapOf( "grant_type" to GrantType.JWT_BEARER.value, - "assertion" to initialToken.serialize() - ) + "assertion" to initialToken.serialize(), + ), ).toTokenResponse() response shouldBeValidFor GrantType.JWT_BEARER diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/LoginPageIntegrationTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/LoginPageIntegrationTest.kt index b843f415..a0517045 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/LoginPageIntegrationTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/LoginPageIntegrationTest.kt @@ -30,8 +30,8 @@ class LoginPageIntegrationTest { val server = MockOAuth2Server( OAuth2Config( interactiveLogin = true, - loginPagePath = "./src/test/resources/login.example.html" - ) + loginPagePath = "./src/test/resources/login.example.html", + ), ).apply { start() } val body = client.get(server.authorizationEndpointUrl("default").authenticationRequest()).body?.string() @@ -45,8 +45,8 @@ class LoginPageIntegrationTest { val server = MockOAuth2Server( OAuth2Config( interactiveLogin = true, - loginPagePath = path - ) + loginPagePath = path, + ), ).apply { start() } val code = client.get(server.authorizationEndpointUrl("default").authenticationRequest()).code diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/MockOAuth2ServerIntegrationTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/MockOAuth2ServerIntegrationTest.kt index 63713607..9091924a 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/MockOAuth2ServerIntegrationTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/MockOAuth2ServerIntegrationTest.kt @@ -44,7 +44,7 @@ class MockOAuth2ServerIntegrationTest { val s = MockOAuth2Server( route("/custom") { OAuth2HttpResponse(status = 200, body = "custom route") - } + }, ).apply { start() } @@ -88,7 +88,7 @@ class MockOAuth2ServerIntegrationTest { fun `wellknown should include https addresses when MockWebServerWrapper is started with https enabled`() { val ssl = Ssl() val server = MockOAuth2Server( - OAuth2Config(httpServer = MockWebServerWrapper(ssl)) + OAuth2Config(httpServer = MockWebServerWrapper(ssl)), ).apply { start() } client.withTrustStore(ssl.sslKeystore.keyStore).get(server.wellKnownUrl("issuer1")).parse().asClue { it urlsShouldStartWith "https" @@ -103,8 +103,8 @@ class MockOAuth2ServerIntegrationTest { DefaultOAuth2TokenCallback( issuerId = "custom", subject = "yolo", - audience = listOf("myaud") - ) + audience = listOf("myaud"), + ), ) client.post( @@ -115,8 +115,8 @@ class MockOAuth2ServerIntegrationTest { "grant_type" to "authorization_code", "scope" to "openid scope1", "redirect_uri" to "http://mycallback", - "code" to "1234" - ) + "code" to "1234", + ), ).toTokenResponse().asClue { it.idToken.shouldNotBeNull() it.idToken.subject shouldBe "yolo" @@ -138,8 +138,8 @@ class MockOAuth2ServerIntegrationTest { issuerId = "default", subject = "mysub", audience = listOf("myaud"), - claims = mapOf("someclaim" to "claimvalue") - ) + claims = mapOf("someclaim" to "claimvalue"), + ), ) val wellKnown = client.get(this.wellKnownUrl("default")).parse() val jwks = client.get(wellKnown.jwksUri.toHttpUrl()).body?.let { JWKSet.parse(it.string()) } @@ -165,9 +165,9 @@ class MockOAuth2ServerIntegrationTest { "sub" to "mysub", "aud" to listOf("myapp"), "customInt" to 123, - "customList" to listOf(1, 2, 3) + "customList" to listOf(1, 2, 3), ), - Duration.ofSeconds(10) + Duration.ofSeconds(10), ) val wellKnown = client.get(this.wellKnownUrl("default")).parse() @@ -193,13 +193,13 @@ class MockOAuth2ServerIntegrationTest { "client1" to "secret", mapOf( "grant_type" to "client_credentials", - "scope" to "scope1" - ) + "scope" to "scope1", + ), ).toTokenResponse().accessToken.asClue { it.shouldNotBeNull() it.claims shouldContainAll mapOf( "sub" to "subByScope", - "aud" to listOf("audByScope") + "aud" to listOf("audByScope"), ) } } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/OidcAuthorizationCodeGrantIntegrationTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/OidcAuthorizationCodeGrantIntegrationTest.kt index 85587175..270184e6 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/OidcAuthorizationCodeGrantIntegrationTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/OidcAuthorizationCodeGrantIntegrationTest.kt @@ -31,7 +31,7 @@ class OidcAuthorizationCodeGrantIntegrationTest { @Test fun `authentication request should return 302 with redirectUri as location and query params state and code`() { client.get( - server.authorizationEndpointUrl("default").authenticationRequest(redirectUri = "http://mycallback", state = "mystate") + server.authorizationEndpointUrl("default").authenticationRequest(redirectUri = "http://mycallback", state = "mystate"), ).asClue { response -> response.code shouldBe 302 response.headers["location"]?.toHttpUrl().asClue { @@ -58,8 +58,8 @@ class OidcAuthorizationCodeGrantIntegrationTest { "grant_type" to "authorization_code", "scope" to "openid scope1", "redirect_uri" to "http://mycallback", - "code" to code - ) + "code" to code, + ), ).toTokenResponse().asClue { it.accessToken shouldNotBe null it.idToken shouldNotBe null @@ -76,7 +76,7 @@ class OidcAuthorizationCodeGrantIntegrationTest { // simulate user interaction by doing the auth request as a post (instead of get with user punching username/pwd and submitting form) val code = client.post( server.authorizationEndpointUrl("default").authenticationRequest(), - mapOf("username" to "foo") + mapOf("username" to "foo"), ).let { authResponse -> authResponse.headers["location"]?.toHttpUrl()?.queryParameter("code") } @@ -91,8 +91,8 @@ class OidcAuthorizationCodeGrantIntegrationTest { "grant_type" to "authorization_code", "scope" to "openid scope1", "redirect_uri" to "http://mycallback", - "code" to code - ) + "code" to code, + ), ).toTokenResponse().asClue { it.accessToken shouldNotBe null it.idToken shouldNotBe null @@ -109,7 +109,7 @@ class OidcAuthorizationCodeGrantIntegrationTest { fun `authorization code flow should return tokens on token request when valid PKCE code_verifier is used`() { val pkce = Pkce() val code = client.get( - server.authorizationEndpointUrl("default").authenticationRequest(pkce = pkce) + server.authorizationEndpointUrl("default").authenticationRequest(pkce = pkce), ).let { authResponse -> authResponse.headers["location"]?.toHttpUrl()?.queryParameter("code") } @@ -126,7 +126,7 @@ class OidcAuthorizationCodeGrantIntegrationTest { fun `authorization code flow should return 400 bad request on token request when invalid PKCE code_verifier is used`() { val pkce = Pkce() val code = client.get( - server.authorizationEndpointUrl("default").authenticationRequest(pkce = pkce) + server.authorizationEndpointUrl("default").authenticationRequest(pkce = pkce), ).let { authResponse -> authResponse.headers["location"]?.toHttpUrl()?.queryParameter("code") } @@ -149,11 +149,11 @@ class OidcAuthorizationCodeGrantIntegrationTest { "grant_type" to "authorization_code", "scope" to "openid scope1", "redirect_uri" to "http://mycallback", - "code" to code + "code" to code, ).apply { if (pkce != null) { put("code_verifier", pkce.verifier.value) } - } + }, ) } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/PasswordGrantIntegrationTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/PasswordGrantIntegrationTest.kt index f7b3ad7b..d917d314 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/PasswordGrantIntegrationTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/PasswordGrantIntegrationTest.kt @@ -31,8 +31,8 @@ class PasswordGrantIntegrationTest { "grant_type" to GrantType.PASSWORD.value, "scope" to "scope1", "username" to "foo", - "password" to "bar" - ) + "password" to "bar", + ), ).toTokenResponse() response shouldBeValidFor GrantType.PASSWORD diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/RefreshTokenGrantIntegrationTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/RefreshTokenGrantIntegrationTest.kt index dec59ba3..880056ad 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/RefreshTokenGrantIntegrationTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/RefreshTokenGrantIntegrationTest.kt @@ -33,7 +33,7 @@ class RefreshTokenGrantIntegrationTest { // simulate user interaction by doing the auth request as a post (instead of get with user punching username/pwd and submitting form) val authorizationCode = client.post( this.authorizationEndpointUrl("default").authenticationRequest(), - mapOf("username" to initialSubject) + mapOf("username" to initialSubject), ).let { authResponse -> authResponse.headers["location"]?.toHttpUrl()?.queryParameter("code") } @@ -49,8 +49,8 @@ class RefreshTokenGrantIntegrationTest { "client_id" to "id", "client_secret" to "secret", "scope" to "openid", - "redirect_uri" to "http://something" - ) + "redirect_uri" to "http://something", + ), ).toTokenResponse() tokenResponseBeforeRefresh.idToken?.subject shouldBe initialSubject @@ -64,8 +64,8 @@ class RefreshTokenGrantIntegrationTest { "grant_type" to GrantType.REFRESH_TOKEN.value, "refresh_token" to refreshToken, "client_id" to "id", - "client_secret" to "secret" - ) + "client_secret" to "secret", + ), ).toTokenResponse() refreshTokenResponse shouldBeValidFor GrantType.REFRESH_TOKEN @@ -94,8 +94,8 @@ class RefreshTokenGrantIntegrationTest { "grant_type" to GrantType.REFRESH_TOKEN.value, "refresh_token" to "canbewhatever", "client_id" to "id", - "client_secret" to "secret" - ) + "client_secret" to "secret", + ), ).toTokenResponse() refreshTokenResponse shouldBeValidFor GrantType.REFRESH_TOKEN @@ -113,8 +113,8 @@ class RefreshTokenGrantIntegrationTest { "grant_type" to GrantType.REFRESH_TOKEN.value, "refresh_token" to "canbewhatever", "client_id" to "id", - "client_secret" to "secret" - ) + "client_secret" to "secret", + ), ).toTokenResponse() refreshTokenResponse shouldBeValidFor GrantType.REFRESH_TOKEN diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/TokenExchangeGrantIntegrationTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/TokenExchangeGrantIntegrationTest.kt index 763c065e..888e3923 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/TokenExchangeGrantIntegrationTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/TokenExchangeGrantIntegrationTest.kt @@ -46,9 +46,9 @@ class TokenExchangeGrantIntegrationTest { subject = initialSubject, claims = mapOf( "claim1" to "value1", - "claim2" to "value2" - ) - ) + "claim2" to "value2", + ), + ), ) val issuerId = "tokenx" @@ -64,8 +64,8 @@ class TokenExchangeGrantIntegrationTest { "client_assertion" to clientAssertion, "subject_token_type" to SubjectTokenType.TOKEN_TYPE_JWT, "subject_token" to initialToken.serialize(), - "audience" to targetAudienceForToken - ) + "audience" to targetAudienceForToken, + ), ).toTokenResponse() response shouldBeValidFor TOKEN_EXCHANGE @@ -93,8 +93,8 @@ class TokenExchangeGrantIntegrationTest { "client_secret" to "somesecret", "subject_token_type" to SubjectTokenType.TOKEN_TYPE_JWT, "subject_token" to "yolo", - "audience" to "targetAudienceForToken" - ) + "audience" to "targetAudienceForToken", + ), ) response.code shouldBe 400 } @@ -113,8 +113,8 @@ class TokenExchangeGrantIntegrationTest { "client_assertion" to clientAssertion, "subject_token_type" to SubjectTokenType.TOKEN_TYPE_JWT, "subject_token" to "na", - "audience" to "na" - ) + "audience" to "na", + ), ) response.code shouldBe 400 } @@ -145,8 +145,8 @@ class TokenExchangeGrantIntegrationTest { "client_assertion" to clientAssertion, "subject_token_type" to SubjectTokenType.TOKEN_TYPE_JWT, "subject_token" to "na", - "audience" to "na" - ) + "audience" to "na", + ), ) response.code shouldBe 400 } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/UserInfoIntegrationTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/UserInfoIntegrationTest.kt index 1be128e4..fc4f472c 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/e2e/UserInfoIntegrationTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/e2e/UserInfoIntegrationTest.kt @@ -21,7 +21,7 @@ class UserInfoIntegrationTest { private val client = client() private val rs384Config = OAuth2Config( - tokenProvider = OAuth2TokenProvider(keyProvider = KeyProvider(initialKeys = emptyList(), algorithm = JWSAlgorithm.RS384.name)) + tokenProvider = OAuth2TokenProvider(keyProvider = KeyProvider(initialKeys = emptyList(), algorithm = JWSAlgorithm.RS384.name)), ) @Test @@ -31,12 +31,12 @@ class UserInfoIntegrationTest { val token = this.issueToken(issuerId = issuerId, subject = "foo", claims = mapOf("extra" to "bar")) client.get( url = this.userInfoUrl(issuerId), - headers = token.asBearerTokenHeader() + headers = token.asBearerTokenHeader(), ).asClue { it.parse>() shouldContainAll mapOf( "sub" to token.claims["sub"], "iss" to token.claims["iss"], - "extra" to token.claims["extra"] + "extra" to token.claims["extra"], ) } } @@ -50,12 +50,12 @@ class UserInfoIntegrationTest { token.header.algorithm.shouldBe(JWSAlgorithm.RS384) client.get( url = this.userInfoUrl(issuerId), - headers = token.asBearerTokenHeader() + headers = token.asBearerTokenHeader(), ).asClue { it.parse>() shouldContainAll mapOf( "sub" to token.claims["sub"], "iss" to token.claims["iss"], - "extra" to token.claims["extra"] + "extra" to token.claims["extra"], ) } } @@ -69,7 +69,7 @@ class UserInfoIntegrationTest { withMockOAuth2Server { client.get( url = this.userInfoUrl(issuerId), - headers = token.asBearerTokenHeader() + headers = token.asBearerTokenHeader(), ).asClue { it.code shouldBe 401 it.message shouldBe "Client Error" diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/examples/AbstractExampleApp.kt b/src/test/kotlin/no/nav/security/mock/oauth2/examples/AbstractExampleApp.kt index 41a06efe..2eb325ad 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/examples/AbstractExampleApp.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/examples/AbstractExampleApp.kt @@ -54,7 +54,7 @@ abstract class AbstractExampleApp(oauth2DiscoveryUrl: String) { MockResponse() .setResponseCode(500) .setBody("unhandled exception with message ${error.message}") - } + }, ) } } @@ -71,7 +71,7 @@ abstract class AbstractExampleApp(oauth2DiscoveryUrl: String) { Request.Builder() .url(metadata.jwkSetURI.toURL()) .get() - .build() + .build(), ).execute().body?.string()?.let { JWKSet.parse(it) } ?: throw RuntimeException("could not retrieve jwks") @@ -82,12 +82,12 @@ abstract class AbstractExampleApp(oauth2DiscoveryUrl: String) { jwtProcessor.jwsTypeVerifier = DefaultJOSEObjectTypeVerifier(JOSEObjectType("JWT")) val keySelector: JWSKeySelector = JWSVerificationKeySelector( JWSAlgorithm.RS256, - ImmutableJWKSet(jwkSet) + ImmutableJWKSet(jwkSet), ) jwtProcessor.jwsKeySelector = keySelector jwtProcessor.jwtClaimsSetVerifier = DefaultJWTClaimsVerifier( JWTClaimsSet.Builder().issuer(issuer.toString()).build(), - HashSet(listOf("sub", "iat", "exp", "aud")) + HashSet(listOf("sub", "iat", "exp", "aud")), ) return try { jwtProcessor.process(jwt, null) diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/examples/clientcredentials/ExampleAppWithClientCredentialsClient.kt b/src/test/kotlin/no/nav/security/mock/oauth2/examples/clientcredentials/ExampleAppWithClientCredentialsClient.kt index dec44451..8aec1672 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/examples/clientcredentials/ExampleAppWithClientCredentialsClient.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/examples/clientcredentials/ExampleAppWithClientCredentialsClient.kt @@ -33,9 +33,9 @@ class ExampleAppWithClientCredentialsClient(oauth2DiscoveryUrl: String) : Abstra .add("client_id", "ExampleAppWithClientCredentialsClient") .add("scope", "scope1") .add("grant_type", "client_credentials") - .build() + .build(), ) - .build() + .build(), ).execute() return tokenResponse.body?.string()?.let { ObjectMapper().readValue(it).get("access_token")?.textValue() diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/examples/clientcredentials/ExampleAppWithClientCredentialsClientTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/examples/clientcredentials/ExampleAppWithClientCredentialsClientTest.kt index 0be1ab43..6bb6d792 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/examples/clientcredentials/ExampleAppWithClientCredentialsClientTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/examples/clientcredentials/ExampleAppWithClientCredentialsClientTest.kt @@ -38,7 +38,7 @@ internal class ExampleAppWithClientCredentialsClientTest { Request.Builder() .url(exampleApp.url("/clientcredentials")) .get() - .build() + .build(), ).execute() assertThat(response.code).isEqualTo(200) diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/examples/openidconnect/ExampleAppWithOpenIdConnect.kt b/src/test/kotlin/no/nav/security/mock/oauth2/examples/openidconnect/ExampleAppWithOpenIdConnect.kt index 04523bf3..74ba6ae2 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/examples/openidconnect/ExampleAppWithOpenIdConnect.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/examples/openidconnect/ExampleAppWithOpenIdConnect.kt @@ -36,9 +36,9 @@ class ExampleAppWithOpenIdConnect(oidcDiscoveryUrl: String) : AbstractExampleApp .add("code", code) .add("redirect_uri", exampleApp.url("/callback").toString()) .add("grant_type", "authorization_code") - .build() + .build(), ) - .build() + .build(), ).execute() val idToken: String = ObjectMapper().readValue(tokenResponse.body!!.string()).get("id_token").textValue() val idTokenClaims: JWTClaimsSet = verifyJwt(idToken, metadata.issuer, retrieveJwks()) @@ -81,7 +81,7 @@ class ExampleAppWithOpenIdConnect(oidcDiscoveryUrl: String) : AbstractExampleApp "response_mode" to listOf("query"), "scope" to listOf("openid scope1"), "state" to listOf("1234"), - "nonce" to listOf("5678") - ) + "nonce" to listOf("5678"), + ), ) } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/examples/openidconnect/ExampleAppWithOpenIdConnectTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/examples/openidconnect/ExampleAppWithOpenIdConnectTest.kt index 7f57d0fe..f14aa4a9 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/examples/openidconnect/ExampleAppWithOpenIdConnectTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/examples/openidconnect/ExampleAppWithOpenIdConnectTest.kt @@ -50,8 +50,8 @@ class ExampleAppWithOpenIdConnectTest { oAuth2Server.enqueueCallback( DefaultOAuth2TokenCallback( issuerId = ISSUER_ID, - subject = "foo" - ) + subject = "foo", + ), ) val loginResponse = client.newCall(Request.Builder().url(exampleApp.url("/login")).build()).execute() assertThat(loginResponse.headers["Set-Cookie"]).contains("id_token=") diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/examples/securedapi/ExampleAppWithSecuredApiTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/examples/securedapi/ExampleAppWithSecuredApiTest.kt index d780b1fc..fa43ed88 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/examples/securedapi/ExampleAppWithSecuredApiTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/examples/securedapi/ExampleAppWithSecuredApiTest.kt @@ -39,7 +39,7 @@ internal class ExampleAppWithSecuredApiTest { Request.Builder() .url(exampleApp.url("/api")) .get() - .build() + .build(), ).execute() assertThat(response.code).isEqualTo(401) } @@ -52,7 +52,7 @@ internal class ExampleAppWithSecuredApiTest { .url(exampleApp.url("/api")) .addHeader("Authorization", "Bearer " + token.serialize()) .get() - .build() + .build(), ).execute() assertThat(response.code).isEqualTo(200) assertThat(response.body?.string()).contains(token.jwtClaimsSet.subject) diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/grant/AuthorizationCodeHandlerTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/grant/AuthorizationCodeHandlerTest.kt index a5230d51..2f6f1594 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/grant/AuthorizationCodeHandlerTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/grant/AuthorizationCodeHandlerTest.kt @@ -34,8 +34,8 @@ internal class AuthorizationCodeHandlerTest { "http://authorizationendpoint".toHttpUrl() .authenticationRequest( state = "mystate", - redirectUri = "http://redirect" - ) + redirectUri = "http://redirect", + ), ) { handler.authorizationCodeResponse(AuthenticationRequest.parse(this.toUri())).asClue { it.impliedResponseType().impliesCodeFlow() shouldBe true @@ -60,7 +60,7 @@ internal class AuthorizationCodeHandlerTest { fun `token response with login including claims should return access_token containing claims from login`( claims: String, expectedClaimKey: String, - expectedClaimValue: String + expectedClaimValue: String, ) { val code: String = handler.retrieveAuthorizationCode(Login("foo", claims)) @@ -75,7 +75,7 @@ internal class AuthorizationCodeHandlerTest { @JvmStatic fun jsonClaimsProvider(): Stream = Stream.of( Arguments.of("{ \"acr\": \"value\" }", "acr", "\"value\""), - Arguments.of("{ \"acr\": { \"reference\": { \"id\": \"value\" } } }", "acr", "{\"reference\":{\"id\":\"value\"}}") + Arguments.of("{ \"acr\": { \"reference\": { \"id\": \"value\" } } }", "acr", "{\"reference\":{\"id\":\"value\"}}"), ) } @@ -113,7 +113,7 @@ internal class AuthorizationCodeHandlerTest { private fun AuthorizationCodeHandler.retrieveAuthorizationCode(login: Login): String = authorizationCodeResponse( authenticationRequest = "http://authorizationendpoint".toHttpUrl().authenticationRequest().asNimbusAuthRequest(), - login = login + login = login, ).authorizationCode.value private fun HttpUrl.asNimbusAuthRequest(): AuthenticationRequest = AuthenticationRequest.parse(this.toUri()) @@ -121,7 +121,7 @@ internal class AuthorizationCodeHandlerTest { private fun tokenRequest( code: String, redirectUri: String = "http://redirect", - scope: String = "openid" + scope: String = "openid", ): OAuth2HttpRequest { return OAuth2HttpRequest( headers = Headers.headersOf("Content-Type", "application/x-www-form-urlencoded"), @@ -132,7 +132,7 @@ internal class AuthorizationCodeHandlerTest { "client_secret=secret&" + "code=$code&" + "redirect_uri=$redirectUri&" + - "scope=$scope" + "scope=$scope", ) } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequestHandlerTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequestHandlerTest.kt index e64683ce..957e0852 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequestHandlerTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequestHandlerTest.kt @@ -44,14 +44,14 @@ internal class OAuth2HttpRequestHandlerTest { path = "/issuer1$AUTHORIZATION_WITH_PARAMS", method = "POST", body = "username=foo", - expectedResponse = OAuth2HttpResponse(status = 302) + expectedResponse = OAuth2HttpResponse(status = 302), ), request( path = "/issuer1$TOKEN", method = "POST", headers = Headers.headersOf("Content-Type", "application/x-www-form-urlencoded"), body = "grant_type=client_credentials&client_id=client&client_secret=secret", - expectedResponse = OAuth2HttpResponse(status = 200) + expectedResponse = OAuth2HttpResponse(status = 200), ), request(path = "/issuer1$END_SESSION", method = "GET", expectedResponse = OAuth2HttpResponse(status = 200)), request(path = "/issuer1$USER_INFO", method = "GET", headers = bearerTokenHeader("issuer1"), expectedResponse = OAuth2HttpResponse(status = 200)), @@ -61,9 +61,9 @@ internal class OAuth2HttpRequestHandlerTest { method = "POST", headers = Headers.headersOf("Content-Type", "application/x-www-form-urlencoded"), body = "authorize_url=http://url", - expectedResponse = OAuth2HttpResponse(status = 302) + expectedResponse = OAuth2HttpResponse(status = 302), ), - request(path = "/favicon.ico", method = "GET", expectedResponse = OAuth2HttpResponse(status = 200)) + request(path = "/favicon.ico", method = "GET", expectedResponse = OAuth2HttpResponse(status = 200)), ) private fun request(path: String, method: String, headers: Headers = Headers.headersOf(), body: String? = null, expectedResponse: OAuth2HttpResponse) = @@ -72,16 +72,16 @@ internal class OAuth2HttpRequestHandlerTest { headers, method, "http://localhost$path".toHttpUrl(), - body + body, ), - expectedResponse + expectedResponse, ) private fun bearerTokenHeader(issuerId: String): Headers { val claims = mapOf( "iss" to "http://localhost/$issuerId", "sub" to "foo", - "extra" to "bar" + "extra" to "bar", ) val bearerToken = tokenProvider.jwt(claims = claims, issuerId = issuerId).serialize() return Headers.headersOf("Authorization", "Bearer $bearerToken") diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequestTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequestTest.kt index 4024a0b0..9087991b 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequestTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRequestTest.kt @@ -15,25 +15,25 @@ internal class OAuth2HttpRequestTest { // no host header, x-forwarded-proto set "http://localhost:8080/mypath?query=1".GET( "x-forwarded-proto", - "https" + "https", ).url shouldBe "https://localhost/mypath?query=1".toHttpUrl() // host header overrides host and port in url "http://localhost:8080/mypath?query=1".GET( "host", - "localhost:8080" + "localhost:8080", ).url shouldBe "http://localhost:8080/mypath?query=1".toHttpUrl() // host header overrides host in url, port from original url should be used "http://localhost:8080/mypath?query=1".GET( "host", - "hostonly" + "hostonly", ).url shouldBe "http://hostonly:8080/mypath?query=1".toHttpUrl() // host header overrides host in url, port from original url should be used "http://localhost:8080/mypath?query=1".GET( "host", - "hostonly:-1" + "hostonly:-1", ).url shouldBe "http://hostonly:8080/mypath?query=1".toHttpUrl() // host header present, x-forwarded-port overrides port in url @@ -41,7 +41,7 @@ internal class OAuth2HttpRequestTest { "host", "host:8080", "x-forwarded-port", - "9090" + "9090", ).url shouldBe "http://host:9090/mypath?query=1".toHttpUrl() // host header and x-forwarded- headers present @@ -51,7 +51,7 @@ internal class OAuth2HttpRequestTest { "x-forwarded-port", "9090", "x-forwarded-proto", - "https" + "https", ).url shouldBe "https://hostheader:9090/mypath?query=1".toHttpUrl() } @@ -59,7 +59,7 @@ internal class OAuth2HttpRequestTest { OAuth2HttpRequest( originalUrl = this.toHttpUrl(), headers = Headers.headersOf(*headers), - method = "GET" + method = "GET", ) @Test @@ -67,7 +67,7 @@ internal class OAuth2HttpRequestTest { val req1 = OAuth2HttpRequest( headers = Headers.headersOf(), method = "GET", - originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl() + originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl(), ) req1.proxyAwareUrl().toString() shouldBe "http://localhost:8080/mypath?query=1" val req2 = OAuth2HttpRequest( @@ -77,10 +77,10 @@ internal class OAuth2HttpRequestTest { "x-forwarded-proto", "https", "x-forwarded-port", - "444" + "444", ), method = "GET", - originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl() + originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl(), ) req2.proxyAwareUrl().toString() shouldBe "https://fakedings.nais.io:444/mypath?query=1" @@ -92,10 +92,10 @@ internal class OAuth2HttpRequestTest { "x-forwarded-proto", "https", "x-forwarded-port", - "444" + "444", ), method = "GET", - originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl() + originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl(), ) req3.proxyAwareUrl().toString() shouldBe "https://fakedings.nais.io:444/mypath?query=1" @@ -105,10 +105,10 @@ internal class OAuth2HttpRequestTest { "host", "fakedings.nais.io:666", "x-forwarded-proto", - "https" + "https", ), method = "GET", - originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl() + originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl(), ) req4.proxyAwareUrl().toString() shouldBe "https://fakedings.nais.io:666/mypath?query=1" @@ -118,40 +118,40 @@ internal class OAuth2HttpRequestTest { "host", "fakedings.nais.io", "x-forwarded-proto", - "https" + "https", ), method = "GET", - originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl() + originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl(), ) req5.proxyAwareUrl().toString() shouldBe "https://fakedings.nais.io/mypath?query=1" val req6 = OAuth2HttpRequest( headers = Headers.headersOf( "host", - "oauth2" + "oauth2", ), method = "GET", - originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl() + originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl(), ) req6.proxyAwareUrl().toString() shouldBe "http://oauth2:8080/mypath?query=1" val req7 = OAuth2HttpRequest( headers = Headers.headersOf( "host", - "oauth2:8080" + "oauth2:8080", ), method = "GET", - originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl() + originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl(), ) req7.proxyAwareUrl().toString() shouldBe "http://oauth2:8080/mypath?query=1" val req8 = OAuth2HttpRequest( headers = Headers.headersOf( "host", - "oauth2" + "oauth2", ), method = "GET", - originalUrl = "https://somehost/mypath?query=1".toHttpUrl() + originalUrl = "https://somehost/mypath?query=1".toHttpUrl(), ) req8.proxyAwareUrl().toString() shouldBe "https://oauth2/mypath?query=1" } @@ -161,7 +161,7 @@ internal class OAuth2HttpRequestTest { val req1 = OAuth2HttpRequest( headers = Headers.headersOf(), method = "GET", - originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl() + originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl(), ) req1.toWellKnown().issuer shouldBe "http://localhost:8080/mypath" val req2 = OAuth2HttpRequest( @@ -171,10 +171,10 @@ internal class OAuth2HttpRequestTest { "x-forwarded-proto", "https", "x-forwarded-port", - "444" + "444", ), method = "GET", - originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl() + originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl(), ) req2.toWellKnown().issuer shouldBe "https://fakedings.nais.io:444/mypath" } @@ -184,7 +184,7 @@ internal class OAuth2HttpRequestTest { val req1 = OAuth2HttpRequest( headers = Headers.headersOf(), method = "GET", - originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl() + originalUrl = "http://localhost:8080/mypath?query=1".toHttpUrl(), ) req1.toWellKnown().issuer shouldBe "http://localhost:8080/mypath" diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRouterTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRouterTest.kt index 38936b79..170f42e0 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRouterTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/http/OAuth2HttpRouterTest.kt @@ -21,7 +21,7 @@ internal class OAuth2HttpRouterTest { }, route("shouldmatch") { OAuth2HttpResponse(status = 200, body = "ANY") - } + }, ) routes.invoke(post("/something/shouldmatch")).body shouldBe "ANY" routes.invoke(options("/something/shouldmatch")).body shouldBe "OPTIONS" @@ -69,7 +69,7 @@ internal class OAuth2HttpRouterTest { ResponseInterceptor { _, response -> val headers = response.headers.newBuilder().add("fromInterceptor", "fromInterceptor").build() response.copy(headers = headers) - } + }, ) get("/1") { it.headers shouldContain ("yolo" to "forever") @@ -83,14 +83,14 @@ internal class OAuth2HttpRouterTest { routes.invoke(get("/1")).asClue { it.headers shouldContainAll listOf( "Content-Type" to "text/plain", - "fromInterceptor" to "fromInterceptor" + "fromInterceptor" to "fromInterceptor", ) it.body shouldBe "1" } routes.invoke(get("/2")).asClue { it.headers shouldContainAll listOf( "Content-Type" to "text/plain", - "fromInterceptor" to "fromInterceptor" + "fromInterceptor" to "fromInterceptor", ) it.body shouldBe "2" } @@ -105,12 +105,12 @@ internal class OAuth2HttpRouterTest { Headers.headersOf(), method, url.toHttpUrl(), - body + body, ) private fun ok(body: String? = null) = OAuth2HttpResponse( headers = Headers.headersOf("Content-Type", "text/plain"), status = 200, - body = body + body = body, ) } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/introspect/IntrospectTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/introspect/IntrospectTest.kt index f288c72a..e4373e06 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/introspect/IntrospectTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/introspect/IntrospectTest.kt @@ -31,7 +31,7 @@ internal class IntrospectTest { "iss" to issuerUrl, "client_id" to "yolo", "token_type" to "token", - "sub" to "foo" + "sub" to "foo", ) val token = tokenProvider.jwt(claims) val request = request("$issuerUrl$INTROSPECT", token.serialize()) @@ -51,7 +51,7 @@ internal class IntrospectTest { "iss" to issuerUrl, "client_id" to "yolo", "token_type" to "token", - "sub" to "foo" + "sub" to "foo", ) val token = rs384TokenProvider.jwt(claims) val request = request("$issuerUrl$INTROSPECT", token.serialize()) @@ -95,7 +95,7 @@ internal class IntrospectTest { "iss" to issuerUrl, "client_id" to "yolo", "token_type" to "token", - "sub" to "foo" + "sub" to "foo", ) val token = rs384TokenProvider.jwt(claims) val request = request("$issuerUrl$INTROSPECT", token.serialize()) @@ -133,11 +133,11 @@ internal class IntrospectTest { "Accept", "application/json", "Content-Type", - "application/x-www-form-urlencoded" + "application/x-www-form-urlencoded", ), method = "POST", url.toHttpUrl(), - body = token?.let { "token=$it&token_type_hint=access_token" } + body = token?.let { "token=$it&token_type_hint=access_token" }, ) } } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/login/LoginRequestHandlerTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/login/LoginRequestHandlerTest.kt index ebc0d10a..c0df1674 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/login/LoginRequestHandlerTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/login/LoginRequestHandlerTest.kt @@ -37,6 +37,6 @@ internal class LoginRequestHandlerTest { originalUrl = "http://localhost/issuer1/login".toHttpUrl(), headers = Headers.headersOf(), method = "POST", - body = body + body = body, ) } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/server/OAuth2HttpServerTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/server/OAuth2HttpServerTest.kt index 498d95d2..9755f246 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/server/OAuth2HttpServerTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/server/OAuth2HttpServerTest.kt @@ -59,8 +59,8 @@ internal class OAuth2HttpServerTest { keyPassword = "", keystoreFile = File("src/test/resources/localhost.p12"), keystorePassword = "", - keystoreType = SslKeystore.KeyStoreType.PKCS12 - ) + keystoreType = SslKeystore.KeyStoreType.PKCS12, + ), ) NettyWrapper(ssl).start(requestHandler).shouldServeRequests(ssl).stop() } @@ -87,7 +87,7 @@ internal class OAuth2HttpServerTest { client.get( this.url("/header"), - Headers.headersOf("header1", "headervalue1") + Headers.headersOf("header1", "headervalue1"), ).body?.string() shouldBe "headermatch" client.get(this.url("/1/2")).body?.string() shouldBe "pathmatch" @@ -102,6 +102,6 @@ internal class OAuth2HttpServerTest { private fun ok(body: String) = OAuth2HttpResponse( status = 200, - body = body + body = body, ) } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/testutils/Grant.kt b/src/test/kotlin/no/nav/security/mock/oauth2/testutils/Grant.kt index eed82f50..243951c6 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/testutils/Grant.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/testutils/Grant.kt @@ -13,7 +13,7 @@ fun HttpUrl.authenticationRequest( responseMode: String = "query", state: String = "1234", nonce: String = "5678", - pkce: Pkce? = null + pkce: Pkce? = null, ): HttpUrl = newBuilder() .addQueryParameter("client_id", clientId) .addQueryParameter("response_type", responseType) @@ -32,7 +32,7 @@ fun HttpUrl.authenticationRequest( data class Pkce( val verifier: CodeVerifier = CodeVerifier(), - val method: CodeChallengeMethod = CodeChallengeMethod.S256 + val method: CodeChallengeMethod = CodeChallengeMethod.S256, ) { val challenge: CodeChallenge = CodeChallenge.compute(method, verifier) } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/testutils/Http.kt b/src/test/kotlin/no/nav/security/mock/oauth2/testutils/Http.kt index fbe6c6f6..a00216e4 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/testutils/Http.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/testutils/Http.kt @@ -2,7 +2,6 @@ package no.nav.security.mock.oauth2.testutils import com.fasterxml.jackson.module.kotlin.jacksonObjectMapper import com.fasterxml.jackson.module.kotlin.readValue -import java.net.URLEncoder import no.nav.security.mock.oauth2.extensions.keyValuesToMap import okhttp3.Credentials import okhttp3.FormBody @@ -11,6 +10,7 @@ import okhttp3.HttpUrl import okhttp3.OkHttpClient import okhttp3.Request import okhttp3.Response +import java.net.URLEncoder import java.security.KeyStore import javax.net.ssl.SSLContext import javax.net.ssl.TrustManagerFactory @@ -18,7 +18,7 @@ import javax.net.ssl.X509TrustManager fun Response.toTokenResponse(): ParsedTokenResponse = ParsedTokenResponse( this.code, - checkNotNull(this.body).string() + checkNotNull(this.body).string(), ) inline fun Response.parse(): T = jacksonObjectMapper().readValue(checkNotNull(body?.string())) @@ -49,61 +49,61 @@ fun OkHttpClient.tokenRequest(url: HttpUrl, parameters: Map): Re fun OkHttpClient.tokenRequest( url: HttpUrl, headers: Headers, - parameters: Map + parameters: Map, ): Response = this.newCall( Request.Builder().post( url = url, headers = headers, - parameters = parameters - ) + parameters = parameters, + ), ).execute() fun OkHttpClient.tokenRequest( url: HttpUrl, basicAuth: Pair, - parameters: Map + parameters: Map, ): Response = tokenRequest( url, Headers.headersOf("Authorization", Credentials.basic(basicAuth.first, basicAuth.second)), - parameters + parameters, ) fun OkHttpClient.post( url: HttpUrl, - parameters: Map + parameters: Map, ): Response = this.newCall( Request.Builder().post( url = url, headers = Headers.headersOf(), - parameters = parameters - ) + parameters = parameters, + ), ).execute() fun OkHttpClient.get( url: HttpUrl, headers: Headers = Headers.headersOf(), - parameters: Map = emptyMap() + parameters: Map = emptyMap(), ): Response = this.newCall( Request.Builder().get( url, headers, - parameters - ) + parameters, + ), ).execute() fun OkHttpClient.options( url: HttpUrl, - headers: Headers = Headers.headersOf() + headers: Headers = Headers.headersOf(), ): Response = this.newCall( Request.Builder().options( url, - headers - ) + headers, + ), ).execute() fun Request.Builder.get(url: HttpUrl, headers: Headers = Headers.headersOf(), parameters: Map = emptyMap()) = diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/testutils/Token.kt b/src/test/kotlin/no/nav/security/mock/oauth2/testutils/Token.kt index 31f9b510..170f5905 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/testutils/Token.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/testutils/Token.kt @@ -54,7 +54,7 @@ object SubjectTokenType { data class ParsedTokenResponse( val status: Int, - val body: String + val body: String, ) { private val tokenResponse: OAuth2TokenResponse = jacksonObjectMapper().readValue(body) val tokenType = tokenResponse.tokenType @@ -88,7 +88,7 @@ infix fun ParsedTokenResponse.shouldBeValidFor(type: GrantType) { fun verifyWith( issuerId: String, server: MockOAuth2Server, - requiredClaims: List = listOf("sub", "iss", "iat", "exp", "aud") + requiredClaims: List = listOf("sub", "iss", "iat", "exp", "aud"), ) = object : Matcher { override fun test(value: SignedJWT): MatcherResult { return try { @@ -98,7 +98,7 @@ fun verifyWith( { "should not happen, famous last words" }, { "JWT should not verify, expected exception." - } + }, ) } catch (e: Exception) { MatcherResult( @@ -106,7 +106,7 @@ fun verifyWith( { "${e.message}" }, { "JWT should not verify, expected exception." - } + }, ) } } @@ -118,13 +118,13 @@ fun nimbusTokenRequest(clientId: String, vararg formParams: Pair "Content-Type", "application/x-www-form-urlencoded", "Authorization", - "Basic ${Base64.getEncoder().encodeToString("$clientId:clientSecret".toByteArray())}" + "Basic ${Base64.getEncoder().encodeToString("$clientId:clientSecret".toByteArray())}", ), "POST", "http://localhost/token".toHttpUrl(), formParams.joinToString("&") { "${it.first}=${it.second}" - } + }, ).asNimbusTokenRequest() fun String.asJwt(): SignedJWT = SignedJWT.parse(this) @@ -137,7 +137,7 @@ val SignedJWT.claims: Map get() = jwtClaimsSet.claims fun SignedJWT.verifyWith( issuer: HttpUrl, jwkSetUri: HttpUrl, - requiredClaims: List = listOf("sub", "iss", "iat", "exp", "aud") + requiredClaims: List = listOf("sub", "iss", "iat", "exp", "aud"), ): JWTClaimsSet { return DefaultJWTProcessor() .apply { @@ -146,7 +146,7 @@ fun SignedJWT.verifyWith( JWTClaimsSet.Builder() .issuer(issuer.toString()) .build(), - HashSet(requiredClaims) + HashSet(requiredClaims), ) }.process(this, null) } @@ -156,7 +156,7 @@ fun clientAssertion( audience: URL, rsaKey: RSAKey = generateRsaKey(), lifetime: Long = 119, - issueTime: Instant = Instant.now() + issueTime: Instant = Instant.now(), ): SignedJWT = JWTClaimsSet.Builder() .issuer(clientId) @@ -174,7 +174,7 @@ fun JWTClaimsSet.sign(rsaKey: RSAKey = generateRsaKey()): SignedJWT = JWSHeader.Builder(JWSAlgorithm.RS256) .keyID(rsaKey.keyID) .type(JOSEObjectType.JWT).build(), - this + this, ).apply { sign(RSASSASigner(rsaKey.toPrivateKey())) } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/token/KeyGeneratorTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/token/KeyGeneratorTest.kt index c6141afe..27bf8ab9 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/token/KeyGeneratorTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/token/KeyGeneratorTest.kt @@ -88,6 +88,6 @@ class KeyGeneratorTest { .subject("test") .issueTime(Date.from(Instant.now())) .expirationTime(Date.from(Instant.now().plusSeconds(20))) - .build() + .build(), ) } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/token/KeyProviderTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/token/KeyProviderTest.kt index 58840fb2..052218e2 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/token/KeyProviderTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/token/KeyProviderTest.kt @@ -45,7 +45,7 @@ internal class KeyProviderTest { fun `signingKey should return a EC key from initial keys file until deque is empty`() { val provider = KeyProvider( initialKeys = KeyProvider.keysFromFile("/mock-oauth2-server-keys-ec.json"), - algorithm = "ES256" + algorithm = "ES256", ) val initialPublicKeys = initialEcPublicKeys() diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenCallbackTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenCallbackTest.kt index a3ab652e..bfbb322e 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenCallbackTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenCallbackTest.kt @@ -23,8 +23,8 @@ internal class OAuth2TokenCallbackTest { claims = mapOf( "sub" to "subByScope1", "aud" to listOf("audByScope1"), - "custom" to "custom1" - ) + "custom" to "custom1", + ), ), RequestMapping( requestParam = "scope", @@ -33,19 +33,19 @@ internal class OAuth2TokenCallbackTest { claims = mapOf( "sub" to "subByScope2", "aud" to listOf("audByScope2"), - "custom" to "custom2" - ) + "custom" to "custom2", + ), ), RequestMapping( requestParam = "grant_type", match = "*", claims = mapOf( "sub" to "defaultSub", - "aud" to listOf("defaultAud") - ) - ) + "aud" to listOf("defaultAud"), + ), + ), ), - tokenExpiry = 120 + tokenExpiry = 120, ) @Test @@ -113,7 +113,7 @@ internal class OAuth2TokenCallbackTest { clientId, "grant_type" to "authorization_code", "code" to "123", - *formParams + *formParams, ) private fun clientCredentialsRequest(vararg formParams: Pair) = diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenProviderECTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenProviderECTest.kt index ce86e2ae..affaef57 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenProviderECTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenProviderECTest.kt @@ -22,8 +22,8 @@ internal class OAuth2TokenProviderECTest { private val tokenProvider = OAuth2TokenProvider( KeyProvider( emptyList(), - JWSAlgorithm.ES256.name - ) + JWSAlgorithm.ES256.name, + ), ) @Test @@ -49,8 +49,8 @@ internal class OAuth2TokenProviderECTest { "iss" to "http://initialissuer", "sub" to "initialsubject", "aud" to "initialaudience", - "initialclaim" to "initialclaim" - ) + "initialclaim" to "initialclaim", + ), ) tokenProvider.exchangeAccessToken( @@ -58,16 +58,16 @@ internal class OAuth2TokenProviderECTest { "myclient", "grant_type" to GrantType.JWT_BEARER.value, "scope" to "scope1", - "assertion" to initialToken.serialize() + "assertion" to initialToken.serialize(), ), issuerUrl = "http://default_if_not_overridden".toHttpUrl(), claimsSet = initialToken.jwtClaimsSet, oAuth2TokenCallback = DefaultOAuth2TokenCallback( claims = mapOf( "extraclaim" to "extra", - "iss" to "http://overrideissuer" - ) - ) + "iss" to "http://overrideissuer", + ), + ), ).jwtClaimsSet.asClue { it.issuer shouldBe "http://overrideissuer" it.subject shouldBe "initialsubject" @@ -101,9 +101,9 @@ internal class OAuth2TokenProviderECTest { tokenRequest = nimbusTokenRequest( "client1", "grant_type" to "authorization_code", - "code" to "123" + "code" to "123", ), issuerUrl = issuerUrl.toHttpUrl(), - oAuth2TokenCallback = DefaultOAuth2TokenCallback() + oAuth2TokenCallback = DefaultOAuth2TokenCallback(), ) } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenProviderRSATest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenProviderRSATest.kt index eeb4027f..e22bcb4a 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenProviderRSATest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/token/OAuth2TokenProviderRSATest.kt @@ -43,8 +43,8 @@ internal class OAuth2TokenProviderRSATest { "iss" to "http://initialissuer", "sub" to "initialsubject", "aud" to "initialaudience", - "initialclaim" to "initialclaim" - ) + "initialclaim" to "initialclaim", + ), ) tokenProvider.exchangeAccessToken( @@ -52,16 +52,16 @@ internal class OAuth2TokenProviderRSATest { "myclient", "grant_type" to GrantType.JWT_BEARER.value, "scope" to "scope1", - "assertion" to initialToken.serialize() + "assertion" to initialToken.serialize(), ), issuerUrl = "http://default_if_not_overridden".toHttpUrl(), claimsSet = initialToken.jwtClaimsSet, oAuth2TokenCallback = DefaultOAuth2TokenCallback( claims = mapOf( "extraclaim" to "extra", - "iss" to "http://overrideissuer" - ) - ) + "iss" to "http://overrideissuer", + ), + ), ).jwtClaimsSet.asClue { it.issuer shouldBe "http://overrideissuer" it.subject shouldBe "initialsubject" @@ -95,9 +95,9 @@ internal class OAuth2TokenProviderRSATest { tokenRequest = nimbusTokenRequest( "client1", "grant_type" to "authorization_code", - "code" to "123" + "code" to "123", ), issuerUrl = issuerUrl.toHttpUrl(), - oAuth2TokenCallback = DefaultOAuth2TokenCallback() + oAuth2TokenCallback = DefaultOAuth2TokenCallback(), ) } diff --git a/src/test/kotlin/no/nav/security/mock/oauth2/userinfo/UserInfoTest.kt b/src/test/kotlin/no/nav/security/mock/oauth2/userinfo/UserInfoTest.kt index 9d634e99..d65647a4 100644 --- a/src/test/kotlin/no/nav/security/mock/oauth2/userinfo/UserInfoTest.kt +++ b/src/test/kotlin/no/nav/security/mock/oauth2/userinfo/UserInfoTest.kt @@ -27,7 +27,7 @@ internal class UserInfoTest { val claims = mapOf( "iss" to issuerUrl, "sub" to "foo", - "extra" to "bar" + "extra" to "bar", ) val bearerToken = tokenProvider.jwt(claims) val request = request("$issuerUrl$USER_INFO", bearerToken.serialize()) @@ -45,7 +45,7 @@ internal class UserInfoTest { val claims = mapOf( "iss" to issuerUrl, "sub" to "foo", - "extra" to "bar" + "extra" to "bar", ) val bearerToken = tokenProvider.jwt(claims) val request = request("$issuerUrl$USER_INFO", bearerToken.serialize()) @@ -97,7 +97,7 @@ internal class UserInfoTest { bearerToken?.let { Headers.headersOf("Authorization", "Bearer $it") } ?: Headers.headersOf(), "GET", url.toHttpUrl(), - null + null, ) } } From d8ffe01f3836d6e23423979e20be7fdeea915307 Mon Sep 17 00:00:00 2001 From: ybelMekk Date: Mon, 3 Jul 2023 11:05:21 +0200 Subject: [PATCH 2/5] bump(mock): johnrengelman shadow --- build.gradle.kts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build.gradle.kts b/build.gradle.kts index d63b3fa1..111dc24c 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -27,7 +27,7 @@ plugins { id("com.github.ben-manes.versions") version "0.47.0" id("org.jmailen.kotlinter") version "3.15.0" id("com.google.cloud.tools.jib") version "3.3.1" - id("com.github.johnrengelman.shadow") version "7.1.2" + id("com.github.johnrengelman.shadow") version "8.1.1" id("net.researchgate.release") version "3.0.2" id("io.github.gradle-nexus.publish-plugin") version "1.3.0" id("org.jetbrains.dokka") version "1.8.20" From 366721ef1427697c30bbe2b921cfbdfcd4d0d2a0 Mon Sep 17 00:00:00 2001 From: ybelMekk Date: Mon, 3 Jul 2023 11:07:42 +0200 Subject: [PATCH 3/5] bump(mock): jib tool --- build.gradle.kts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build.gradle.kts b/build.gradle.kts index 111dc24c..8cddf550 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -26,7 +26,7 @@ plugins { id("se.patrikerdes.use-latest-versions") version "0.2.18" id("com.github.ben-manes.versions") version "0.47.0" id("org.jmailen.kotlinter") version "3.15.0" - id("com.google.cloud.tools.jib") version "3.3.1" + id("com.google.cloud.tools.jib") version "3.3.2" id("com.github.johnrengelman.shadow") version "8.1.1" id("net.researchgate.release") version "3.0.2" id("io.github.gradle-nexus.publish-plugin") version "1.3.0" From 6cc02eba9cb59d7092fff8018c654f300ad32676 Mon Sep 17 00:00:00 2001 From: ybelMekk Date: Mon, 3 Jul 2023 11:10:53 +0200 Subject: [PATCH 4/5] bump(mock): nimbus sdk --- build.gradle.kts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build.gradle.kts b/build.gradle.kts index 8cddf550..8868a151 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -4,7 +4,7 @@ import com.github.benmanes.gradle.versions.updates.DependencyUpdatesTask val assertjVersion = "3.24.2" val kotlinLoggingVersion = "3.0.5" val logbackVersion = "1.4.8" -val nimbusSdkVersion = "10.9.2" +val nimbusSdkVersion = "10.10.1" val mockWebServerVersion = "4.11.0" val jacksonVersion = "2.15.2" val nettyVersion = "4.1.94.Final" From 5cdab516425853bd938e22cc2ec244651ef6bc71 Mon Sep 17 00:00:00 2001 From: ybelMekk Date: Mon, 3 Jul 2023 11:14:09 +0200 Subject: [PATCH 5/5] bump(mock): ktor --- build.gradle.kts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build.gradle.kts b/build.gradle.kts index 8868a151..22aea49e 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -15,7 +15,7 @@ val kotestVersion = "5.6.2" val bouncyCastleVersion = "1.70" val springBootVersion = "2.7.5" val reactorTestVersion = "3.4.24" -val ktorVersion = "2.3.1" +val ktorVersion = "2.3.2" val mavenRepoBaseUrl = "https://oss.sonatype.org" val mainClassKt = "no.nav.security.mock.oauth2.StandaloneMockOAuth2ServerKt"