【问题标题】:sessionRegistry is empty when I use ConcurrentSessionControlAuthenticationStrategy instead of ConcurrentSessionControlStrategy当我使用 ConcurrentSessionControlAuthenticationStrategy 而不是 ConcurrentSessionControlStrategy 时 sessionRegistry 为空
【发布时间】:2015-12-04 10:43:40
【问题描述】:

在我写的http标签内:

我有以下 sas bean

 <beans:bean id="sas" class="org.springframework.security.web.authentication.session.ConcurrentSessionControlStrategy">
        <beans:constructor-arg  ref="sessionRegistry" />
        <beans:property name="maximumSessions" value="1" />
    </beans:bean>

在代码中我从注册表中获取信息:

@Autowired
private SessionRegistry sessionRegistry;
....
    sessionRegistry.getAllPrincipals()

现在它正在工作。

但是org.springframework.security.web.authentication.session.ConcurrentSessionControlStrategy 类已被弃用的问题

我这样替换了sas bean

<beans:bean id="sas" class="org.springframework.security.web.authentication.session.ConcurrentSessionControlAuthenticationStrategy">
    <beans:constructor-arg  ref="sessionRegistry" />
    <beans:property name="maximumSessions" value="1" />
</beans:bean>

但是现在

sessionRegistry.getAllPrincipals()

总是返回空列表。

如何解决?

附: 完整配置:

web.xml:

<?xml version="1.0" encoding="UTF-8"?>
<web-app
        version="3.0"
        xmlns="http://java.sun.com/xml/ns/javaee"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="
        http://java.sun.com/xml/ns/javaee
        http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd
        ">

    <listener>
        <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
    </listener>

    <listener>
        <listener-class>
            org.springframework.web.context.request.RequestContextListener
        </listener-class>
    </listener>

    <listener>
        <listener-class>net.bull.javamelody.SessionListener</listener-class>
    </listener>

    <listener>
        <listener-class>org.springframework.security.web.session.HttpSessionEventPublisher</listener-class>
    </listener>

    <context-param>
        <param-name>contextConfigLocation</param-name>
        <param-value>WEB-INF/applicationContext.xml</param-value>
    </context-param>
    <context-param>
        <param-name>spring.profiles.default</param-name>
        <param-value>test</param-value>
    </context-param>
    <context-param>
        <param-name>defaultHtmlEscape</param-name>
        <param-value>true</param-value>
    </context-param>
    <!-- Spring MVC -->
    <servlet>
        <servlet-name>appServlet</servlet-name>
        <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
        <init-param>
            <param-name>contextConfigLocation</param-name>
            <param-value>WEB-INF/webContext.xml</param-value>
        </init-param>
        <load-on-startup>1</load-on-startup>
    </servlet>

    <servlet-mapping>
        <servlet-name>appServlet</servlet-name>
        <url-pattern>/</url-pattern>
    </servlet-mapping>

    <!-- Spring Security -->
    <filter>
        <filter-name>springSecurityFilterChain</filter-name>
        <filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>springSecurityFilterChain</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

    <filter>
        <filter-name>XSSFilter</filter-name>
        <filter-class>com.cj.xss.XSSFilter</filter-class>
    </filter>
    <filter>
        <filter-name>javamelody</filter-name>
        <filter-class>net.bull.javamelody.MonitoringFilter</filter-class>
        <init-param>
            <param-name>monitoring-path</param-name>
            <param-value>/admin/monitoring</param-value>
        </init-param>
    </filter>
    <filter-mapping>
        <filter-name>javamelody</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>   
    <filter-mapping>
        <filter-name>XSSFilter</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

    <filter>
        <filter-name>charsetFilter</filter-name>
        <filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
        <init-param>
            <param-name>encoding</param-name>
            <param-value>UTF-8</param-value>
        </init-param>
        <init-param>
            <param-name>forceEncoding</param-name>
            <param-value>true</param-value>
        </init-param>
    </filter>
    <filter-mapping>
        <filter-name>charsetFilter</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

    <error-page>
        <error-code>404</error-code>
        <location>/error</location>
    </error-page>

