spring-attic / spring-cloud-security

Security concerns for distributed applications implemented in Spring
Apache License 2.0
533 stars 245 forks source link

config property "security.resource.jwt.key-uri" caused UnknownHostException #227

Open AnnieCattice opened 4 years ago

AnnieCattice commented 4 years ago

Describe the bug application ran failed with the message:

org.springframework.web.client.ResourceAccessException: I/O error on GET request for "http://data-auth-server:9000/oauth/token_key": data-auth-server; nested exception is java.net.UnknownHostException: data-auth-server

Sample

version describe:

<spring.boot.version>2.2.1.RELEASE</spring.boot.version>
<spring.cloud.version>Hoxton.RELEASE</spring.cloud.version>
  1. here is my configuaration of oauth2 server application:

    server:
    port: 9000
    spring:
    application:
    name: data-auth-server
  2. when i try to config security.resource.jwt.key-uri to my oauth2 client application,yml could be this:

    security:
    oauth2: 
    resource:
      jwt:
        key-uri: http://data-auth-server:9000/oauth/token_key
  3. i started the application,and got the full trace stack info:

    
    Caused by: org.springframework.web.client.ResourceAccessException: I/O error on GET request for "http://data-auth-server:9000/oauth/token_key": data-auth-server; nested exception is java.net.UnknownHostException: data-auth-server
    at org.springframework.web.client.RestTemplate.doExecute(RestTemplate.java:751) ~[spring-web-5.2.1.RELEASE.jar:5.2.1.RELEASE]
    at org.springframework.web.client.RestTemplate.execute(RestTemplate.java:677) ~[spring-web-5.2.1.RELEASE.jar:5.2.1.RELEASE]
    at org.springframework.web.client.RestTemplate.exchange(RestTemplate.java:586) ~[spring-web-5.2.1.RELEASE.jar:5.2.1.RELEASE]
    at org.springframework.boot.autoconfigure.security.oauth2.resource.ResourceServerTokenServicesConfiguration$JwtTokenServicesConfiguration.getKeyFromServer(ResourceServerTokenServicesConfiguration.java:318) ~[spring-security-oauth2-autoconfigure-2.1.2.RELEASE.jar:2.1.2.RELEASE]
    at org.springframework.boot.autoconfigure.security.oauth2.resource.ResourceServerTokenServicesConfiguration$JwtTokenServicesConfiguration.jwtTokenEnhancer(ResourceServerTokenServicesConfiguration.java:283) ~[spring-security-oauth2-autoconfigure-2.1.2.RELEASE.jar:2.1.2.RELEASE]
    at org.springframework.boot.autoconfigure.security.oauth2.resource.ResourceServerTokenServicesConfiguration$JwtTokenServicesConfiguration$$EnhancerBySpringCGLIB$$ead76d0e.CGLIB$jwtTokenEnhancer$1(<generated>) ~[spring-security-oauth2-autoconfigure-2.1.2.RELEASE.jar:2.1.2.RELEASE]
    at org.springframework.boot.autoconfigure.security.oauth2.resource.ResourceServerTokenServicesConfiguration$JwtTokenServicesConfiguration$$EnhancerBySpringCGLIB$$ead76d0e$$FastClassBySpringCGLIB$$99bec3ca.invoke(<generated>) ~[spring-security-oauth2-autoconfigure-2.1.2.RELEASE.jar:2.1.2.RELEASE]
    at org.springframework.cglib.proxy.MethodProxy.invokeSuper(MethodProxy.java:244) ~[spring-core-5.2.1.RELEASE.jar:5.2.1.RELEASE]
    at org.springframework.context.annotation.ConfigurationClassEnhancer$BeanMethodInterceptor.intercept(ConfigurationClassEnhancer.java:363) ~[spring-context-5.2.1.RELEASE.jar:5.2.1.RELEASE]
    at org.springframework.boot.autoconfigure.security.oauth2.resource.ResourceServerTokenServicesConfiguration$JwtTokenServicesConfiguration$$EnhancerBySpringCGLIB$$ead76d0e.jwtTokenEnhancer(<generated>) ~[spring-security-oauth2-autoconfigure-2.1.2.RELEASE.jar:2.1.2.RELEASE]
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:1.8.0_162]
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:1.8.0_162]
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:1.8.0_162]
    at java.lang.reflect.Method.invoke(Method.java:498) ~[na:1.8.0_162]
    at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:154) ~[spring-beans-5.2.1.RELEASE.jar:5.2.1.RELEASE]
    ... 57 common frames omitted

