diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index d4098431cd..5278e6faf8 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -320,9 +320,9 @@ jobs: - name: Run Quarkus tests run: | echo '::group::Compiling testsuite' - mvn clean install -nsu -B -Pquarkus,auth-server-quarkus -DskipTests -f testsuite/pom.xml + mvn clean install -nsu -B -Pauth-server-quarkus -DskipTests -f testsuite/pom.xml echo '::endgroup::' - mvn clean install -nsu -B -Pquarkus,auth-server-quarkus -f testsuite/integration-arquillian/tests/base/pom.xml -Dtest='!org.keycloak.testsuite.adapter.**,!**.crossdc.**,!**.cluster.**' | misc/log/trimmer.sh + mvn clean install -nsu -B -Pauth-server-quarkus -f testsuite/integration-arquillian/tests/base/pom.xml -Dtest='!org.keycloak.testsuite.adapter.**,!**.crossdc.**,!**.cluster.**' | misc/log/trimmer.sh TEST_RESULT=${PIPESTATUS[0]} find . -path '*/target/surefire-reports/*.xml' | zip reports-base-unit-tests.zip -@ exit $TEST_RESULT @@ -365,9 +365,9 @@ jobs: - name: Run Quarkus adapter tests run: | echo '::group::Compiling testsuite' - mvn clean install -nsu -B -Pquarkus,auth-server-quarkus -DskipTests -f testsuite/pom.xml + mvn clean install -nsu -B -Pauth-server-quarkus -DskipTests -f testsuite/pom.xml echo '::endgroup::' - mvn clean install -nsu -B -Pquarkus,auth-server-quarkus -f testsuite/integration-arquillian/tests/base/pom.xml -Dtest=org.keycloak.testsuite.adapter.** | misc/log/trimmer.sh + mvn clean install -nsu -B -Pauth-server-quarkus -f testsuite/integration-arquillian/tests/base/pom.xml -Dtest=org.keycloak.testsuite.adapter.** | misc/log/trimmer.sh TEST_RESULT=${PIPESTATUS[0]} find . -path '*/target/surefire-reports/*.xml' | zip reports-adapter-tests.zip -@ exit $TEST_RESULT @@ -410,7 +410,7 @@ jobs: - name: Run Quarkus cluster tests run: | echo '::group::Compiling testsuite' - mvn clean install -nsu -B -Pquarkus,auth-server-quarkus -DskipTests -f testsuite/pom.xml + mvn clean install -nsu -B -Pauth-server-quarkus -DskipTests -f testsuite/pom.xml echo '::endgroup::' mvn clean install -nsu -B -Pauth-server-cluster-quarkus -Dsession.cache.owners=2 -Dtest=**.cluster.** -f testsuite/integration-arquillian/pom.xml | misc/log/trimmer.sh TEST_RESULT=${PIPESTATUS[0]} diff --git a/quarkus/deployment/pom.xml b/quarkus/deployment/pom.xml index b5da3bcfbe..e7c7668b7e 100644 --- a/quarkus/deployment/pom.xml +++ b/quarkus/deployment/pom.xml @@ -108,6 +108,11 @@ maven-surefire-plugin + + + org.jboss.logmanager.LogManager + + diff --git a/quarkus/pom.xml b/quarkus/pom.xml index e51f4b1a8c..e4770c4b2e 100755 --- a/quarkus/pom.xml +++ b/quarkus/pom.xml @@ -31,13 +31,13 @@ pom - 1.9.1.Final + 1.10.0.CR1 4.5.8.Final 2.11.3 ${jackson.version} - 5.4.22.Final - 8.0.21 - 4.5.1 + 5.4.23.Final + 8.0.22 + 4.5.2 1.27 3.0.0-M5 1.5.4.Final-format-001 diff --git a/quarkus/runtime/src/main/java/org/keycloak/cli/MainCommand.java b/quarkus/runtime/src/main/java/org/keycloak/cli/MainCommand.java index 091ed5f276..adea5abc9e 100644 --- a/quarkus/runtime/src/main/java/org/keycloak/cli/MainCommand.java +++ b/quarkus/runtime/src/main/java/org/keycloak/cli/MainCommand.java @@ -20,8 +20,6 @@ package org.keycloak.cli; import static org.keycloak.cli.Picocli.error; import static org.keycloak.cli.Picocli.println; -import io.quarkus.bootstrap.runner.ClassLoadingResource; -import io.quarkus.bootstrap.runner.JarResource; import io.quarkus.bootstrap.runner.RunnerClassLoader; import org.keycloak.configuration.KeycloakConfigSourceProvider; @@ -93,48 +91,14 @@ public class MainCommand { private void beforeReaugmentationOnWindows() throws Exception { // On Windows, files generated during re-augmentation are locked and can't be re-created. - // To workaround this behavior, we close these files as they are not needed during re-augmentation, - // but when actually running the application. + // To workaround this behavior, we reset the internal cache of the runner classloader and force files + // to be closed prior to re-augmenting the application // See KEYCLOAK-16218 if (Environment.isWindows()) { - Field resourcesMapField = null; + ClassLoader classLoader = Thread.currentThread().getContextClassLoader(); - try { - RunnerClassLoader cl = (RunnerClassLoader) Thread.currentThread().getContextClassLoader(); - - resourcesMapField = cl.getClass().getDeclaredField("resourceDirectoryMap"); - resourcesMapField.setAccessible(true); - - Map resourcesMap = (Map) resourcesMapField.get(cl); - - for (ClassLoadingResource[] resources : resourcesMap.values()) { - for (ClassLoadingResource resource : resources) { - if (resource instanceof JarResource) { - Field jarPath = null; - - try { - JarResource jr = (JarResource) resource; - - jarPath = jr.getClass().getDeclaredField("jarPath"); - jarPath.setAccessible(true); - - Path path = (Path) jarPath.get(jr); - - if (path.getFileName().endsWith("generated-bytecode.jar")) { - jr.close(); - } - } finally { - if (jarPath != null) { - jarPath.setAccessible(false); - } - } - } - } - } - } finally { - if (resourcesMapField != null) { - resourcesMapField.setAccessible(false); - } + if (classLoader instanceof RunnerClassLoader) { + RunnerClassLoader.class.cast(classLoader).resetInternalCaches(); } } } diff --git a/services/src/main/java/org/keycloak/services/resources/LoginActionsService.java b/services/src/main/java/org/keycloak/services/resources/LoginActionsService.java index 6a7d5d25df..20e1a19a8c 100755 --- a/services/src/main/java/org/keycloak/services/resources/LoginActionsService.java +++ b/services/src/main/java/org/keycloak/services/resources/LoginActionsService.java @@ -855,7 +855,8 @@ public class LoginActionsService { @Path("consent") @POST @Consumes(MediaType.APPLICATION_FORM_URLENCODED) - public Response processConsent(final MultivaluedMap formData) { + public Response processConsent() { + MultivaluedMap formData = request.getDecodedFormParameters(); event.event(EventType.LOGIN); String code = formData.getFirst(SESSION_CODE); String clientId = session.getContext().getUri().getQueryParameters().getFirst(Constants.CLIENT_ID); diff --git a/services/src/main/java/org/keycloak/services/resources/account/AccountFormService.java b/services/src/main/java/org/keycloak/services/resources/account/AccountFormService.java index 2860a465f9..917553be41 100755 --- a/services/src/main/java/org/keycloak/services/resources/account/AccountFormService.java +++ b/services/src/main/java/org/keycloak/services/resources/account/AccountFormService.java @@ -348,7 +348,9 @@ public class AccountFormService extends AbstractSecuredLocalService { @Path("/") @POST @Consumes(MediaType.APPLICATION_FORM_URLENCODED) - public Response processAccountUpdate(final MultivaluedMap formData) { + public Response processAccountUpdate() { + MultivaluedMap formData = request.getDecodedFormParameters(); + if (auth == null) { return login(null); } @@ -409,7 +411,9 @@ public class AccountFormService extends AbstractSecuredLocalService { @Path("sessions") @POST - public Response processSessionsLogout(final MultivaluedMap formData) { + public Response processSessionsLogout() { + MultivaluedMap formData = request.getDecodedFormParameters(); + if (auth == null) { return login("sessions"); } @@ -441,7 +445,9 @@ public class AccountFormService extends AbstractSecuredLocalService { @Path("applications") @POST @Consumes(MediaType.APPLICATION_FORM_URLENCODED) - public Response processRevokeGrant(final MultivaluedMap formData) { + public Response processRevokeGrant() { + MultivaluedMap formData = request.getDecodedFormParameters(); + if (auth == null) { return login("applications"); } @@ -495,7 +501,9 @@ public class AccountFormService extends AbstractSecuredLocalService { @Path("totp") @POST @Consumes(MediaType.APPLICATION_FORM_URLENCODED) - public Response processTotpUpdate(final MultivaluedMap formData) { + public Response processTotpUpdate() { + MultivaluedMap formData = request.getDecodedFormParameters(); + if (auth == null) { return login("totp"); } @@ -565,7 +573,9 @@ public class AccountFormService extends AbstractSecuredLocalService { @Path("password") @POST @Consumes(MediaType.APPLICATION_FORM_URLENCODED) - public Response processPasswordUpdate(final MultivaluedMap formData) { + public Response processPasswordUpdate() { + MultivaluedMap formData = request.getDecodedFormParameters(); + if (auth == null) { return login("password"); } @@ -647,7 +657,9 @@ public class AccountFormService extends AbstractSecuredLocalService { @Path("identity") @POST @Consumes(MediaType.APPLICATION_FORM_URLENCODED) - public Response processFederatedIdentityUpdate(final MultivaluedMap formData) { + public Response processFederatedIdentityUpdate() { + MultivaluedMap formData = request.getDecodedFormParameters(); + if (auth == null) { return login("identity"); } @@ -753,7 +765,9 @@ public class AccountFormService extends AbstractSecuredLocalService { @Path("resource/{resource_id}/grant") @POST - public Response grantPermission(@PathParam("resource_id") String resourceId, @FormParam("action") String action, @FormParam("permission_id") String[] permissionId, @FormParam("requester") String requester, MultivaluedMap formData) { + public Response grantPermission(@PathParam("resource_id") String resourceId, @FormParam("action") String action, @FormParam("permission_id") String[] permissionId, @FormParam("requester") String requester) { + MultivaluedMap formData = request.getDecodedFormParameters(); + if (auth == null) { return login("resource"); } @@ -875,7 +889,9 @@ public class AccountFormService extends AbstractSecuredLocalService { @Path("resource/{resource_id}/share") @POST - public Response shareResource(@PathParam("resource_id") String resourceId, @FormParam("user_id") String[] userIds, @FormParam("scope_id") String[] scopes, MultivaluedMap formData) { + public Response shareResource(@PathParam("resource_id") String resourceId, @FormParam("user_id") String[] userIds, @FormParam("scope_id") String[] scopes) { + MultivaluedMap formData = request.getDecodedFormParameters(); + if (auth == null) { return login("resource"); } @@ -962,7 +978,9 @@ public class AccountFormService extends AbstractSecuredLocalService { @Path("resource") @POST - public Response processResourceActions(@FormParam("resource_id") String[] resourceIds, @FormParam("action") String action, MultivaluedMap formData) { + public Response processResourceActions(@FormParam("resource_id") String[] resourceIds, @FormParam("action") String action) { + MultivaluedMap formData = request.getDecodedFormParameters(); + if (auth == null) { return login("resource"); } diff --git a/services/src/main/java/org/keycloak/transaction/JtaTransactionWrapper.java b/services/src/main/java/org/keycloak/transaction/JtaTransactionWrapper.java index 197cd285e3..9b3eeae298 100644 --- a/services/src/main/java/org/keycloak/transaction/JtaTransactionWrapper.java +++ b/services/src/main/java/org/keycloak/transaction/JtaTransactionWrapper.java @@ -88,8 +88,7 @@ public class JtaTransactionWrapper implements KeycloakTransaction { @Override public void commit() { try { - if (Status.STATUS_NO_TRANSACTION == tm.getStatus() || - Status.STATUS_ACTIVE != tm.getStatus()) { + if (Status.STATUS_NO_TRANSACTION == tm.getStatus()) { return; } logger.debug("JtaTransactionWrapper commit"); @@ -104,8 +103,7 @@ public class JtaTransactionWrapper implements KeycloakTransaction { @Override public void rollback() { try { - if (Status.STATUS_NO_TRANSACTION == tm.getStatus() || - Status.STATUS_ACTIVE != tm.getStatus()) { + if (Status.STATUS_NO_TRANSACTION == tm.getStatus()) { return; } logger.debug("JtaTransactionWrapper rollback"); diff --git a/testsuite/integration-arquillian/servers/auth-server/services/testsuite-providers/src/main/java/org/keycloak/testsuite/rest/TestApplicationResourceProvider.java b/testsuite/integration-arquillian/servers/auth-server/services/testsuite-providers/src/main/java/org/keycloak/testsuite/rest/TestApplicationResourceProvider.java index 3507033d88..816bf2afb3 100644 --- a/testsuite/integration-arquillian/servers/auth-server/services/testsuite-providers/src/main/java/org/keycloak/testsuite/rest/TestApplicationResourceProvider.java +++ b/testsuite/integration-arquillian/servers/auth-server/services/testsuite-providers/src/main/java/org/keycloak/testsuite/rest/TestApplicationResourceProvider.java @@ -39,6 +39,7 @@ import javax.ws.rs.Path; import javax.ws.rs.PathParam; import javax.ws.rs.Produces; import javax.ws.rs.QueryParam; +import javax.ws.rs.core.Context; import javax.ws.rs.core.MultivaluedMap; import javax.ws.rs.core.Response; import javax.ws.rs.core.UriBuilder; @@ -58,6 +59,9 @@ public class TestApplicationResourceProvider implements RealmResourceProvider { private final BlockingQueue adminTestAvailabilityAction; private final TestApplicationResourceProviderFactory.OIDCClientData oidcClientData; + @Context + HttpRequest request; + public TestApplicationResourceProvider(KeycloakSession session, BlockingQueue adminLogoutActions, BlockingQueue adminPushNotBeforeActions, BlockingQueue adminTestAvailabilityAction, TestApplicationResourceProviderFactory.OIDCClientData oidcClientData) { @@ -122,7 +126,8 @@ public class TestApplicationResourceProvider implements RealmResourceProvider { @Consumes(javax.ws.rs.core.MediaType.APPLICATION_FORM_URLENCODED) @Produces(MediaType.TEXT_HTML_UTF_8) @Path("/{action}") - public String post(@PathParam("action") String action, MultivaluedMap formParams) { + public String post(@PathParam("action") String action) { + MultivaluedMap formParams = request.getDecodedFormParameters(); String title = "APP_REQUEST"; if (action.equals("auth")) { title = "AUTH_RESPONSE"; diff --git a/testsuite/integration-arquillian/servers/auth-server/services/testsuite-providers/src/main/java/org/keycloak/testsuite/rest/TestApplicationResourceProviderFactory.java b/testsuite/integration-arquillian/servers/auth-server/services/testsuite-providers/src/main/java/org/keycloak/testsuite/rest/TestApplicationResourceProviderFactory.java index d6811b4892..926f2f055f 100644 --- a/testsuite/integration-arquillian/servers/auth-server/services/testsuite-providers/src/main/java/org/keycloak/testsuite/rest/TestApplicationResourceProviderFactory.java +++ b/testsuite/integration-arquillian/servers/auth-server/services/testsuite-providers/src/main/java/org/keycloak/testsuite/rest/TestApplicationResourceProviderFactory.java @@ -17,6 +17,7 @@ package org.keycloak.testsuite.rest; +import org.jboss.resteasy.spi.ResteasyProviderFactory; import org.keycloak.Config.Scope; import org.keycloak.crypto.Algorithm; import org.keycloak.crypto.KeyType; @@ -47,7 +48,11 @@ public class TestApplicationResourceProviderFactory implements RealmResourceProv @Override public RealmResourceProvider create(KeycloakSession session) { - return new TestApplicationResourceProvider(session, adminLogoutActions, pushNotBeforeActions, testAvailabilityActions, oidcClientData); + TestApplicationResourceProvider provider = new TestApplicationResourceProvider(session, adminLogoutActions, pushNotBeforeActions, testAvailabilityActions, oidcClientData); + + ResteasyProviderFactory.getInstance().injectProperties(provider); + + return provider; } @Override