</web-app>

安全上下文:

<beans:beans
        xmlns="http://www.springframework.org/schema/security"
        xmlns:beans="http://www.springframework.org/schema/beans"
        xmlns:sec="http://www.springframework.org/schema/security"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="
        http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans-4.0.xsd
        http://www.springframework.org/schema/security
        http://www.springframework.org/schema/security/spring-security.xsd">

    <http auto-config="true" pattern="/admin/**" authentication-manager-ref="adminAuthenticationManager">
        <access-denied-handler error-page="/403" />
        <custom-filter ref="concurrencyFilter" after="SECURITY_CONTEXT_FILTER"/>
        <form-login login-page="/loginAdmin" login-processing-url="/admin/j_spring_security_check_admin"
                    default-target-url="/admin"
                    authentication-failure-url="/loginAdminFailed"
                    authentication-success-handler-ref="authAdminSuccessHandler"/>

        <intercept-url pattern="/admin/j_spring_security_check_admin" access="ROLE_ANONYMOUS"/>
        <intercept-url pattern="/admin/accounts/**" access="ROLE_SUPERADMIN"/>
        <intercept-url pattern="/admin/users/**" access="ROLE_SUPERADMIN"/>
        <intercept-url pattern="/admin/terminals/**" access="ROLE_SUPERADMIN, ROLE_TERMINAL_MODERATOR, ROLE_MODERATOR"/>
        <intercept-url pattern="/admin/money/**" access="ROLE_FINANSIER, ROLE_SUPERADMIN"/>
        <intercept-url pattern="/admin/moderation/**" access="ROLE_SUPERADMIN,ROLE_MODERATOR"/>
        <intercept-url pattern="/admin/moderation/pictures"
                       access="ROLE_SUPERADMIN,ROLE_MODERATOR, ROLE_IMAGE_MODERATOR"/>
        <intercept-url pattern="/admin/statistic/**" access="ROLE_SUPERADMIN"/>
        <intercept-url pattern="/admin/rules/**" access="ROLE_SUPERADMIN"/>
        <intercept-url pattern="/admin/terminals/addImageToTerminal"
                       access="ROLE_SUPERADMIN, ROLE_TERMINAL_MODERATOR, ROLE_MODERATOR"/>
        <intercept-url pattern="/admin/terminals/deleteTerminalImage"
                       access="ROLE_SUPERADMIN, ROLE_TERMINAL_MODERATOR, ROLE_MODERATOR"/>
        <intercept-url pattern="/admin/systemGroupsModeration" access="ROLE_SUPERADMIN"/>
        <intercept-url pattern="/admin/adminUsers" access="ROLE_SUPERADMIN"/>
        <intercept-url pattern="/admin/contentModeration/**" access="ROLE_SUPERADMIN, ROLE_MODERATOR, ROLE_IMAGE_MODERATOR"/>
        <intercept-url pattern="/admin/campaignModeration/**" access="ROLE_SUPERADMIN, ROLE_MODERATOR"/>
        <intercept-url pattern="/admin/monitoring" access="ROLE_SUPERADMIN"/>

        <logout logout-url="/logout" logout-success-url="/loginAdmin"/>
        <port-mappings>
            <port-mapping http="${http.port}" https="${https.port}"/>
        </port-mappings>
        <session-management session-authentication-strategy-ref="sas" invalid-session-url="/invalid-session" />
    </http>
    <http auto-config="true" authentication-manager-ref="userAuthenticationManager">
        <form-login login-page="/"
                    default-target-url="/member/personalAccount"
                    authentication-failure-url="/loginfailed" authentication-success-handler-ref="authSuccessHandler"/>

        <!-- <intercept-url pattern="/common/*" filters="none" /> -->
        <intercept-url pattern="/member/createCompany/addParams" access="ROLE_ANONYMOUS, ROLE_USER"/>
        <intercept-url pattern="/member/**" access="ROLE_USER"/>
        <intercept-url pattern="/owner/*" access="ROLE_OWNER"/>
        <intercept-url pattern="/member/getImage/*"
                       access="ROLE_ANONYMOUS, ROLE_OWNER,ROLE_USER, ROLE_SUPERADMIN, ROLE_TERMINAL_MODERATOR, ROLE_IMAGE_MODERATOR, ROLE_CAMPAIGN_MODERATOR, ROLE_FINANSIER, ROLE_MODERATOR"/>

        <logout logout-url="/logout" logout-success-url="/"/>
        <port-mappings>
            <port-mapping http="${http.port}" https="${https.port}"/>
        </port-mappings>
    </http>

    <beans:bean id="userSecurityService" class="com.terminal.service.impl.UserSecurityService"/>
    <beans:bean id="authSuccessHandler" class="com.terminal.filter.RoleAuthSuccessHandler"/>

    <beans:bean id="authAdminSuccessHandler" class="com.terminal.filter.admin.RoleAuthAdminHandler"/>
    <beans:bean id="adminSecurityService" class="com.terminal.service.admin.impl.TerminalAdminSecurityServiceImpl"/>

    <beans:bean id="webexpressionHandler"
                class="org.springframework.security.web.access.expression.DefaultWebSecurityExpressionHandler"/>

    <authentication-manager id="adminAuthenticationManager">
        <authentication-provider user-service-ref="adminSecurityService">
            <password-encoder ref="encoder"/>
        </authentication-provider>
    </authentication-manager>

    <authentication-manager id="userAuthenticationManager">
        <authentication-provider user-service-ref="userSecurityService">
            <password-encoder ref="encoder"/>
        </authentication-provider>
    </authentication-manager>

    <authentication-manager id="internalUserAuthenticationManager">
        <authentication-provider user-service-ref="userSecurityService">
            <password-encoder ref="noopEncoder"/>
        </authentication-provider>
    </authentication-manager>

    <beans:bean id="encoder" class="org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder">
        <beans:constructor-arg index="0" value="10"/>
    </beans:bean>
    <beans:bean id="noopEncoder" class="org.springframework.security.crypto.password.NoOpPasswordEncoder"/>

    <beans:bean id="sessionRegistry" class="org.springframework.security.core.session.SessionRegistryImpl"/>

    <beans:bean id="sas" class="org.springframework.security.web.authentication.session.ConcurrentSessionControlStrategy">
        <beans:constructor-arg  ref="sessionRegistry" />
        <beans:property name="maximumSessions" value="1" />
    </beans:bean>

    <beans:bean id="concurrencyFilter"
                class="org.springframework.security.web.session.ConcurrentSessionFilter">
        <beans:property name="sessionRegistry" ref="sessionRegistry" />
        <beans:property name="expiredUrl" value="/" />
    </beans:bean>

