1

Spring-Security 4 XML 構成を使用して、spring-mvc webapp でパスワード認証を正常に実装しています。

私が抱えている問題は、CredentialsExpiredException が DaoAuthenticationProvider によってスローされると、システムがパスワードをリセットする代わりにログインフォームにリダイレクトすることです。

私の context-security xml 構成は次のとおりです。

<?xml version="1.0" encoding="UTF-8"?>
<b:beans xmlns="http://www.springframework.org/schema/security"
xmlns:b="http://www.springframework.org/schema/beans" 
xmlns:p="http://www.springframework.org/schema/p"
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.xsd 
                    http://www.springframework.org/schema/security  http://www.springframework.org/schema/security/spring-security.xsd">

<b:bean id="authenticationEntryPoint" class="org.springframework.security.web.authentication.LoginUrlAuthenticationEntryPoint">
    <b:constructor-arg value="/index/form" />
</b:bean>

<http auto-config="true" use-expressions="true" disable-url-rewriting="true" entry-point-ref="authenticationEntryPoint" >
    <intercept-url pattern="/" access="permitAll" requires-channel="https"/>
    <intercept-url pattern="/index" access="permitAll" requires-channel="https"/>
    <intercept-url pattern="/index/*" access="permitAll" requires-channel="https"/>
    <intercept-url pattern="/**" access="hasAnyRole('USER','SYS_ADMIN' )" requires-channel="https"/>
    <form-login   
            login-page="/index/form"
                default-target-url="/dashboard"
                login-processing-url="/index"
                username-parameter="username"
                password-parameter="password"
                authentication-failure-handler-ref="exceptionTranslationFilter"
                always-use-default-target="true"/>
    <logout logout-url="/logout" logout-success-url="/index/logout"/>

    <session-management>
        <concurrency-control max-sessions="1" error-if-maximum-exceeded="true" />
    </session-management>
</http>

 <!-- password expiry functionality starts  -->
<b:bean id="exceptionTranslationFilter" class="org.springframework.security.web.authentication.ExceptionMappingAuthenticationFailureHandler">
    <b:property name="exceptionMappings">
        <b:props>
            <b:prop key="org.springframework.security.authentication.CredentialsExpiredException">/resetpassword</b:prop>
        </b:props>
    </b:property>
    <b:property name="defaultFailureUrl" value="/index/error"/>
</b:bean>


 <b:bean id="authenticationManager" class="org.springframework.security.authentication.ProviderManager">
    <b:constructor-arg name="providers">
        <b:list>
            <b:ref bean="daoAuthenticationProvider"/>
        </b:list>
    </b:constructor-arg>
</b:bean> 

<b:bean id="daoAuthenticationProvider" class="org.springframework.security.authentication.dao.DaoAuthenticationProvider ">
    <b:property name="userDetailsService" ref="customUserDetailsService" />
    <b:property name="passwordEncoder" ref="passwordEncoder" />
</b:bean>



<authentication-manager alias="authenticationManager">
    <authentication-provider user-service-ref="customUserDetailsService" />
    <authentication-provider ref="daoAuthenticationProvider" /> 
</authentication-manager>


<b:bean id="passwordEncoder" class="org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder" >
</b:bean>

上記の構成では、資格情報の有効期限が切れたユーザーの正しいユーザー名とパスワードを入力すると、url = "/index/form" にリダイレクトされます。

デバッガーを実行しました (Eclipse を使用しています)。コードの実行は次のとおりです (すべてのクラスは Spring Security 4 に属しています)。

AbstractUserDetailsAuthenticationProvider.authenticate()は、postAuthenticationChecks.check(user); の実行時にCredentialsExpiredExceptionをスローします。

ExceptionMappingAuthenticationFailureHandler.onAuthenticationFailure()は、getRedirectStrategy().sendRedirect(request, response, url);を呼び出す前にURL を/resetpasswordに取得します。

DefaultRedirectStrategy.sendRedirect()は、リダイレクト URL を「/myapp/resetpassword」に取得します。

この問題はLoginUrlAuthenticationEntryPoint.commence(HttpServletRequest request, HttpServletResponse response, AuthenticationException authException) で発生します。

useForward が false に設定されているため、redirectUrl = buildRedirectUrlToLoginPage(request, response, authException); を呼び出します。

redirectUrlは「/index/form」になってしまいます。

useForwardを trueに設定し、 LoginUrlAuthenticationEntryPoint をサブクラス化して defineUrlToUseForThisRequest をオーバーライドしても、取得するAuthenticationException のタイプはInsufficientAuthenticationExceptionです。

興味深いことに、私のブラウザの URL は ですがhttps://localhost:8443/myapp/resetpassword、表示されるのはログイン フォームです。

以前にこの問題に遭遇したことがありますか? もしそうなら、どのようにしてパスワードをリセットするためにスプリングをリダイレクトしましたか?

https://stackoverflow.com/a/14383194/158499から取得した構成のほとんど

前もってありがとう、ルーカス

4

1 に答える 1