oAuth2.0 + Spring中的异常响应无效

时间:2015-08-12 06:30:16

标签: spring-security oauth-2.0 spring-security-oauth2

我在REST上使用oAuth 2.0和Spring安全性。我已成功获得以下格式的访问令牌。

{
"access_token": "f6c21098-dd67-4324-ac57-a5ba820bb452",
  "token_type": "bearer",
  "refresh_token": "ae013bfb-c088-4dae-b2e2-db6fed1bb96b",
  "expires_in": 119
}

但是只要我在pom.xml中添加以下依赖项,我就会得到以下响应。

{
      "value": "fd29c8b5-499a-4604-8084-3eca934110d5",
      "expiration": 1439417920535,
      "tokenType": "bearer",
      "refreshToken": {
        "value": "f3793739-42e8-4786-86c4-e194ccd2abba",
        "expiration": 1439957920534
      },
      "scope": [],
      "additionalInformation": {},
      "expired": false,
      "expiresIn": 59999
    }

这些依赖项用于将Java对象映射到JSON。

<dependency>
    <groupId>com.fasterxml.jackson.core</groupId>
    <artifactId>jackson-core</artifactId>
    <version>2.4.0</version>
</dependency>

<dependency>
    <groupId>com.fasterxml.jackson.core</groupId>
    <artifactId>jackson-databind</artifactId>
    <version>2.4.0</version>
</dependency>  

另外,当我试图输入错误的url params(例如cleint_id,用户名等)时,我收到了带有合理错误信息的回复。

{
  "error": "invalid_grant",
  "error_description": "Bad User Credentials."
}

但是在添加了jackson dependdenc之后,我得到了json格式的所有异常的响应,这是非常误导的。