</beans:beans>

applicationContext.xml:

<beans
        xmlns="http://www.springframework.org/schema/beans"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xmlns:context="http://www.springframework.org/schema/context"
        xsi:schemaLocation="
        http://www.springframework.org/schema/context
        http://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans-4.0.xsd
        ">

    <import resource="classpath:META-INF/dataContext.xml"/>
    <import resource="classpath:META-INF/restTemplateContext.xml" />
    <import resource="classpath:META-INF/securityContext.xml"/>

    <context:component-scan base-package="com.terminal" >
        <context:include-filter type="annotation" expression="org.aspectj.lang.annotation.Aspect"/>
        <context:exclude-filter type="annotation" expression="org.springframework.stereotype.Controller"/>
    </context:component-scan>
</beans>

dataContext.xml

<beans
        xmlns="http://www.springframework.org/schema/beans"
        xmlns:p="http://www.springframework.org/schema/p"
        xmlns:context="http://www.springframework.org/schema/context"
        xmlns:tx="http://www.springframework.org/schema/tx"
        xmlns:jdbc="http://www.springframework.org/schema/jdbc"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xmlns:task="http://www.springframework.org/schema/task"
        xsi:schemaLocation="http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/context
        http://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/tx
        http://www.springframework.org/schema/tx/spring-tx.xsd
        http://www.springframework.org/schema/jdbc
        http://www.springframework.org/schema/jdbc/spring-jdbc-3.2.xsd

         http://www.springframework.org/schema/task http://www.springframework.org/schema/task/spring-task.xsd">

    <tx:annotation-driven transaction-manager="transactionManager"/>

    <context:component-scan base-package="com.terminal.domain, com.terminal.dao, com.terminal.utils"/>

    <bean id="transactionManager"
          class="org.springframework.orm.hibernate4.HibernateTransactionManager">
        <property name="sessionFactory" ref="sessionFactory"/>
    </bean>

    <bean id="messageSource"
          class="org.springframework.context.support.ResourceBundleMessageSource">
        <property name="basenames">
            <list>
                <value>mymessages</value>
            </list>
        </property>
    </bean>

    <task:scheduler id="jobScheduler" pool-size="10"/>

    <beans profile="test">

        <bean id="wrappedDataSource" class="net.bull.javamelody.SpringDataSourceFactoryBean">
            <property name="targetName" value="dataSource" />
        </bean>

        <bean class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close" id="dataSource">
            <property name="driverClassName" value="org.h2.Driver" />
            <property name="url" value="jdbc:h2:~/test;MODE=PostgreSQL" />
            <property name="username" value="sa" />
            <property name="password" value="" />
        </bean>

        <bean id="sessionFactory"
              class="org.springframework.orm.hibernate4.LocalSessionFactoryBean">
            <property name="dataSource" ref="wrappedDataSource"/>
            <property name="configLocation">
                <value>classpath:hibernate-test.cfg.xml</value>
            </property>
            <property name="hibernateProperties">
                <props>
                    <prop key="hibernate.show_sql">true</prop>
                    <prop key="hibernate.connection.charSet">UTF-8</prop>
                    <prop key="hibernate.show_sql">true</prop>
                    <prop key="hibernate.format_sql">true</prop>
                    <prop key="hbm2ddl.auto">create-drop</prop>
                </props>
            </property>
        </bean>

        <context:property-placeholder location="classpath:jdbc.properties"/>

    </beans>
    <beans profile="dev">

        <bean id="wrappedDataSource" class="net.bull.javamelody.SpringDataSourceFactoryBean">
            <property name="targetName" value="dataSource" />
        </bean>

        <bean id="sessionFactory"
              class="org.springframework.orm.hibernate4.LocalSessionFactoryBean">
            <property name="dataSource" ref="wrappedDataSource"/>
            <property name="configLocation">
                <value>classpath:hibernate.cfg.xml</value>
            </property>
            <property name="hibernateProperties">
                <props>
                    <prop key="hibernate.show_sql">true</prop>
                    <prop key="hibernate.dialect">${jdbc.dialect}</prop>
                    <prop key="hibernate.connection.charSet">UTF-8</prop>
                    <prop key="hibernate.show_sql">true</prop>
                    <prop key="hibernate.format_sql">true</prop>
                    <prop key="hbm2ddl.auto">validate</prop>
                </props>
            </property>
        </bean>

        <context:property-placeholder location="classpath:jdbc-local.properties"/>
        <bean id="dataSource"
              class="org.springframework.jdbc.datasource.DriverManagerDataSource"
              p:driverClassName="${jdbc.driverClassName}" p:url="${jdbc.databaseurl}"
              p:username="${jdbc.username}" p:password="${jdbc.password}"/>
    </beans>
    <beans profile="prod">

        <bean id="wrappedDataSource" class="net.bull.javamelody.SpringDataSourceFactoryBean">
            <property name="targetName" value="dataSource" />
        </bean>

        <bean id="sessionFactory"
              class="org.springframework.orm.hibernate4.LocalSessionFactoryBean">
            <property name="dataSource" ref="wrappedDataSource"/>
            <property name="configLocation">
                <value>classpath:hibernate.cfg.xml</value>
            </property>
            <property name="hibernateProperties">
                <props>
                    <prop key="hibernate.show_sql">true</prop>
                    <prop key="hibernate.dialect">${jdbc.dialect}</prop>
                    <prop key="hibernate.connection.charSet">UTF-8</prop>
                    <prop key="hibernate.show_sql">true</prop>
                    <prop key="hibernate.format_sql">true</prop>
                    <prop key="hbm2ddl.auto">validate</prop>
                </props>
            </property>
        </bean>

        <context:property-placeholder location="classpath:jdbc.properties"/>
        <bean id="dataSource"
              class="org.springframework.jdbc.datasource.DriverManagerDataSource"
              p:driverClassName="${jdbc.driverClassName}" p:url="${jdbc.databaseurl}"
              p:username="${jdbc.username}" p:password="${jdbc.password}"/>
    </beans>
