From 8c58f39a49edd86b1a488cf2ed494bf03c1efa8f Mon Sep 17 00:00:00 2001 From: Dominik Schlosser Date: Sun, 23 Apr 2023 22:37:35 +0200 Subject: [PATCH] Updates Datastore provider to contain full data model Closes #15490 --- .../datastore/LegacyDatastoreProvider.java | 40 +++++++++++++++++++ .../map/datastore/ImportKeycloakSession.java | 6 +++ .../map/datastore/MapDatastoreProvider.java | 24 +++++++++++ .../keycloak/storage/DatastoreProvider.java | 11 +++++ .../org/keycloak/models/KeycloakSession.java | 2 + .../models/SingleUseObjectProvider.java | 0 .../client/JWTClientAuthenticator.java | 2 +- .../client/JWTClientSecretAuthenticator.java | 2 +- .../credential/OTPCredentialProvider.java | 2 +- .../keycloak/protocol/oidc/TokenManager.java | 2 +- .../endpoints/TokenRevocationEndpoint.java | 2 +- .../BackchannelAuthenticationEndpoint.java | 2 +- .../oidc/grants/device/DeviceGrantType.java | 12 +++--- .../device/endpoints/DeviceEndpoint.java | 4 +- .../oidc/par/endpoints/ParEndpoint.java | 2 +- .../request/AuthzEndpointParParser.java | 2 +- .../protocol/oidc/utils/OAuth2CodeParser.java | 4 +- .../keycloak/protocol/saml/SamlProtocol.java | 2 +- .../keycloak/protocol/saml/SamlService.java | 2 +- .../services/DefaultKeycloakSession.java | 24 +++++------ .../managers/AuthenticationManager.java | 2 +- .../resources/LoginActionsServiceChecks.java | 2 +- .../util/saml/HandleArtifactStepBuilder.java | 4 +- .../SingleUseObjectModelTest.java | 30 +++++++------- 24 files changed, 131 insertions(+), 54 deletions(-) rename {server-spi-private => server-spi}/src/main/java/org/keycloak/models/SingleUseObjectProvider.java (100%) diff --git a/model/legacy-private/src/main/java/org/keycloak/storage/datastore/LegacyDatastoreProvider.java b/model/legacy-private/src/main/java/org/keycloak/storage/datastore/LegacyDatastoreProvider.java index 0f24dd3584..345da7cee2 100644 --- a/model/legacy-private/src/main/java/org/keycloak/storage/datastore/LegacyDatastoreProvider.java +++ b/model/legacy-private/src/main/java/org/keycloak/storage/datastore/LegacyDatastoreProvider.java @@ -23,9 +23,13 @@ import org.keycloak.models.GroupProvider; import org.keycloak.models.KeycloakSession; import org.keycloak.models.RealmProvider; import org.keycloak.models.RoleProvider; +import org.keycloak.models.SingleUseObjectProvider; +import org.keycloak.models.UserLoginFailureProvider; import org.keycloak.models.UserProvider; +import org.keycloak.models.UserSessionProvider; import org.keycloak.models.cache.CacheRealmProvider; import org.keycloak.models.cache.UserCache; +import org.keycloak.sessions.AuthenticationSessionProvider; import org.keycloak.storage.ClientScopeStorageManager; import org.keycloak.storage.ClientStorageManager; import org.keycloak.storage.DatastoreProvider; @@ -41,12 +45,16 @@ public class LegacyDatastoreProvider implements DatastoreProvider, LegacyStoreMa private final LegacyDatastoreProviderFactory factory; private final KeycloakSession session; + private AuthenticationSessionProvider authenticationSessionProvider; private ClientProvider clientProvider; private ClientScopeProvider clientScopeProvider; private GroupProvider groupProvider; + private UserLoginFailureProvider userLoginFailureProvider; private RealmProvider realmProvider; private RoleProvider roleProvider; + private SingleUseObjectProvider singleUseObjectProvider; private UserProvider userProvider; + private UserSessionProvider userSessionProvider; private ClientScopeStorageManager clientScopeStorageManager; private RoleStorageManager roleStorageManager; @@ -170,6 +178,14 @@ public class LegacyDatastoreProvider implements DatastoreProvider, LegacyStoreMa } } + @Override + public AuthenticationSessionProvider authSessions() { + if (authenticationSessionProvider == null) { + authenticationSessionProvider = session.getProvider(AuthenticationSessionProvider.class); + } + return authenticationSessionProvider; + } + @Override public ClientProvider clients() { if (clientProvider == null) { @@ -194,6 +210,14 @@ public class LegacyDatastoreProvider implements DatastoreProvider, LegacyStoreMa return groupProvider; } + @Override + public UserLoginFailureProvider loginFailures() { + if (userLoginFailureProvider == null) { + userLoginFailureProvider = session.getProvider(UserLoginFailureProvider.class); + } + return userLoginFailureProvider; + } + @Override public RealmProvider realms() { if (realmProvider == null) { @@ -210,6 +234,14 @@ public class LegacyDatastoreProvider implements DatastoreProvider, LegacyStoreMa return roleProvider; } + @Override + public SingleUseObjectProvider singleUseObjects() { + if (singleUseObjectProvider == null) { + singleUseObjectProvider = session.getProvider(SingleUseObjectProvider.class); + } + return singleUseObjectProvider; + } + @Override public UserProvider users() { if (userProvider == null) { @@ -218,6 +250,14 @@ public class LegacyDatastoreProvider implements DatastoreProvider, LegacyStoreMa return userProvider; } + @Override + public UserSessionProvider userSessions() { + if (userSessionProvider == null) { + userSessionProvider = session.getProvider(UserSessionProvider.class); + } + return userSessionProvider; + } + @Override public ExportImportManager getExportImportManager() { return new LegacyExportImportManager(session); diff --git a/model/map/src/main/java/org/keycloak/models/map/datastore/ImportKeycloakSession.java b/model/map/src/main/java/org/keycloak/models/map/datastore/ImportKeycloakSession.java index 5edee71011..2a1eb781f2 100644 --- a/model/map/src/main/java/org/keycloak/models/map/datastore/ImportKeycloakSession.java +++ b/model/map/src/main/java/org/keycloak/models/map/datastore/ImportKeycloakSession.java @@ -36,6 +36,7 @@ import org.keycloak.models.RealmProvider; import org.keycloak.models.RealmSpi; import org.keycloak.models.RoleProvider; import org.keycloak.models.RoleSpi; +import org.keycloak.models.SingleUseObjectProvider; import org.keycloak.models.ThemeManager; import org.keycloak.models.TokenManager; import org.keycloak.models.UserCredentialManager; @@ -264,6 +265,11 @@ public class ImportKeycloakSession implements KeycloakSession { throw new ModelException("not supported yet"); } + @Override + public SingleUseObjectProvider singleUseObjects() { + throw new ModelException("not supported yet"); + } + @Override public void close() { session.close(); diff --git a/model/map/src/main/java/org/keycloak/models/map/datastore/MapDatastoreProvider.java b/model/map/src/main/java/org/keycloak/models/map/datastore/MapDatastoreProvider.java index 8baa6404d3..27d011e20f 100644 --- a/model/map/src/main/java/org/keycloak/models/map/datastore/MapDatastoreProvider.java +++ b/model/map/src/main/java/org/keycloak/models/map/datastore/MapDatastoreProvider.java @@ -23,7 +23,11 @@ import org.keycloak.models.GroupProvider; import org.keycloak.models.KeycloakSession; import org.keycloak.models.RealmProvider; import org.keycloak.models.RoleProvider; +import org.keycloak.models.SingleUseObjectProvider; +import org.keycloak.models.UserLoginFailureProvider; import org.keycloak.models.UserProvider; +import org.keycloak.models.UserSessionProvider; +import org.keycloak.sessions.AuthenticationSessionProvider; import org.keycloak.storage.DatastoreProvider; import org.keycloak.storage.ExportImportManager; @@ -39,6 +43,11 @@ public class MapDatastoreProvider implements DatastoreProvider { public void close() { } + @Override + public AuthenticationSessionProvider authSessions() { + return session.getProvider(AuthenticationSessionProvider.class); + } + @Override public ClientScopeProvider clientScopes() { return session.getProvider(ClientScopeProvider.class); @@ -54,6 +63,11 @@ public class MapDatastoreProvider implements DatastoreProvider { return session.getProvider(GroupProvider.class); } + @Override + public UserLoginFailureProvider loginFailures() { + return session.getProvider(UserLoginFailureProvider.class); + } + @Override public RealmProvider realms() { return session.getProvider(RealmProvider.class); @@ -64,11 +78,21 @@ public class MapDatastoreProvider implements DatastoreProvider { return session.getProvider(RoleProvider.class); } + @Override + public SingleUseObjectProvider singleUseObjects() { + return session.getProvider(SingleUseObjectProvider.class); + } + @Override public UserProvider users() { return session.getProvider(UserProvider.class); } + @Override + public UserSessionProvider userSessions() { + return session.getProvider(UserSessionProvider.class); + } + @Override public ExportImportManager getExportImportManager() { return new MapExportImportManager(session); diff --git a/server-spi-private/src/main/java/org/keycloak/storage/DatastoreProvider.java b/server-spi-private/src/main/java/org/keycloak/storage/DatastoreProvider.java index 9170638f1d..a3e6702980 100644 --- a/server-spi-private/src/main/java/org/keycloak/storage/DatastoreProvider.java +++ b/server-spi-private/src/main/java/org/keycloak/storage/DatastoreProvider.java @@ -22,11 +22,16 @@ import org.keycloak.models.ClientScopeProvider; import org.keycloak.models.GroupProvider; import org.keycloak.models.RealmProvider; import org.keycloak.models.RoleProvider; +import org.keycloak.models.SingleUseObjectProvider; +import org.keycloak.models.UserLoginFailureProvider; import org.keycloak.models.UserProvider; +import org.keycloak.models.UserSessionProvider; import org.keycloak.provider.Provider; +import org.keycloak.sessions.AuthenticationSessionProvider; public interface DatastoreProvider extends Provider { + AuthenticationSessionProvider authSessions(); ClientScopeProvider clientScopes(); @@ -34,11 +39,17 @@ public interface DatastoreProvider extends Provider { GroupProvider groups(); + UserLoginFailureProvider loginFailures(); + RealmProvider realms(); RoleProvider roles(); + + SingleUseObjectProvider singleUseObjects(); UserProvider users(); + UserSessionProvider userSessions(); + ExportImportManager getExportImportManager(); } diff --git a/server-spi/src/main/java/org/keycloak/models/KeycloakSession.java b/server-spi/src/main/java/org/keycloak/models/KeycloakSession.java index 2c327351bf..6af9ef3d74 100755 --- a/server-spi/src/main/java/org/keycloak/models/KeycloakSession.java +++ b/server-spi/src/main/java/org/keycloak/models/KeycloakSession.java @@ -201,6 +201,8 @@ public interface KeycloakSession extends AutoCloseable { AuthenticationSessionProvider authenticationSessions(); + SingleUseObjectProvider singleUseObjects(); + void close(); diff --git a/server-spi-private/src/main/java/org/keycloak/models/SingleUseObjectProvider.java b/server-spi/src/main/java/org/keycloak/models/SingleUseObjectProvider.java similarity index 100% rename from server-spi-private/src/main/java/org/keycloak/models/SingleUseObjectProvider.java rename to server-spi/src/main/java/org/keycloak/models/SingleUseObjectProvider.java diff --git a/services/src/main/java/org/keycloak/authentication/authenticators/client/JWTClientAuthenticator.java b/services/src/main/java/org/keycloak/authentication/authenticators/client/JWTClientAuthenticator.java index 4529cef01b..37c77ff6d1 100644 --- a/services/src/main/java/org/keycloak/authentication/authenticators/client/JWTClientAuthenticator.java +++ b/services/src/main/java/org/keycloak/authentication/authenticators/client/JWTClientAuthenticator.java @@ -190,7 +190,7 @@ public class JWTClientAuthenticator extends AbstractClientAuthenticator { throw new RuntimeException("Missing ID on the token"); } - SingleUseObjectProvider singleUseCache = context.getSession().getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseCache = context.getSession().singleUseObjects(); int lifespanInSecs = Math.max(token.getExpiration() - currentTime, 10); if (singleUseCache.putIfAbsent(token.getId(), lifespanInSecs)) { logger.tracef("Added token '%s' to single-use cache. Lifespan: %d seconds, client: %s", token.getId(), lifespanInSecs, clientId); diff --git a/services/src/main/java/org/keycloak/authentication/authenticators/client/JWTClientSecretAuthenticator.java b/services/src/main/java/org/keycloak/authentication/authenticators/client/JWTClientSecretAuthenticator.java index 608f623fbd..19fbd72a56 100644 --- a/services/src/main/java/org/keycloak/authentication/authenticators/client/JWTClientSecretAuthenticator.java +++ b/services/src/main/java/org/keycloak/authentication/authenticators/client/JWTClientSecretAuthenticator.java @@ -192,7 +192,7 @@ public class JWTClientSecretAuthenticator extends AbstractClientAuthenticator { throw new RuntimeException("Missing ID on the token"); } - SingleUseObjectProvider singleUseCache = context.getSession().getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseCache = context.getSession().singleUseObjects(); int lifespanInSecs = Math.max(token.getExpiration() - currentTime, 10); if (singleUseCache.putIfAbsent(token.getId(), lifespanInSecs)) { diff --git a/services/src/main/java/org/keycloak/credential/OTPCredentialProvider.java b/services/src/main/java/org/keycloak/credential/OTPCredentialProvider.java index 0f73630974..b72d122666 100644 --- a/services/src/main/java/org/keycloak/credential/OTPCredentialProvider.java +++ b/services/src/main/java/org/keycloak/credential/OTPCredentialProvider.java @@ -117,7 +117,7 @@ public class OTPCredentialProvider implements CredentialProvider notes = singleUseStore.get(OAuth2DeviceCodeModel.createKey(deviceCode)); return notes != null ? OAuth2DeviceCodeModel.fromCache(realm, deviceCode, notes) : null; } public static void removeDeviceByDeviceCode(KeycloakSession session, String deviceCode) { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); singleUseStore.remove(OAuth2DeviceCodeModel.createKey(deviceCode)); } public static void removeDeviceByUserCode(KeycloakSession session, RealmModel realm, String userCode) { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); singleUseStore.remove(OAuth2DeviceUserCodeModel.createKey(realm, userCode)); } public static boolean isPollingAllowed(KeycloakSession session, OAuth2DeviceCodeModel deviceCodeModel) { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); return singleUseStore.putIfAbsent(deviceCodeModel.serializePollingKey(), deviceCodeModel.getPollingInterval()); } public static boolean approveUserCode(KeycloakSession session, RealmModel realm, String userCode, String userSessionId, Map additionalParams) { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); OAuth2DeviceCodeModel deviceCodeModel = DeviceEndpoint.getDeviceByUserCode(session, realm, userCode); if (deviceCodeModel != null) { @@ -179,7 +179,7 @@ public class DeviceGrantType { } public static boolean denyUserCode(KeycloakSession session, RealmModel realm, String userCode) { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); OAuth2DeviceCodeModel deviceCodeModel = DeviceEndpoint.getDeviceByUserCode(session, realm, userCode); if (deviceCodeModel != null) { diff --git a/services/src/main/java/org/keycloak/protocol/oidc/grants/device/endpoints/DeviceEndpoint.java b/services/src/main/java/org/keycloak/protocol/oidc/grants/device/endpoints/DeviceEndpoint.java index 5928e5d294..53e1266038 100644 --- a/services/src/main/java/org/keycloak/protocol/oidc/grants/device/endpoints/DeviceEndpoint.java +++ b/services/src/main/java/org/keycloak/protocol/oidc/grants/device/endpoints/DeviceEndpoint.java @@ -164,7 +164,7 @@ public class DeviceEndpoint extends AuthorizationEndpointBase implements RealmRe // To inform "expired_token" to the client, the lifespan of the cache provider is longer than device code int lifespanSeconds = expiresIn + interval + 10; - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); singleUseStore.put(deviceCode.serializeKey(), lifespanSeconds, deviceCode.toMap()); singleUseStore.put(userCode.serializeKey(), lifespanSeconds, userCode.serializeValue()); @@ -292,7 +292,7 @@ public class DeviceEndpoint extends AuthorizationEndpointBase implements RealmRe } public static OAuth2DeviceCodeModel getDeviceByUserCode(KeycloakSession session, RealmModel realm, String userCode) { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); Map notes = singleUseStore.get(OAuth2DeviceUserCodeModel.createKey(realm, userCode)); if (notes != null) { diff --git a/services/src/main/java/org/keycloak/protocol/oidc/par/endpoints/ParEndpoint.java b/services/src/main/java/org/keycloak/protocol/oidc/par/endpoints/ParEndpoint.java index de52e04d0d..1df489b236 100644 --- a/services/src/main/java/org/keycloak/protocol/oidc/par/endpoints/ParEndpoint.java +++ b/services/src/main/java/org/keycloak/protocol/oidc/par/endpoints/ParEndpoint.java @@ -157,7 +157,7 @@ public class ParEndpoint extends AbstractParEndpoint { }); params.put(PAR_CREATED_TIME, String.valueOf(System.currentTimeMillis())); - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); singleUseStore.put(key, expiresIn, params); ParResponse parResponse = new ParResponse(requestUri, expiresIn); diff --git a/services/src/main/java/org/keycloak/protocol/oidc/par/endpoints/request/AuthzEndpointParParser.java b/services/src/main/java/org/keycloak/protocol/oidc/par/endpoints/request/AuthzEndpointParParser.java index c7cddd365d..57882c408f 100644 --- a/services/src/main/java/org/keycloak/protocol/oidc/par/endpoints/request/AuthzEndpointParParser.java +++ b/services/src/main/java/org/keycloak/protocol/oidc/par/endpoints/request/AuthzEndpointParParser.java @@ -49,7 +49,7 @@ public class AuthzEndpointParParser extends AuthzEndpointRequestParser { public AuthzEndpointParParser(KeycloakSession session, ClientModel client, String requestUri) { this.session = session; this.client = client; - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); String key; try { key = requestUri.substring(ParEndpoint.REQUEST_URI_PREFIX_LENGTH); diff --git a/services/src/main/java/org/keycloak/protocol/oidc/utils/OAuth2CodeParser.java b/services/src/main/java/org/keycloak/protocol/oidc/utils/OAuth2CodeParser.java index 4a747d90e1..ae5b991a9b 100644 --- a/services/src/main/java/org/keycloak/protocol/oidc/utils/OAuth2CodeParser.java +++ b/services/src/main/java/org/keycloak/protocol/oidc/utils/OAuth2CodeParser.java @@ -52,7 +52,7 @@ public class OAuth2CodeParser { * @return code parameter to be used in OAuth2 handshake */ public static String persistCode(KeycloakSession session, AuthenticatedClientSessionModel clientSession, OAuth2Code codeData) { - SingleUseObjectProvider codeStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider codeStore = session.singleUseObjects(); String key = codeData.getId(); if (key == null) { @@ -112,7 +112,7 @@ public class OAuth2CodeParser { result.clientSession = userSession.getAuthenticatedClientSessionByClient(clientUUID); - SingleUseObjectProvider codeStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider codeStore = session.singleUseObjects(); Map codeData = codeStore.remove(codeUUID); // Either code not available or was already used diff --git a/services/src/main/java/org/keycloak/protocol/saml/SamlProtocol.java b/services/src/main/java/org/keycloak/protocol/saml/SamlProtocol.java index d50b5aa699..4e3f6367a1 100755 --- a/services/src/main/java/org/keycloak/protocol/saml/SamlProtocol.java +++ b/services/src/main/java/org/keycloak/protocol/saml/SamlProtocol.java @@ -207,7 +207,7 @@ public class SamlProtocol implements LoginProtocol { private SingleUseObjectProvider getSingleUseStore() { if (singleUseStore == null) { - singleUseStore = session.getProvider(SingleUseObjectProvider.class); + singleUseStore = session.singleUseObjects(); } return singleUseStore; } diff --git a/services/src/main/java/org/keycloak/protocol/saml/SamlService.java b/services/src/main/java/org/keycloak/protocol/saml/SamlService.java index 4beb99751e..235df586ab 100755 --- a/services/src/main/java/org/keycloak/protocol/saml/SamlService.java +++ b/services/src/main/java/org/keycloak/protocol/saml/SamlService.java @@ -1126,7 +1126,7 @@ public class SamlService extends AuthorizationEndpointBase { private SingleUseObjectProvider getSingleUseStore() { - return session.getProvider(SingleUseObjectProvider.class); + return session.singleUseObjects(); } /** diff --git a/services/src/main/java/org/keycloak/services/DefaultKeycloakSession.java b/services/src/main/java/org/keycloak/services/DefaultKeycloakSession.java index 43b62f0d6b..0aef15c8fe 100644 --- a/services/src/main/java/org/keycloak/services/DefaultKeycloakSession.java +++ b/services/src/main/java/org/keycloak/services/DefaultKeycloakSession.java @@ -33,6 +33,7 @@ import org.keycloak.models.KeycloakTransactionManager; import org.keycloak.models.RealmModel; import org.keycloak.models.RealmProvider; import org.keycloak.models.RoleProvider; +import org.keycloak.models.SingleUseObjectProvider; import org.keycloak.models.ThemeManager; import org.keycloak.models.TokenManager; import org.keycloak.models.UserCredentialManager; @@ -79,9 +80,6 @@ public class DefaultKeycloakSession implements KeycloakSession { private DatastoreProvider datastoreProvider; @Deprecated private UserCredentialManager userCredentialStorageManager; - private UserSessionProvider sessionProvider; - private UserLoginFailureProvider userLoginFailureProvider; - private AuthenticationSessionProvider authenticationSessionProvider; private final KeycloakContext context; private KeyManager keyManager; private ThemeManager themeManager; @@ -390,26 +388,22 @@ public class DefaultKeycloakSession implements KeycloakSession { @Override public UserSessionProvider sessions() { - if (sessionProvider == null) { - sessionProvider = getProvider(UserSessionProvider.class); - } - return sessionProvider; + return getDatastoreProvider().userSessions(); } @Override public UserLoginFailureProvider loginFailures() { - if (userLoginFailureProvider == null) { - userLoginFailureProvider = getProvider(UserLoginFailureProvider.class); - } - return userLoginFailureProvider; + return getDatastoreProvider().loginFailures(); } @Override public AuthenticationSessionProvider authenticationSessions() { - if (authenticationSessionProvider == null) { - authenticationSessionProvider = getProvider(AuthenticationSessionProvider.class); - } - return authenticationSessionProvider; + return getDatastoreProvider().authSessions(); + } + + @Override + public SingleUseObjectProvider singleUseObjects() { + return getDatastoreProvider().singleUseObjects(); } @Override diff --git a/services/src/main/java/org/keycloak/services/managers/AuthenticationManager.java b/services/src/main/java/org/keycloak/services/managers/AuthenticationManager.java index 85efcfc08f..798d707156 100755 --- a/services/src/main/java/org/keycloak/services/managers/AuthenticationManager.java +++ b/services/src/main/java/org/keycloak/services/managers/AuthenticationManager.java @@ -1052,7 +1052,7 @@ public class AuthenticationManager { if (actionTokenKeyToInvalidate != null) { SingleUseObjectKeyModel actionTokenKey = DefaultActionTokenKey.from(actionTokenKeyToInvalidate); if (actionTokenKey != null) { - SingleUseObjectProvider singleUseObjectProvider = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseObjectProvider = session.singleUseObjects(); singleUseObjectProvider.put(actionTokenKeyToInvalidate, actionTokenKey.getExpiration() - Time.currentTime(), null); // Token is invalidated } } diff --git a/services/src/main/java/org/keycloak/services/resources/LoginActionsServiceChecks.java b/services/src/main/java/org/keycloak/services/resources/LoginActionsServiceChecks.java index d885860ec6..8d2d98d75e 100644 --- a/services/src/main/java/org/keycloak/services/resources/LoginActionsServiceChecks.java +++ b/services/src/main/java/org/keycloak/services/resources/LoginActionsServiceChecks.java @@ -300,7 +300,7 @@ public class LoginActionsServiceChecks { } public static void checkTokenWasNotUsedYet(T token, ActionTokenContext context) throws VerificationException { - SingleUseObjectProvider singleUseObjectProvider = context.getSession().getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseObjectProvider = context.getSession().singleUseObjects(); if (singleUseObjectProvider.get(token.serializeKey()) != null) { throw new ExplainedTokenVerificationException(token, Errors.EXPIRED_CODE, Messages.EXPIRED_ACTION); diff --git a/testsuite/integration-arquillian/tests/base/src/main/java/org/keycloak/testsuite/util/saml/HandleArtifactStepBuilder.java b/testsuite/integration-arquillian/tests/base/src/main/java/org/keycloak/testsuite/util/saml/HandleArtifactStepBuilder.java index e2a534444f..ec8e7f8bad 100644 --- a/testsuite/integration-arquillian/tests/base/src/main/java/org/keycloak/testsuite/util/saml/HandleArtifactStepBuilder.java +++ b/testsuite/integration-arquillian/tests/base/src/main/java/org/keycloak/testsuite/util/saml/HandleArtifactStepBuilder.java @@ -196,8 +196,8 @@ public class HandleArtifactStepBuilder extends SamlDocumentStepBuilder session.getProvider(SingleUseObjectProvider.class).get(artifact).get(SamlProtocol.USER_SESSION_ID)); - sessionStateChecker.setClientSessionProvider(session -> session.getProvider(SingleUseObjectProvider.class).get(artifact).get(SamlProtocol.CLIENT_SESSION_ID)); + sessionStateChecker.setUserSessionProvider(session -> session.singleUseObjects().get(artifact).get(SamlProtocol.USER_SESSION_ID)); + sessionStateChecker.setClientSessionProvider(session -> session.singleUseObjects().get(artifact).get(SamlProtocol.CLIENT_SESSION_ID)); } HttpPost post = Soap.createMessage().addToBody(DocumentUtil.getDocument(transformed)).buildHttpPost(authServerSamlUrl); diff --git a/testsuite/model/src/test/java/org/keycloak/testsuite/model/singleUseObject/SingleUseObjectModelTest.java b/testsuite/model/src/test/java/org/keycloak/testsuite/model/singleUseObject/SingleUseObjectModelTest.java index 59eaaea177..74017c1dfa 100644 --- a/testsuite/model/src/test/java/org/keycloak/testsuite/model/singleUseObject/SingleUseObjectModelTest.java +++ b/testsuite/model/src/test/java/org/keycloak/testsuite/model/singleUseObject/SingleUseObjectModelTest.java @@ -69,7 +69,7 @@ public class SingleUseObjectModelTest extends KeycloakModelTest { @Test public void testActionTokens() { DefaultActionTokenKey key = withRealm(realmId, (session, realm) -> { - SingleUseObjectProvider singleUseObjectProvider = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseObjectProvider = session.singleUseObjects(); int time = Time.currentTime(); DefaultActionTokenKey actionTokenKey = new DefaultActionTokenKey(userId, UUID.randomUUID().toString(), time + 60, null); Map notes = new HashMap<>(); @@ -79,7 +79,7 @@ public class SingleUseObjectModelTest extends KeycloakModelTest { }); inComittedTransaction(session -> { - SingleUseObjectProvider singleUseObjectProvider = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseObjectProvider = session.singleUseObjects(); Map notes = singleUseObjectProvider.get(key.serializeKey()); Assert.assertNotNull(notes); Assert.assertEquals("bar", notes.get("foo")); @@ -90,7 +90,7 @@ public class SingleUseObjectModelTest extends KeycloakModelTest { }); inComittedTransaction(session -> { - SingleUseObjectProvider singleUseObjectProvider = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseObjectProvider = session.singleUseObjects(); Map notes = singleUseObjectProvider.get(key.serializeKey()); Assert.assertNull(notes); @@ -100,7 +100,7 @@ public class SingleUseObjectModelTest extends KeycloakModelTest { }); inComittedTransaction(session -> { - SingleUseObjectProvider singleUseObjectProvider = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseObjectProvider = session.singleUseObjects(); Map notes = singleUseObjectProvider.get(key.serializeKey()); Assert.assertNotNull(notes); Assert.assertEquals("bar", notes.get("foo")); @@ -109,7 +109,7 @@ public class SingleUseObjectModelTest extends KeycloakModelTest { setTimeOffset(70); inComittedTransaction(session -> { - SingleUseObjectProvider singleUseObjectProvider = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseObjectProvider = session.singleUseObjects(); Map notes = singleUseObjectProvider.get(key.serializeKey()); notes = singleUseObjectProvider.get(key.serializeKey()); Assert.assertNull(notes); @@ -126,14 +126,14 @@ public class SingleUseObjectModelTest extends KeycloakModelTest { notes2.put("baf", "meow"); inComittedTransaction(session -> { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); Assert.assertFalse(singleUseStore.replace(key, notes2)); singleUseStore.put(key, 60, notes); }); inComittedTransaction(session -> { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); Map actualNotes = singleUseStore.get(key); Assert.assertEquals(notes, actualNotes); @@ -141,7 +141,7 @@ public class SingleUseObjectModelTest extends KeycloakModelTest { }); inComittedTransaction(session -> { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); Map actualNotes = singleUseStore.get(key); Assert.assertEquals(notes2, actualNotes); @@ -151,12 +151,12 @@ public class SingleUseObjectModelTest extends KeycloakModelTest { }); inComittedTransaction(session -> { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); Assert.assertTrue(singleUseStore.putIfAbsent(key, 60)); }); inComittedTransaction(session -> { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); Map actualNotes = singleUseStore.get(key); assertThat(actualNotes, Matchers.anEmptyMap()); }); @@ -164,7 +164,7 @@ public class SingleUseObjectModelTest extends KeycloakModelTest { setTimeOffset(70); inComittedTransaction(session -> { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); Assert.assertNull(singleUseStore.get(key)); }); } @@ -196,7 +196,7 @@ public class SingleUseObjectModelTest extends KeycloakModelTest { if (index.incrementAndGet() == 1) { actionTokenKey.set(withRealm(realmId, (session, realm) -> { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); singleUseStore.put(key, 60, notes); int time = Time.currentTime(); @@ -212,7 +212,7 @@ public class SingleUseObjectModelTest extends KeycloakModelTest { // check if single-use object/action token is available on all nodes inComittedTransaction(session -> { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); while (singleUseStore.get(key) == null || singleUseStore.get(actionTokenKey.get()) == null) { sleep(1000); } @@ -224,7 +224,7 @@ public class SingleUseObjectModelTest extends KeycloakModelTest { // remove objects on one node if (index.incrementAndGet() == 5) { inComittedTransaction(session -> { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); singleUseStore.remove(key); singleUseStore.remove(actionTokenKey.get()); }); @@ -236,7 +236,7 @@ public class SingleUseObjectModelTest extends KeycloakModelTest { // check if single-use object/action token is removed inComittedTransaction(session -> { - SingleUseObjectProvider singleUseStore = session.getProvider(SingleUseObjectProvider.class); + SingleUseObjectProvider singleUseStore = session.singleUseObjects(); while (singleUseStore.get(key) != null && singleUseStore.get(actionTokenKey.get()) != null) { sleep(1000);