{
  "cause": {
    "cause": {
      "cause": null,
      "stackTrace": [
        {
          "methodName": "loadClientByClientId",
          "fileName": "InMemoryClientDetailsService.java",
          "lineNumber": 36,
          "className": "org.springframework.security.oauth2.provider.InMemoryClientDetailsService",
          "nativeMethod": false
        },
        {
          "methodName": "loadUserByUsername",
          "fileName": "ClientDetailsUserDetailsService.java",
          "lineNumber": 44,
          "className": "org.springframework.security.oauth2.provider.client.ClientDetailsUserDetailsService",
          "nativeMethod": false
        },
        {
          "methodName": "retrieveUser",
          "fileName": "DaoAuthenticationProvider.java",
          "lineNumber": 101,
          "className": "org.springframework.security.authentication.dao.DaoAuthenticationProvider",
          "nativeMethod": false
        },
        ...
      {
        "methodName": "doFilter",
        "fileName": "WebAppFilterManager.java",
        "lineNumber": 1017,
        "className": "com.ibm.ws.webcontainer.filter.WebAppFilterManager",
        "nativeMethod": false
      }
   }
  }
 }

下面是带有oAuth的XML文件

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


    <!-- Enable the method security to use the 
         @PreAuthorize, @PreFilter, @PostAuthorize and @PostFilter annotations
         in methods and secure it.

    <global-method-security pre-post-annotations="enabled" />

 secure the application´s urls with the specific Role --> 


    <!--  <beans:bean id="mySuccessHandler" class="com.siwaves.server.health.custom.rest.api.security.MySavedRequestAwareAuthenticationSuccessHandler" />
    <beans:bean id="myFailureHandler" class="org.springframework.security.web.authentication.SimpleUrlAuthenticationFailureHandler" />-->

    <!-- Define the application authentication manager to use a custom Class (mongoUserDetailsService)
         to validate the user access, and the password enconding -->
    <authentication-manager alias="authenticationManager" xmlns="http://www.springframework.org/schema/security">
        <authentication-provider user-service-ref="mongoUserDetailsService">
              <password-encoder ref="encoder"  /> 
        </authentication-provider>
        <authentication-provider user-service-ref="patientUserDetailsService">
              <password-encoder ref="encoder"  />
              </authentication-provider>
                <authentication-provider>
            <user-service >
                <user name="aryan" password="aryan" authorities="ROLE_SUPERADMIN" />
            </user-service>
        </authentication-provider>
    </authentication-manager>

  <bean id="encoder"  class="org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder">  
  <constructor-arg name="strength" value="10" />  
 </bean>  

<bean id="patientShelf" class="com.siwaves.server.health.repository.MongoPatientShelf"></bean>

 <!-- **************************************************************************************** -->

    <!-- This is default url to get a token from OAuth -->
    <http pattern="/oauth/token" create-session="stateless" authentication-manager-ref="clientAuthenticationManager" xmlns="http://www.springframework.org/schema/security">
        <intercept-url pattern="/oauth/token" access="IS_AUTHENTICATED_FULLY" />

        <anonymous enabled="false" />
        <http-basic entry-point-ref="clientAuthenticationEntryPoint" />
        <!-- include this only if you need to authenticate clients via request 
            parameters -->
        <custom-filter ref="clientCredentialsTokenEndpointFilter"
            after="BASIC_AUTH_FILTER" />
        <access-denied-handler ref="oauthAccessDeniedHandler" />
    </http>

    <!-- This is where we tells spring security what URL should be protected 
        and what roles have access to them -->
    <http pattern="/api/**" create-session="never"
        entry-point-ref="oauthAuthenticationEntryPoint"
        access-decision-manager-ref="accessDecisionManager"
        xmlns="http://www.springframework.org/schema/security">
        <anonymous enabled="false" />
    <!--  <intercept-url pattern="/api/**" access="ROLE_ADMIN"/>-->
        <!--  <intercept-url pattern="/listCampaigns" access="hasAnyRole('ROLE_ADMIN','ROLE_PATIENT')" />
        <intercept-url pattern="/listUsers" access="hasRole('ROLE_ADMIN')" />-->
        <intercept-url pattern="/api/addpatient" access="ROLE_ADMIN" method="POST" />
        <intercept-url pattern="/api/addpatient/image/{p_id}" access="ROLE_ADMIN" method="POST" />
        <intercept-url pattern="/api/patients" access="ROLE_ADMIN" method="GET" />
        <intercept-url pattern="/api/editpatient/{p_id}" access="ROLE_ADMIN" />
        <intercept-url pattern="/api/searchpatients" access="ROLE_ADMIN" />
        <intercept-url pattern="/api/sensordata" access="ROLE_ADMIN" />
        <intercept-url pattern="/api/sensordata/{p_id}" access="ROLE_ADMIN" />
        <intercept-url pattern="/api/sensordata/heart/{p_id}" access="ROLE_ADMIN" />
        <custom-filter ref="resourceServerFilter" before="PRE_AUTH_FILTER" />
        <access-denied-handler ref="oauthAccessDeniedHandler" />
        <!--  <csrf />-->
        <!-- <http-basic/>
        <form-login login-processing-url="/api" authentication-success-handler-ref="mySuccessHandler" authentication-failure-handler-ref="myFailureHandler" />  -->
    </http>

        <bean id="oauthAuthenticationEntryPoint"
        class="org.springframework.security.oauth2.provider.error.OAuth2AuthenticationEntryPoint">
        <property name="realmName" value="test" />
    </bean>

    <bean id="clientAuthenticationEntryPoint"
        class="org.springframework.security.oauth2.provider.error.OAuth2AuthenticationEntryPoint">
        <property name="realmName" value="test/client" />
        <property name="typeName" value="Basic" />
    </bean>

    <bean id="oauthAccessDeniedHandler"
        class="org.springframework.security.oauth2.provider.error.OAuth2AccessDeniedHandler" />

    <bean id="clientCredentialsTokenEndpointFilter"
        class="org.springframework.security.oauth2.provider.client.ClientCredentialsTokenEndpointFilter">
        <property name="authenticationManager" ref="clientAuthenticationManager" />
    </bean>

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

    <authentication-manager id="clientAuthenticationManager"
        xmlns="http://www.springframework.org/schema/security">
        <authentication-provider user-service-ref="clientDetailsUserService" />
    </authentication-manager>




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


    <!-- This defined token store, we have used inmemory tokenstore for now 
        but this can be changed to a user defined one -->
    <bean id="tokenStore"
        class="org.springframework.security.oauth2.provider.token.InMemoryTokenStore" />

    <!-- This is where we defined token based configurations, token validity 
        and other things -->
    <bean id="tokenServices"
        class="org.springframework.security.oauth2.provider.token.DefaultTokenServices">
        <property name="tokenStore" ref="tokenStore" />
        <property name="supportRefreshToken" value="true" />
        <property name="accessTokenValiditySeconds" value="120" />
        <property name="clientDetailsService" ref="clientDetails" />
    </bean>

    <bean id="userApprovalHandler"
        class="org.springframework.security.oauth2.provider.approval.TokenServicesUserApprovalHandler">
        <property name="tokenServices" ref="tokenServices" />
    </bean>

    <oauth:authorization-server
        client-details-service-ref="clientDetails" token-services-ref="tokenServices"
        user-approval-handler-ref="userApprovalHandler">
        <oauth:authorization-code />
        <oauth:implicit />
        <oauth:refresh-token />
        <oauth:client-credentials />
        <oauth:password />
    </oauth:authorization-server>

    <oauth:resource-server id="resourceServerFilter"
        resource-id="test" token-services-ref="tokenServices" />

    <oauth:client-details-service id="clientDetails">
        <!-- client -->
        <oauth:client client-id="restapp" access-token-validity="60000" refresh-token-validity="600000"
            authorized-grant-types="authorization_code,client_credentials"
            authorities="ROLE_ADMIN, ROLE_NURSE" scope="read,write,trust" secret="secret" />

        <oauth:client client-id="restapp" access-token-validity="60000" refresh-token-validity="600000"
            authorized-grant-types="password,authorization_code,refresh_token,implicit"
            secret="restapp" authorities="ROLE_ADMIN, ROLE_NURSE" />

        <oauth:client client-id="restpatient" access-token-validity="60000" refresh-token-validity="600000"
            authorized-grant-types="authorization_code,client_credentials"
            authorities="ROLE_PATIENT" scope="read" secret="secret" />

        <oauth:client client-id="restpatient" access-token-validity="60000" refresh-token-validity="600000"
            authorized-grant-types="password,authorization_code,refresh_token,implicit"
            secret="secretpatient" authorities="ROLE_PATIENT"/>

    </oauth:client-details-service>

    <sec:global-method-security
        pre-post-annotations="enabled" proxy-target-class="true">
        <!--you could also wire in the expression handler up at the layer of the 
            http filters. See https://jira.springsource.org/browse/SEC-1452 -->
        <sec:expression-handler ref="oauthExpressionHandler" />
    </sec:global-method-security>

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

     <!-- **************************************************************************************** -->
</beans>

任何帮助都将不胜感激。

0 个答案:

没有答案