How to change response when token expire using AuthExceptionEntryPoint?

时光毁灭记忆、已成空白 提交于 2020-07-09 11:47:58

问题


There are two scenarios for 401 Unauthorized response:

  1. Token Expired (received from request header)
    • When token expires, It send default spring security exception in response.
  2. Token not found (not received in request header) Custom Response
    • It send custom response, using AuthExceptionEntryPoint class.

How can i prepare same response into (1)Token Expired that i am sending in (2)Token not found?

Following are the configuration:

webSecuritycofig.xml

    <?xml version="1.0" encoding="UTF-8"?>
<beans:beans xmlns="http://www.springframework.org/schema/security"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:beans="http://www.springframework.org/schema/beans"
    xmlns:oauth="http://www.springframework.org/schema/security/oauth2"
    xmlns:context="http://www.springframework.org/schema/context"
    xmlns:p="http://www.springframework.org/schema/p"
    xsi:schemaLocation="
        http://www.springframework.org/schema/security/oauth2
        http://www.springframework.org/schema/security/spring-security-oauth2.xsd
        http://www.springframework.org/schema/security
        http://www.springframework.org/schema/security/spring-security-3.2.xsd
        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" >

    <context:property-placeholder location="classpath:hibernate.properties"
                                  ignore-unresolvable="true" />
    <context:property-placeholder location="classpath:messages.properties"
        ignore-unresolvable="true" />
        </http>
        

    <http pattern="/oauth/token" create-session="stateless"
          authentication-manager-ref="clientAuthenticationManager"
          entry-point-ref="oauthAuthenticationEntryPoint">
        <intercept-url pattern="/oauth/token" access="IS_AUTHENTICATED_FULLY"
                       method="GET" />
        <anonymous enabled="false" />
        <http-basic entry-point-ref="oauthAuthenticationEntryPoint" />
        <custom-filter ref="clientCredentialsTokenEndpointFilter"
                       before="BASIC_AUTH_FILTER" />
        <access-denied-handler ref="oauthAccessDeniedHandler" />
    </http>

    <http pattern="/**/**" create-session="never"
          entry-point-ref="oauthAuthenticationEntryPoint"
          access-decision-manager-ref="accessDecisionManager"
          use-expressions="false">
        <anonymous enabled="false" />
        <intercept-url pattern="/secure/**" method="GET"
                       access="IS_AUTHENTICATED_FULLY" />
        <intercept-url pattern="/secure/**" method="POST"
                       access="IS_AUTHENTICATED_FULLY" />
        <intercept-url pattern="/secure/**" method="DELETE"
                       access="IS_AUTHENTICATED_FULLY" />
        <intercept-url pattern="/secure/**" method="PUT"
                       access="IS_AUTHENTICATED_FULLY" />
        <custom-filter ref="resourceServerFilter" before="PRE_AUTH_FILTER" />
        <access-denied-handler ref="oauthAccessDeniedHandler" />
    </http>

    <authentication-manager id="clientAuthenticationManager">
        <authentication-provider user-service-ref="clientDetailsUserService" />
    </authentication-manager>

    <beans:bean id="clientCredentialsTokenEndpointFilter" class="com.security.LoginTracker">
        <beans:property name="authenticationManager" ref="clientAuthenticationManager" />
    </beans:bean>

    <beans:bean id="clientDetailsUserService"
                class="org.springframework.security.oauth2.provider.client.ClientDetailsUserDetailsService">
        <beans:constructor-arg ref="clientDetails" />
    </beans:bean>

    <oauth:authorization-server
            client-details-service-ref="clientDetails" token-services-ref="tokenServices">
        <oauth:authorization-code />
        <oauth:implicit />
        <oauth:refresh-token />
        <oauth:client-credentials />
        <oauth:password />
    </oauth:authorization-server>
