* AuthenticationProviders are usually tried in order until one provides a non-null response.
* A non-null response indicates the provider had authority to decide on the authentication request and no further
@@ -47,9 +43,8 @@ import org.springframework.util.Assert;
* If no provider returns a non-null response, or indicates it can even process an Authentication,
* the ProviderManager will throw a ProviderNotFoundException.
*
- * The exception to this process is when a provider throws an {@link AccountStatusException} or if the configured
- * concurrent session controller throws a {@link ConcurrentLoginException}. In both these cases, no further providers
- * in the list will be queried.
+ * The exception to this process is when a provider throws an {@link AccountStatusException}, in which case no
+ * further providers in the list will be queried.
*
*
Event Publishing
*
@@ -68,7 +63,7 @@ import org.springframework.util.Assert;
* @author Ben Alex
* @author Luke Taylor
* @version $Id$
- * @see ConcurrentSessionController
+ *
* @see DefaultAuthenticationEventPublisher
*/
public class ProviderManager extends AbstractAuthenticationManager implements MessageSourceAware, InitializingBean {
@@ -79,7 +74,6 @@ public class ProviderManager extends AbstractAuthenticationManager implements Me
//~ Instance fields ================================================================================================
private AuthenticationEventPublisher eventPublisher = new NullEventPublisher();
- private ConcurrentSessionController sessionController = new NullConcurrentSessionController();
private List providers = Collections.emptyList();
protected MessageSourceAccessor messages = SpringSecurityMessageSource.getAccessor();
private AuthenticationManager parent;
@@ -151,20 +145,12 @@ public class ProviderManager extends AbstractAuthenticationManager implements Me
}
}
- // Finally check if the concurrent session controller will allow authentication
- try {
- if (result != null) {
- sessionController.checkAuthenticationAllowed(result);
- sessionController.registerSuccessfulAuthentication(result);
- eventPublisher.publishAuthenticationSuccess(result);
-
- return result;
- }
- } catch (AuthenticationException e) {
- lastException = e;
+ if (result != null) {
+ eventPublisher.publishAuthenticationSuccess(result);
+ return result;
}
- // Session control failed, parent was null, or didn't authenticate (or throw an exception).
+ // Parent was null, or didn't authenticate (or throw an exception).
if (lastException == null) {
lastException = new ProviderNotFoundException(messages.getMessage("ProviderManager.providerNotFound",
@@ -199,16 +185,6 @@ public class ProviderManager extends AbstractAuthenticationManager implements Me
return providers;
}
- /**
- * The configured {@link ConcurrentSessionController} is returned or the {@link
- * NullConcurrentSessionController} if a specific one has not been set.
- *
- * @return {@link ConcurrentSessionController} instance
- */
- ConcurrentSessionController getSessionController() {
- return sessionController;
- }
-
public void setMessageSource(MessageSource messageSource) {
this.messages = new MessageSourceAccessor(messageSource);
}
@@ -239,22 +215,8 @@ public class ProviderManager extends AbstractAuthenticationManager implements Me
this.providers = providers;
}
- /**
- * Set the {@link ConcurrentSessionController} to be used for limiting users' sessions.
- *
- * @param sessionController {@link ConcurrentSessionController}
- */
- public void setSessionController(ConcurrentSessionController sessionController) {
- this.sessionController = sessionController;
- }
-
private static final class NullEventPublisher implements AuthenticationEventPublisher {
public void publishAuthenticationFailure(AuthenticationException exception, Authentication authentication) {}
public void publishAuthenticationSuccess(Authentication authentication) {}
}
-
- private static final class NullConcurrentSessionController implements ConcurrentSessionController {
- public void checkAuthenticationAllowed(Authentication request) {}
- public void registerSuccessfulAuthentication(Authentication authentication) {}
- }
}
diff --git a/core/src/main/java/org/springframework/security/authentication/concurrent/ConcurrentLoginException.java b/core/src/main/java/org/springframework/security/authentication/concurrent/ConcurrentLoginException.java
deleted file mode 100644
index ca5632735b..0000000000
--- a/core/src/main/java/org/springframework/security/authentication/concurrent/ConcurrentLoginException.java
+++ /dev/null
@@ -1,34 +0,0 @@
-/* Copyright 2004, 2005, 2006 Acegi Technology Pty Limited
- *
- * 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.springframework.security.authentication.concurrent;
-
-import org.springframework.security.core.AuthenticationException;
-
-
-/**
- * Thrown by ConcurrentSessionControllerImpl if an attempt is made to login and the user has already
- * exceeded their maxmimum allowed sessions.
- *
- * @author Ben Alex
- * @version $Id$
- */
-public class ConcurrentLoginException extends AuthenticationException {
- //~ Constructors ===================================================================================================
-
- public ConcurrentLoginException(String msg) {
- super(msg);
- }
-}
diff --git a/core/src/main/java/org/springframework/security/authentication/concurrent/ConcurrentSessionControllerImpl.java b/core/src/main/java/org/springframework/security/authentication/concurrent/ConcurrentSessionControllerImpl.java
deleted file mode 100644
index 18699ce03c..0000000000
--- a/core/src/main/java/org/springframework/security/authentication/concurrent/ConcurrentSessionControllerImpl.java
+++ /dev/null
@@ -1,174 +0,0 @@
-/* Copyright 2004, 2005, 2006 Acegi Technology Pty Limited
- *
- * 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.springframework.security.authentication.concurrent;
-
-import java.util.List;
-
-import org.springframework.security.core.Authentication;
-import org.springframework.security.core.AuthenticationException;
-import org.springframework.security.core.SpringSecurityMessageSource;
-
-import org.springframework.beans.factory.InitializingBean;
-
-import org.springframework.context.MessageSource;
-import org.springframework.context.MessageSourceAware;
-import org.springframework.context.support.MessageSourceAccessor;
-
-import org.springframework.util.Assert;
-
-
-/**
- * Base implementation of {@link ConcurrentSessionControllerImpl} which prohibits simultaneous logins.
- *
- * @author Ben Alex
- * @version $Id$
- */
-public class ConcurrentSessionControllerImpl implements ConcurrentSessionController, InitializingBean,
- MessageSourceAware {
- //~ Instance fields ================================================================================================
-
- protected MessageSourceAccessor messages = SpringSecurityMessageSource.getAccessor();
- private SessionRegistry sessionRegistry;
- private boolean exceptionIfMaximumExceeded = false;
- private int maximumSessions = 1;
-
- //~ Methods ========================================================================================================
-
- public void afterPropertiesSet() throws Exception {
- Assert.notNull(sessionRegistry, "SessionRegistry required");
- Assert.isTrue(maximumSessions != 0,
- "MaximumLogins must be either -1 to allow unlimited logins, or a positive integer to specify a maximum");
- Assert.notNull(this.messages, "A message source must be set");
- }
-
- public void checkAuthenticationAllowed(Authentication request) throws AuthenticationException {
- Assert.notNull(request, "Authentication request cannot be null (violation of interface contract)");
-
- String sessionId = obtainSessionId(request);
-
- final List sessions = sessionRegistry.getAllSessions(request.getPrincipal(), false);
-
- int sessionCount = sessions == null ? 0 : sessions.size();
-
- int allowableSessions = getMaximumSessionsForThisUser(request);
- Assert.isTrue(allowableSessions != 0, "getMaximumSessionsForThisUser() must return either -1 to allow "
- + "unlimited logins, or a positive integer to specify a maximum");
-
- if (sessionCount < allowableSessions) {
- // They haven't got too many login sessions running at present
- return;
- }
-
- if (allowableSessions == -1) {
- // We permit unlimited logins
- return;
- }
-
- if (sessionCount == allowableSessions) {
- // Only permit it though if this request is associated with one of the sessions
- for (SessionInformation si : sessions) {
- if (si.getSessionId().equals(sessionId)) {
- return;
- }
- }
- }
-
- allowableSessionsExceeded(sessionId, sessions, allowableSessions, sessionRegistry);
- }
-
- /**
- * Allows subclasses to customise behaviour when too many sessions are detected.
- *
- * @param sessionId the session ID of the present request
- * @param sessions either null or all unexpired sessions associated with the principal
- * @param allowableSessions the number of concurrent sessions the user is allowed to have
- * @param registry an instance of the SessionRegistry for subclass use
- *
- * @throws ConcurrentLoginException if the
- */
- protected void allowableSessionsExceeded(String sessionId, List sessions, int allowableSessions,
- SessionRegistry registry) {
- if (exceptionIfMaximumExceeded || (sessions == null)) {
- throw new ConcurrentLoginException(messages.getMessage("ConcurrentSessionControllerImpl.exceededAllowed",
- new Object[] {new Integer(allowableSessions)},
- "Maximum sessions of {0} for this principal exceeded"));
- }
-
- // Determine least recently used session, and mark it for invalidation
- SessionInformation leastRecentlyUsed = null;
-
- for (int i = 0; i < sessions.size(); i++) {
- if ((leastRecentlyUsed == null)
- || sessions.get(i).getLastRequest().before(leastRecentlyUsed.getLastRequest())) {
- leastRecentlyUsed = sessions.get(i);
- }
- }
-
- leastRecentlyUsed.expireNow();
- }
-
- public void registerSuccessfulAuthentication(Authentication authentication) {
- Assert.notNull(authentication, "Authentication cannot be null (violation of interface contract)");
-
- sessionRegistry.registerNewSession(obtainSessionId(authentication), authentication.getPrincipal());
- }
-
- /**
- * Method intended for use by subclasses to override the maximum number of sessions that are permitted for
- * a particular authentication. The default implementation simply returns the maximumSessions value
- * for the bean.
- *
- * @param authentication to determine the maximum sessions for
- *
- * @return either -1 meaning unlimited, or a positive integer to limit (never zero)
- */
- protected int getMaximumSessionsForThisUser(Authentication authentication) {
- return maximumSessions;
- }
-
- public void setExceptionIfMaximumExceeded(boolean exceptionIfMaximumExceeded) {
- this.exceptionIfMaximumExceeded = exceptionIfMaximumExceeded;
- }
-
- public void setMaximumSessions(int maximumSessions) {
- this.maximumSessions = maximumSessions;
- }
-
- public void setMessageSource(MessageSource messageSource) {
- this.messages = new MessageSourceAccessor(messageSource);
- }
-
- public void setSessionRegistry(SessionRegistry sessionRegistry) {
- this.sessionRegistry = sessionRegistry;
- }
-
- public SessionRegistry getSessionRegistry() {
- return sessionRegistry;
- }
-
- private String obtainSessionId(Authentication auth) {
- if (auth.getDetails() == null || !(auth.getDetails() instanceof SessionIdentifierAware)) {
- throw new IllegalArgumentException("The 'details' property of the supplied Authentication " +
- "object must be set and must implement 'SessionIdentifierAware', but Authentication.getDetails() " +
- "returned " + auth.getDetails());
- }
-
- String sessionId = ((SessionIdentifierAware) auth.getDetails()).getSessionId();
- Assert.hasText(sessionId, "SessionIdentifierAware did not return a Session ID (" + auth.getDetails() + ")");
-
- return sessionId;
- }
-}
diff --git a/core/src/main/java/org/springframework/security/authentication/concurrent/NullConcurrentSessionController.java b/core/src/main/java/org/springframework/security/authentication/concurrent/NullConcurrentSessionController.java
deleted file mode 100644
index 84624abb9e..0000000000
--- a/core/src/main/java/org/springframework/security/authentication/concurrent/NullConcurrentSessionController.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/* Copyright 2004, 2005, 2006 Acegi Technology Pty Limited
- *
- * 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.springframework.security.authentication.concurrent;
-
-import org.springframework.security.core.Authentication;
-import org.springframework.security.core.AuthenticationException;
-
-
-/**
- * No-op implementation of {@link org.springframework.security.authentication.concurrent.ConcurrentSessionController}.
- *
- * @author Ben Alex
- * @version $Id$
- */
-class NullConcurrentSessionController implements ConcurrentSessionController {
- //~ Methods ========================================================================================================
-
- public void checkAuthenticationAllowed(Authentication request)
- throws AuthenticationException {}
-
- public void registerSuccessfulAuthentication(Authentication authentication) {}
-}
diff --git a/core/src/main/java/org/springframework/security/authentication/event/AuthenticationFailureConcurrentLoginEvent.java b/core/src/main/java/org/springframework/security/authentication/event/AuthenticationFailureConcurrentLoginEvent.java
deleted file mode 100644
index 48c6c65444..0000000000
--- a/core/src/main/java/org/springframework/security/authentication/event/AuthenticationFailureConcurrentLoginEvent.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/* Copyright 2004, 2005, 2006 Acegi Technology Pty Limited
- *
- * 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.springframework.security.authentication.event;
-
-import org.springframework.security.core.Authentication;
-import org.springframework.security.core.AuthenticationException;
-
-
-/**
- * Application event which indicates authentication failure due to the user attempting to login to too many
- * concurrent sessions.
- *
- * @author Ben Alex
- * @version $Id$
- */
-public class AuthenticationFailureConcurrentLoginEvent extends AbstractAuthenticationFailureEvent {
- //~ Constructors ===================================================================================================
-
- public AuthenticationFailureConcurrentLoginEvent(Authentication authentication, AuthenticationException exception) {
- super(authentication, exception);
- }
-}
diff --git a/core/src/test/java/org/springframework/security/authentication/ProviderManagerTests.java b/core/src/test/java/org/springframework/security/authentication/ProviderManagerTests.java
index 81acc9a7f0..f9276914ad 100644
--- a/core/src/test/java/org/springframework/security/authentication/ProviderManagerTests.java
+++ b/core/src/test/java/org/springframework/security/authentication/ProviderManagerTests.java
@@ -16,6 +16,7 @@
package org.springframework.security.authentication;
import static org.junit.Assert.*;
+import static org.mockito.Matchers.any;
import static org.mockito.Mockito.*;
import java.util.ArrayList;
@@ -24,13 +25,6 @@ import java.util.List;
import org.junit.Test;
import org.springframework.context.MessageSource;
-import org.springframework.security.authentication.AuthenticationProvider;
-import org.springframework.security.authentication.ProviderManager;
-import org.springframework.security.authentication.ProviderNotFoundException;
-import org.springframework.security.authentication.TestingAuthenticationToken;
-import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
-import org.springframework.security.authentication.concurrent.ConcurrentLoginException;
-import org.springframework.security.authentication.concurrent.ConcurrentSessionController;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.GrantedAuthority;
@@ -81,18 +75,6 @@ public class ProviderManagerTests {
verify(publisher).publishAuthenticationSuccess(result);
}
- @Test
- public void concurrentSessionControllerConfiguration() throws Exception {
- ProviderManager target = new ProviderManager();
-
- //The NullConcurrentSessionController should be the default
- assertNotNull(target.getSessionController());
-
- ConcurrentSessionController csc = mock(ConcurrentSessionController.class);
- target.setSessionController(csc);
- assertSame(csc, target.getSessionController());
- }
-
@Test(expected=IllegalArgumentException.class)
public void startupFailsIfProviderListDoesNotContainProviders() throws Exception {
List