Authentication Spring WS-Security LDAP身份验证

Authentication Spring WS-Security LDAP身份验证,authentication,spring-security,ldap,spring-ws,ws-security,Authentication,Spring Security,Ldap,Spring Ws,Ws Security,我在使用LDAP用户身份验证让LDAP身份验证与SpringWS一起工作时遇到问题。我已经找到了几个例子来说明如何做到这一点,其中一些使用了不同的bean,有些甚至编写了自己的验证器。不幸的是,似乎没有一个具备使这项工作正常进行所需的全部细节。此外,因为似乎有几种不同的方法可以让它工作,我不确定最好的方法。我尝试了wss4j(apache)和xwss(sun)安全提供程序,得到了类似的结果。我知道ws-security部件工作正常(没有使用SimplePasswordValidationCall

我在使用LDAP用户身份验证让LDAP身份验证与SpringWS一起工作时遇到问题。我已经找到了几个例子来说明如何做到这一点,其中一些使用了不同的bean,有些甚至编写了自己的验证器。不幸的是,似乎没有一个具备使这项工作正常进行所需的全部细节。此外,因为似乎有几种不同的方法可以让它工作,我不确定最好的方法。我尝试了wss4j(apache)和xwss(sun)安全提供程序,得到了类似的结果。我知道ws-security部件工作正常(没有使用SimplePasswordValidationCallbackHandler的LDAP部件也可以正常工作),甚至LDAP上下文也可以从LDAP存储库检索用户,但最终密码验证失败。另外,我不明白这有什么关系,但我正在使用Active Directory作为我的LDAP提供程序

    <sws:interceptors>
        <bean class="com.xxxxx.xxxxxx.xxxx.controller.interceptors.EcrsPayloadLoggingInterceptor"/>

        <bean class="org.springframework.ws.soap.security.xwss.XwsSecurityInterceptor">
            <property name="policyConfiguration" value="classpath:securityPolicy.xml" />
            <property name="callbackHandlers">
                <list>
                    <ref bean="authenticationHandler"/>
                </list>
            </property>
        </bean>
    </sws:interceptors>

    <bean id="securityContextSource" class="org.springframework.security.ldap.DefaultSpringSecurityContextSource">
            <constructor-arg value="ldap://localhost:389/DC=xxxx,DC=xxxx,DC=local"/>
            <property name="userDn" value="CN=user1,CN=Users,DC=xxxx,DC=xxxxx,DC=local"/>
            <property name="password" value="password1"/>
    </bean>

    <bean id="ldapUserSearch" class="org.springframework.security.ldap.search.FilterBasedLdapUserSearch">
            <constructor-arg name="searchBase" value=""/>
            <constructor-arg name="searchFilter" value="(sAMAccountName={0})"/>
            <constructor-arg name="contextSource" ref="apacheContextSource"/>
            <property name="searchSubtree" value="true"/>
    </bean>

    <bean id="ldapAuthoritiesPopulator" class="org.springframework.security.ldap.userdetails.DefaultLdapAuthoritiesPopulator">
            <constructor-arg name="contextSource" ref="apacheContextSource"/>
            <constructor-arg name="groupSearchBase" value="CN=Users"/>
            <property name="groupRoleAttribute" value="CN"/>
    </bean>

    <bean id="ldapUserDetailsService" class="org.springframework.security.ldap.userdetails.LdapUserDetailsService">
            <constructor-arg name="userSearch" ref="ldapUserSearch"/>
            <constructor-arg name="authoritiesPopulator" ref="ldapAuthoritiesPopulator"/>
    </bean>

    <bean id="authenticationHandler" class="org.springframework.ws.soap.security.xwss.callback.SpringDigestPasswordValidationCallbackHandler">
        <property name="userDetailsService" ref="ldapUserDetailsService"/>
    </bean>

securityPolicy.xml:


这是我找到的解决方案

    <sws:interceptors>
        <bean class="com.xxxx.xxxxx.xxxx.controller.interceptors.EcrsPayloadLoggingInterceptor"/>

        <bean class="org.springframework.ws.soap.security.xwss.XwsSecurityInterceptor">
            <property name="policyConfiguration" value="classpath:securityPolicy.xml" />
            <property name="callbackHandlers">
                <list>
                    <ref bean="authenticationHandler"/>
                </list>
            </property>
        </bean>
    </sws:interceptors>

    <bean id="authenticationHandler" class="org.springframework.ws.soap.security.xwss.callback.SpringPlainTextPasswordValidationCallbackHandler">
        <property name="authenticationManager" ref="authManager" />
    </bean>

    <s:authentication-manager id="authManager">
        <s:authentication-provider ref='ldapAuthProvider'/>
    </s:authentication-manager>

    <bean id="ldapAuthProvider" class="org.springframework.security.ldap.authentication.LdapAuthenticationProvider">
       <constructor-arg>
           <bean class="org.springframework.security.ldap.authentication.BindAuthenticator">
               <constructor-arg ref="securityContextSource" />
               <property name="userSearch" ref="ldapUserSearch"/>
           </bean>
       </constructor-arg>
       <constructor-arg name="authoritiesPopulator" ref="ldapAuthoritiesPopulator"/>
    </bean>

    <bean id="securityContextSource" class="org.springframework.security.ldap.DefaultSpringSecurityContextSource">
            <constructor-arg value="ldap://localhost:389/DC=xxx,DC=xxxxx,DC=local"/>
            <property name="userDn" value="CN=xxxxxx,CN=xxxx,DC=xxx,DC=xxxx,DC=local"/>
            <property name="password" value="xxxxxxx"/>
    </bean>

    <bean id="ldapUserSearch" class="org.springframework.security.ldap.search.FilterBasedLdapUserSearch">
            <constructor-arg name="searchBase" value=""/>
            <constructor-arg name="searchFilter" value="(sAMAccountName={0})"/>
            <constructor-arg name="contextSource" ref="securityContextSource"/>
            <property name="searchSubtree" value="true"/>
    </bean>

    <bean id="ldapAuthoritiesPopulator" class="org.springframework.security.ldap.userdetails.DefaultLdapAuthoritiesPopulator">
            <constructor-arg name="contextSource" ref="securityContextSource"/>
            <constructor-arg name="groupSearchBase" value="CN=Users"/>
            <property name="groupRoleAttribute" value="CN"/>
    </bean>

另外,这是我的securityPolicy.xml
    <sws:interceptors>
        <bean class="com.xxxx.xxxxx.xxxx.controller.interceptors.EcrsPayloadLoggingInterceptor"/>

        <bean class="org.springframework.ws.soap.security.xwss.XwsSecurityInterceptor">
            <property name="policyConfiguration" value="classpath:securityPolicy.xml" />
            <property name="callbackHandlers">
                <list>
                    <ref bean="authenticationHandler"/>
                </list>
            </property>
        </bean>
    </sws:interceptors>

    <bean id="authenticationHandler" class="org.springframework.ws.soap.security.xwss.callback.SpringPlainTextPasswordValidationCallbackHandler">
        <property name="authenticationManager" ref="authManager" />
    </bean>

    <s:authentication-manager id="authManager">
        <s:authentication-provider ref='ldapAuthProvider'/>
    </s:authentication-manager>

    <bean id="ldapAuthProvider" class="org.springframework.security.ldap.authentication.LdapAuthenticationProvider">
       <constructor-arg>
           <bean class="org.springframework.security.ldap.authentication.BindAuthenticator">
               <constructor-arg ref="securityContextSource" />
               <property name="userSearch" ref="ldapUserSearch"/>
           </bean>
       </constructor-arg>
       <constructor-arg name="authoritiesPopulator" ref="ldapAuthoritiesPopulator"/>
    </bean>

    <bean id="securityContextSource" class="org.springframework.security.ldap.DefaultSpringSecurityContextSource">
            <constructor-arg value="ldap://localhost:389/DC=xxx,DC=xxxxx,DC=local"/>
            <property name="userDn" value="CN=xxxxxx,CN=xxxx,DC=xxx,DC=xxxx,DC=local"/>
            <property name="password" value="xxxxxxx"/>
    </bean>

    <bean id="ldapUserSearch" class="org.springframework.security.ldap.search.FilterBasedLdapUserSearch">
            <constructor-arg name="searchBase" value=""/>
            <constructor-arg name="searchFilter" value="(sAMAccountName={0})"/>
            <constructor-arg name="contextSource" ref="securityContextSource"/>
            <property name="searchSubtree" value="true"/>
    </bean>

    <bean id="ldapAuthoritiesPopulator" class="org.springframework.security.ldap.userdetails.DefaultLdapAuthoritiesPopulator">
            <constructor-arg name="contextSource" ref="securityContextSource"/>
            <constructor-arg name="groupSearchBase" value="CN=Users"/>
            <property name="groupRoleAttribute" value="CN"/>
    </bean>