by the way, if i use the following configuration for client application,it runs well:
```yml
security:
  oauth2: 
    resource:
      jwt:
        key-uri: http://localhost:9000/oauth/token_key

is there any way to solve this exception?

ryanjbaxter commented 4 years ago

Is data-auth-server actually a host name that DNS would resolve? It seems like an issue with your environment rather than an issue with Spring Cloud Security.

AnnieCattice commented 4 years ago

sorry about taking a long time to reply it.

  1. in data-auth-server, i created a rest controller for testing:
    @RestController
    @RequestMapping("/user")
    public class UserController {
    @GetMapping("/getCurrentUser")
    public Object getCurrentUser(Authentication authentication, HttpServletRequest request) {
        return authentication;
    }
    }
  2. in oauth2 client , here is the code for testing :

    @RestController
    @Slf4j
    public class LoginController {
    
    private final OAuth2RestTemplate oAuth2RestTemplate;
    
    @Autowired
    public LoginController(OAuth2RestTemplate oAuth2RestTemplate) {
        this.oAuth2RestTemplate = oAuth2RestTemplate;
    }
    @GetMapping(value = "/user/get")
    public Object getCurrentUser(){
        Object user = this.oAuth2RestTemplate.getForEntity("http://data-auth-server/user/getCurrentUser",Object.class);
        log.info("current login user's info:{}",JSON.toJSONString(user));
        return ResponseEntity.ok().body(new HashMap<>());
    }
    }

    oauth2Template config:

    @Bean
    @LoadBalanced
    public OAuth2RestTemplate oAuth2RestTemplate(OAuth2ProtectedResourceDetails resource, OAuth2ClientContext context){
        return new OAuth2RestTemplate(resource,context);
    }

the log has been printed as :

2019-12-10 11:47:46.011  INFO 1764 --- [  XNIO-1 task-1] c.n.l.DynamicServerListLoadBalancer      : DynamicServerListLoadBalancer for client data-auth-server initialized: DynamicServerListLoadBalancer:{NFLoadBalancer:name=data-auth-server,current list of Servers=[192.168.1.124:9000],Load balancer stats=Zone stats: {unknown=[Zone:unknown; Instance count:1;   Active connections count: 0;    Circuit breaker tripped count: 0;   Active connections per server: 0.0;]
},Server stats: [[Server:192.168.1.124:9000;    Zone:UNKNOWN;   Total Requests:0;   Successive connection failure:0;    Total blackout seconds:0;   Last connection made:Thu Jan 01 08:00:00 CST 1970;  First connection made: Thu Jan 01 08:00:00 CST 1970;    Active Connections:0;   total failure count in last (1000) msecs:0; average resp time:0.0;  90 percentile resp time:0.0;    95 percentile resp time:0.0;    min resp time:0.0;  max resp time:0.0;  stddev resp time:0.0]
]}ServerList:com.alibaba.cloud.nacos.ribbon.NacosServerList@362e7648
2019-12-10 11:47:46.115  INFO 1764 --- [  XNIO-1 task-1] com.lcg.data.rest.sys.LoginController    : current login user's info:{"body":{"authorities":[{"authority":"admin"}],"details":{"remoteAddress":"192.168.1.124","tokenValue":"eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJ1c2VyX25hbWUiOiJsaW5jaHVhbmdhbmciLCJzY29wZSI6WyJhbGwiXSwiZXhwIjoxNTc1OTUyODQ3LCJhdXRob3JpdGllcyI6WyJhZG1pbiJdLCJqdGkiOiJjOTM5NGI5Yi03ODk1LTQ4YTMtYjg4Ny1jMGM3OTg0MzcwMmIiLCJjbGllbnRfaWQiOiJhZG1pbiIsImVuaGFuY2UiOiJlbmhhbmNlIGluZm8ifQ.Vt44tP90WS5uBeog90bijD-GEidZKuO2Wea5suU_tRI","tokenType":"Bearer"},"authenticated":true,"userAuthentication":{"authorities":[{"authority":"admin"}],"authenticated":true,"principal":"TestUser","credentials":"N/A","name":"linchuangang"},"oauth2Request":{"clientId":"admin","scope":["all"],"requestParameters":{"client_id":"admin"},"resourceIds":[],"authorities":[],"approved":true,"refresh":false,"responseTypes":[],"extensions":{}},"principal":"TestUser","credentials":"","clientOnly":false,"name":"TestUser"},"headers":{"X-Content-Type-Options":["nosniff"],"X-XSS-Protection":["1; mode=block"],"Cache-Control":["no-cache, no-store, max-age=0, must-revalidate"],"Pragma":["no-cache"],"Expires":["0"],"X-Frame-Options":["DENY"],"Content-Type":["application/json"],"Transfer-Encoding":["chunked"],"Date":["Tue, 10 Dec 2019 03:47:46 GMT"]},"statusCode":"OK","statusCodeValue":200}
2019-12-10 11:47:46.455  INFO 1764 --- [erListUpdater-0] c.netflix.config.ChainedDynamicProperty  : Flipping property: data-auth-server.ribbon.ActiveConnectionsLimit to use NEXT property: niws.loadbalancer.availabilityFilteringRule.activeConnectionsLimit = 2147483647

as the result shows , Oauth2RestTemplate could recognize data-auth-server host name and calls request with real ip address.

this is full configurations in application.yml for the oauth2 client:

oauth2:
  server:
    uri: http://data-auth-server
    token-uri: /oauth/token
    auth-uri: /oauth/authorize
    key-uri: /oauth/token_key
security:
  oauth2: 
    client:
      client-id: admin
      client-secret: admin123456
      user-authorization-uri: ${oauth2.server.uri}${oauth2.server.token-uri}
      access-token-uri: ${oauth2.server.uri}${oauth2.server.auth-uri}
    resource:
      jwt:
        key-uri: http://localhost:9000/oauth/token_key
  1. if i use jwt as system authorizing, i have to set key-uri with real host address like http://localhost:9000/oauth/token_key. that is the problem i care about. what if i run two replicates of data-auth-server service in eureka, and i don't know which host should be used for jwt.key-uri.

  2. besides, i find out access-token-uri: http://data-auth-server/oauth/authorize is working well, why jwt.key-uri is not supported for this pattern : http://${spring.application.name}/xxx