Fixing the registration_client_uri to point to a valid URI after updating a client
Closes #23229 Signed-off-by: Pedro Igor <pigor.craveiro@gmail.com>
This commit is contained in:
parent
6f2579393b
commit
f476a42d66
3 changed files with 26 additions and 4 deletions
|
@ -22,6 +22,8 @@ import org.keycloak.protocol.oidc.OIDCLoginProtocol;
|
|||
import org.keycloak.protocol.oidc.OIDCLoginProtocolService;
|
||||
import org.keycloak.protocol.oidc.endpoints.LogoutEndpoint;
|
||||
import org.keycloak.protocol.saml.SamlProtocol;
|
||||
import org.keycloak.services.clientregistration.ClientRegistrationService;
|
||||
import org.keycloak.services.clientregistration.oidc.OIDCClientRegistrationProvider;
|
||||
import org.keycloak.services.resources.IdentityBrokerService;
|
||||
import org.keycloak.services.resources.LoginActionsService;
|
||||
import org.keycloak.services.resources.RealmsResource;
|
||||
|
@ -210,4 +212,8 @@ public class Urls {
|
|||
public static URI samlRequestEndpoint(final URI baseUri, final String realmName) {
|
||||
return realmBase(baseUri).path(RealmsResource.class, "getProtocol").build(realmName, SamlProtocol.LOGIN_PROTOCOL);
|
||||
}
|
||||
|
||||
public static URI clientRegistration(URI baseUri, String realm, String protocol, String clientId) {
|
||||
return realmBase(baseUri).path(RealmsResource.class, "getClientsService").path(ClientRegistrationService.class, "provider").path(OIDCClientRegistrationProvider.class, "getOIDC").build(realm, protocol, clientId);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -21,11 +21,14 @@ import org.keycloak.OAuth2Constants;
|
|||
import org.keycloak.common.util.Time;
|
||||
import org.keycloak.models.ClientModel;
|
||||
import org.keycloak.models.ClientSecretConstants;
|
||||
import org.keycloak.models.KeycloakContext;
|
||||
import org.keycloak.models.KeycloakSession;
|
||||
import org.keycloak.models.ProtocolMapperModel;
|
||||
import org.keycloak.models.RealmModel;
|
||||
import org.keycloak.models.utils.ModelToRepresentation;
|
||||
import org.keycloak.models.utils.RepresentationToModel;
|
||||
import org.keycloak.protocol.oidc.OIDCAdvancedConfigWrapper;
|
||||
import org.keycloak.protocol.oidc.OIDCLoginProtocol;
|
||||
import org.keycloak.protocol.oidc.mappers.AbstractPairwiseSubMapper;
|
||||
import org.keycloak.protocol.oidc.mappers.PairwiseSubMapperHelper;
|
||||
import org.keycloak.protocol.oidc.mappers.SHA256PairwiseSubMapper;
|
||||
|
@ -35,6 +38,7 @@ import org.keycloak.representations.idm.ProtocolMapperRepresentation;
|
|||
import org.keycloak.representations.oidc.OIDCClientRepresentation;
|
||||
import org.keycloak.services.ErrorResponseException;
|
||||
import org.keycloak.services.ServicesLogger;
|
||||
import org.keycloak.services.Urls;
|
||||
import org.keycloak.services.clientregistration.AbstractClientRegistrationProvider;
|
||||
import org.keycloak.services.clientregistration.ClientRegistrationException;
|
||||
import org.keycloak.services.clientregistration.ErrorCodes;
|
||||
|
@ -49,6 +53,8 @@ import jakarta.ws.rs.PathParam;
|
|||
import jakarta.ws.rs.Produces;
|
||||
import jakarta.ws.rs.core.MediaType;
|
||||
import jakarta.ws.rs.core.Response;
|
||||
import org.keycloak.urls.UrlType;
|
||||
|
||||
import java.net.URI;
|
||||
import java.util.List;
|
||||
import java.util.concurrent.atomic.AtomicBoolean;
|
||||
|
@ -94,7 +100,7 @@ public class OIDCClientRegistrationProvider extends AbstractClientRegistrationPr
|
|||
|
||||
validateClient(clientModel, clientOIDC, true);
|
||||
|
||||
URI uri = session.getContext().getUri().getAbsolutePathBuilder().path(client.getClientId()).build();
|
||||
URI uri = getRegistrationClientUri(clientModel);
|
||||
clientOIDC = DescriptionConverter.toExternalResponse(session, client, uri);
|
||||
clientOIDC.setClientIdIssuedAt(Time.currentTime());
|
||||
return Response.created(uri).entity(clientOIDC).build();
|
||||
|
@ -112,7 +118,7 @@ public class OIDCClientRegistrationProvider extends AbstractClientRegistrationPr
|
|||
|
||||
ClientRepresentation clientRepresentation = get(client);
|
||||
|
||||
OIDCClientRepresentation clientOIDC = DescriptionConverter.toExternalResponse(session, clientRepresentation, session.getContext().getUri().getRequestUri());
|
||||
OIDCClientRepresentation clientOIDC = DescriptionConverter.toExternalResponse(session, clientRepresentation, getRegistrationClientUri(client));
|
||||
return Response.ok(clientOIDC).build();
|
||||
}
|
||||
|
||||
|
@ -136,7 +142,7 @@ public class OIDCClientRegistrationProvider extends AbstractClientRegistrationPr
|
|||
|
||||
validateClient(clientModel, clientOIDC, false);
|
||||
|
||||
URI uri = session.getContext().getUri().getAbsolutePathBuilder().path(client.getClientId()).build();
|
||||
URI uri = getRegistrationClientUri(clientModel);
|
||||
clientOIDC = DescriptionConverter.toExternalResponse(session, client, uri);
|
||||
return Response.ok(clientOIDC).build();
|
||||
} catch (ClientRegistrationException cre) {
|
||||
|
@ -189,4 +195,11 @@ public class OIDCClientRegistrationProvider extends AbstractClientRegistrationPr
|
|||
clientModel.getProtocolMappersStream().map(ModelToRepresentation::toRepresentation).collect(Collectors.toList());
|
||||
rep.setProtocolMappers(mappings);
|
||||
}
|
||||
|
||||
private URI getRegistrationClientUri(ClientModel client) {
|
||||
KeycloakContext context = session.getContext();
|
||||
RealmModel realm = context.getRealm();
|
||||
URI backendUri = context.getUri(UrlType.BACKEND).getBaseUri();
|
||||
return Urls.clientRegistration(backendUri, realm.getName(), OIDCLoginProtocol.LOGIN_PROTOCOL, client.getClientId());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -54,6 +54,7 @@ import static org.junit.Assert.assertNotNull;
|
|||
import static org.junit.Assert.assertTrue;
|
||||
import static org.junit.Assert.fail;
|
||||
import static org.keycloak.testsuite.auth.page.AuthRealm.TEST;
|
||||
import static org.keycloak.testsuite.util.OAuthClient.AUTH_SERVER_ROOT;
|
||||
|
||||
/**
|
||||
* @author <a href="mailto:sthorger@redhat.com">Stian Thorgersen</a>
|
||||
|
@ -147,7 +148,7 @@ public class OIDCClientRegistrationTest extends AbstractClientRegistrationTest {
|
|||
assertNotNull(response.getClientId());
|
||||
assertNotNull(response.getClientSecret());
|
||||
assertEquals(0, response.getClientSecretExpiresAt().intValue());
|
||||
assertNotNull(response.getRegistrationClientUri());
|
||||
assertEquals(AUTH_SERVER_ROOT + "/realms/" + REALM_NAME + "/clients-registrations/openid-connect/" + response.getClientId(), response.getRegistrationClientUri());
|
||||
assertEquals("RegistrationAccessTokenTest", response.getClientName());
|
||||
assertEquals("http://root", response.getClientUri());
|
||||
assertEquals(1, response.getRedirectUris().size());
|
||||
|
@ -173,6 +174,7 @@ public class OIDCClientRegistrationTest extends AbstractClientRegistrationTest {
|
|||
assertNotNull(response.getClientSecret());
|
||||
assertEquals(0, response.getClientSecretExpiresAt().intValue());
|
||||
assertEquals(OIDCLoginProtocol.CLIENT_SECRET_BASIC, response.getTokenEndpointAuthMethod());
|
||||
assertEquals(AUTH_SERVER_ROOT + "/realms/" + REALM_NAME + "/clients-registrations/openid-connect/" + response.getClientId(), response.getRegistrationClientUri());
|
||||
}
|
||||
|
||||
@Test
|
||||
|
@ -186,6 +188,7 @@ public class OIDCClientRegistrationTest extends AbstractClientRegistrationTest {
|
|||
|
||||
OIDCClientRepresentation updated = reg.oidc().update(response);
|
||||
|
||||
assertEquals(AUTH_SERVER_ROOT + "/realms/" + REALM_NAME + "/clients-registrations/openid-connect/" + updated.getClientId(), updated.getRegistrationClientUri());
|
||||
assertTrue(CollectionUtil.collectionEquals(Collections.singletonList("http://newredirect"), updated.getRedirectUris()));
|
||||
assertTrue(CollectionUtil.collectionEquals(Arrays.asList(OAuth2Constants.AUTHORIZATION_CODE, OAuth2Constants.IMPLICIT, OAuth2Constants.REFRESH_TOKEN, OAuth2Constants.PASSWORD), updated.getGrantTypes()));
|
||||
assertTrue(CollectionUtil.collectionEquals(Arrays.asList(OAuth2Constants.CODE, OIDCResponseType.NONE, OIDCResponseType.ID_TOKEN, "id_token token", "code id_token", "code token", "code id_token token"), updated.getResponseTypes()));
|
||||
|
|
Loading…
Reference in a new issue