</beans>

restTemplateContext.xml

<beans
        xmlns="http://www.springframework.org/schema/beans"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="
        http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans-4.0.xsd
        ">

    <bean id="restTemplate" class="org.springframework.web.client.RestTemplate">
        <property name="messageConverters">
            <list>
                <bean class="org.springframework.http.converter.json.MappingJackson2HttpMessageConverter"/>
                <bean class="org.springframework.http.converter.FormHttpMessageConverter"/>
                <bean class="com.terminal.converter.MatrixVariablesMessageConverter"/>
            </list>
        </property>
    </bean>
</beans>

securityContext.xml

<beans:beans
        xmlns="http://www.springframework.org/schema/security"
        xmlns:beans="http://www.springframework.org/schema/beans"
        xmlns:sec="http://www.springframework.org/schema/security"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="
        http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans-4.0.xsd
        http://www.springframework.org/schema/security
        http://www.springframework.org/schema/security/spring-security.xsd">

    <http auto-config="true" pattern="/admin/**" authentication-manager-ref="adminAuthenticationManager">
        <access-denied-handler error-page="/403" />
        <custom-filter ref="concurrencyFilter" after="SECURITY_CONTEXT_FILTER"/>
        <form-login login-page="/loginAdmin" login-processing-url="/admin/j_spring_security_check_admin"
                    default-target-url="/admin"
                    authentication-failure-url="/loginAdminFailed"
                    authentication-success-handler-ref="authAdminSuccessHandler"/>

        <intercept-url pattern="/admin/j_spring_security_check_admin" access="ROLE_ANONYMOUS"/>
        <intercept-url pattern="/admin/accounts/**" access="ROLE_SUPERADMIN"/>
        <intercept-url pattern="/admin/users/**" access="ROLE_SUPERADMIN"/>
        <intercept-url pattern="/admin/terminals/**" access="ROLE_SUPERADMIN, ROLE_TERMINAL_MODERATOR, ROLE_MODERATOR"/>
        <intercept-url pattern="/admin/money/**" access="ROLE_FINANSIER, ROLE_SUPERADMIN"/>
        <intercept-url pattern="/admin/moderation/**" access="ROLE_SUPERADMIN,ROLE_MODERATOR"/>
        <intercept-url pattern="/admin/moderation/pictures"
                       access="ROLE_SUPERADMIN,ROLE_MODERATOR, ROLE_IMAGE_MODERATOR"/>
        <intercept-url pattern="/admin/statistic/**" access="ROLE_SUPERADMIN"/>
        <intercept-url pattern="/admin/rules/**" access="ROLE_SUPERADMIN"/>
        <intercept-url pattern="/admin/terminals/addImageToTerminal"
                       access="ROLE_SUPERADMIN, ROLE_TERMINAL_MODERATOR, ROLE_MODERATOR"/>
        <intercept-url pattern="/admin/terminals/deleteTerminalImage"
                       access="ROLE_SUPERADMIN, ROLE_TERMINAL_MODERATOR, ROLE_MODERATOR"/>
        <intercept-url pattern="/admin/systemGroupsModeration" access="ROLE_SUPERADMIN"/>
        <intercept-url pattern="/admin/adminUsers" access="ROLE_SUPERADMIN"/>
        <intercept-url pattern="/admin/contentModeration/**" access="ROLE_SUPERADMIN, ROLE_MODERATOR, ROLE_IMAGE_MODERATOR"/>
        <intercept-url pattern="/admin/campaignModeration/**" access="ROLE_SUPERADMIN, ROLE_MODERATOR"/>
        <intercept-url pattern="/admin/monitoring" access="ROLE_SUPERADMIN"/>

        <logout logout-url="/logout" logout-success-url="/loginAdmin"/>
        <port-mappings>
            <port-mapping http="${http.port}" https="${https.port}"/>
        </port-mappings>
        <session-management session-authentication-strategy-ref="sas" invalid-session-url="/invalid-session" />
    </http>
    <http auto-config="true" authentication-manager-ref="userAuthenticationManager">
        <form-login login-page="/"
                    default-target-url="/member/personalAccount"
                    authentication-failure-url="/loginfailed" authentication-success-handler-ref="authSuccessHandler"/>

        <!-- <intercept-url pattern="/common/*" filters="none" /> -->
        <intercept-url pattern="/member/createCompany/addParams" access="ROLE_ANONYMOUS, ROLE_USER"/>
        <intercept-url pattern="/member/**" access="ROLE_USER"/>
        <intercept-url pattern="/owner/*" access="ROLE_OWNER"/>
        <intercept-url pattern="/member/getImage/*"
                       access="ROLE_ANONYMOUS, ROLE_OWNER,ROLE_USER, ROLE_SUPERADMIN, ROLE_TERMINAL_MODERATOR, ROLE_IMAGE_MODERATOR, ROLE_CAMPAIGN_MODERATOR, ROLE_FINANSIER, ROLE_MODERATOR"/>

        <logout logout-url="/logout" logout-success-url="/"/>
        <port-mappings>
            <port-mapping http="${http.port}" https="${https.port}"/>
        </port-mappings>
    </http>

    <beans:bean id="userSecurityService" class="com.terminal.service.impl.UserSecurityService"/>
    <beans:bean id="authSuccessHandler" class="com.terminal.filter.RoleAuthSuccessHandler"/>

    <beans:bean id="authAdminSuccessHandler" class="com.terminal.filter.admin.RoleAuthAdminHandler"/>
    <beans:bean id="adminSecurityService" class="com.terminal.service.admin.impl.TerminalAdminSecurityServiceImpl"/>

    <beans:bean id="webexpressionHandler"
                class="org.springframework.security.web.access.expression.DefaultWebSecurityExpressionHandler"/>

    <authentication-manager id="adminAuthenticationManager">
        <authentication-provider user-service-ref="adminSecurityService">
            <password-encoder ref="encoder"/>
        </authentication-provider>
    </authentication-manager>

    <authentication-manager id="userAuthenticationManager">
        <authentication-provider user-service-ref="userSecurityService">
            <password-encoder ref="encoder"/>
        </authentication-provider>
    </authentication-manager>

    <authentication-manager id="internalUserAuthenticationManager">
        <authentication-provider user-service-ref="userSecurityService">
            <password-encoder ref="noopEncoder"/>
        </authentication-provider>
    </authentication-manager>

    <beans:bean id="encoder" class="org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder">
        <beans:constructor-arg index="0" value="10"/>
    </beans:bean>
    <beans:bean id="noopEncoder" class="org.springframework.security.crypto.password.NoOpPasswordEncoder"/>

    <beans:bean id="sessionRegistry" class="org.springframework.security.core.session.SessionRegistryImpl"/>

    <beans:bean id="sas" class="org.springframework.security.web.authentication.session.ConcurrentSessionControlStrategy">
        <beans:constructor-arg  ref="sessionRegistry" />
        <beans:property name="maximumSessions" value="1" />
    </beans:bean>

    <beans:bean id="concurrencyFilter"
                class="org.springframework.security.web.session.ConcurrentSessionFilter">
        <beans:property name="sessionRegistry" ref="sessionRegistry" />
        <beans:property name="expiredUrl" value="/" />
    </beans:bean>

