2015-01-22 2 views
0

Я пытаюсь вызвать балансировщик нагрузки, чтобы получить доступ к экземпляру службы, чтобы построить токен доступа OAuth2RestTemplate uri в моем классе конфигурации, но по какой-то причине я продолжаю получать исключения, когда компонент создается , Кто-нибудь сталкивался с этим вопросом раньше? Или, может быть, может быть некоторое понимание?Ribbon LB/OAuth2RestTemplate

Завод метод «restTemplate» бросил исключение; вложенное исключение java.lang.IllegalStateException: Не удалось найти ILoadBalancer для службы: Служба

Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'restTemplate' defined in class path resource [com/apop/services/config/rest/RestConfiguration.class]: Bean instantiation via factory method failed; nested exception is org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.security.oauth2.client.OAuth2RestTemplate]: Factory method 'serviceRestTemplate' threw exception; nested exception is java.lang.IllegalStateException: Unable to locate ILoadBalancer for service: service 

Также здесь мои услуги и конфигурационные классы:

@Service 
public class ServiceIntegration implements Service, Serializable { 


@Resource(name = "serviceRestTemplate") 
OAuth2RestTemplate serviceRestTemplate; 

@Autowired 
private LoadBalancerClient balancerClient; 

@Value("${service}") 
private String service; 

private ResponseExceptionHelper responseExceptionHelper = new ResponseExceptionHelper(); 

public ResponseExceptionHelper getResponseExceptionHelper() { 
    return responseExceptionHelper; 
} 

public void setResponseExceptionHelper(
     ResponseExceptionHelper responseExceptionHelper) { 
    this.responseExceptionHelper = responseExceptionHelper; 
} 

/** 
* @param payload 
* @param path 
* @param method 
* @return 
* @throws ResponseException 
*/ 
private String execute(OAuth2RestTemplate restTemplate, String endPoint, String payload, HttpMethod method) 
     throws ResponseException { 
    HttpHeaders headers = new HttpHeaders(); 

    headers.setContentType(MediaType.APPLICATION_JSON); 
    HttpEntity<String> requestEntity = new HttpEntity<String>(payload, headers); 

    String response = null; 
    try { 

     ServiceInstance serviceInstance = balancerClient.choose(service); 
     String uri = String.format("http://%s:%s/%s", serviceInstance.getHost(), serviceInstance.getPort(), service) + endPoint; 
     ResponseEntity<String> responseEntity = restTemplate.exchange(uri, method, requestEntity, String.class); 
     if (responseEntity != null) { 
      response = responseEntity.getBody(); 
     } 
    } catch (Exception e) { 
     logger.error(error, e); 
     throw e; 
    } 

    logger.info(response); 
    return response; 
} 

} 

Config:

@Configuration 
@ComponentScan 
@EnableAutoConfiguration 
public class RestConfiguration { 


@Value("${service}") 
private String service; 


@Value("${token.service.endpoint}") 
private String tokenServiceEndpoint; 


@Value("${clientId}") 
private String clientId; 

@Value("${clientSecret}") 
private String clientSecret; 

@Value("${grant}") 
private String grant; 

@Autowired 
private LoadBalancerClient balancerClient; 


@Bean 
public OAuth2RestTemplate serviceRestTemplate() { 
    ClientCredentialsResourceDetails resources = getClientDetails(); 
    OAuth2RestTemplate restTemplate = new OAuth2RestTemplate(resources, new DefaultOAuth2ClientContext()); 
    return restTemplate; 
} 


public ClientCredentialsResourceDetails getClientDetails() { 
    ServiceInstance serviceInstance = balancerClient.choose(service); 
    String uri = String.format("http://%s:%s/%s", serviceInstance.getHost(), serviceInstance.getPort(), legacyService) + tokenServiceEndpoint; 

    ClientCredentialsResourceDetails resource = new ClientCredentialsResourceDetails(); 
    resource.setAccessTokenUri(uri); 
    resource.setClientSecret(clientId); 
    resource.setClientId(clientSecret); 
    resource.setGrantType(grant); 
    return resource; 
} 

} 
+1

N.B. если вы создаете 'OAuth2ClientContext', как будто вы не получаете разделения между параллельными контекстами (так что это действительно действительно подходит для грантов учетных данных клиента). –

ответ

0

Вы пытаются сделать сервисное обнаружение в определении @Bean (так супер рано), прежде чем каталог услуг будет доступен. Было бы лучше использовать RibbonInterceptor в нормальном состоянии OAuth2RestTemplate (как в RibbonAutoConfiguration).

+0

интересный. Есть ли пример использования RibbonInterceptor? – EvilJinious1

+0

Вот как мы создаем «RestTemplate» с поддержкой ленты, используя «RibbonInterceptor» https://github.com/spring-cloud/spring-cloud-netflix/blob/master/spring-cloud-netflix-core/src/main /java/org/springframework/cloud/netflix/ribbon/RibbonAutoConfiguration.java#L57-L65 – spencergibb