KEYCLOAK-2061 Direct Access Grants disabled by default
This commit is contained in:
parent
ec327c99f4
commit
5b61a10b55
49 changed files with 195 additions and 26 deletions
|
@ -90,6 +90,7 @@
|
|||
|
||||
<update tableName="CLIENT">
|
||||
<column name="STANDARD_FLOW_ENABLED" valueBoolean="false"/>
|
||||
<column name="DIRECT_ACCESS_GRANTS_ENABLED" valueBoolean="true"/>
|
||||
<where>DIRECT_GRANTS_ONLY = :value</where>
|
||||
<whereParams>
|
||||
<param valueBoolean="true" />
|
||||
|
|
|
@ -27,7 +27,7 @@ public class Update1_7_0 extends Update {
|
|||
boolean directGrantsOnly = client.getBoolean("directGrantsOnly", false);
|
||||
client.append("standardFlowEnabled", !directGrantsOnly);
|
||||
client.append("implicitFlowEnabled", false);
|
||||
client.append("directAccessGrantsEnabled", true);
|
||||
client.append("directAccessGrantsEnabled", directGrantsOnly);
|
||||
client.removeField("directGrantsOnly");
|
||||
|
||||
clients.save(client);
|
||||
|
|
|
@ -82,11 +82,24 @@
|
|||
<section>
|
||||
<title>Migrating to 1.7.0.CR1</title>
|
||||
<simplesect>
|
||||
<title>Option 'Update Profile On First Login' moved from Identity provider to Review Profile authenticator</title>
|
||||
<title>Direct access grants disabled by default for clients</title>
|
||||
<para>
|
||||
form-error-page in web.xml will no longer work for client adapter authentication errors. You must define an error-page for
|
||||
the the various HTTP error codes. See documentation for more details if you want to catch and handle adapter error conditions.
|
||||
In order to add more compliance with OpenID Connect specification, we added flags into admin console to Client Settings page,
|
||||
where you can enable/disable various kinds of OpenID Connect/OAuth2 flows (Standard flow, Implicit flow, Direct Access Grants, Service Accounts).
|
||||
As part of this, we have <literal>Direct Access Grants</literal> (corresponds to OAuth2 <literal>Resource Owner Password Credentials Grant</literal>) disabled by default for new clients.
|
||||
</para>
|
||||
<para>
|
||||
Clients migrated from previous version have <literal>Direct Access Grants</literal> enabled just if they had flag <literal>Direct Grants Only</literal> on. The
|
||||
<literal>Direct Grants Only</literal> flag was removed as if you enable Direct Access Grants and disable both Standard+Implicit flow, you will achieve same effect.
|
||||
</para>
|
||||
<para>
|
||||
We also added builtin client <literal>admin-cli</literal> to each realm. This client has <literal>Direct Access Grants</literal> enabled.
|
||||
So if you're using Admin REST API or Keycloak admin-client, you should update your configuration to use <literal>admin-cli</literal> instead
|
||||
of <literal>security-admin-console</literal> as the latter one doesn't have direct access grants enabled anymore by default.
|
||||
</para>
|
||||
</simplesect>
|
||||
<simplesect>
|
||||
<title>Option 'Update Profile On First Login' moved from Identity provider to Review Profile authenticator</title>
|
||||
<para>
|
||||
In this version, we added <literal>First Broker Login</literal>, which allows you to specify what exactly should be done
|
||||
when new user is logged through Identity provider (or Social provider), but there is no existing Keycloak user
|
||||
|
@ -100,6 +113,13 @@
|
|||
and then you configure the option under <literal>Review Profile</literal> authenticator.
|
||||
</para>
|
||||
</simplesect>
|
||||
<simplesect>
|
||||
<title>Element 'form-error-page' in web.xml not supported anymore</title>
|
||||
<para>
|
||||
form-error-page in web.xml will no longer work for client adapter authentication errors. You must define an error-page for
|
||||
the various HTTP error codes. See documentation for more details if you want to catch and handle adapter error conditions.
|
||||
</para>
|
||||
</simplesect>
|
||||
</section>
|
||||
<section>
|
||||
<title>Migrating to 1.6.0.Final</title>
|
||||
|
|
|
@ -24,6 +24,7 @@
|
|||
"clients": [
|
||||
{
|
||||
"clientId": "examples-admin-client",
|
||||
"directAccessGrantsEnabled": true,
|
||||
"enabled": true,
|
||||
"fullScopeAllowed": true,
|
||||
"baseUrl": "/examples-admin-client",
|
||||
|
|
|
@ -43,6 +43,7 @@
|
|||
"clients": [
|
||||
{
|
||||
"clientId": "basic-auth-service",
|
||||
"directAccessGrantsEnabled": true,
|
||||
"enabled": true,
|
||||
"adminUrl": "/basicauth",
|
||||
"baseUrl": "/basicauth",
|
||||
|
|
|
@ -49,6 +49,7 @@
|
|||
"enabled": true,
|
||||
"fullScopeAllowed": true,
|
||||
"baseUrl": "/admin-client",
|
||||
"directAccessGrantsEnabled": true,
|
||||
"redirectUris": [
|
||||
"/admin-client/*"
|
||||
],
|
||||
|
|
|
@ -178,7 +178,7 @@
|
|||
"clientId": "admin-client",
|
||||
"enabled": true,
|
||||
"publicClient": true,
|
||||
"directGrantsOnly": true
|
||||
"directAccessGrantsEnabled": true
|
||||
},
|
||||
{
|
||||
"clientId": "product-sa-client",
|
||||
|
|
|
@ -182,7 +182,7 @@
|
|||
"clientId": "ssh-jmx-admin-client",
|
||||
"enabled": true,
|
||||
"publicClient": false,
|
||||
"directGrantsOnly": true,
|
||||
"directAccessGrantsEnabled": true,
|
||||
"secret": "password"
|
||||
}
|
||||
],
|
||||
|
|
|
@ -55,6 +55,7 @@ role_read-token=Read token
|
|||
role_offline-access=Offline access
|
||||
client_account=Account
|
||||
client_security-admin-console=Security Admin Console
|
||||
client_admin-cli=Admin CLI
|
||||
client_realm-management=Realm Management
|
||||
client_broker=Broker
|
||||
|
||||
|
|
|
@ -113,6 +113,7 @@ role_read-token=Read token
|
|||
role_offline-access=Offline access
|
||||
client_account=Account
|
||||
client_security-admin-console=Security Admin Console
|
||||
client_admin-cli=Admin CLI
|
||||
client_realm-management=Realm Management
|
||||
client_broker=Broker
|
||||
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
package org.keycloak.migration;
|
||||
|
||||
import org.keycloak.models.ProtocolMapperModel;
|
||||
import org.keycloak.models.RealmModel;
|
||||
import org.keycloak.provider.Provider;
|
||||
import org.keycloak.representations.idm.ProtocolMapperRepresentation;
|
||||
|
||||
|
@ -21,4 +22,6 @@ public interface MigrationProvider extends Provider {
|
|||
|
||||
List<ProtocolMapperModel> getBuiltinMappers(String protocol);
|
||||
|
||||
void setupAdminCli(RealmModel realm);
|
||||
|
||||
}
|
||||
|
|
|
@ -2,6 +2,7 @@ package org.keycloak.migration.migrators;
|
|||
|
||||
import java.util.List;
|
||||
|
||||
import org.keycloak.migration.MigrationProvider;
|
||||
import org.keycloak.migration.ModelVersion;
|
||||
import org.keycloak.models.Constants;
|
||||
import org.keycloak.models.KeycloakSession;
|
||||
|
@ -18,6 +19,9 @@ public class MigrateTo1_7_0 {
|
|||
List<RealmModel> realms = session.realms().getRealms();
|
||||
for (RealmModel realm : realms) {
|
||||
realm.setAccessTokenLifespanForImplicitFlow(Constants.DEFAULT_ACCESS_TOKEN_LIFESPAN_FOR_IMPLICIT_FLOW_TIMEOUT);
|
||||
|
||||
MigrationProvider migrationProvider = session.getProvider(MigrationProvider.class);
|
||||
migrationProvider.setupAdminCli(realm);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -8,6 +8,7 @@ import org.keycloak.OAuth2Constants;
|
|||
*/
|
||||
public interface Constants {
|
||||
String ADMIN_CONSOLE_CLIENT_ID = "security-admin-console";
|
||||
String ADMIN_CLI_CLIENT_ID = "admin-cli";
|
||||
|
||||
String ACCOUNT_MANAGEMENT_CLIENT_ID = "account";
|
||||
String IMPERSONATION_SERVICE_CLIENT_ID = "impersonation";
|
||||
|
|
|
@ -225,6 +225,11 @@ public class TokenEndpoint {
|
|||
throw new ErrorResponseException("invalid_grant", "Auth error", Response.Status.BAD_REQUEST);
|
||||
}
|
||||
|
||||
if (!client.isStandardFlowEnabled()) {
|
||||
event.error(Errors.NOT_ALLOWED);
|
||||
throw new ErrorResponseException("invalid_grant", "Client not allowed to exchange code", Response.Status.BAD_REQUEST);
|
||||
}
|
||||
|
||||
UserModel user = session.users().getUserById(userSession.getUser().getId(), realm);
|
||||
if (user == null) {
|
||||
event.error(Errors.USER_NOT_FOUND);
|
||||
|
@ -331,6 +336,11 @@ public class TokenEndpoint {
|
|||
public Response buildResourceOwnerPasswordCredentialsGrant() {
|
||||
event.detail(Details.AUTH_METHOD, "oauth_credentials");
|
||||
|
||||
if (!client.isDirectAccessGrantsEnabled()) {
|
||||
event.error(Errors.NOT_ALLOWED);
|
||||
throw new ErrorResponseException("invalid_grant", "Client not allowed for direct access grants", Response.Status.BAD_REQUEST);
|
||||
}
|
||||
|
||||
if (client.isConsentRequired()) {
|
||||
event.error(Errors.CONSENT_DENIED);
|
||||
throw new ErrorResponseException("invalid_client", "Client requires user consent", Response.Status.BAD_REQUEST);
|
||||
|
|
|
@ -113,6 +113,7 @@ public class RealmManager implements RealmImporter {
|
|||
setupAccountManagement(realm);
|
||||
setupBrokerService(realm);
|
||||
setupAdminConsole(realm);
|
||||
setupAdminCli(realm);
|
||||
setupImpersonationService(realm);
|
||||
setupAuthenticationFlows(realm);
|
||||
setupRequiredActions(realm);
|
||||
|
@ -158,6 +159,30 @@ public class RealmManager implements RealmImporter {
|
|||
adminConsole.addScopeMapping(adminRole);
|
||||
}
|
||||
|
||||
public void setupAdminCli(RealmModel realm) {
|
||||
ClientModel adminCli = realm.getClientByClientId(Constants.ADMIN_CLI_CLIENT_ID);
|
||||
if (adminCli == null) {
|
||||
adminCli = new ClientManager(this).createClient(realm, Constants.ADMIN_CLI_CLIENT_ID);
|
||||
adminCli.setName("${client_" + Constants.ADMIN_CLI_CLIENT_ID + "}");
|
||||
adminCli.setEnabled(true);
|
||||
adminCli.setPublicClient(true);
|
||||
adminCli.setFullScopeAllowed(false);
|
||||
adminCli.setStandardFlowEnabled(false);
|
||||
adminCli.setDirectAccessGrantsEnabled(true);
|
||||
|
||||
RoleModel adminRole;
|
||||
if (realm.getName().equals(Config.getAdminRealm())) {
|
||||
adminRole = realm.getRole(AdminRoles.ADMIN);
|
||||
} else {
|
||||
String realmAdminApplicationClientId = getRealmAdminClientId(realm);
|
||||
ClientModel realmAdminApp = realm.getClientByClientId(realmAdminApplicationClientId);
|
||||
adminRole = realmAdminApp.getRole(AdminRoles.REALM_ADMIN);
|
||||
}
|
||||
adminCli.addScopeMapping(adminRole);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public String getRealmAdminClientId(RealmModel realm) {
|
||||
return Constants.REALM_MANAGEMENT_CLIENT_ID;
|
||||
}
|
||||
|
@ -375,6 +400,7 @@ public class RealmManager implements RealmImporter {
|
|||
|
||||
if (!hasBrokerClient(rep)) setupBrokerService(realm);
|
||||
if (!hasAdminConsoleClient(rep)) setupAdminConsole(realm);
|
||||
if (!hasAdminCliClient(rep)) setupAdminCli(realm);
|
||||
if (!hasRealmRole(rep, Constants.OFFLINE_ACCESS_ROLE)) setupOfflineTokens(realm);
|
||||
|
||||
RepresentationToModel.importRealm(session, rep, realm);
|
||||
|
@ -428,6 +454,10 @@ public class RealmManager implements RealmImporter {
|
|||
return hasClient(rep, Constants.ADMIN_CONSOLE_CLIENT_ID);
|
||||
}
|
||||
|
||||
private boolean hasAdminCliClient(RealmRepresentation rep) {
|
||||
return hasClient(rep, Constants.ADMIN_CLI_CLIENT_ID);
|
||||
}
|
||||
|
||||
private boolean hasClient(RealmRepresentation rep, String clientId) {
|
||||
if (rep.getClients() != null) {
|
||||
for (ClientRepresentation clientRep : rep.getClients()) {
|
||||
|
|
|
@ -10,12 +10,14 @@ import org.keycloak.migration.MigrationProvider;
|
|||
import org.keycloak.models.ClaimMask;
|
||||
import org.keycloak.models.KeycloakSession;
|
||||
import org.keycloak.models.ProtocolMapperModel;
|
||||
import org.keycloak.models.RealmModel;
|
||||
import org.keycloak.models.utils.ModelToRepresentation;
|
||||
import org.keycloak.protocol.LoginProtocol;
|
||||
import org.keycloak.protocol.LoginProtocolFactory;
|
||||
import org.keycloak.protocol.oidc.OIDCLoginProtocolFactory;
|
||||
import org.keycloak.provider.ProviderFactory;
|
||||
import org.keycloak.representations.idm.ProtocolMapperRepresentation;
|
||||
import org.keycloak.services.managers.RealmManager;
|
||||
|
||||
/**
|
||||
* Various common utils needed for migration from older version to newer
|
||||
|
@ -59,6 +61,11 @@ public class DefaultMigrationProvider implements MigrationProvider {
|
|||
return providerFactory.getBuiltinMappers();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setupAdminCli(RealmModel realm) {
|
||||
new RealmManager(session).setupAdminCli(realm);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void close() {
|
||||
}
|
||||
|
|
|
@ -183,7 +183,7 @@ public class ContainersTestEnricher {
|
|||
private void initializeAdminClient() {
|
||||
adminClient.set(Keycloak.getInstance(
|
||||
getAuthServerContextRootFromSystemProperty() + "/auth",
|
||||
MASTER, ADMIN, ADMIN, Constants.ADMIN_CONSOLE_CLIENT_ID));
|
||||
MASTER, ADMIN, ADMIN, Constants.ADMIN_CLI_CLIENT_ID));
|
||||
}
|
||||
|
||||
private void initializeOAuthClient() {
|
||||
|
|
|
@ -187,7 +187,7 @@ public class AdapterTestStrategy extends ExternalResource {
|
|||
Assert.assertTrue(pageSource.contains("iPhone") && pageSource.contains("iPad"));
|
||||
|
||||
// View stats
|
||||
List<Map<String, String>> stats = Keycloak.getInstance("http://localhost:8081/auth", "master", "admin", "admin", "security-admin-console").realm("demo").getClientSessionStats();
|
||||
List<Map<String, String>> stats = Keycloak.getInstance("http://localhost:8081/auth", "master", "admin", "admin", Constants.ADMIN_CLI_CLIENT_ID).realm("demo").getClientSessionStats();
|
||||
Map<String, String> customerPortalStats = null;
|
||||
Map<String, String> productPortalStats = null;
|
||||
for (Map<String, String> s : stats) {
|
||||
|
@ -594,7 +594,7 @@ public class AdapterTestStrategy extends ExternalResource {
|
|||
loginAndCheckSession(driver, loginPage);
|
||||
|
||||
// logout mposolda with admin client
|
||||
Keycloak keycloakAdmin = Keycloak.getInstance(AUTH_SERVER_URL, "master", "admin", "admin", Constants.ADMIN_CONSOLE_CLIENT_ID);
|
||||
Keycloak keycloakAdmin = Keycloak.getInstance(AUTH_SERVER_URL, "master", "admin", "admin", Constants.ADMIN_CLI_CLIENT_ID);
|
||||
ApiUtil.findClientByClientId(keycloakAdmin.realm("demo"), "session-portal").logoutUser("mposolda");
|
||||
|
||||
// bburke should be still logged with original httpSession in our browser window
|
||||
|
|
|
@ -131,7 +131,7 @@ public class RelativeUriAdapterTest {
|
|||
Assert.assertTrue(pageSource.contains("iPhone") && pageSource.contains("iPad"));
|
||||
|
||||
// View stats
|
||||
List<Map<String, String>> stats = Keycloak.getInstance("http://localhost:8081/auth", "master", "admin", "admin", "security-admin-console").realm("demo").getClientSessionStats();
|
||||
List<Map<String, String>> stats = Keycloak.getInstance("http://localhost:8081/auth", "master", "admin", "admin", Constants.ADMIN_CLI_CLIENT_ID).realm("demo").getClientSessionStats();
|
||||
Map<String, String> customerPortalStats = null;
|
||||
Map<String, String> productPortalStats = null;
|
||||
for (Map<String, String> s : stats) {
|
||||
|
|
|
@ -43,7 +43,7 @@ public class AddUserTest {
|
|||
try {
|
||||
server.start();
|
||||
|
||||
Keycloak keycloak = Keycloak.getInstance("http://localhost:8081/auth", "master", "addusertest-admin", "password", Constants.ADMIN_CONSOLE_CLIENT_ID);
|
||||
Keycloak keycloak = Keycloak.getInstance("http://localhost:8081/auth", "master", "addusertest-admin", "password", Constants.ADMIN_CLI_CLIENT_ID);
|
||||
keycloak.realms().findAll();
|
||||
|
||||
RealmRepresentation testRealm = new RealmRepresentation();
|
||||
|
|
|
@ -45,10 +45,12 @@ public abstract class AbstractClientTest {
|
|||
testRealm.setEnabled(true);
|
||||
testRealm.setAccessCodeLifespanUserAction(600);
|
||||
KeycloakModelUtils.generateRealmKeys(testRealm);
|
||||
|
||||
appRealm.getClientByClientId("test-app").setDirectAccessGrantsEnabled(true);
|
||||
}
|
||||
});
|
||||
|
||||
keycloak = Keycloak.getInstance("http://localhost:8081/auth", "master", "admin", "admin", Constants.ADMIN_CONSOLE_CLIENT_ID);
|
||||
keycloak = Keycloak.getInstance("http://localhost:8081/auth", "master", "admin", "admin", Constants.ADMIN_CLI_CLIENT_ID);
|
||||
realm = keycloak.realm(REALM_NAME);
|
||||
}
|
||||
|
||||
|
|
|
@ -79,7 +79,7 @@ public class AdminAPITest {
|
|||
RealmManager manager = new RealmManager(session);
|
||||
|
||||
RealmModel adminRealm = manager.getRealm(Config.getAdminRealm());
|
||||
ClientModel adminConsole = adminRealm.getClientByClientId(Constants.ADMIN_CONSOLE_CLIENT_ID);
|
||||
ClientModel adminConsole = adminRealm.getClientByClientId(Constants.ADMIN_CLI_CLIENT_ID);
|
||||
TokenManager tm = new TokenManager();
|
||||
UserModel admin = session.users().getUserByUsername("admin", adminRealm);
|
||||
ClientSessionModel clientSession = session.sessions().createClientSession(adminRealm, adminConsole);
|
||||
|
|
|
@ -4,6 +4,7 @@ import org.junit.Rule;
|
|||
import org.junit.Test;
|
||||
import org.keycloak.admin.client.resource.ClientResource;
|
||||
import org.keycloak.admin.client.resource.ProtocolMappersResource;
|
||||
import org.keycloak.models.Constants;
|
||||
import org.keycloak.protocol.oidc.OIDCLoginProtocolFactory;
|
||||
import org.keycloak.representations.idm.ClientRepresentation;
|
||||
import org.keycloak.representations.idm.ProtocolMapperRepresentation;
|
||||
|
@ -42,7 +43,7 @@ public class ClientTest extends AbstractClientTest {
|
|||
|
||||
@Test
|
||||
public void getClients() {
|
||||
assertNames(realm.clients().findAll(), "account", "realm-management", "security-admin-console", "broker");
|
||||
assertNames(realm.clients().findAll(), "account", "realm-management", "security-admin-console", "broker", Constants.ADMIN_CLI_CLIENT_ID);
|
||||
}
|
||||
|
||||
private String createClient() {
|
||||
|
@ -60,7 +61,7 @@ public class ClientTest extends AbstractClientTest {
|
|||
String id = createClient();
|
||||
|
||||
assertNotNull(realm.clients().get(id));
|
||||
assertNames(realm.clients().findAll(), "account", "realm-management", "security-admin-console", "broker", "my-app");
|
||||
assertNames(realm.clients().findAll(), "account", "realm-management", "security-admin-console", "broker", "my-app", Constants.ADMIN_CLI_CLIENT_ID);
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
|
@ -117,7 +117,7 @@ public class ImpersonationTest {
|
|||
RealmManager manager = new RealmManager(session);
|
||||
|
||||
RealmModel adminRealm = manager.getRealm(realm);
|
||||
ClientModel adminConsole = adminRealm.getClientByClientId(Constants.ADMIN_CONSOLE_CLIENT_ID);
|
||||
ClientModel adminConsole = adminRealm.getClientByClientId(Constants.ADMIN_CLI_CLIENT_ID);
|
||||
TokenManager tm = new TokenManager();
|
||||
UserModel admin = session.users().getUserByUsername(username, adminRealm);
|
||||
ClientSessionModel clientSession = session.sessions().createClientSession(adminRealm, adminConsole);
|
||||
|
|
|
@ -77,6 +77,8 @@ public class FederationProvidersIntegrationTest {
|
|||
ldapFedProvider.getLdapIdentityStore().updatePassword(john, "Password1");
|
||||
|
||||
LDAPObject existing = FederationTestUtils.addLDAPUser(ldapFedProvider, appRealm, "existing", "Existing", "Foo", "existing@email.org", null, "5678");
|
||||
|
||||
appRealm.getClientByClientId("test-app").setDirectAccessGrantsEnabled(true);
|
||||
}
|
||||
});
|
||||
|
||||
|
|
|
@ -77,6 +77,8 @@ public class BruteForceTest {
|
|||
|
||||
appRealm.setBruteForceProtected(true);
|
||||
appRealm.setFailureFactor(2);
|
||||
|
||||
appRealm.getClientByClientId("test-app").setDirectAccessGrantsEnabled(true);
|
||||
}
|
||||
|
||||
});
|
||||
|
@ -116,7 +118,7 @@ public class BruteForceTest {
|
|||
}
|
||||
|
||||
public String getAdminToken() throws Exception {
|
||||
String clientId = Constants.ADMIN_CONSOLE_CLIENT_ID;
|
||||
String clientId = Constants.ADMIN_CLI_CLIENT_ID;
|
||||
return oauth.doGrantAccessTokenRequest("master", "admin", "admin", null, clientId, null).getAccessToken();
|
||||
}
|
||||
|
||||
|
|
|
@ -127,7 +127,11 @@ public class CustomFlowTest {
|
|||
// Set passthrough clientAuthenticator for our clients
|
||||
ClientModel dummyClient = new ClientManager().createClient(appRealm, "dummy-client");
|
||||
dummyClient.setClientAuthenticatorType(PassThroughClientAuthenticator.PROVIDER_ID);
|
||||
appRealm.getClientByClientId("test-app").setClientAuthenticatorType(PassThroughClientAuthenticator.PROVIDER_ID);
|
||||
dummyClient.setDirectAccessGrantsEnabled(true);
|
||||
|
||||
ClientModel testApp = appRealm.getClientByClientId("test-app");
|
||||
testApp.setClientAuthenticatorType(PassThroughClientAuthenticator.PROVIDER_ID);
|
||||
testApp.setDirectAccessGrantsEnabled(true);
|
||||
}
|
||||
});
|
||||
|
||||
|
|
|
@ -48,6 +48,7 @@ public class JaxrsBasicAuthTest {
|
|||
app.setEnabled(true);
|
||||
app.setSecret("password");
|
||||
app.setFullScopeAllowed(true);
|
||||
app.setDirectAccessGrantsEnabled(true);
|
||||
|
||||
JaxrsBasicAuthTest.appRealm = appRealm;
|
||||
}
|
||||
|
|
|
@ -456,7 +456,7 @@ public class SamlAdapterTestStrategy extends ExternalResource {
|
|||
|
||||
public static void uploadSP(String AUTH_SERVER_URL) {
|
||||
try {
|
||||
Keycloak keycloak = Keycloak.getInstance(AUTH_SERVER_URL, "master", "admin", "admin", Constants.ADMIN_CONSOLE_CLIENT_ID, null);
|
||||
Keycloak keycloak = Keycloak.getInstance(AUTH_SERVER_URL, "master", "admin", "admin", Constants.ADMIN_CLI_CLIENT_ID, null);
|
||||
RealmResource admin = keycloak.realm("demo");
|
||||
|
||||
admin.toRepresentation();
|
||||
|
|
|
@ -62,15 +62,19 @@ public class GroupTest {
|
|||
@Override
|
||||
public void config(RealmManager manager, RealmModel adminstrationRealm, RealmModel appRealm) {
|
||||
ClientModel app = new ClientManager(manager).createClient(appRealm, "resource-owner");
|
||||
app.setDirectAccessGrantsEnabled(true);
|
||||
app.setSecret("secret");
|
||||
|
||||
app = appRealm.getClientByClientId("test-app");
|
||||
app.setDirectAccessGrantsEnabled(true);
|
||||
|
||||
UserModel user = session.users().addUser(appRealm, "direct-login");
|
||||
user.setEmail("direct-login@localhost");
|
||||
user.setEnabled(true);
|
||||
|
||||
|
||||
session.users().updateCredential(appRealm, user, UserCredentialModel.password("password"));
|
||||
keycloak = Keycloak.getInstance("http://localhost:8081/auth", "master", "admin", "admin", Constants.ADMIN_CONSOLE_CLIENT_ID);
|
||||
keycloak = Keycloak.getInstance("http://localhost:8081/auth", "master", "admin", "admin", Constants.ADMIN_CLI_CLIENT_ID);
|
||||
}
|
||||
});
|
||||
|
||||
|
|
|
@ -90,7 +90,7 @@ public class ImportTest extends AbstractModelTest {
|
|||
Assert.assertEquals(0, session.users().getFederatedIdentities(user, realm).size());
|
||||
|
||||
List<ClientModel> resources = realm.getClients();
|
||||
Assert.assertEquals(7, resources.size());
|
||||
Assert.assertEquals(8, resources.size());
|
||||
|
||||
// Test applications imported
|
||||
ClientModel application = realm.getClientByClientId("Application");
|
||||
|
@ -101,7 +101,7 @@ public class ImportTest extends AbstractModelTest {
|
|||
Assert.assertNotNull(otherApp);
|
||||
Assert.assertNull(nonExisting);
|
||||
Map<String, ClientModel> clients = realm.getClientNameMap();
|
||||
Assert.assertEquals(7, clients.size());
|
||||
Assert.assertEquals(8, clients.size());
|
||||
Assert.assertTrue(clients.values().contains(application));
|
||||
Assert.assertTrue(clients.values().contains(otherApp));
|
||||
Assert.assertTrue(clients.values().contains(accountApp));
|
||||
|
|
|
@ -92,7 +92,14 @@ import static org.junit.Assert.*;
|
|||
public class AccessTokenTest {
|
||||
|
||||
@ClassRule
|
||||
public static KeycloakRule keycloakRule = new KeycloakRule();
|
||||
public static KeycloakRule keycloakRule = new KeycloakRule(new KeycloakRule.KeycloakSetup() {
|
||||
|
||||
@Override
|
||||
public void config(RealmManager manager, RealmModel adminstrationRealm, RealmModel appRealm) {
|
||||
appRealm.getClientByClientId("test-app").setDirectAccessGrantsEnabled(true);
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
@Rule
|
||||
public WebRule webRule = new WebRule(this);
|
||||
|
|
|
@ -61,6 +61,7 @@ public class ClientAuthSignedJWTTest {
|
|||
app1.setClientAuthenticatorType(JWTClientAuthenticator.PROVIDER_ID);
|
||||
|
||||
ClientModel app2 = appRealm.addClient("client2");
|
||||
app2.setDirectAccessGrantsEnabled(true);
|
||||
new ClientManager(manager).enableServiceAccount(app2);
|
||||
app2.setClientAuthenticatorType(JWTClientAuthenticator.PROVIDER_ID);
|
||||
|
||||
|
|
|
@ -67,6 +67,7 @@ public class OfflineTokenTest {
|
|||
appRealm.setSsoSessionIdleTimeout(30);
|
||||
|
||||
ClientModel app = new ClientManager(manager).createClient(appRealm, "offline-client");
|
||||
app.setDirectAccessGrantsEnabled(true);
|
||||
app.setSecret("secret1");
|
||||
String testAppRedirectUri = appRealm.getClientByClientId("test-app").getRedirectUris().iterator().next();
|
||||
offlineClientAppUri = UriUtils.getOrigin(testAppRedirectUri) + "/offline-client";
|
||||
|
|
|
@ -71,7 +71,14 @@ import static org.junit.Assert.assertNull;
|
|||
public class RefreshTokenTest {
|
||||
|
||||
@ClassRule
|
||||
public static KeycloakRule keycloakRule = new KeycloakRule();
|
||||
public static KeycloakRule keycloakRule = new KeycloakRule(new KeycloakRule.KeycloakSetup() {
|
||||
|
||||
@Override
|
||||
public void config(RealmManager manager, RealmModel adminstrationRealm, RealmModel appRealm) {
|
||||
appRealm.getClientByClientId("test-app").setDirectAccessGrantsEnabled(true);
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
@Rule
|
||||
public WebRule webRule = new WebRule(this);
|
||||
|
|
|
@ -35,9 +35,11 @@ public class ResourceOwnerPasswordCredentialsGrantTest {
|
|||
@Override
|
||||
public void config(RealmManager manager, RealmModel adminstrationRealm, RealmModel appRealm) {
|
||||
ClientModel app = new ClientManager(manager).createClient(appRealm, "resource-owner");
|
||||
app.setDirectAccessGrantsEnabled(true);
|
||||
app.setSecret("secret");
|
||||
|
||||
ClientModel app2 = new ClientManager(manager).createClient(appRealm, "resource-owner-public");
|
||||
app2.setDirectAccessGrantsEnabled(true);
|
||||
app2.setPublicClient(true);
|
||||
|
||||
UserModel user = session.users().addUser(appRealm, "direct-login");
|
||||
|
@ -191,6 +193,41 @@ public class ResourceOwnerPasswordCredentialsGrantTest {
|
|||
.assertEvent();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void grantAccessTokenClientNotAllowed() throws Exception {
|
||||
keycloakRule.update(new KeycloakRule.KeycloakSetup() {
|
||||
@Override
|
||||
public void config(RealmManager manager, RealmModel adminstrationRealm, RealmModel appRealm) {
|
||||
ClientModel client = appRealm.getClientByClientId("resource-owner");
|
||||
client.setDirectAccessGrantsEnabled(false);
|
||||
}
|
||||
});
|
||||
|
||||
oauth.clientId("resource-owner");
|
||||
|
||||
OAuthClient.AccessTokenResponse response = oauth.doGrantAccessTokenRequest("secret", "test-user@localhost", "password");
|
||||
|
||||
assertEquals(400, response.getStatusCode());
|
||||
|
||||
assertEquals("invalid_grant", response.getError());
|
||||
|
||||
events.expectLogin()
|
||||
.client("resource-owner")
|
||||
.session((String) null)
|
||||
.clearDetails()
|
||||
.error(Errors.NOT_ALLOWED)
|
||||
.user((String) null)
|
||||
.assertEvent();
|
||||
|
||||
keycloakRule.update(new KeycloakRule.KeycloakSetup() {
|
||||
@Override
|
||||
public void config(RealmManager manager, RealmModel adminstrationRealm, RealmModel appRealm) {
|
||||
ClientModel client = appRealm.getClientByClientId("resource-owner");
|
||||
client.setDirectAccessGrantsEnabled(true);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
public void grantAccessTokenVerifyEmail() throws Exception {
|
||||
|
||||
|
|
|
@ -30,6 +30,7 @@ import org.keycloak.models.RealmModel;
|
|||
import org.keycloak.protocol.oidc.OIDCLoginProtocolService;
|
||||
import org.keycloak.representations.AccessTokenResponse;
|
||||
import org.keycloak.representations.UserInfo;
|
||||
import org.keycloak.services.managers.RealmManager;
|
||||
import org.keycloak.testsuite.rule.KeycloakRule;
|
||||
import org.keycloak.testsuite.rule.WebResource;
|
||||
import org.keycloak.testsuite.rule.WebRule;
|
||||
|
@ -56,7 +57,14 @@ import static org.junit.Assert.assertNotNull;
|
|||
public class UserInfoTest {
|
||||
|
||||
@ClassRule
|
||||
public static KeycloakRule keycloakRule = new KeycloakRule();
|
||||
public static KeycloakRule keycloakRule = new KeycloakRule(new KeycloakRule.KeycloakSetup() {
|
||||
|
||||
@Override
|
||||
public void config(RealmManager manager, RealmModel adminstrationRealm, RealmModel appRealm) {
|
||||
appRealm.getClientByClientId("test-app").setDirectAccessGrantsEnabled(true);
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
@Rule
|
||||
public WebRule webRule = new WebRule(this);
|
||||
|
|
|
@ -457,7 +457,7 @@ public class SamlBindingTest {
|
|||
|
||||
public static void uploadSP() {
|
||||
try {
|
||||
Keycloak keycloak = Keycloak.getInstance("http://localhost:8081/auth", "master", "admin", "admin", Constants.ADMIN_CONSOLE_CLIENT_ID, null);
|
||||
Keycloak keycloak = Keycloak.getInstance("http://localhost:8081/auth", "master", "admin", "admin", Constants.ADMIN_CLI_CLIENT_ID, null);
|
||||
RealmResource admin = keycloak.realm("demo");
|
||||
|
||||
admin.toRepresentation();
|
||||
|
|
|
@ -120,6 +120,7 @@
|
|||
{
|
||||
"name": "customer-portal",
|
||||
"enabled": true,
|
||||
"directAccessGrantsEnabled": true,
|
||||
"adminUrl": "http://localhost:8081/customer-portal",
|
||||
"baseUrl": "http://localhost:8081/customer-portal",
|
||||
"redirectUris": [
|
||||
|
|
|
@ -156,6 +156,7 @@
|
|||
"name": "Applicationn",
|
||||
"enabled": true,
|
||||
"implicitFlowEnabled": true,
|
||||
"directAccessGrantsEnabled": true,
|
||||
"nodeReRegistrationTimeout": 50,
|
||||
"registeredNodes": {
|
||||
"node1": 10,
|
||||
|
|
|
@ -75,6 +75,7 @@
|
|||
"enabled": true,
|
||||
"adminUrl": "http://localhost:8082/customer-portal",
|
||||
"baseUrl": "http://localhost:8082/customer-portal",
|
||||
"directAccessGrantsEnabled": true,
|
||||
"redirectUris": [
|
||||
"http://localhost:8082/customer-portal/*"
|
||||
],
|
||||
|
|
|
@ -46,6 +46,7 @@
|
|||
"fullScopeAllowed": true,
|
||||
"adminUrl": "http://localhost:8080/customer-portal",
|
||||
"baseUrl": "http://localhost:8080/customer-portal",
|
||||
"directAccessGrantsEnabled": true,
|
||||
"redirectUris": [
|
||||
"http://localhost:8080/customer-portal/*"
|
||||
],
|
||||
|
|
|
@ -75,6 +75,7 @@
|
|||
"enabled": true,
|
||||
"adminUrl": "http://localhost:8082/customer-portal",
|
||||
"baseUrl": "http://localhost:8082/customer-portal",
|
||||
"directAccessGrantsEnabled": true,
|
||||
"redirectUris": [
|
||||
"http://localhost:8082/customer-portal/*"
|
||||
],
|
||||
|
|
|
@ -46,6 +46,7 @@
|
|||
"fullScopeAllowed": true,
|
||||
"adminUrl": "http://localhost:8080/customer-portal",
|
||||
"baseUrl": "http://localhost:8080/customer-portal",
|
||||
"directAccessGrantsEnabled": true,
|
||||
"redirectUris": [
|
||||
"http://localhost:8080/customer-portal/*"
|
||||
],
|
||||
|
|
|
@ -75,6 +75,7 @@
|
|||
"enabled": true,
|
||||
"adminUrl": "http://localhost:8082/customer-portal",
|
||||
"baseUrl": "http://localhost:8082/customer-portal",
|
||||
"directAccessGrantsEnabled": true,
|
||||
"redirectUris": [
|
||||
"http://localhost:8082/customer-portal/*"
|
||||
],
|
||||
|
|
|
@ -75,6 +75,7 @@
|
|||
"enabled": true,
|
||||
"adminUrl": "http://localhost:8082/customer-portal",
|
||||
"baseUrl": "http://localhost:8082/customer-portal",
|
||||
"directAccessGrantsEnabled": true,
|
||||
"redirectUris": [
|
||||
"http://localhost:8082/customer-portal/*"
|
||||
],
|
||||
|
|
|
@ -75,6 +75,7 @@
|
|||
"enabled": true,
|
||||
"adminUrl": "http://localhost:8082/customer-portal",
|
||||
"baseUrl": "http://localhost:8082/customer-portal",
|
||||
"directAccessGrantsEnabled": true,
|
||||
"redirectUris": [
|
||||
"http://localhost:8082/customer-portal/*"
|
||||
],
|
||||
|
|
|
@ -75,6 +75,7 @@
|
|||
"enabled": true,
|
||||
"adminUrl": "http://localhost:8082/customer-portal",
|
||||
"baseUrl": "http://localhost:8082/customer-portal",
|
||||
"directAccessGrantsEnabled": true,
|
||||
"redirectUris": [
|
||||
"http://localhost:8082/customer-portal/*"
|
||||
],
|
||||
|
|
|
@ -46,6 +46,7 @@
|
|||
"fullScopeAllowed": true,
|
||||
"adminUrl": "http://localhost:8080/customer-portal",
|
||||
"baseUrl": "http://localhost:8080/customer-portal",
|
||||
"directAccessGrantsEnabled": true,
|
||||
"redirectUris": [
|
||||
"http://localhost:8080/customer-portal/*"
|
||||
],
|
||||
|
|
Loading…
Reference in a new issue