More robust instantiation in SpringClientFactory
SpringClientFactory returns null if the class is not aware of IClientConfig. This change catches the exception when trying the constructor with IClientConfig so classes that aren't aware of IClientConfig can be created. Fixes gh-1608
This commit is contained in:
committed by
Spencer Gibb
parent
3b41b5e15f
commit
b27ba0434a
@@ -16,6 +16,8 @@
|
||||
|
||||
package org.springframework.cloud.netflix.ribbon;
|
||||
|
||||
import java.lang.reflect.Constructor;
|
||||
|
||||
import org.springframework.beans.BeanUtils;
|
||||
import org.springframework.cloud.context.named.NamedContextFactory;
|
||||
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
|
||||
@@ -80,33 +82,30 @@ public class SpringClientFactory extends NamedContextFactory<RibbonClientSpecifi
|
||||
static <C> C instantiateWithConfig(AnnotationConfigApplicationContext context,
|
||||
Class<C> clazz, IClientConfig config) {
|
||||
C result = null;
|
||||
if (IClientConfigAware.class.isAssignableFrom(clazz)) {
|
||||
IClientConfigAware obj = (IClientConfigAware) BeanUtils.instantiate(clazz);
|
||||
obj.initWithNiwsConfig(config);
|
||||
@SuppressWarnings("unchecked")
|
||||
C value = (C) obj;
|
||||
result = value;
|
||||
|
||||
try {
|
||||
Constructor<C> constructor = clazz.getConstructor(IClientConfig.class);
|
||||
result = constructor.newInstance(config);
|
||||
} catch (Throwable e) {
|
||||
// Ignored
|
||||
}
|
||||
else {
|
||||
try {
|
||||
if (clazz.getConstructor(IClientConfig.class) != null) {
|
||||
result = clazz.getConstructor(IClientConfig.class)
|
||||
.newInstance(config);
|
||||
}
|
||||
else {
|
||||
result = BeanUtils.instantiate(clazz);
|
||||
}
|
||||
|
||||
if (result == null) {
|
||||
result = BeanUtils.instantiate(clazz);
|
||||
|
||||
if (result instanceof IClientConfigAware) {
|
||||
((IClientConfigAware) result).initWithNiwsConfig(config);
|
||||
}
|
||||
catch (Throwable ex) {
|
||||
// NOPMD
|
||||
|
||||
if (context != null) {
|
||||
context.getAutowireCapableBeanFactory().autowireBean(result);
|
||||
}
|
||||
}
|
||||
if (context != null) {
|
||||
context.getAutowireCapableBeanFactory().autowireBean(result);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public <C> C getInstance(String name, Class<C> type) {
|
||||
C instance = super.getInstance(name, type);
|
||||
if (instance != null) {
|
||||
|
||||
@@ -23,9 +23,13 @@ import org.springframework.cloud.netflix.archaius.ArchaiusAutoConfiguration;
|
||||
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
|
||||
|
||||
import com.netflix.client.DefaultLoadBalancerRetryHandler;
|
||||
import com.netflix.client.IClientConfigAware;
|
||||
import com.netflix.client.config.DefaultClientConfigImpl;
|
||||
import com.netflix.client.config.IClientConfig;
|
||||
import com.netflix.niws.client.http.RestClient;
|
||||
import com.sun.jersey.client.apache4.ApacheHttpClient4;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.springframework.boot.test.util.EnvironmentTestUtils.addEnvironment;
|
||||
|
||||
@@ -35,6 +39,31 @@ import static org.springframework.boot.test.util.EnvironmentTestUtils.addEnviron
|
||||
*/
|
||||
public class SpringClientFactoryTests {
|
||||
|
||||
public static class ClientConfigInjectedByConstructor {
|
||||
|
||||
private IClientConfig clientConfig;
|
||||
|
||||
public ClientConfigInjectedByConstructor(IClientConfig clientConfig) {
|
||||
this.clientConfig = clientConfig;
|
||||
}
|
||||
}
|
||||
|
||||
public static class ClientConfigInjectedByInitMethod implements IClientConfigAware {
|
||||
|
||||
private IClientConfig clientConfig;
|
||||
|
||||
@Override
|
||||
public void initWithNiwsConfig(IClientConfig clientConfig) {
|
||||
this.clientConfig = clientConfig;
|
||||
}
|
||||
}
|
||||
|
||||
public static class NoClientConfigAware {
|
||||
|
||||
public NoClientConfigAware() {
|
||||
// no client config
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testConfigureRetry() {
|
||||
@@ -65,4 +94,25 @@ public class SpringClientFactoryTests {
|
||||
.getHttpClient().getParams().getParameter(ClientPNames.COOKIE_POLICY));
|
||||
factory.destroy();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testInstantiateWithConfigInjectByConstructor() {
|
||||
IClientConfig clientConfig = new DefaultClientConfigImpl();
|
||||
ClientConfigInjectedByConstructor instance = SpringClientFactory.instantiateWithConfig(ClientConfigInjectedByConstructor.class, clientConfig);
|
||||
assertThat(instance.clientConfig).isSameAs(clientConfig);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testInstantiateWithConfigInjectedByInitMethod() {
|
||||
IClientConfig clientConfig = new DefaultClientConfigImpl();
|
||||
ClientConfigInjectedByInitMethod instance = SpringClientFactory.instantiateWithConfig(ClientConfigInjectedByInitMethod.class, clientConfig);
|
||||
assertThat(instance.clientConfig).isSameAs(clientConfig);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testInstantiateWithoutConfig() {
|
||||
IClientConfig clientConfig = new DefaultClientConfigImpl();
|
||||
NoClientConfigAware instance = SpringClientFactory.instantiateWithConfig(NoClientConfigAware.class, clientConfig);
|
||||
assertThat(instance).isNotNull();
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user