mirror of
https://github.com/keycloak/keycloak.git
synced 2026-01-09 23:12:06 -03:30
Refactor AuthenticationSessionManager
Closes #43825 Signed-off-by: Pedro Ruivo <1492066+pruivo@users.noreply.github.com> Signed-off-by: Alexander Schwartz <alexander.schwartz@ibm.com> Co-authored-by: Pedro Ruivo <1492066+pruivo@users.noreply.github.com> Co-authored-by: Alexander Schwartz <alexander.schwartz@ibm.com>
This commit is contained in:
parent
be6a3814fb
commit
6317c02a27
@ -99,6 +99,11 @@ In a scenario where {project_name} acts as a broker and connects via OpenID Conn
|
||||
|
||||
This behavior is deprecated and will be removed in a future version of Keycloak.
|
||||
|
||||
=== `AuthenticationManager.AuthResult` is now a record
|
||||
|
||||
The inner class `AuthenticationManager.AuthResult` in the `keycloak-services` module is now a record.
|
||||
The getter methods like `getSession()` have been deprecated in favor of the `session()` accessors.
|
||||
|
||||
// ------------------------ Removed features ------------------------ //
|
||||
== Removed features
|
||||
|
||||
|
||||
@ -53,12 +53,12 @@ public class CookieAuthenticator implements Authenticator {
|
||||
} else {
|
||||
AuthenticationSessionModel authSession = context.getAuthenticationSession();
|
||||
LoginProtocol protocol = context.getSession().getProvider(LoginProtocol.class, authSession.getProtocol());
|
||||
authSession.setAuthNote(Constants.LOA_MAP, authResult.getSession().getNote(Constants.LOA_MAP));
|
||||
context.setUser(authResult.getUser());
|
||||
authSession.setAuthNote(Constants.LOA_MAP, authResult.session().getNote(Constants.LOA_MAP));
|
||||
context.setUser(authResult.user());
|
||||
AcrStore acrStore = new AcrStore(context.getSession(), authSession);
|
||||
|
||||
// Cookie re-authentication is skipped if re-authentication is required
|
||||
if (protocol.requireReauthentication(authResult.getSession(), authSession)) {
|
||||
if (protocol.requireReauthentication(authResult.session(), authSession)) {
|
||||
// Full re-authentication, so we start with no loa
|
||||
acrStore.setLevelAuthenticatedToCurrentRequest(Constants.NO_LOA);
|
||||
authSession.setAuthNote(AuthenticationManager.FORCED_REAUTHENTICATION, "true");
|
||||
@ -69,7 +69,7 @@ public class CookieAuthenticator implements Authenticator {
|
||||
} else {
|
||||
String topLevelFlowId = context.getTopLevelFlow().getId();
|
||||
int previouslyAuthenticatedLevel = acrStore.getHighestAuthenticatedLevelFromPreviousAuthentication(topLevelFlowId);
|
||||
AuthenticatorUtils.updateCompletedExecutions(context.getAuthenticationSession(), authResult.getSession(), context.getExecution().getId());
|
||||
AuthenticatorUtils.updateCompletedExecutions(context.getAuthenticationSession(), authResult.session(), context.getExecution().getId());
|
||||
|
||||
if (acrStore.getRequestedLevelOfAuthentication(context.getTopLevelFlow()) > previouslyAuthenticatedLevel) {
|
||||
// Step-up authentication, we keep the loa from the existing user session.
|
||||
@ -85,7 +85,7 @@ public class CookieAuthenticator implements Authenticator {
|
||||
// Cookie only authentication
|
||||
acrStore.setLevelAuthenticatedToCurrentRequest(previouslyAuthenticatedLevel);
|
||||
authSession.setAuthNote(AuthenticationManager.SSO_AUTH, "true");
|
||||
context.attachUserSession(authResult.getSession());
|
||||
context.attachUserSession(authResult.session());
|
||||
|
||||
if (isOrganizationContext(context)) {
|
||||
// if re-authenticating in the scope of an organization, an organization must be resolved prior to authenticating the user
|
||||
|
||||
@ -79,8 +79,8 @@ public class ResetCredentialChooseUser implements Authenticator, AuthenticatorFa
|
||||
AuthenticationManager.AuthResult authResult = AuthenticationManager.authenticateIdentityCookie(context.getSession(), context.getRealm(), true);
|
||||
//skip user choice if sso session exists
|
||||
if (authResult != null) {
|
||||
context.getAuthenticationSession().setAuthNote(AbstractUsernameFormAuthenticator.ATTEMPTED_USERNAME, authResult.getUser().getUsername());
|
||||
context.setUser(authResult.getUser());
|
||||
context.getAuthenticationSession().setAuthNote(AbstractUsernameFormAuthenticator.ATTEMPTED_USERNAME, authResult.user().getUsername());
|
||||
context.setUser(authResult.user());
|
||||
context.success();
|
||||
return;
|
||||
}
|
||||
|
||||
@ -49,9 +49,9 @@ public class UserSessionLimitsAuthenticator implements Authenticator {
|
||||
|
||||
// check if new user and client session are needed
|
||||
AuthenticationManager.AuthResult authResult = AuthenticationManager.authenticateIdentityCookie(context.getSession(), context.getRealm(), true);
|
||||
final boolean newUserSession = authResult == null || authResult.getSession() == null;
|
||||
final boolean newClientSession = authResult == null || authResult.getSession() == null
|
||||
|| authResult.getSession().getAuthenticatedClientSessionByClient(currentClient.getId()) == null;
|
||||
final boolean newUserSession = authResult == null || authResult.session() == null;
|
||||
final boolean newClientSession = authResult == null || authResult.session() == null
|
||||
|| authResult.session().getAuthenticatedClientSessionByClient(currentClient.getId()) == null;
|
||||
|
||||
// Get the configuration for this authenticator
|
||||
behavior = config.get(UserSessionLimitsAuthenticatorFactory.BEHAVIOR);
|
||||
|
||||
@ -32,7 +32,7 @@ public class Tokens {
|
||||
AuthResult authResult = new AppAuthManager.BearerTokenAuthenticator(keycloakSession).authenticate();
|
||||
|
||||
if (authResult != null) {
|
||||
return authResult.getToken();
|
||||
return authResult.token();
|
||||
}
|
||||
|
||||
return null;
|
||||
@ -44,7 +44,7 @@ public class Tokens {
|
||||
.authenticate();
|
||||
|
||||
if (authResult != null) {
|
||||
return authResult.getToken();
|
||||
return authResult.token();
|
||||
}
|
||||
|
||||
return null;
|
||||
|
||||
@ -409,7 +409,7 @@ public class OID4VCIssuerEndpoint {
|
||||
String vcIssuanceFlow = clientSession.getNote(PreAuthorizedCodeGrantType.VC_ISSUANCE_FLOW);
|
||||
|
||||
if (vcIssuanceFlow == null || !vcIssuanceFlow.equals(PreAuthorizedCodeGrantTypeFactory.GRANT_TYPE)) {
|
||||
AccessToken accessToken = bearerTokenAuthenticator.authenticate().getToken();
|
||||
AccessToken accessToken = bearerTokenAuthenticator.authenticate().token();
|
||||
if (Arrays.stream(accessToken.getScope().split(" "))
|
||||
.noneMatch(tokenScope -> tokenScope.equals(requestedCredential.getScope()))) {
|
||||
LOGGER.debugf("Scope check failure: required scope = %s, " +
|
||||
@ -523,8 +523,8 @@ public class OID4VCIssuerEndpoint {
|
||||
String mappingKey = CREDENTIAL_IDENTIFIER_PREFIX + credentialRequestVO.getCredentialIdentifier();
|
||||
|
||||
// First try to get the client session and look for the mapping there
|
||||
UserSessionModel userSession = authResult.getSession();
|
||||
AuthenticatedClientSessionModel clientSession = userSession.getAuthenticatedClientSessionByClient(authResult.getClient().getId());
|
||||
UserSessionModel userSession = authResult.session();
|
||||
AuthenticatedClientSessionModel clientSession = userSession.getAuthenticatedClientSessionByClient(authResult.client().getId());
|
||||
String mappedCredentialConfigurationId = null;
|
||||
|
||||
if (clientSession != null) {
|
||||
@ -947,11 +947,11 @@ public class OID4VCIssuerEndpoint {
|
||||
|
||||
private AuthenticatedClientSessionModel getAuthenticatedClientSession() {
|
||||
AuthenticationManager.AuthResult authResult = getAuthResult();
|
||||
UserSessionModel userSessionModel = authResult.getSession();
|
||||
UserSessionModel userSessionModel = authResult.session();
|
||||
|
||||
AuthenticatedClientSessionModel clientSession = userSessionModel.
|
||||
getAuthenticatedClientSessionByClient(
|
||||
authResult.getClient().getId());
|
||||
authResult.client().getId());
|
||||
if (clientSession == null) {
|
||||
throw new BadRequestException(getErrorResponse(ErrorType.INVALID_TOKEN));
|
||||
}
|
||||
@ -1126,16 +1126,16 @@ public class OID4VCIssuerEndpoint {
|
||||
|
||||
Map<String, Object> subjectClaims = new HashMap<>();
|
||||
protocolMappers
|
||||
.forEach(mapper -> mapper.setClaimsForSubject(subjectClaims, authResult.getSession()));
|
||||
.forEach(mapper -> mapper.setClaimsForSubject(subjectClaims, authResult.session()));
|
||||
|
||||
// Validate that requested claims from authorization_details are present
|
||||
validateRequestedClaimsArePresent(subjectClaims, authResult.getSession(), credentialConfig.getScope());
|
||||
validateRequestedClaimsArePresent(subjectClaims, authResult.session(), credentialConfig.getScope());
|
||||
|
||||
// Include all available claims
|
||||
subjectClaims.forEach((key, value) -> vc.getCredentialSubject().setClaims(key, value));
|
||||
|
||||
protocolMappers
|
||||
.forEach(mapper -> mapper.setClaimsForCredential(vc, authResult.getSession()));
|
||||
.forEach(mapper -> mapper.setClaimsForCredential(vc, authResult.session()));
|
||||
|
||||
LOGGER.debugf("The credential to sign is: %s", vc);
|
||||
|
||||
|
||||
@ -259,8 +259,8 @@ public class LogoutEndpoint {
|
||||
// Check if we have session in the browser. If yes and it is different session than referenced by id_token_hint, the confirmation should be displayed
|
||||
AuthenticationManager.AuthResult authResult = AuthenticationManager.authenticateIdentityCookie(session, realm, false);
|
||||
if (authResult != null) {
|
||||
userSession = authResult.getSession();
|
||||
if (idToken != null && idToken.getSessionState() != null && !idToken.getSessionState().equals(authResult.getSession().getId())) {
|
||||
userSession = authResult.session();
|
||||
if (idToken != null && idToken.getSessionState() != null && !idToken.getSessionState().equals(authResult.session().getId())) {
|
||||
forcedConfirmation = true;
|
||||
}
|
||||
} else {
|
||||
@ -440,7 +440,7 @@ public class LogoutEndpoint {
|
||||
// authenticate identity cookie, but ignore an access token timeout as we're logging out anyways.
|
||||
AuthenticationManager.AuthResult authResult = AuthenticationManager.authenticateIdentityCookie(session, realm, false);
|
||||
if (authResult != null) {
|
||||
userSession = userSession != null ? userSession : authResult.getSession();
|
||||
userSession = userSession != null ? userSession : authResult.session();
|
||||
return initiateBrowserLogout(userSession);
|
||||
} else if (userSession != null) {
|
||||
// identity cookie is missing but there's valid id_token_hint which matches session cookie => continue with browser logout
|
||||
|
||||
@ -130,9 +130,9 @@ public class StandardTokenExchangeProvider extends AbstractTokenExchangeProvider
|
||||
throw new CorsErrorResponseException(cors, OAuthErrorException.INVALID_REQUEST, "Invalid token", Response.Status.BAD_REQUEST);
|
||||
}
|
||||
|
||||
UserModel tokenUser = authResult.getUser();
|
||||
UserSessionModel tokenSession = authResult.getSession();
|
||||
AccessToken token = authResult.getToken();
|
||||
UserModel tokenUser = authResult.user();
|
||||
UserSessionModel tokenSession = authResult.session();
|
||||
AccessToken token = authResult.token();
|
||||
|
||||
event.user(tokenUser);
|
||||
event.detail(Details.USERNAME, tokenUser.getUsername());
|
||||
|
||||
@ -123,9 +123,9 @@ public class V1TokenExchangeProvider extends AbstractTokenExchangeProvider {
|
||||
throw new CorsErrorResponseException(cors, OAuthErrorException.INVALID_REQUEST, "Invalid token", Response.Status.BAD_REQUEST);
|
||||
}
|
||||
|
||||
tokenUser = authResult.getUser();
|
||||
tokenSession = authResult.getSession();
|
||||
token = authResult.getToken();
|
||||
tokenUser = authResult.user();
|
||||
tokenSession = authResult.session();
|
||||
token = authResult.token();
|
||||
}
|
||||
|
||||
String requestedSubject = context.getFormParams().getFirst(OAuth2Constants.REQUESTED_SUBJECT);
|
||||
|
||||
@ -230,7 +230,7 @@ public class SamlService extends AuthorizationEndpointBase {
|
||||
return error(session, null, Response.Status.BAD_REQUEST, Messages.INVALID_REQUEST);
|
||||
}
|
||||
// assume this is a logout response
|
||||
UserSessionModel userSession = authResult.getSession();
|
||||
UserSessionModel userSession = authResult.session();
|
||||
if (userSession.getState() != UserSessionModel.State.LOGGING_OUT) {
|
||||
logger.warn("Unknown saml response.");
|
||||
logger.warn("UserSession is not tagged as logging out.");
|
||||
@ -567,7 +567,7 @@ public class SamlService extends AuthorizationEndpointBase {
|
||||
boolean postBinding = Objects.equals(SamlProtocol.SAML_POST_BINDING, logoutBinding);
|
||||
|
||||
String bindingUri = SamlProtocol.getLogoutServiceUrl(session, client, logoutBinding, false);
|
||||
UserSessionModel userSession = authResult.getSession();
|
||||
UserSessionModel userSession = authResult.session();
|
||||
userSession.setNote(SamlProtocol.SAML_LOGOUT_BINDING_URI, bindingUri);
|
||||
if (samlClient.requiresRealmSignature()) {
|
||||
userSession.setNote(SamlProtocol.SAML_LOGOUT_SIGNATURE_ALGORITHM, samlClient.getSignatureAlgorithm().toString());
|
||||
|
||||
@ -49,8 +49,8 @@ public class AppAuthManager extends AuthenticationManager {
|
||||
AuthResult authResult = super.authenticateIdentityCookie(session, realm);
|
||||
if (authResult == null) return null;
|
||||
// refresh the cookies!
|
||||
createLoginCookie(session, realm, authResult.getUser(), authResult.getSession(), session.getContext().getUri(), session.getContext().getConnection());
|
||||
if (authResult.getSession().isRememberMe()) createRememberMeCookie(authResult.getUser().getUsername(), session.getContext().getUri(), session);
|
||||
createLoginCookie(session, realm, authResult.user(), authResult.session(), session.getContext().getUri(), session.getContext().getConnection());
|
||||
if (authResult.session().isRememberMe()) createRememberMeCookie(authResult.user().getUsername(), session.getContext().getUri(), session);
|
||||
return authResult;
|
||||
}
|
||||
|
||||
|
||||
@ -1,44 +0,0 @@
|
||||
/*
|
||||
* Copyright 2017 Red Hat, Inc. and/or its affiliates
|
||||
* and other contributors as indicated by the @author tags.
|
||||
*
|
||||
* 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 License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.keycloak.services.managers;
|
||||
|
||||
/**
|
||||
* @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
|
||||
*/
|
||||
class AuthSessionId {
|
||||
|
||||
// Decoded ID of authenticationSession WITHOUT route attached (EG. "5e161e00-d426-4ea6-98e9-52eb9844e2d7")
|
||||
private final String decodedId;
|
||||
|
||||
// Encoded ID of authenticationSession WITH route attached (EG. "5e161e00-d426-4ea6-98e9-52eb9844e2d7.node1")
|
||||
private final String encodedId;
|
||||
|
||||
AuthSessionId(String decodedId, String encodedId) {
|
||||
this.decodedId = decodedId;
|
||||
this.encodedId = encodedId;
|
||||
}
|
||||
|
||||
|
||||
public String getDecodedId() {
|
||||
return decodedId;
|
||||
}
|
||||
|
||||
public String getEncodedId() {
|
||||
return encodedId;
|
||||
}
|
||||
}
|
||||
@ -913,11 +913,11 @@ public class AuthenticationManager {
|
||||
|
||||
AuthResult authResult = verifyIdentityToken(session, realm, session.getContext().getUri(), session.getContext().getConnection(), checkActive, false, null, true, tokenString,
|
||||
session.getContext().getRequestHeaders(), verifier -> verifier.withChecks(VALIDATE_IDENTITY_COOKIE));
|
||||
if (authResult == null || authResult.getSession() == null) {
|
||||
if (authResult == null || authResult.session() == null) {
|
||||
expireIdentityCookie(session);
|
||||
return null;
|
||||
}
|
||||
authResult.getSession().setLastSessionRefresh(Time.currentTime());
|
||||
authResult.session().setLastSessionRefresh(Time.currentTime());
|
||||
return authResult;
|
||||
}
|
||||
|
||||
@ -942,7 +942,7 @@ public class AuthenticationManager {
|
||||
if (!compareSessionIdWithSessionCookie(session, userSession.getId())) {
|
||||
AuthResult result = authenticateIdentityCookie(session, realm, false);
|
||||
if (result != null) {
|
||||
UserSessionModel oldSession = result.getSession();
|
||||
UserSessionModel oldSession = result.session();
|
||||
if (oldSession != null && !oldSession.getId().equals(userSession.getId())) {
|
||||
logger.debugv("Removing old user session: session: {0}", oldSession.getId());
|
||||
session.sessions().removeUserSession(realm, oldSession);
|
||||
@ -1653,31 +1653,35 @@ public class AuthenticationManager {
|
||||
SUCCESS, ACCOUNT_TEMPORARILY_DISABLED, ACCOUNT_DISABLED, ACTIONS_REQUIRED, INVALID_USER, INVALID_CREDENTIALS, MISSING_PASSWORD, MISSING_TOTP, FAILED
|
||||
}
|
||||
|
||||
public static class AuthResult {
|
||||
private final UserModel user;
|
||||
private final UserSessionModel session;
|
||||
private final AccessToken token;
|
||||
private final ClientModel client;
|
||||
|
||||
public AuthResult(UserModel user, UserSessionModel session, AccessToken token, ClientModel client) {
|
||||
this.user = user;
|
||||
this.session = session;
|
||||
this.token = token;
|
||||
this.client = client;
|
||||
}
|
||||
|
||||
public record AuthResult(UserModel user, UserSessionModel session, AccessToken token, ClientModel client) {
|
||||
/**
|
||||
* @deprecated use {@link #session()} instead.
|
||||
*/
|
||||
@Deprecated(since = "26.5", forRemoval = true)
|
||||
public UserSessionModel getSession() {
|
||||
return session;
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated use {@link #user()} instead.
|
||||
*/
|
||||
@Deprecated(since = "26.5", forRemoval = true)
|
||||
public UserModel getUser() {
|
||||
return user;
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated use {@link #token()} instead.
|
||||
*/
|
||||
@Deprecated(since = "26.5", forRemoval = true)
|
||||
public AccessToken getToken() {
|
||||
return token;
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated use {@link #client()} instead.
|
||||
*/
|
||||
@Deprecated(since = "26.5", forRemoval = true)
|
||||
public ClientModel getClient() {
|
||||
return client;
|
||||
}
|
||||
|
||||
@ -37,7 +37,6 @@ import org.keycloak.models.KeycloakSession;
|
||||
import org.keycloak.models.RealmModel;
|
||||
import org.keycloak.models.UserSessionModel;
|
||||
import org.keycloak.models.UserSessionProvider;
|
||||
import org.keycloak.models.utils.KeycloakModelUtils;
|
||||
import org.keycloak.models.utils.SessionExpiration;
|
||||
import org.keycloak.protocol.RestartLoginCookie;
|
||||
import org.keycloak.sessions.AuthenticationSessionModel;
|
||||
@ -53,6 +52,7 @@ import static org.keycloak.services.managers.AuthenticationManager.authenticateI
|
||||
public class AuthenticationSessionManager {
|
||||
|
||||
private static final Logger log = Logger.getLogger(AuthenticationSessionManager.class);
|
||||
private static final Base64.Encoder BASE_64_ENCODER_NO_PADDING = Base64.getEncoder().withoutPadding();
|
||||
|
||||
private final KeycloakSession session;
|
||||
|
||||
@ -60,13 +60,10 @@ public class AuthenticationSessionManager {
|
||||
this.session = session;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Creates a fresh authentication session for the given realm . Optionally sets the browser
|
||||
* authentication session cookie with the ID of the new session.
|
||||
* @param realm
|
||||
* @param browserCookie Set the cookie in the browser for the
|
||||
* @return
|
||||
*/
|
||||
public RootAuthenticationSessionModel createAuthenticationSession(RealmModel realm, boolean browserCookie) {
|
||||
RootAuthenticationSessionModel rootAuthSession = session.authenticationSessions().createRootAuthenticationSession(realm);
|
||||
@ -80,46 +77,29 @@ public class AuthenticationSessionManager {
|
||||
}
|
||||
|
||||
public RootAuthenticationSessionModel getCurrentRootAuthenticationSession(RealmModel realm) {
|
||||
String oldEncodedId = getAuthSessionCookies(realm);
|
||||
if (oldEncodedId == null) {
|
||||
AuthSessionCookie authSession = getAuthSessionCookies(realm);
|
||||
if (authSession == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
AuthSessionId authSessionId = decodeAuthSessionId(oldEncodedId);
|
||||
String sessionId = authSessionId.getDecodedId();
|
||||
|
||||
RootAuthenticationSessionModel rootAuthSession = session.authenticationSessions().getRootAuthenticationSession(realm, sessionId);
|
||||
|
||||
if (rootAuthSession != null) {
|
||||
reencodeAuthSessionCookie(oldEncodedId, authSessionId, realm);
|
||||
return rootAuthSession;
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
reEncodeAuthSessionCookie(authSession);
|
||||
return authSession.rootSession();
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns current authentication session if it exists, otherwise returns {@code null}.
|
||||
* @param realm
|
||||
* @return
|
||||
* @return The current authentication session if it exists, otherwise returns {@code null}.
|
||||
*/
|
||||
public AuthenticationSessionModel getCurrentAuthenticationSession(RealmModel realm, ClientModel client, String tabId) {
|
||||
String oldEncodedId = getAuthSessionCookies(realm);
|
||||
if (oldEncodedId == null) {
|
||||
AuthSessionCookie rootAuth = getAuthSessionCookies(realm);
|
||||
if (rootAuth == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
AuthSessionId authSessionId = decodeAuthSessionId(oldEncodedId);
|
||||
String sessionId = authSessionId.getDecodedId();
|
||||
|
||||
AuthenticationSessionModel authSession = getAuthenticationSessionByIdAndClient(realm, sessionId, client, tabId);
|
||||
|
||||
AuthenticationSessionModel authSession = rootAuth.rootSession().getAuthenticationSession(client, tabId);
|
||||
if (authSession != null) {
|
||||
reencodeAuthSessionCookie(oldEncodedId, authSessionId, realm);
|
||||
return authSession;
|
||||
} else {
|
||||
return null;
|
||||
reEncodeAuthSessionCookie(rootAuth);
|
||||
}
|
||||
return authSession;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -139,48 +119,33 @@ public class AuthenticationSessionManager {
|
||||
* @param authSessionId decoded authSessionId (without route info attached)
|
||||
*/
|
||||
public void setAuthSessionIdHashCookie(String authSessionId) {
|
||||
String authSessionIdHash = Base64.getEncoder().withoutPadding().encodeToString(HashUtils.hash(JavaAlgorithm.SHA256, authSessionId.getBytes(StandardCharsets.UTF_8)));
|
||||
String authSessionIdHash = BASE_64_ENCODER_NO_PADDING.encodeToString(HashUtils.hash(JavaAlgorithm.SHA256, authSessionId.getBytes(StandardCharsets.UTF_8)));
|
||||
|
||||
session.getProvider(CookieProvider.class).set(CookieType.AUTH_SESSION_ID_HASH, authSessionIdHash);
|
||||
|
||||
log.debugf("Set KC_AUTH_SESSION_HASH cookie with value %s", authSessionIdHash);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
*
|
||||
* @param encodedAuthSessionId encoded ID with attached route in cluster environment (EG. "NWUxNjFlMDAtZDQyNi00ZWE2LTk4ZTktNTJlYjk4NDRlMmQ3L.node1" )
|
||||
* @return object with decoded and actually encoded authSessionId
|
||||
*/
|
||||
AuthSessionId decodeAuthSessionId(String encodedAuthSessionId) {
|
||||
log.debugf("Found AUTH_SESSION_ID cookie with value %s", encodedAuthSessionId);
|
||||
StickySessionEncoderProvider encoder = session.getProvider(StickySessionEncoderProvider.class);
|
||||
String decodedAuthSessionId = encoder.decodeSessionId(encodedAuthSessionId);
|
||||
String reencoded = encoder.encodeSessionId(decodedAuthSessionId);
|
||||
|
||||
if (!KeycloakModelUtils.isValidUUID(decodedAuthSessionId)) {
|
||||
decodedAuthSessionId = decodeBase64AndValidateSignature(decodedAuthSessionId, false);
|
||||
}
|
||||
|
||||
return new AuthSessionId(decodedAuthSessionId, reencoded);
|
||||
}
|
||||
|
||||
void reencodeAuthSessionCookie(String oldEncodedAuthSessionId, AuthSessionId newAuthSessionId, RealmModel realm) {
|
||||
if (!oldEncodedAuthSessionId.equals(newAuthSessionId.getEncodedId())) {
|
||||
log.debugf("Route changed. Will update authentication session cookie. Old: '%s', New: '%s'", oldEncodedAuthSessionId,
|
||||
newAuthSessionId.getEncodedId());
|
||||
setAuthSessionCookie(newAuthSessionId.getDecodedId());
|
||||
private void reEncodeAuthSessionCookie(AuthSessionCookie authSessionCookie) {
|
||||
if (authSessionCookie.routeChanged()) {
|
||||
setAuthSessionCookie(authSessionCookie.sessionId());
|
||||
}
|
||||
}
|
||||
|
||||
public String decodeBase64AndValidateSignature(String encodedBase64AuthSessionId, boolean validate) {
|
||||
try {
|
||||
String decodedAuthSessionId = new String(Base64Url.decode(encodedBase64AuthSessionId), StandardCharsets.UTF_8);
|
||||
if (decodedAuthSessionId.lastIndexOf(".") != -1) {
|
||||
String authSessionId = decodedAuthSessionId.substring(0, decodedAuthSessionId.indexOf("."));
|
||||
String signature = decodedAuthSessionId.substring(decodedAuthSessionId.indexOf(".") + 1);
|
||||
return validate ? validateAuthSessionIdSignature(authSessionId, signature) : authSessionId;
|
||||
int dotIndex = decodedAuthSessionId.lastIndexOf('.');
|
||||
if (dotIndex == -1) {
|
||||
//not found / invalid
|
||||
return null;
|
||||
}
|
||||
String authSessionId = decodedAuthSessionId.substring(0, dotIndex);
|
||||
if (!validate) {
|
||||
return authSessionId;
|
||||
}
|
||||
String signature = decodedAuthSessionId.substring(dotIndex + 1);
|
||||
return validateAuthSessionIdSignature(authSessionId, signature);
|
||||
} catch (Exception e) {
|
||||
log.errorf("Error decoding auth session id with value: %s", encodedBase64AuthSessionId, e);
|
||||
}
|
||||
@ -223,10 +188,9 @@ public class AuthenticationSessionManager {
|
||||
}
|
||||
|
||||
/**
|
||||
* @param realm
|
||||
* @return the value of the AUTH_SESSION_ID cookie. It is assumed that values could be encoded with signature and with route added (EG. "NWUxNjFlMDAtZDQyNi00ZWE2LTk4ZTktNTJlYjk4NDRlMmQ3L.node1" )
|
||||
*/
|
||||
String getAuthSessionCookies(RealmModel realm) {
|
||||
AuthSessionCookie getAuthSessionCookies(RealmModel realm) {
|
||||
String oldEncodedId = session.getProvider(CookieProvider.class).get(CookieType.AUTH_SESSION_ID);
|
||||
if (oldEncodedId == null || oldEncodedId.isEmpty()) {
|
||||
return null;
|
||||
@ -245,7 +209,15 @@ public class AuthenticationSessionManager {
|
||||
// but make sure the root authentication session actually exists
|
||||
// without this check there is a risk of resolving user sessions from invalid root authentication sessions as they share the same id
|
||||
RootAuthenticationSessionModel rootAuthenticationSession = session.authenticationSessions().getRootAuthenticationSession(realm, decodedAuthSessionId);
|
||||
return rootAuthenticationSession != null ? oldEncodedId : null;
|
||||
if (rootAuthenticationSession == null) {
|
||||
return null;
|
||||
}
|
||||
String reEncoded = routeEncoder.encodeSessionId(decodedAuthSessionId);
|
||||
boolean routeChanged = !Objects.equals(oldEncodedId, reEncoded);
|
||||
if (routeChanged) {
|
||||
log.debugf("Route changed. Will update authentication session cookie. Old: '%s', New: '%s'", oldEncodedId, reEncoded);
|
||||
}
|
||||
return new AuthSessionCookie(rootAuthenticationSession, routeChanged);
|
||||
}
|
||||
|
||||
public void removeAuthenticationSession(RealmModel realm, AuthenticationSessionModel authSession, boolean expireRestartCookie) {
|
||||
@ -265,8 +237,7 @@ public class AuthenticationSessionManager {
|
||||
|
||||
/**
|
||||
* Remove authentication session from root session. Possibly remove whole root authentication session if there are no other browser tabs
|
||||
* @param realm
|
||||
* @param authSession
|
||||
*
|
||||
* @return true if whole root authentication session was removed. False just if single tab was removed
|
||||
*/
|
||||
public boolean removeTabIdInAuthenticationSession(RealmModel realm, AuthenticationSessionModel authSession) {
|
||||
@ -285,31 +256,28 @@ public class AuthenticationSessionManager {
|
||||
* This happens when one browser tab successfully finished authentication (including required actions and consent screen if applicable)
|
||||
* Just authenticationSession of the current browser tab is removed from "root authentication session" and other tabs are kept, so
|
||||
* authentication can be automatically finished in other browser tabs (typically with authChecker.js javascript)
|
||||
*
|
||||
* @param realm
|
||||
* @param authSession
|
||||
*/
|
||||
public void updateAuthenticationSessionAfterSuccessfulAuthentication(RealmModel realm, AuthenticationSessionModel authSession) {
|
||||
boolean removedRootAuthSession = removeTabIdInAuthenticationSession(realm, authSession);
|
||||
if (!removedRootAuthSession) {
|
||||
if(realm.getSsoSessionIdleTimeout() < SessionExpiration.getAuthSessionLifespan(realm) && realm.getSsoSessionMaxLifespan() < SessionExpiration.getAuthSessionLifespan(realm)) {
|
||||
removeAuthenticationSession(realm, authSession, true);
|
||||
}
|
||||
else {
|
||||
RootAuthenticationSessionModel rootAuthSession = authSession.getParentSession();
|
||||
|
||||
// 1 minute by default. Same timeout, which is used for client to complete "authorization code" flow
|
||||
// Very short timeout should be OK as when this cookie is set, other existing browser tabs are supposed to be refreshed immediately by JS script authChecker.js
|
||||
// and login user automatically. No need to have authenticationSession and cookie living any longer
|
||||
int authSessionExpiresIn = realm.getAccessCodeLifespan();
|
||||
|
||||
// Set timestamp to the past to make sure that authSession is scheduled for expiration in "authSessionExpiresIn" seconds
|
||||
int authSessionExpirationTime = Time.currentTime() - SessionExpiration.getAuthSessionLifespan(realm) + authSessionExpiresIn;
|
||||
rootAuthSession.setTimestamp(authSessionExpirationTime);
|
||||
|
||||
log.tracef("Removed authentication session of root session '%s' with tabId '%s'. But there are remaining tabs in the root session. Root authentication session will expire in %d seconds", rootAuthSession.getId(), authSession.getTabId(), authSessionExpiresIn);
|
||||
}
|
||||
if (removedRootAuthSession) {
|
||||
return;
|
||||
}
|
||||
if (realm.getSsoSessionIdleTimeout() < SessionExpiration.getAuthSessionLifespan(realm) && realm.getSsoSessionMaxLifespan() < SessionExpiration.getAuthSessionLifespan(realm)) {
|
||||
removeAuthenticationSession(realm, authSession, true);
|
||||
return;
|
||||
}
|
||||
RootAuthenticationSessionModel rootAuthSession = authSession.getParentSession();
|
||||
|
||||
// 1 minute by default. Same timeout, which is used for client to complete "authorization code" flow
|
||||
// Very short timeout should be OK as when this cookie is set, other existing browser tabs are supposed to be refreshed immediately by JS script authChecker.js
|
||||
// and login user automatically. No need to have authenticationSession and cookie living any longer
|
||||
int authSessionExpiresIn = realm.getAccessCodeLifespan();
|
||||
|
||||
// Set timestamp to the past to make sure that authSession is scheduled for expiration in "authSessionExpiresIn" seconds
|
||||
int authSessionExpirationTime = Time.currentTime() - SessionExpiration.getAuthSessionLifespan(realm) + authSessionExpiresIn;
|
||||
rootAuthSession.setTimestamp(authSessionExpirationTime);
|
||||
|
||||
log.tracef("Removed authentication session of root session '%s' with tabId '%s'. But there are remaining tabs in the root session. Root authentication session will expire in %d seconds", rootAuthSession.getId(), authSession.getTabId(), authSessionExpiresIn);
|
||||
}
|
||||
|
||||
// Check to see if we already have authenticationSession with same ID
|
||||
@ -330,41 +298,47 @@ public class AuthenticationSessionManager {
|
||||
}
|
||||
|
||||
public UserSessionModel getUserSessionFromAuthenticationCookie(RealmModel realm) {
|
||||
String oldEncodedId = getAuthSessionCookies(realm);
|
||||
AuthSessionCookie rootAuth = getAuthSessionCookies(realm);
|
||||
|
||||
if (oldEncodedId == null) {
|
||||
if (rootAuth == null) {
|
||||
// ideally, we should not rely on auth session id to retrieve user sessions
|
||||
// in case the auth session was removed, we fall back to the identity cookie
|
||||
// we are here doing the user session lookup twice, however the second lookup is going to make sure the
|
||||
// session exists in remote caches
|
||||
AuthenticationManager.AuthResult authResult = authenticateIdentityCookie(session, realm, true);
|
||||
|
||||
if (authResult != null && authResult.getSession() != null) {
|
||||
oldEncodedId = authResult.getSession().getId();
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
return getUserSessionFromIdentityCookie(realm);
|
||||
}
|
||||
|
||||
AuthSessionId authSessionId = decodeAuthSessionId(oldEncodedId);
|
||||
String sessionId = authSessionId.getDecodedId();
|
||||
|
||||
// TODO: remove this code once InfinispanUserSessionProvider is removed or no longer using any remote caches, as other implementations don't need this call.
|
||||
// This will remove userSession "locally" if it doesn't exist on remoteCache
|
||||
var userSessionProvider = getUserSessionProvider();
|
||||
userSessionProvider.getUserSessionWithPredicate(realm, sessionId, false, Objects::isNull);
|
||||
|
||||
UserSessionModel userSession = userSessionProvider.getUserSession(realm, sessionId);
|
||||
UserSessionModel userSession = getUserSessionProvider().getUserSession(realm, rootAuth.sessionId());
|
||||
|
||||
if (userSession != null) {
|
||||
reencodeAuthSessionCookie(oldEncodedId, authSessionId, realm);
|
||||
return userSession;
|
||||
} else {
|
||||
reEncodeAuthSessionCookie(rootAuth);
|
||||
}
|
||||
return userSession;
|
||||
}
|
||||
|
||||
private UserSessionModel getUserSessionFromIdentityCookie(RealmModel realm) {
|
||||
AuthenticationManager.AuthResult authResult = authenticateIdentityCookie(session, realm, true);
|
||||
if (authResult == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
assert authResult.session() != null;
|
||||
|
||||
// if we reach this point, the cookie is not found. Set it.
|
||||
setAuthSessionCookie(authResult.session().getId());
|
||||
return authResult.session();
|
||||
}
|
||||
|
||||
private UserSessionProvider getUserSessionProvider() {
|
||||
return session.sessions();
|
||||
}
|
||||
|
||||
record AuthSessionCookie(RootAuthenticationSessionModel rootSession, boolean routeChanged) {
|
||||
|
||||
public String sessionId() {
|
||||
return rootSession.getId();
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@ -248,13 +248,12 @@ public class IdentityBrokerService implements UserAuthenticationIdentityProvider
|
||||
return Response.status(302).location(builder.build()).build();
|
||||
}
|
||||
|
||||
cookieResult.getSession();
|
||||
event.session(cookieResult.getSession());
|
||||
event.user(cookieResult.getUser());
|
||||
event.detail(Details.USERNAME, cookieResult.getUser().getUsername());
|
||||
event.session(cookieResult.session());
|
||||
event.user(cookieResult.user());
|
||||
event.detail(Details.USERNAME, cookieResult.user().getUsername());
|
||||
|
||||
AuthenticatedClientSessionModel clientSession = null;
|
||||
for (AuthenticatedClientSessionModel cs : cookieResult.getSession().getAuthenticatedClientSessions().values()) {
|
||||
for (AuthenticatedClientSessionModel cs : cookieResult.session().getAuthenticatedClientSessions().values()) {
|
||||
if (cs.getClient().getClientId().equals(clientId)) {
|
||||
byte[] decoded = Base64Url.decode(hash);
|
||||
MessageDigest md = null;
|
||||
@ -263,7 +262,7 @@ public class IdentityBrokerService implements UserAuthenticationIdentityProvider
|
||||
} catch (NoSuchAlgorithmException e) {
|
||||
throw new ErrorPageException(session, Response.Status.INTERNAL_SERVER_ERROR, Messages.UNEXPECTED_ERROR_HANDLING_REQUEST);
|
||||
}
|
||||
String input = nonce + cookieResult.getSession().getId() + clientId + providerAlias;
|
||||
String input = nonce + cookieResult.session().getId() + clientId + providerAlias;
|
||||
byte[] check = md.digest(input.getBytes(StandardCharsets.UTF_8));
|
||||
if (MessageDigest.isEqual(decoded, check)) {
|
||||
clientSession = cs;
|
||||
@ -311,7 +310,7 @@ public class IdentityBrokerService implements UserAuthenticationIdentityProvider
|
||||
|
||||
|
||||
// Create AuthenticationSessionModel with same ID like userSession and refresh cookie
|
||||
UserSessionModel userSession = cookieResult.getSession();
|
||||
UserSessionModel userSession = cookieResult.session();
|
||||
|
||||
// Auth session with ID corresponding to our userSession may already exists in some rare cases (EG. if some client tried to login in another browser tab with "prompt=login")
|
||||
RootAuthenticationSessionModel rootAuthSession = session.authenticationSessions().getRootAuthenticationSession(realmModel, userSession.getId());
|
||||
@ -331,7 +330,7 @@ public class IdentityBrokerService implements UserAuthenticationIdentityProvider
|
||||
authSession.setProtocol(client.getProtocol());
|
||||
authSession.setRedirectUri(redirectUri);
|
||||
authSession.setClientNote(OIDCLoginProtocol.STATE_PARAM, UUID.randomUUID().toString());
|
||||
authSession.setAuthNote(LINKING_IDENTITY_PROVIDER, cookieResult.getSession().getId() + clientId + providerAlias);
|
||||
authSession.setAuthNote(LINKING_IDENTITY_PROVIDER, cookieResult.session().getId() + clientId + providerAlias);
|
||||
|
||||
event.detail(Details.CODE_ID, userSession.getId());
|
||||
event.success();
|
||||
@ -485,10 +484,10 @@ public class IdentityBrokerService implements UserAuthenticationIdentityProvider
|
||||
.authenticate();
|
||||
|
||||
if (authResult != null) {
|
||||
AccessToken token = authResult.getToken();
|
||||
ClientModel clientModel = authResult.getClient();
|
||||
AccessToken token = authResult.token();
|
||||
ClientModel clientModel = authResult.client();
|
||||
event.client(clientModel);
|
||||
event.user(authResult.getUser());
|
||||
event.user(authResult.user());
|
||||
|
||||
session.getContext().setClient(clientModel);
|
||||
|
||||
@ -506,14 +505,14 @@ public class IdentityBrokerService implements UserAuthenticationIdentityProvider
|
||||
IdentityProviderModel identityProviderConfig = getIdentityProviderConfig(providerAlias);
|
||||
|
||||
if (identityProviderConfig.isStoreToken()) {
|
||||
FederatedIdentityModel identity = this.session.users().getFederatedIdentity(this.realmModel, authResult.getUser(), providerAlias);
|
||||
FederatedIdentityModel identity = this.session.users().getFederatedIdentity(this.realmModel, authResult.user(), providerAlias);
|
||||
|
||||
if (identity == null) {
|
||||
return corsResponse(badRequest("User [" + authResult.getUser().getId() + "] is not associated with identity provider [" + providerAlias + "]."), clientModel);
|
||||
return corsResponse(badRequest("User [" + authResult.user().getId() + "] is not associated with identity provider [" + providerAlias + "]."), clientModel);
|
||||
}
|
||||
|
||||
if (identity.getToken() == null) {
|
||||
return corsResponse(notFound("No token stored for user [" + authResult.getUser().getId() + "] with associated identity provider [" + providerAlias + "]."), clientModel);
|
||||
return corsResponse(notFound("No token stored for user [" + authResult.user().getId() + "] with associated identity provider [" + providerAlias + "]."), clientModel);
|
||||
}
|
||||
|
||||
String oldToken = identity.getToken();
|
||||
@ -529,7 +528,7 @@ public class IdentityBrokerService implements UserAuthenticationIdentityProvider
|
||||
if (!Objects.equals(oldToken, identity.getToken())) {
|
||||
// The API of the IdentityProvider doesn't allow use to pass down the realm and the user, so we check if the token has changed,
|
||||
// and then update the store.
|
||||
session.users().updateFederatedIdentity(session.getContext().getRealm(), authResult.getUser(), identity);
|
||||
session.users().updateFederatedIdentity(session.getContext().getRealm(), authResult.user(), identity);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -133,7 +133,7 @@ public class LoginActionsServiceChecks {
|
||||
AuthResult authResult = AuthenticationManager.authenticateIdentityCookie(session, realm, true);
|
||||
|
||||
if (authResult != null) {
|
||||
UserSessionModel userSession = authResult.getSession();
|
||||
UserSessionModel userSession = authResult.session();
|
||||
if (!user.equals(userSession.getUser())) {
|
||||
// do not allow authenticated users performing actions that are bound to other user and fire an event
|
||||
// it might be an attempt to hijack a user account or perform actions on behalf of others
|
||||
|
||||
@ -205,7 +205,7 @@ public class SessionCodeChecks {
|
||||
if (response.getStatus() != Response.Status.FOUND.getStatusCode()) {
|
||||
AuthenticationManager.AuthResult authResult = authenticateIdentityCookie(session, realm, false);
|
||||
|
||||
if (authResult != null && authResult.getSession() != null) {
|
||||
if (authResult != null && authResult.session() != null) {
|
||||
response = null;
|
||||
|
||||
if (client != null && clientData != null) {
|
||||
|
||||
@ -83,7 +83,7 @@ public class AccountConsole implements AccountResourceProvider {
|
||||
public void init() {
|
||||
AuthenticationManager.AuthResult authResult = authManager.authenticateIdentityCookie(session, realm);
|
||||
if (authResult != null) {
|
||||
auth = new Auth(realm, authResult.getToken(), authResult.getUser(), client, authResult.getSession(), true);
|
||||
auth = new Auth(realm, authResult.token(), authResult.user(), client, authResult.session(), true);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -119,24 +119,24 @@ public class AccountLoader {
|
||||
throw new NotAuthorizedException("Bearer token required");
|
||||
}
|
||||
|
||||
AccessToken accessToken = authResult.getToken();
|
||||
AccessToken accessToken = authResult.token();
|
||||
|
||||
if (accessToken.getAudience() == null || accessToken.getResourceAccess(client.getClientId()) == null) {
|
||||
// transform for introspection to get the required claims
|
||||
AccessTokenIntrospectionProvider provider = (AccessTokenIntrospectionProvider) session.getProvider(TokenIntrospectionProvider.class,
|
||||
AccessTokenIntrospectionProviderFactory.ACCESS_TOKEN_TYPE);
|
||||
accessToken = provider.transformAccessToken(accessToken, authResult.getSession());
|
||||
accessToken = provider.transformAccessToken(accessToken, authResult.session());
|
||||
}
|
||||
|
||||
if (!accessToken.hasAudience(client.getClientId())) {
|
||||
throw new NotAuthorizedException("Invalid audience for client " + client.getClientId());
|
||||
}
|
||||
|
||||
Auth auth = new Auth(session.getContext().getRealm(), accessToken, authResult.getUser(), client, authResult.getSession(), false);
|
||||
Auth auth = new Auth(session.getContext().getRealm(), accessToken, authResult.user(), client, authResult.session(), false);
|
||||
|
||||
Cors.builder().allowedOrigins(auth.getToken()).allowedMethods("GET", "PUT", "POST", "DELETE").auth().add();
|
||||
|
||||
if (authResult.getUser().getServiceAccountClientLink() != null) {
|
||||
if (authResult.user().getServiceAccountClientLink() != null) {
|
||||
throw new NotAuthorizedException("Service accounts are not allowed to access this service");
|
||||
}
|
||||
|
||||
|
||||
@ -229,7 +229,7 @@ public class AdminConsole {
|
||||
throw new NotAuthorizedException("Bearer");
|
||||
}
|
||||
|
||||
final String issuedFor = authResult.getToken().getIssuedFor();
|
||||
final String issuedFor = authResult.token().getIssuedFor();
|
||||
if (!Constants.ADMIN_CONSOLE_CLIENT_ID.equals(issuedFor)) {
|
||||
if (issuedFor == null) {
|
||||
throw new ForbiddenException("No azp claim in the token");
|
||||
@ -241,7 +241,7 @@ public class AdminConsole {
|
||||
}
|
||||
}
|
||||
|
||||
UserModel user= authResult.getUser();
|
||||
UserModel user= authResult.user();
|
||||
String displayName;
|
||||
if ((user.getFirstName() != null && !user.getFirstName().trim().equals("")) || (user.getLastName() != null && !user.getLastName().trim().equals(""))) {
|
||||
displayName = user.getFirstName();
|
||||
@ -277,7 +277,7 @@ public class AdminConsole {
|
||||
Locale locale = session.getContext().resolveLocale(user);
|
||||
|
||||
return Cors.builder()
|
||||
.allowedOrigins(authResult.getToken())
|
||||
.allowedOrigins(authResult.token())
|
||||
.allowedMethods("GET")
|
||||
.auth()
|
||||
.add(Response.ok(new WhoAmI(user.getId(), realm.getName(), displayName, createRealm, realmAccess, locale, Boolean.parseBoolean(user.getFirstAttribute(IS_TEMP_ADMIN_ATTR_NAME)))));
|
||||
|
||||
@ -207,9 +207,9 @@ public class AdminRoot {
|
||||
throw new NotAuthorizedException("Bearer");
|
||||
}
|
||||
|
||||
session.getContext().setBearerToken(authResult.getToken());
|
||||
session.getContext().setBearerToken(authResult.token());
|
||||
|
||||
return new AdminAuth(realm, authResult.getToken(), authResult.getUser(), authResult.getClient());
|
||||
return new AdminAuth(realm, authResult.token(), authResult.user(), authResult.client());
|
||||
}
|
||||
|
||||
public static UriBuilder realmsUrl(UriInfo uriInfo) {
|
||||
|
||||
@ -51,7 +51,7 @@ public class ExampleRestResource {
|
||||
private void checkRealmAdmin() {
|
||||
if (auth == null) {
|
||||
throw new NotAuthorizedException("Bearer");
|
||||
} else if (auth.getToken().getRealmAccess() == null || !auth.getToken().getRealmAccess().isUserInRole("admin")) {
|
||||
} else if (auth.token().getRealmAccess() == null || !auth.token().getRealmAccess().isUserInRole("admin")) {
|
||||
throw new ForbiddenException("Does not have realm admin role");
|
||||
}
|
||||
}
|
||||
|
||||
@ -61,7 +61,7 @@ public class OID4VCTargetRoleMapperTest extends OID4VCTest {
|
||||
roleMapper.setMapperModel(pmm, "jwt_vc");
|
||||
AppAuthManager.BearerTokenAuthenticator authenticator = new AppAuthManager.BearerTokenAuthenticator(session);
|
||||
authenticator.setTokenString(token);
|
||||
UserSessionModel userSessionModel = authenticator.authenticate().getSession();
|
||||
UserSessionModel userSessionModel = authenticator.authenticate().session();
|
||||
roleMapper.setClaimsForSubject(claimsMap, userSessionModel);
|
||||
assertTrue("The roles should be included as a claim.", claimsMap.containsKey("roles"));
|
||||
if (claimsMap.get("roles") instanceof HashSet roles) {
|
||||
|
||||
@ -145,9 +145,9 @@ public abstract class OID4VCIssuerEndpointTest extends OID4VCTest {
|
||||
|
||||
protected static String prepareSessionCode(KeycloakSession session, AppAuthManager.BearerTokenAuthenticator authenticator, String note) {
|
||||
AuthenticationManager.AuthResult authResult = authenticator.authenticate();
|
||||
UserSessionModel userSessionModel = authResult.getSession();
|
||||
UserSessionModel userSessionModel = authResult.session();
|
||||
AuthenticatedClientSessionModel authenticatedClientSessionModel = userSessionModel.getAuthenticatedClientSessionByClient(
|
||||
authResult.getClient().getId());
|
||||
authResult.client().getId());
|
||||
String codeId = SecretGenerator.getInstance().randomString();
|
||||
String nonce = SecretGenerator.getInstance().randomString();
|
||||
OAuth2Code oAuth2Code = new OAuth2Code(codeId,
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user