<!-- <beans:bean id="messageSource" class="org.springframework.context.support.ResourceBundleMessageSource" p:basename="/WEB-INF/messages">
</beans:bean>
<beans:bean id="validator" class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean">
    <beans:property name="validationMessageSource" ref="messageSource"/>
 </beans:bean> -->
    <beans:bean id="clientDetails"
                class="org.springframework.security.oauth2.provider.JdbcClientDetailsService">
        <beans:constructor-arg name="dataSource" ref="dataSource"></beans:constructor-arg>
    </beans:bean>
    <beans:bean id="oauthAccessDeniedHandler"
                class="org.springframework.security.oauth2.provider.error.OAuth2AccessDeniedHandler" />
    <beans:bean id="oauthAuthenticationEntryPoint"
                class="com.security.AuthExceptionEntryPoint" />

    <beans:bean id="accessDecisionManager"
                class="org.springframework.security.access.vote.UnanimousBased" xmlns="http://www.springframework.org/schema/beans">
        <beans:constructor-arg>
            <beans:list>
                <beans:bean
                        class="org.springframework.security.oauth2.provider.vote.ScopeVoter" />
                <beans:bean class="org.springframework.security.access.vote.RoleVoter" />
                <beans:bean
                        class="org.springframework.security.access.vote.AuthenticatedVoter" />
            </beans:list>
        </beans:constructor-arg>
    </beans:bean>

    <!-- <authentication-manager alias="authenticationManager"> <authentication-provider>
        <jdbc-person-service id="jdbcUserService" data-source-ref="dataSource" users-by-username-query="select
        email_address, password, enabled from tblm_user where enabled=true and suspended=false
        and email_address = ?" authorities-by-username-query="select u.email_address,
        r.contactEmailAddress from tblm_user u, tblm_role r where r.role_id=u.role_id and u.enabled=true
        and u.suspended=false and u.email_address= ?" /> </authentication-provider>
        </authentication-manager> -->
        <authentication-manager alias="authenticationManager">
            <authentication-provider ref="customAuthenticationProvider" />
        </authentication-manager>
    <beans:bean id="tokenStore"
                class="org.springframework.security.oauth2.provider.token.JdbcTokenStore">
        <beans:constructor-arg name="dataSource" ref="dataSource"></beans:constructor-arg>
    </beans:bean>
    <beans:bean id="tokenEnhancer1"
                class="com.security.CustomTokenEnhancer" />
    <beans:bean id="tokenServices"
                class="org.springframework.security.oauth2.provider.token.DefaultTokenServices">
        <beans:property name="tokenStore" ref="tokenStore" />
        <beans:property name="supportRefreshToken" value="true" />
        <beans:property name="accessTokenValiditySeconds"
            value="31536000" />
        <beans:property name="refreshTokenValiditySeconds"
            value="31536010" />                     
    </beans:bean>

    <oauth:expression-handler id="oauthExpressionHandler" />
    <oauth:web-expression-handler id="oauthWebExpressionHandler" />

    <beans:bean id="dataSource"
                class="org.springframework.jdbc.datasource.DriverManagerDataSource">
        <beans:property name="driverClassName" value="${jdbc.driverClassName}" />
        <beans:property name="url" value="${jdbc.url}" />
        <beans:property name="username" value="${jdbc.user}" />
        <beans:property name="password" value="${jdbc.pass}" />
    </beans:bean>
    <oauth:resource-server id="resourceServerFilter"
                           token-services-ref="tokenServices" />
</beans:beans>

AuthExceptionEntryPoint.java

public class AuthExceptionEntryPoint  implements AuthenticationEntryPoint{

/* (non-Javadoc)
 * @see org.springframework.security.web.AuthenticationEntryPoint#commence(javax.servlet.http.HttpServletRequest, javax.servlet.http.HttpServletResponse, org.springframework.security.core.AuthenticationException)
 */
@Override
public void commence(HttpServletRequest request, HttpServletResponse response, AuthenticationException authException) throws IOException, ServletException {

     final Map<String, Object> mapBodyException = new HashMap<>() ;

       
        mapBodyException.put("status", "error");
        mapBodyException.put("code", HttpStatus.UNAUTHORIZED);
        mapBodyException.put("page",null);
        mapBodyException.put("message"  , "Authentication Error") ;
        response.setContentType("application/json") ;
        response.setStatus(HttpServletResponse.SC_UNAUTHORIZED) ;

        final ObjectMapper mapper = new ObjectMapper() ;
        mapper.writeValue(response.getOutputStream(), mapBodyException) ;
}

SecurityConfig.java

  @Configuration
@ImportResource({ "classpath:websecurityconfig.xml" })
public class SecurityConfig extends WebSecurityConfigurerAdapter {

    /* (non-Javadoc)
     * @see org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter#configure(org.springframework.security.config.annotation.web.builders.HttpSecurity)
     */
    @Override
    protected void configure(HttpSecurity http) throws Exception {
        
        http.exceptionHandling().authenticationEntryPoint(new AuthExceptionEntryPoint());

    
    }

Versions:

springframework.version : 4.3.0.RELEASE

springframework.security.version :3.2.5.RELEASE

来源:https://stackoverflow.com/questions/62596805/how-to-change-response-when-token-expire-using-authexceptionentrypoint

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!