brute force refactr, mv protocol

This commit is contained in:
Bill Burke 2016-01-15 19:25:28 -05:00
parent 5017d71383
commit 007e9530ec
33 changed files with 159 additions and 88 deletions

View file

@ -32,8 +32,8 @@ import java.util.List;
public class SamlProtocolFactory extends AbstractLoginProtocolFactory { public class SamlProtocolFactory extends AbstractLoginProtocolFactory {
@Override @Override
public Object createProtocolEndpoint(RealmModel realm, EventBuilder event, AuthenticationManager authManager) { public Object createProtocolEndpoint(RealmModel realm, EventBuilder event) {
return new SamlService(realm, event, authManager); return new SamlService(realm, event);
} }
@Override @Override

View file

@ -61,8 +61,8 @@ public class SamlService extends AuthorizationEndpointBase {
protected static final Logger logger = Logger.getLogger(SamlService.class); protected static final Logger logger = Logger.getLogger(SamlService.class);
public SamlService(RealmModel realm, EventBuilder event, AuthenticationManager authManager) { public SamlService(RealmModel realm, EventBuilder event) {
super(realm, event, authManager); super(realm, event);
} }
public abstract class BindingProtocol { public abstract class BindingProtocol {
@ -556,7 +556,7 @@ public class SamlService extends AuthorizationEndpointBase {
@POST @POST
@Consumes("application/soap+xml") @Consumes("application/soap+xml")
public Response soapBinding(InputStream inputStream) { public Response soapBinding(InputStream inputStream) {
SamlEcpProfileService bindingService = new SamlEcpProfileService(realm, event, authManager); SamlEcpProfileService bindingService = new SamlEcpProfileService(realm, event);
ResteasyProviderFactory.getInstance().injectProperties(bindingService); ResteasyProviderFactory.getInstance().injectProperties(bindingService);

View file

@ -36,8 +36,8 @@ public class SamlEcpProfileService extends SamlService {
private static final String NS_PREFIX_SAML_PROTOCOL = "samlp"; private static final String NS_PREFIX_SAML_PROTOCOL = "samlp";
private static final String NS_PREFIX_SAML_ASSERTION = "saml"; private static final String NS_PREFIX_SAML_ASSERTION = "saml";
public SamlEcpProfileService(RealmModel realm, EventBuilder event, AuthenticationManager authManager) { public SamlEcpProfileService(RealmModel realm, EventBuilder event) {
super(realm, event, authManager); super(realm, event);
} }
public Response authenticate(InputStream inputStream) { public Response authenticate(InputStream inputStream) {

View file

@ -30,7 +30,7 @@ public interface LoginProtocolFactory extends ProviderFactory<LoginProtocol> {
*/ */
List<ProtocolMapperModel> getDefaultBuiltinMappers(); List<ProtocolMapperModel> getDefaultBuiltinMappers();
Object createProtocolEndpoint(RealmModel realm, EventBuilder event, AuthenticationManager authManager); Object createProtocolEndpoint(RealmModel realm, EventBuilder event);
/** /**
* Setup default values for new clients. This expects that the representation has already set up the client * Setup default values for new clients. This expects that the representation has already set up the client

View file

@ -0,0 +1,16 @@
package org.keycloak.services.managers;
import org.keycloak.common.ClientConnection;
import org.keycloak.models.KeycloakSession;
import org.keycloak.models.RealmModel;
import org.keycloak.provider.Provider;
/**
* @author <a href="mailto:bill@burkecentral.com">Bill Burke</a>
* @version $Revision: 1 $
*/
public interface BruteForceProtector extends Provider {
void failedLogin(RealmModel realm, String username, ClientConnection clientConnection);
boolean isTemporarilyDisabled(KeycloakSession session, RealmModel realm, String username);
}

View file

@ -0,0 +1,10 @@
package org.keycloak.services.managers;
import org.keycloak.provider.ProviderFactory;
/**
* @author <a href="mailto:bill@burkecentral.com">Bill Burke</a>
* @version $Revision: 1 $
*/
public interface BruteForceProtectorFactory extends ProviderFactory<BruteForceProtector> {
}

View file

@ -0,0 +1,34 @@
package org.keycloak.services.managers;
import org.keycloak.models.UserFederationProvider;
import org.keycloak.models.UserFederationProviderFactory;
import org.keycloak.provider.Provider;
import org.keycloak.provider.ProviderFactory;
import org.keycloak.provider.Spi;
/**
* @author <a href="mailto:sthorger@redhat.com">Stian Thorgersen</a>
*/
public class BruteForceProtectorSpi implements Spi {
@Override
public boolean isInternal() {
return true;
}
@Override
public String getName() {
return "bruteForceProtector";
}
@Override
public Class<? extends Provider> getProviderClass() {
return BruteForceProtector.class;
}
@Override
public Class<? extends ProviderFactory> getProviderFactoryClass() {
return BruteForceProtectorFactory.class;
}
}

View file

@ -11,3 +11,8 @@ org.keycloak.events.EventStoreSpi
org.keycloak.exportimport.ExportSpi org.keycloak.exportimport.ExportSpi
org.keycloak.exportimport.ImportSpi org.keycloak.exportimport.ImportSpi
org.keycloak.timer.TimerSpi org.keycloak.timer.TimerSpi
org.keycloak.services.managers.BruteForceProtectorSpi
org.keycloak.protocol.ClientInstallationSpi
org.keycloak.protocol.LoginProtocolSpi
org.keycloak.protocol.ProtocolMapperSpi

View file

@ -84,6 +84,13 @@ public class AuthenticationProcessor {
return this; return this;
} }
public BruteForceProtector getBruteForceProtector() {
if (protector == null) {
protector = session.getProvider(BruteForceProtector.class);
}
return protector;
}
public RealmModel getRealm() { public RealmModel getRealm() {
return realm; return realm;
} }
@ -149,11 +156,6 @@ public class AuthenticationProcessor {
return this; return this;
} }
public AuthenticationProcessor setProtector(BruteForceProtector protector) {
this.protector = protector;
return this;
}
public AuthenticationProcessor setEventBuilder(EventBuilder eventBuilder) { public AuthenticationProcessor setEventBuilder(EventBuilder eventBuilder) {
this.event = eventBuilder; this.event = eventBuilder;
return this; return this;
@ -405,7 +407,7 @@ public class AuthenticationProcessor {
@Override @Override
public BruteForceProtector getProtector() { public BruteForceProtector getProtector() {
return AuthenticationProcessor.this.protector; return AuthenticationProcessor.this.getBruteForceProtector();
} }
@Override @Override
@ -571,7 +573,6 @@ public class AuthenticationProcessor {
.setForwardedSuccessMessage(reset.getSuccessMessage()) .setForwardedSuccessMessage(reset.getSuccessMessage())
.setConnection(connection) .setConnection(connection)
.setEventBuilder(event) .setEventBuilder(event)
.setProtector(protector)
.setRealm(realm) .setRealm(realm)
.setSession(session) .setSession(session)
.setUriInfo(uriInfo) .setUriInfo(uriInfo)

View file

@ -48,10 +48,9 @@ public abstract class AuthorizationEndpointBase {
@Context @Context
protected ClientConnection clientConnection; protected ClientConnection clientConnection;
public AuthorizationEndpointBase(RealmModel realm, EventBuilder event, AuthenticationManager authManager) { public AuthorizationEndpointBase(RealmModel realm, EventBuilder event) {
this.realm = realm; this.realm = realm;
this.event = event; this.event = event;
this.authManager = authManager;
} }
protected AuthenticationProcessor createProcessor(ClientSessionModel clientSession, String flowId, String flowPath) { protected AuthenticationProcessor createProcessor(ClientSessionModel clientSession, String flowId, String flowPath) {
@ -62,7 +61,6 @@ public abstract class AuthorizationEndpointBase {
.setBrowserFlow(true) .setBrowserFlow(true)
.setConnection(clientConnection) .setConnection(clientConnection)
.setEventBuilder(event) .setEventBuilder(event)
.setProtector(authManager.getProtector())
.setRealm(realm) .setRealm(realm)
.setSession(session) .setSession(session)
.setUriInfo(uriInfo) .setUriInfo(uriInfo)

View file

@ -160,8 +160,8 @@ public class OIDCLoginProtocolFactory extends AbstractLoginProtocolFactory {
} }
@Override @Override
public Object createProtocolEndpoint(RealmModel realm, EventBuilder event, AuthenticationManager authManager) { public Object createProtocolEndpoint(RealmModel realm, EventBuilder event) {
return new OIDCLoginProtocolService(realm, event, authManager); return new OIDCLoginProtocolService(realm, event);
} }
@Override @Override

View file

@ -45,7 +45,6 @@ public class OIDCLoginProtocolService {
private RealmModel realm; private RealmModel realm;
private TokenManager tokenManager; private TokenManager tokenManager;
private EventBuilder event; private EventBuilder event;
private AuthenticationManager authManager;
@Context @Context
private UriInfo uriInfo; private UriInfo uriInfo;
@ -56,11 +55,10 @@ public class OIDCLoginProtocolService {
@Context @Context
private HttpHeaders headers; private HttpHeaders headers;
public OIDCLoginProtocolService(RealmModel realm, EventBuilder event, AuthenticationManager authManager) { public OIDCLoginProtocolService(RealmModel realm, EventBuilder event) {
this.realm = realm; this.realm = realm;
this.tokenManager = new TokenManager(); this.tokenManager = new TokenManager();
this.event = event; this.event = event;
this.authManager = authManager;
} }
public static UriBuilder tokenServiceBaseUrl(UriInfo uriInfo) { public static UriBuilder tokenServiceBaseUrl(UriInfo uriInfo) {
@ -117,7 +115,7 @@ public class OIDCLoginProtocolService {
*/ */
@Path("auth") @Path("auth")
public Object auth() { public Object auth() {
AuthorizationEndpoint endpoint = new AuthorizationEndpoint(authManager, realm, event); AuthorizationEndpoint endpoint = new AuthorizationEndpoint(realm, event);
ResteasyProviderFactory.getInstance().injectProperties(endpoint); ResteasyProviderFactory.getInstance().injectProperties(endpoint);
return endpoint; return endpoint;
} }
@ -127,7 +125,7 @@ public class OIDCLoginProtocolService {
*/ */
@Path("registrations") @Path("registrations")
public Object registerPage() { public Object registerPage() {
AuthorizationEndpoint endpoint = new AuthorizationEndpoint(authManager, realm, event); AuthorizationEndpoint endpoint = new AuthorizationEndpoint(realm, event);
ResteasyProviderFactory.getInstance().injectProperties(endpoint); ResteasyProviderFactory.getInstance().injectProperties(endpoint);
return endpoint.register(); return endpoint.register();
} }
@ -137,7 +135,7 @@ public class OIDCLoginProtocolService {
*/ */
@Path("forgot-credentials") @Path("forgot-credentials")
public Object forgotCredentialsPage() { public Object forgotCredentialsPage() {
AuthorizationEndpoint endpoint = new AuthorizationEndpoint(authManager, realm, event); AuthorizationEndpoint endpoint = new AuthorizationEndpoint(realm, event);
ResteasyProviderFactory.getInstance().injectProperties(endpoint); ResteasyProviderFactory.getInstance().injectProperties(endpoint);
return endpoint.forgotCredentials(); return endpoint.forgotCredentials();
} }
@ -147,7 +145,7 @@ public class OIDCLoginProtocolService {
*/ */
@Path("token") @Path("token")
public Object token() { public Object token() {
TokenEndpoint endpoint = new TokenEndpoint(tokenManager, authManager, realm, event); TokenEndpoint endpoint = new TokenEndpoint(tokenManager, realm, event);
ResteasyProviderFactory.getInstance().injectProperties(endpoint); ResteasyProviderFactory.getInstance().injectProperties(endpoint);
return endpoint; return endpoint;
} }
@ -155,7 +153,7 @@ public class OIDCLoginProtocolService {
@Path("login") @Path("login")
@Deprecated @Deprecated
public Object loginPage() { public Object loginPage() {
AuthorizationEndpoint endpoint = new AuthorizationEndpoint(authManager, realm, event); AuthorizationEndpoint endpoint = new AuthorizationEndpoint(realm, event);
ResteasyProviderFactory.getInstance().injectProperties(endpoint); ResteasyProviderFactory.getInstance().injectProperties(endpoint);
return endpoint.legacy(OIDCLoginProtocol.CODE_PARAM); return endpoint.legacy(OIDCLoginProtocol.CODE_PARAM);
} }
@ -170,7 +168,7 @@ public class OIDCLoginProtocolService {
@Path("grants/access") @Path("grants/access")
@Deprecated @Deprecated
public Object grantAccessToken() { public Object grantAccessToken() {
TokenEndpoint endpoint = new TokenEndpoint(tokenManager, authManager, realm, event); TokenEndpoint endpoint = new TokenEndpoint(tokenManager, realm, event);
ResteasyProviderFactory.getInstance().injectProperties(endpoint); ResteasyProviderFactory.getInstance().injectProperties(endpoint);
return endpoint.legacy(OAuth2Constants.PASSWORD); return endpoint.legacy(OAuth2Constants.PASSWORD);
} }
@ -178,7 +176,7 @@ public class OIDCLoginProtocolService {
@Path("refresh") @Path("refresh")
@Deprecated @Deprecated
public Object refreshAccessToken() { public Object refreshAccessToken() {
TokenEndpoint endpoint = new TokenEndpoint(tokenManager, authManager, realm, event); TokenEndpoint endpoint = new TokenEndpoint(tokenManager, realm, event);
ResteasyProviderFactory.getInstance().injectProperties(endpoint); ResteasyProviderFactory.getInstance().injectProperties(endpoint);
return endpoint.legacy(OAuth2Constants.REFRESH_TOKEN); return endpoint.legacy(OAuth2Constants.REFRESH_TOKEN);
} }
@ -186,7 +184,7 @@ public class OIDCLoginProtocolService {
@Path("access/codes") @Path("access/codes")
@Deprecated @Deprecated
public Object accessCodeToToken() { public Object accessCodeToToken() {
TokenEndpoint endpoint = new TokenEndpoint(tokenManager, authManager, realm, event); TokenEndpoint endpoint = new TokenEndpoint(tokenManager, realm, event);
ResteasyProviderFactory.getInstance().injectProperties(endpoint); ResteasyProviderFactory.getInstance().injectProperties(endpoint);
return endpoint.legacy(OAuth2Constants.AUTHORIZATION_CODE); return endpoint.legacy(OAuth2Constants.AUTHORIZATION_CODE);
} }
@ -225,7 +223,7 @@ public class OIDCLoginProtocolService {
@Path("logout") @Path("logout")
public Object logout() { public Object logout() {
LogoutEndpoint endpoint = new LogoutEndpoint(tokenManager, authManager, realm, event); LogoutEndpoint endpoint = new LogoutEndpoint(tokenManager, realm, event);
ResteasyProviderFactory.getInstance().injectProperties(endpoint); ResteasyProviderFactory.getInstance().injectProperties(endpoint);
return endpoint; return endpoint;
} }

View file

@ -63,8 +63,8 @@ public class AuthorizationEndpoint extends AuthorizationEndpointBase {
private String legacyResponseType; private String legacyResponseType;
public AuthorizationEndpoint(AuthenticationManager authManager, RealmModel realm, EventBuilder event) { public AuthorizationEndpoint(RealmModel realm, EventBuilder event) {
super(realm, event, authManager); super(realm, event);
event.event(EventType.LOGIN); event.event(EventType.LOGIN);
} }

View file

@ -61,13 +61,11 @@ public class LogoutEndpoint {
private UriInfo uriInfo; private UriInfo uriInfo;
private TokenManager tokenManager; private TokenManager tokenManager;
private AuthenticationManager authManager;
private RealmModel realm; private RealmModel realm;
private EventBuilder event; private EventBuilder event;
public LogoutEndpoint(TokenManager tokenManager, AuthenticationManager authManager, RealmModel realm, EventBuilder event) { public LogoutEndpoint(TokenManager tokenManager, RealmModel realm, EventBuilder event) {
this.tokenManager = tokenManager; this.tokenManager = tokenManager;
this.authManager = authManager;
this.realm = realm; this.realm = realm;
this.event = event; this.event = event;
} }
@ -117,7 +115,7 @@ public class LogoutEndpoint {
} }
// authenticate identity cookie, but ignore an access token timeout as we're logging out anyways. // authenticate identity cookie, but ignore an access token timeout as we're logging out anyways.
AuthenticationManager.AuthResult authResult = authManager.authenticateIdentityCookie(session, realm, false); AuthenticationManager.AuthResult authResult = AuthenticationManager.authenticateIdentityCookie(session, realm, false);
if (authResult != null) { if (authResult != null) {
userSession = userSession != null ? userSession : authResult.getSession(); userSession = userSession != null ? userSession : authResult.getSession();
if (redirect != null) userSession.setNote(OIDCLoginProtocol.LOGOUT_REDIRECT_URI, redirect); if (redirect != null) userSession.setNote(OIDCLoginProtocol.LOGOUT_REDIRECT_URI, redirect);
@ -129,7 +127,7 @@ public class LogoutEndpoint {
return response; return response;
} else if (userSession != null) { // non browser logout } else if (userSession != null) { // non browser logout
event.event(EventType.LOGOUT); event.event(EventType.LOGOUT);
authManager.backchannelLogout(session, realm, userSession, uriInfo, clientConnection, headers, true); AuthenticationManager.backchannelLogout(session, realm, userSession, uriInfo, clientConnection, headers, true);
event.user(userSession.getUser()).session(userSession).success(); event.user(userSession.getUser()).session(userSession).success();
} }
@ -185,7 +183,7 @@ public class LogoutEndpoint {
} }
private void logout(UserSessionModel userSession) { private void logout(UserSessionModel userSession) {
authManager.backchannelLogout(session, realm, userSession, uriInfo, clientConnection, headers, true); AuthenticationManager.backchannelLogout(session, realm, userSession, uriInfo, clientConnection, headers, true);
event.user(userSession.getUser()).session(userSession).success(); event.user(userSession.getUser()).session(userSession).success();
} }

View file

@ -76,7 +76,6 @@ public class TokenEndpoint {
private ClientConnection clientConnection; private ClientConnection clientConnection;
private final TokenManager tokenManager; private final TokenManager tokenManager;
private final AuthenticationManager authManager;
private final RealmModel realm; private final RealmModel realm;
private final EventBuilder event; private final EventBuilder event;
@ -86,9 +85,8 @@ public class TokenEndpoint {
private String legacyGrantType; private String legacyGrantType;
public TokenEndpoint(TokenManager tokenManager, AuthenticationManager authManager, RealmModel realm, EventBuilder event) { public TokenEndpoint(TokenManager tokenManager, RealmModel realm, EventBuilder event) {
this.tokenManager = tokenManager; this.tokenManager = tokenManager;
this.authManager = authManager;
this.realm = realm; this.realm = realm;
this.event = event; this.event = event;
} }
@ -372,7 +370,6 @@ public class TokenEndpoint {
.setFlowId(flowId) .setFlowId(flowId)
.setConnection(clientConnection) .setConnection(clientConnection)
.setEventBuilder(event) .setEventBuilder(event)
.setProtector(authManager.getProtector())
.setRealm(realm) .setRealm(realm)
.setSession(session) .setSession(session)
.setUriInfo(uriInfo) .setUriInfo(uriInfo)

View file

@ -1,7 +1,6 @@
package org.keycloak.services.listeners; package org.keycloak.services.listeners;
import org.keycloak.models.KeycloakSessionFactory; import org.keycloak.models.KeycloakSessionFactory;
import org.keycloak.services.managers.BruteForceProtector;
import javax.servlet.ServletContextEvent; import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener; import javax.servlet.ServletContextListener;
@ -17,10 +16,6 @@ public class KeycloakSessionDestroyListener implements ServletContextListener {
@Override @Override
public void contextDestroyed(ServletContextEvent sce) { public void contextDestroyed(ServletContextEvent sce) {
BruteForceProtector protector = (BruteForceProtector) sce.getServletContext().getAttribute(BruteForceProtector.class.getName());
if (protector != null) {
protector.shutdown();
}
KeycloakSessionFactory sessionFactory = (KeycloakSessionFactory) sce.getServletContext().getAttribute(KeycloakSessionFactory.class.getName()); KeycloakSessionFactory sessionFactory = (KeycloakSessionFactory) sce.getServletContext().getAttribute(KeycloakSessionFactory.class.getName());
if (sessionFactory != null) { if (sessionFactory != null) {
sessionFactory.close(); sessionFactory.close();

View file

@ -70,19 +70,6 @@ public class AuthenticationManager {
public static final String KEYCLOAK_LOGOUT_PROTOCOL = "KEYCLOAK_LOGOUT_PROTOCOL"; public static final String KEYCLOAK_LOGOUT_PROTOCOL = "KEYCLOAK_LOGOUT_PROTOCOL";
public static final String CURRENT_REQUIRED_ACTION = "CURRENT_REQUIRED_ACTION"; public static final String CURRENT_REQUIRED_ACTION = "CURRENT_REQUIRED_ACTION";
protected BruteForceProtector protector;
public AuthenticationManager() {
}
public AuthenticationManager(BruteForceProtector protector) {
this.protector = protector;
}
public BruteForceProtector getProtector() {
return protector;
}
public static boolean isSessionValid(RealmModel realm, UserSessionModel userSession) { public static boolean isSessionValid(RealmModel realm, UserSessionModel userSession) {
if (userSession == null) { if (userSession == null) {
logger.debug("No user session"); logger.debug("No user session");

View file

@ -20,8 +20,8 @@ import java.util.concurrent.TimeUnit;
* @author <a href="mailto:bill@burkecentral.com">Bill Burke</a> * @author <a href="mailto:bill@burkecentral.com">Bill Burke</a>
* @version $Revision: 1 $ * @version $Revision: 1 $
*/ */
public class BruteForceProtector implements Runnable { public class DefaultBruteForceProtector implements Runnable, BruteForceProtector {
protected static Logger logger = Logger.getLogger(BruteForceProtector.class); protected static Logger logger = Logger.getLogger(DefaultBruteForceProtector.class);
protected volatile boolean run = true; protected volatile boolean run = true;
protected int maxDeltaTimeSeconds = 60 * 60 * 12; // 12 hours protected int maxDeltaTimeSeconds = 60 * 60 * 12; // 12 hours
@ -67,7 +67,7 @@ public class BruteForceProtector implements Runnable {
} }
} }
public BruteForceProtector(KeycloakSessionFactory factory) { public DefaultBruteForceProtector(KeycloakSessionFactory factory) {
this.factory = factory; this.factory = factory;
} }
@ -204,6 +204,7 @@ public class BruteForceProtector implements Runnable {
} }
} }
@Override
public void failedLogin(RealmModel realm, String username, ClientConnection clientConnection) { public void failedLogin(RealmModel realm, String username, ClientConnection clientConnection) {
try { try {
FailedLogin event = new FailedLogin(realm.getId(), username, clientConnection.getRemoteAddr()); FailedLogin event = new FailedLogin(realm.getId(), username, clientConnection.getRemoteAddr());
@ -217,6 +218,7 @@ public class BruteForceProtector implements Runnable {
} }
} }
@Override
public boolean isTemporarilyDisabled(KeycloakSession session, RealmModel realm, String username) { public boolean isTemporarilyDisabled(KeycloakSession session, RealmModel realm, String username) {
UsernameLoginFailureModel failure = session.sessions().getUserLoginFailure(realm, username.toLowerCase()); UsernameLoginFailureModel failure = session.sessions().getUserLoginFailure(realm, username.toLowerCase());
if (failure == null) { if (failure == null) {
@ -231,4 +233,8 @@ public class BruteForceProtector implements Runnable {
return false; return false;
} }
@Override
public void close() {
}
} }

View file

@ -0,0 +1,41 @@
package org.keycloak.services.managers;
import org.keycloak.Config;
import org.keycloak.models.KeycloakSession;
import org.keycloak.models.KeycloakSessionFactory;
/**
* @author <a href="mailto:bill@burkecentral.com">Bill Burke</a>
* @version $Revision: 1 $
*/
public class DefaultBruteForceProtectorFactory implements BruteForceProtectorFactory {
DefaultBruteForceProtector protector;
@Override
public BruteForceProtector create(KeycloakSession session) {
return protector;
}
@Override
public void init(Config.Scope config) {
}
@Override
public void postInit(KeycloakSessionFactory factory) {
protector = new DefaultBruteForceProtector(factory);
protector.start();
}
@Override
public void close() {
protector.shutdown();
}
@Override
public String getId() {
return "default-brute-force-detector";
}
}

View file

@ -699,7 +699,6 @@ public class IdentityBrokerService implements IdentityProvider.AuthenticationCal
.setFlowId(flowId) .setFlowId(flowId)
.setConnection(clientConnection) .setConnection(clientConnection)
.setEventBuilder(event) .setEventBuilder(event)
.setProtector(protector)
.setRealm(realmModel) .setRealm(realmModel)
.setSession(session) .setSession(session)
.setUriInfo(uriInfo) .setUriInfo(uriInfo)

View file

@ -17,7 +17,6 @@ import org.keycloak.representations.idm.UserRepresentation;
import org.keycloak.services.DefaultKeycloakSessionFactory; import org.keycloak.services.DefaultKeycloakSessionFactory;
import org.keycloak.services.filters.KeycloakTransactionCommitter; import org.keycloak.services.filters.KeycloakTransactionCommitter;
import org.keycloak.services.managers.ApplianceBootstrap; import org.keycloak.services.managers.ApplianceBootstrap;
import org.keycloak.services.managers.BruteForceProtector;
import org.keycloak.services.managers.RealmManager; import org.keycloak.services.managers.RealmManager;
import org.keycloak.services.managers.UsersSyncManager; import org.keycloak.services.managers.UsersSyncManager;
import org.keycloak.services.resources.admin.AdminRoot; import org.keycloak.services.resources.admin.AdminRoot;
@ -60,12 +59,7 @@ public class KeycloakApplication extends Application {
this.sessionFactory = createSessionFactory(); this.sessionFactory = createSessionFactory();
dispatcher.getDefaultContextObjects().put(KeycloakApplication.class, this); dispatcher.getDefaultContextObjects().put(KeycloakApplication.class, this);
BruteForceProtector protector = new BruteForceProtector(sessionFactory);
dispatcher.getDefaultContextObjects().put(BruteForceProtector.class, protector);
ResteasyProviderFactory.pushContext(BruteForceProtector.class, protector); // for injection
ResteasyProviderFactory.pushContext(KeycloakApplication.class, this); // for injection ResteasyProviderFactory.pushContext(KeycloakApplication.class, this); // for injection
protector.start();
context.setAttribute(BruteForceProtector.class.getName(), protector);
context.setAttribute(KeycloakSessionFactory.class.getName(), this.sessionFactory); context.setAttribute(KeycloakSessionFactory.class.getName(), this.sessionFactory);
singletons.add(new ServerVersionResource()); singletons.add(new ServerVersionResource());

View file

@ -21,6 +21,7 @@
*/ */
package org.keycloak.services.resources; package org.keycloak.services.resources;
import org.apache.http.auth.AUTH;
import org.jboss.logging.Logger; import org.jboss.logging.Logger;
import org.jboss.resteasy.spi.HttpRequest; import org.jboss.resteasy.spi.HttpRequest;
import org.keycloak.authentication.authenticators.broker.AbstractIdpAuthenticator; import org.keycloak.authentication.authenticators.broker.AbstractIdpAuthenticator;
@ -121,8 +122,6 @@ public class LoginActionsService {
@Context @Context
protected KeycloakSession session; protected KeycloakSession session;
private AuthenticationManager authManager;
private EventBuilder event; private EventBuilder event;
public static UriBuilder loginActionsBaseUrl(UriInfo uriInfo) { public static UriBuilder loginActionsBaseUrl(UriInfo uriInfo) {
@ -154,9 +153,8 @@ public class LoginActionsService {
return baseUriBuilder.path(RealmsResource.class).path(RealmsResource.class, "getLoginActionsService"); return baseUriBuilder.path(RealmsResource.class).path(RealmsResource.class, "getLoginActionsService");
} }
public LoginActionsService(RealmModel realm, AuthenticationManager authManager, EventBuilder event) { public LoginActionsService(RealmModel realm, EventBuilder event) {
this.realm = realm; this.realm = realm;
this.authManager = authManager;
this.event = event; this.event = event;
} }
@ -293,7 +291,6 @@ public class LoginActionsService {
.setFlowId(flow.getId()) .setFlowId(flow.getId())
.setConnection(clientConnection) .setConnection(clientConnection)
.setEventBuilder(event) .setEventBuilder(event)
.setProtector(authManager.getProtector())
.setRealm(realm) .setRealm(realm)
.setSession(session) .setSession(session)
.setUriInfo(uriInfo) .setUriInfo(uriInfo)
@ -454,7 +451,7 @@ public class LoginActionsService {
ClientSessionModel clientSession = clientSessionCode.getClientSession(); ClientSessionModel clientSession = clientSessionCode.getClientSession();
authManager.expireIdentityCookie(realm, uriInfo, clientConnection); AuthenticationManager.expireIdentityCookie(realm, uriInfo, clientConnection);
return processRegistration(execution, clientSession, null); return processRegistration(execution, clientSession, null);
} }
@ -648,7 +645,7 @@ public class LoginActionsService {
event.detail(Details.CONSENT, Details.CONSENT_VALUE_CONSENT_GRANTED); event.detail(Details.CONSENT, Details.CONSENT_VALUE_CONSENT_GRANTED);
event.success(); event.success();
return authManager.redirectAfterSuccessfulFlow(session, realm, userSession, clientSession, request, uriInfo, clientConnection, event); return AuthenticationManager.redirectAfterSuccessfulFlow(session, realm, userSession, clientSession, request, uriInfo, clientConnection, event);
} }
@Path("email-verification") @Path("email-verification")

View file

@ -81,10 +81,9 @@ public class RealmsResource {
RealmModel realm = init(name); RealmModel realm = init(name);
EventBuilder event = new EventBuilder(realm, session, clientConnection); EventBuilder event = new EventBuilder(realm, session, clientConnection);
AuthenticationManager authManager = new AuthenticationManager(protector);
LoginProtocolFactory factory = (LoginProtocolFactory)session.getKeycloakSessionFactory().getProviderFactory(LoginProtocol.class, OIDCLoginProtocol.LOGIN_PROTOCOL); LoginProtocolFactory factory = (LoginProtocolFactory)session.getKeycloakSessionFactory().getProviderFactory(LoginProtocol.class, OIDCLoginProtocol.LOGIN_PROTOCOL);
OIDCLoginProtocolService endpoint = (OIDCLoginProtocolService)factory.createProtocolEndpoint(realm, event, authManager); OIDCLoginProtocolService endpoint = (OIDCLoginProtocolService)factory.createProtocolEndpoint(realm, event);
ResteasyProviderFactory.getInstance().injectProperties(endpoint); ResteasyProviderFactory.getInstance().injectProperties(endpoint);
return endpoint.getLoginStatusIframe(); return endpoint.getLoginStatusIframe();
@ -97,10 +96,9 @@ public class RealmsResource {
RealmModel realm = init(name); RealmModel realm = init(name);
EventBuilder event = new EventBuilder(realm, session, clientConnection); EventBuilder event = new EventBuilder(realm, session, clientConnection);
AuthenticationManager authManager = new AuthenticationManager(protector);
LoginProtocolFactory factory = (LoginProtocolFactory)session.getKeycloakSessionFactory().getProviderFactory(LoginProtocol.class, protocol); LoginProtocolFactory factory = (LoginProtocolFactory)session.getKeycloakSessionFactory().getProviderFactory(LoginProtocol.class, protocol);
Object endpoint = factory.createProtocolEndpoint(realm, event, authManager); Object endpoint = factory.createProtocolEndpoint(realm, event);
ResteasyProviderFactory.getInstance().injectProperties(endpoint); ResteasyProviderFactory.getInstance().injectProperties(endpoint);
return endpoint; return endpoint;
@ -117,8 +115,7 @@ public class RealmsResource {
public LoginActionsService getLoginActionsService(final @PathParam("realm") String name) { public LoginActionsService getLoginActionsService(final @PathParam("realm") String name) {
RealmModel realm = init(name); RealmModel realm = init(name);
EventBuilder event = new EventBuilder(realm, session, clientConnection); EventBuilder event = new EventBuilder(realm, session, clientConnection);
AuthenticationManager authManager = new AuthenticationManager(protector); LoginActionsService service = new LoginActionsService(realm, event);
LoginActionsService service = new LoginActionsService(realm, authManager, event);
ResteasyProviderFactory.getInstance().injectProperties(service); ResteasyProviderFactory.getInstance().injectProperties(service);
return service; return service;
} }

View file

@ -1,5 +1,3 @@
org.keycloak.protocol.LoginProtocolSpi
org.keycloak.protocol.ProtocolMapperSpi
org.keycloak.exportimport.ClientDescriptionConverterSpi org.keycloak.exportimport.ClientDescriptionConverterSpi
org.keycloak.wellknown.WellKnownSpi org.keycloak.wellknown.WellKnownSpi
org.keycloak.messages.MessagesSpi org.keycloak.messages.MessagesSpi
@ -9,4 +7,3 @@ org.keycloak.authentication.RequiredActionSpi
org.keycloak.authentication.FormAuthenticatorSpi org.keycloak.authentication.FormAuthenticatorSpi
org.keycloak.authentication.FormActionSpi org.keycloak.authentication.FormActionSpi
org.keycloak.services.clientregistration.ClientRegistrationSpi org.keycloak.services.clientregistration.ClientRegistrationSpi
org.keycloak.protocol.ClientInstallationSpi

View file

@ -0,0 +1 @@
org.keycloak.services.managers.DefaultBruteForceProtectorFactory