</beans:beans>

【问题讨论】:

    标签: java spring session spring-security


    【解决方案1】:

    我遇到了同样的问题,问题是由于 web.xml 中的配置错误,spring 上下文中加载了 2 个 sessionRegistry 实例 并且控制器中引用的sessionRegistry bean 与spring-security 中引用的bean 不同。

    修复您的 web.xml,确保 DispatcherServlet 不会再次加载根 contextConfigLocation 中存在的相同 bean 下面的例子,dispatcherServlet 只加载了 servlet-context.xml,其中有 spring mvc 相关的东西,而 root-context.xml 只导入了其他的,比如 dao、service、security 配置 bean..

     <context-param>
        <param-name>contextConfigLocation</param-name>
        <param-value>
            /WEB-INF/spring/root-context.xml
        </param-value>
      </context-param>
    
     <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
        <init-param>
          <param-name>contextConfigLocation</param-name>
          <param-value>/WEB-INF/spring/appServlet/servlet-context.xml</param-value>
        </init-param>
    

    更新:要检查的另一个问题是如果您只有 ConcurrentSessionControlAuthenticationStrategy ,这不是注册会话,所以我们需要与 RegisterSessionAuthenticationStrategy 组合如下

      <bean id="sas" class="org.springframework.security.web.authentication.session.CompositeSessionAuthenticationStrategy">
            <constructor-arg>
                <list>
                    <bean class="org.springframework.security.web.authentication.session.ConcurrentSessionControlAuthenticationStrategy">
                        <constructor-arg ref="sessionRegistry"/>
                        <property name="maximumSessions" value="1" />
                        <property name="exceptionIfMaximumExceeded" value="true" />
                    </bean>
                    <bean class="org.springframework.security.web.authentication.session.SessionFixationProtectionStrategy">
                    </bean>
                    <bean class="org.springframework.security.web.authentication.session.RegisterSessionAuthenticationStrategy">
                        <constructor-arg ref="sessionRegistry"/>
                    </bean>
                </list>
             </constructor-arg>
        </bean>
    

    【讨论】:

    • 如果 spring 有不止一个候选人要自动装配 - 它会抱怨模棱两可
    • 你的意思是 autowired sessionRegistry 是 ambiguos 吗?发布您的 web.xml 和其他 xml,您在哪里配置了 bean,可能是您有一些重复的 bean 或者您导入了任何其他类。
    • @gstackoverflow 仅当这 2 个 bean 在相同的上下文中时,否则没有歧义,如果您在 ContextLoaderListener 中的安全性具有实例 x,并且您在 DispatcherServlet 中再次创建一个你有 2 个实例,但 spring 不会抱怨,因为每个上下文都包含一个实例。
    • @Anudeep Gade 我添加了一对配置文件。如果还不够,请告诉我
    • 你在 applicationContext.xml 中有什么
    猜你喜欢
    • 1970-01-01
    • 2020-06-18
    • 1970-01-01
    • 2020-05-05
    • 2014-08-06
    • 2018-10-21
    • 2018-04-30
    • 2020-08-04
    • 1970-01-01
    相关资源
    最近更新 更多