From 9dbaafed6582a31c7174a7e48e49c159cabd0a4c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Olivier=20Ch=C3=A9dru?= Date: Mon, 19 Jun 2023 18:11:16 +0200 Subject: [PATCH] Upgrade to Dropwizard 4 (#91) --- .github/workflows/build.yml | 2 +- README.md | 4 +-- pom.xml | 35 +++++++++++++----- .../authentication/DontRefreshSession.java | 11 +++--- .../DontRefreshSessionFilter.java | 13 +++---- .../authentication/JwtCookieAuthBundle.java | 19 ++++------ .../JwtCookieAuthConfiguration.java | 4 +-- .../JwtCookieAuthRequestFilter.java | 19 +++++----- .../JwtCookieAuthResponseFilter.java | 6 ++-- .../authentication/JwtCookiePrincipal.java | 4 ++- .../JwtCookieSecurityContext.java | 11 +++--- .../JwtCookieAuthenticationTest.java | 36 +++++++++++++++---- .../authentication/TestApplication.java | 12 +++---- .../cookie/authentication/TestResource.java | 14 +++----- 14 files changed, 114 insertions(+), 76 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 2f097fc..bd81340 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -13,7 +13,7 @@ jobs: - uses: actions/setup-java@v3 with: distribution: 'zulu' - java-version: '8' + java-version: '11' - name: maven build env: GPG_SECRET_KEY: ${{ secrets.GPG_SECRET_KEY }} diff --git a/README.md b/README.md index ebb1e0a..a15b059 100644 --- a/README.md +++ b/README.md @@ -4,7 +4,7 @@ [![Javadoc](https://www.javadoc.io/badge/org.dhatim/dropwizard-jwt-cookie-authentication.svg)](http://www.javadoc.io/doc/org.dhatim/dropwizard-jwt-cookie-authentication) [![Mentioned in Awesome Dropwizard](https://awesome.re/mentioned-badge.svg)](https://github.com/stve/awesome-dropwizard) -**Please note version 4 requires Dropwizard 2.** +**Please note version 5 requires Java 11 and Dropwizard 4.** # dropwizard-jwt-cookie-authentication @@ -26,7 +26,7 @@ Add the dropwizard-jwt-cookie-authentication library as a dependency to your `po org.dhatim dropwizard-jwt-cookie-authentication - 4.5.0 + 5.0.0 ``` diff --git a/pom.xml b/pom.xml index 783c85d..c709c20 100644 --- a/pom.xml +++ b/pom.xml @@ -1,5 +1,6 @@ - + 4.0.0 org.dhatim @@ -25,7 +26,8 @@ scm:git:git@github.com:dhatim/dropwizard-jwt-cookie-authentication.git - scm:git:git@github.com:dhatim/dropwizard-jwt-cookie-authentication.git + scm:git:git@github.com:dhatim/dropwizard-jwt-cookie-authentication.git + git@github.com:dhatim/dropwizard-jwt-cookie-authentication.git @@ -33,7 +35,6 @@ 1.8 1.8 UTF-8 - 2.1.6 0.11.5 false @@ -56,16 +57,30 @@ + + + + io.dropwizard + dropwizard-bom + 4.0.0 + pom + import + + + + + jakarta.annotation + jakarta.annotation-api + 2.1.1 + io.dropwizard dropwizard-core - ${dropwizard.version} io.dropwizard dropwizard-auth - ${dropwizard.version} io.jsonwebtoken @@ -84,17 +99,21 @@ org.junit.jupiter - junit-jupiter-engine + junit-jupiter-api 5.9.3 test io.dropwizard dropwizard-testing - ${dropwizard.version} test - + + io.dropwizard + dropwizard-client + test + + diff --git a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/DontRefreshSession.java b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/DontRefreshSession.java index df8c16c..eb442e3 100644 --- a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/DontRefreshSession.java +++ b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/DontRefreshSession.java @@ -1,12 +1,12 @@ /** * Copyright 2023 Dhatim - * + *

* Licensed under the Apache License, Version 2.0 (the "License"); you may not * use this file except in compliance with the License. You may obtain a copy of * the License at - * + *

* http://www.apache.org/licenses/LICENSE-2.0 - * + *

* Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the @@ -15,11 +15,12 @@ */ package org.dhatim.dropwizard.jwt.cookie.authentication; -import java.lang.annotation.Retention; +import jakarta.ws.rs.NameBinding; + import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; -import javax.ws.rs.NameBinding; /** * An annotation that can be used to avoid reseting the session TTL when an API is called diff --git a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/DontRefreshSessionFilter.java b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/DontRefreshSessionFilter.java index 4beb877..4e22864 100644 --- a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/DontRefreshSessionFilter.java +++ b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/DontRefreshSessionFilter.java @@ -1,12 +1,12 @@ /** * Copyright 2023 Dhatim - * + *

* Licensed under the Apache License, Version 2.0 (the "License"); you may not * use this file except in compliance with the License. You may obtain a copy of * the License at - * + *

* http://www.apache.org/licenses/LICENSE-2.0 - * + *

* Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the @@ -15,12 +15,13 @@ */ package org.dhatim.dropwizard.jwt.cookie.authentication; +import jakarta.ws.rs.container.ContainerRequestContext; +import jakarta.ws.rs.container.ContainerRequestFilter; + import java.io.IOException; -import javax.ws.rs.container.ContainerRequestContext; -import javax.ws.rs.container.ContainerRequestFilter; @DontRefreshSession -public class DontRefreshSessionFilter implements ContainerRequestFilter{ +public class DontRefreshSessionFilter implements ContainerRequestFilter { public static String DONT_REFRESH_SESSION_PROPERTY = "dontRefreshSession"; diff --git a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthBundle.java b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthBundle.java index 2ea46a8..36db930 100644 --- a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthBundle.java +++ b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthBundle.java @@ -18,25 +18,20 @@ import com.fasterxml.jackson.databind.module.SimpleModule; import com.google.common.hash.Hashing; import com.google.common.primitives.Ints; -import io.dropwizard.Configuration; -import io.dropwizard.ConfiguredBundle; -import io.dropwizard.auth.AuthDynamicFeature; -import io.dropwizard.auth.AuthFilter; -import io.dropwizard.auth.AuthValueFactoryProvider; -import io.dropwizard.auth.Authorizer; -import io.dropwizard.auth.DefaultUnauthorizedHandler; -import io.dropwizard.auth.UnauthorizedHandler; +import io.dropwizard.auth.*; +import io.dropwizard.core.Configuration; +import io.dropwizard.core.ConfiguredBundle; +import io.dropwizard.core.setup.Bootstrap; +import io.dropwizard.core.setup.Environment; import io.dropwizard.jersey.setup.JerseyEnvironment; -import io.dropwizard.setup.Bootstrap; -import io.dropwizard.setup.Environment; import io.jsonwebtoken.Claims; import io.jsonwebtoken.SignatureAlgorithm; import io.jsonwebtoken.impl.DefaultClaims; +import jakarta.ws.rs.container.ContainerResponseFilter; import org.glassfish.jersey.server.filter.RolesAllowedDynamicFeature; import javax.crypto.KeyGenerator; import javax.crypto.spec.SecretKeySpec; -import javax.ws.rs.container.ContainerResponseFilter; import java.nio.charset.StandardCharsets; import java.security.Key; import java.security.NoSuchAlgorithmException; @@ -161,7 +156,7 @@ public AuthFilter getAuthRequestFilter(Key key, String cookieName) { .setCookieName(cookieName) .setAuthenticator(new JwtCookiePrincipalAuthenticator(key, deserializer)) .setPrefix(JWT_COOKIE_PREFIX) - .setAuthorizer((Authorizer

) (P::isInRole)) + .setAuthorizer((Authorizer

) (principal, role, requestContext) -> principal.isInRole(role)) .setUnauthorizedHandler(unauthorizedHandler) .buildAuthFilter(); } diff --git a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthConfiguration.java b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthConfiguration.java index 69ba9c5..bdfc261 100644 --- a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthConfiguration.java +++ b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthConfiguration.java @@ -15,8 +15,8 @@ */ package org.dhatim.dropwizard.jwt.cookie.authentication; -import javax.annotation.Nullable; -import javax.validation.constraints.NotEmpty; +import jakarta.annotation.Nullable; +import jakarta.validation.constraints.NotEmpty; import static org.dhatim.dropwizard.jwt.cookie.authentication.JwtCookieAuthBundle.JWT_COOKIE_DEFAULT_NAME; diff --git a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthRequestFilter.java b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthRequestFilter.java index 254330b..074f245 100644 --- a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthRequestFilter.java +++ b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthRequestFilter.java @@ -1,12 +1,12 @@ /** * Copyright 2023 Dhatim - * + *

* Licensed under the Apache License, Version 2.0 (the "License"); you may not * use this file except in compliance with the License. You may obtain a copy of * the License at - * + *

* http://www.apache.org/licenses/LICENSE-2.0 - * + *

* Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the @@ -17,14 +17,15 @@ import io.dropwizard.auth.AuthFilter; import io.dropwizard.auth.AuthenticationException; +import jakarta.annotation.Priority; +import jakarta.ws.rs.InternalServerErrorException; +import jakarta.ws.rs.Priorities; +import jakarta.ws.rs.container.ContainerRequestContext; +import jakarta.ws.rs.core.Cookie; + import java.io.IOException; import java.util.Objects; import java.util.Optional; -import javax.annotation.Priority; -import javax.ws.rs.InternalServerErrorException; -import javax.ws.rs.Priorities; -import javax.ws.rs.container.ContainerRequestContext; -import javax.ws.rs.core.Cookie; @Priority(Priorities.AUTHENTICATION) class JwtCookieAuthRequestFilter

extends AuthFilter { @@ -66,7 +67,7 @@ public Builder setCookieName(String cookieName) { } @Override - protected JwtCookieAuthRequestFilter

newInstance() { + protected JwtCookieAuthRequestFilter

newInstance() { return new JwtCookieAuthRequestFilter(Objects.requireNonNull(cookieName, "cookieName is not set")); } } diff --git a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthResponseFilter.java b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthResponseFilter.java index 4f0ef58..444e773 100644 --- a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthResponseFilter.java +++ b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthResponseFilter.java @@ -18,10 +18,10 @@ import io.jsonwebtoken.Claims; import io.jsonwebtoken.Jwts; import io.jsonwebtoken.SignatureAlgorithm; +import jakarta.ws.rs.container.ContainerRequestContext; +import jakarta.ws.rs.container.ContainerResponseContext; +import jakarta.ws.rs.container.ContainerResponseFilter; -import javax.ws.rs.container.ContainerRequestContext; -import javax.ws.rs.container.ContainerResponseContext; -import javax.ws.rs.container.ContainerResponseFilter; import java.io.IOException; import java.security.Key; import java.security.Principal; diff --git a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookiePrincipal.java b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookiePrincipal.java index c056594..5e500df 100644 --- a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookiePrincipal.java +++ b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookiePrincipal.java @@ -15,8 +15,10 @@ */ package org.dhatim.dropwizard.jwt.cookie.authentication; +import jakarta.ws.rs.container.ContainerRequestContext; +import org.checkerframework.checker.nullness.qual.Nullable; + import java.security.Principal; -import javax.ws.rs.container.ContainerRequestContext; /** * A principal persisted in JWT cookies diff --git a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieSecurityContext.java b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieSecurityContext.java index 29710ce..e0180f0 100644 --- a/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieSecurityContext.java +++ b/src/main/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieSecurityContext.java @@ -1,12 +1,12 @@ /** * Copyright 2023 Dhatim - * + *

* Licensed under the Apache License, Version 2.0 (the "License"); you may not * use this file except in compliance with the License. You may obtain a copy of * the License at - * + *

* http://www.apache.org/licenses/LICENSE-2.0 - * + *

* Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the @@ -15,14 +15,15 @@ */ package org.dhatim.dropwizard.jwt.cookie.authentication; +import jakarta.ws.rs.core.SecurityContext; + import java.security.Principal; import java.util.Optional; -import javax.ws.rs.core.SecurityContext; /** * Security context set after a JWT cookie authentication */ -class JwtCookieSecurityContext implements SecurityContext{ +class JwtCookieSecurityContext implements SecurityContext { private final JwtCookiePrincipal subject; private final boolean secure; diff --git a/src/test/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthenticationTest.java b/src/test/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthenticationTest.java index 138c910..0c9aad4 100644 --- a/src/test/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthenticationTest.java +++ b/src/test/java/org/dhatim/dropwizard/jwt/cookie/authentication/JwtCookieAuthenticationTest.java @@ -15,19 +15,25 @@ */ package org.dhatim.dropwizard.jwt.cookie.authentication; -import io.dropwizard.Configuration; +import io.dropwizard.client.HttpClientBuilder; +import io.dropwizard.client.JerseyClientBuilder; +import io.dropwizard.core.Configuration; +import io.dropwizard.jackson.Jackson; import io.dropwizard.testing.junit5.DropwizardAppExtension; import io.dropwizard.testing.junit5.DropwizardExtensionsSupport; import io.jsonwebtoken.lang.Strings; +import jakarta.ws.rs.client.Client; +import jakarta.ws.rs.client.Entity; +import jakarta.ws.rs.client.WebTarget; +import jakarta.ws.rs.core.MediaType; +import jakarta.ws.rs.core.NewCookie; +import jakarta.ws.rs.core.Response; +import org.apache.hc.client5.http.cookie.BasicCookieStore; import org.junit.jupiter.api.Assertions; +import org.junit.jupiter.api.BeforeAll; import org.junit.jupiter.api.Test; import org.junit.jupiter.api.extension.ExtendWith; -import javax.ws.rs.client.Entity; -import javax.ws.rs.client.WebTarget; -import javax.ws.rs.core.MediaType; -import javax.ws.rs.core.NewCookie; -import javax.ws.rs.core.Response; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; @@ -41,10 +47,26 @@ public class JwtCookieAuthenticationTest { private static final DropwizardAppExtension EXT = new DropwizardAppExtension(TestApplication.class); + + private static Client CLIENT; + + @BeforeAll + protected static void createClient() { + JerseyClientBuilder builder = new JerseyClientBuilder(EXT.getEnvironment()); + builder.using(Jackson.newObjectMapper()); + builder.setApacheHttpClientBuilder(new HttpClientBuilder(EXT.getEnvironment()) { + @Override + protected org.apache.hc.client5.http.impl.classic.HttpClientBuilder customizeBuilder(org.apache.hc.client5.http.impl.classic.HttpClientBuilder builder) { + return super.customizeBuilder(builder).setDefaultCookieStore(new BasicCookieStore()); + } + }); + CLIENT = builder.build("client"); + } + private static final String COOKIE_NAME = "sessionToken"; private WebTarget getTarget() { - return EXT.client().target("http://localhost:" + EXT.getLocalPort() + "/application").path("principal"); + return CLIENT.target("http://localhost:" + EXT.getLocalPort() + "/application/principal"); } @Test diff --git a/src/test/java/org/dhatim/dropwizard/jwt/cookie/authentication/TestApplication.java b/src/test/java/org/dhatim/dropwizard/jwt/cookie/authentication/TestApplication.java index d8da2e2..cf9f5be 100644 --- a/src/test/java/org/dhatim/dropwizard/jwt/cookie/authentication/TestApplication.java +++ b/src/test/java/org/dhatim/dropwizard/jwt/cookie/authentication/TestApplication.java @@ -1,13 +1,13 @@ package org.dhatim.dropwizard.jwt.cookie.authentication; import com.codahale.metrics.health.HealthCheck; -import io.dropwizard.Application; -import io.dropwizard.Configuration; +import io.dropwizard.core.Application; +import io.dropwizard.core.Configuration; +import io.dropwizard.core.server.SimpleServerFactory; +import io.dropwizard.core.setup.Bootstrap; +import io.dropwizard.core.setup.Environment; import io.dropwizard.jetty.HttpConnectorFactory; -import io.dropwizard.logging.DefaultLoggingFactory; -import io.dropwizard.server.SimpleServerFactory; -import io.dropwizard.setup.Bootstrap; -import io.dropwizard.setup.Environment; +import io.dropwizard.logging.common.DefaultLoggingFactory; public class TestApplication extends Application { diff --git a/src/test/java/org/dhatim/dropwizard/jwt/cookie/authentication/TestResource.java b/src/test/java/org/dhatim/dropwizard/jwt/cookie/authentication/TestResource.java index 06521a6..639a884 100644 --- a/src/test/java/org/dhatim/dropwizard/jwt/cookie/authentication/TestResource.java +++ b/src/test/java/org/dhatim/dropwizard/jwt/cookie/authentication/TestResource.java @@ -16,15 +16,11 @@ package org.dhatim.dropwizard.jwt.cookie.authentication; import io.dropwizard.auth.Auth; -import javax.annotation.security.RolesAllowed; -import javax.ws.rs.Consumes; -import javax.ws.rs.GET; -import javax.ws.rs.POST; -import javax.ws.rs.Path; -import javax.ws.rs.Produces; -import javax.ws.rs.container.ContainerRequestContext; -import javax.ws.rs.core.Context; -import javax.ws.rs.core.MediaType; +import jakarta.annotation.security.RolesAllowed; +import jakarta.ws.rs.*; +import jakarta.ws.rs.container.ContainerRequestContext; +import jakarta.ws.rs.core.Context; +import jakarta.ws.rs.core.MediaType; @Path("principal") public class TestResource {