mirror of https://github.com/apache/jclouds.git
fixed exception parsing to return the correct parent exception
This commit is contained in:
parent
89ae22364c
commit
becf96d822
|
@ -35,6 +35,8 @@ import javax.inject.Named;
|
||||||
|
|
||||||
import org.jclouds.concurrent.Timeout;
|
import org.jclouds.concurrent.Timeout;
|
||||||
import org.jclouds.internal.ClassMethodArgs;
|
import org.jclouds.internal.ClassMethodArgs;
|
||||||
|
import org.jclouds.rest.AuthorizationException;
|
||||||
|
import org.jclouds.rest.ResourceNotFoundException;
|
||||||
import org.jclouds.rest.annotations.Delegate;
|
import org.jclouds.rest.annotations.Delegate;
|
||||||
import org.jclouds.util.Utils;
|
import org.jclouds.util.Utils;
|
||||||
|
|
||||||
|
@ -52,8 +54,8 @@ import com.google.common.util.concurrent.ListenableFuture;
|
||||||
public class SyncProxy implements InvocationHandler {
|
public class SyncProxy implements InvocationHandler {
|
||||||
|
|
||||||
@SuppressWarnings("unchecked")
|
@SuppressWarnings("unchecked")
|
||||||
public static <T> T proxy(Class<T> clazz, SyncProxy proxy) throws IllegalArgumentException,
|
public static <T> T proxy(Class<T> clazz, SyncProxy proxy) throws IllegalArgumentException, SecurityException,
|
||||||
SecurityException, NoSuchMethodException {
|
NoSuchMethodException {
|
||||||
return (T) Proxy.newProxyInstance(clazz.getClassLoader(), new Class<?>[] { clazz }, proxy);
|
return (T) Proxy.newProxyInstance(clazz.getClassLoader(), new Class<?>[] { clazz }, proxy);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -68,15 +70,14 @@ public class SyncProxy implements InvocationHandler {
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
public SyncProxy(Class<?> declaring, Object async,
|
public SyncProxy(Class<?> declaring, Object async,
|
||||||
@Named("sync") ConcurrentMap<ClassMethodArgs, Object> delegateMap,
|
@Named("sync") ConcurrentMap<ClassMethodArgs, Object> delegateMap, Map<Class<?>, Class<?>> sync2Async)
|
||||||
Map<Class<?>, Class<?>> sync2Async) throws SecurityException, NoSuchMethodException {
|
throws SecurityException, NoSuchMethodException {
|
||||||
this.delegateMap = delegateMap;
|
this.delegateMap = delegateMap;
|
||||||
this.delegate = async;
|
this.delegate = async;
|
||||||
this.declaring = declaring;
|
this.declaring = declaring;
|
||||||
this.sync2Async = sync2Async;
|
this.sync2Async = sync2Async;
|
||||||
if (!declaring.isAnnotationPresent(Timeout.class)) {
|
if (!declaring.isAnnotationPresent(Timeout.class)) {
|
||||||
throw new IllegalArgumentException(String.format(
|
throw new IllegalArgumentException(String.format("type %s does not specify a default @Timeout", declaring));
|
||||||
"type %s does not specify a default @Timeout", declaring));
|
|
||||||
}
|
}
|
||||||
Timeout typeTimeout = declaring.getAnnotation(Timeout.class);
|
Timeout typeTimeout = declaring.getAnnotation(Timeout.class);
|
||||||
long typeNanos = convertToNanos(typeTimeout);
|
long typeNanos = convertToNanos(typeTimeout);
|
||||||
|
@ -86,12 +87,10 @@ public class SyncProxy implements InvocationHandler {
|
||||||
timeoutMap = Maps.newHashMap();
|
timeoutMap = Maps.newHashMap();
|
||||||
for (Method method : declaring.getMethods()) {
|
for (Method method : declaring.getMethods()) {
|
||||||
if (!objectMethods.contains(method)) {
|
if (!objectMethods.contains(method)) {
|
||||||
Method delegatedMethod = delegate.getClass().getMethod(method.getName(),
|
Method delegatedMethod = delegate.getClass().getMethod(method.getName(), method.getParameterTypes());
|
||||||
method.getParameterTypes());
|
|
||||||
if (!Arrays.equals(delegatedMethod.getExceptionTypes(), method.getExceptionTypes()))
|
if (!Arrays.equals(delegatedMethod.getExceptionTypes(), method.getExceptionTypes()))
|
||||||
throw new IllegalArgumentException(String.format(
|
throw new IllegalArgumentException(String.format(
|
||||||
"method %s has different typed exceptions than delegated method %s",
|
"method %s has different typed exceptions than delegated method %s", method, delegatedMethod));
|
||||||
method, delegatedMethod));
|
|
||||||
if (delegatedMethod.getReturnType().isAssignableFrom(ListenableFuture.class)) {
|
if (delegatedMethod.getReturnType().isAssignableFrom(ListenableFuture.class)) {
|
||||||
if (method.isAnnotationPresent(Timeout.class)) {
|
if (method.isAnnotationPresent(Timeout.class)) {
|
||||||
Timeout methodTimeout = method.getAnnotation(Timeout.class);
|
Timeout methodTimeout = method.getAnnotation(Timeout.class);
|
||||||
|
@ -122,16 +121,16 @@ public class SyncProxy implements InvocationHandler {
|
||||||
return this.toString();
|
return this.toString();
|
||||||
} else if (method.isAnnotationPresent(Delegate.class)) {
|
} else if (method.isAnnotationPresent(Delegate.class)) {
|
||||||
Class<?> asyncClass = sync2Async.get(method.getReturnType());
|
Class<?> asyncClass = sync2Async.get(method.getReturnType());
|
||||||
checkState(asyncClass != null, "please configure corresponding async class for "
|
checkState(asyncClass != null, "please configure corresponding async class for " + method.getReturnType()
|
||||||
+ method.getReturnType() + " in your RestClientModule");
|
+ " in your RestClientModule");
|
||||||
Object returnVal = delegateMap.get(new ClassMethodArgs(asyncClass, method, args));
|
Object returnVal = delegateMap.get(new ClassMethodArgs(asyncClass, method, args));
|
||||||
return returnVal;
|
return returnVal;
|
||||||
} else if (syncMethodMap.containsKey(method)) {
|
} else if (syncMethodMap.containsKey(method)) {
|
||||||
return syncMethodMap.get(method).invoke(delegate, args);
|
return syncMethodMap.get(method).invoke(delegate, args);
|
||||||
} else {
|
} else {
|
||||||
try {
|
try {
|
||||||
return ((ListenableFuture<?>) methodMap.get(method).invoke(delegate, args)).get(
|
return ((ListenableFuture<?>) methodMap.get(method).invoke(delegate, args)).get(timeoutMap.get(method),
|
||||||
timeoutMap.get(method), TimeUnit.NANOSECONDS);
|
TimeUnit.NANOSECONDS);
|
||||||
} catch (ExecutionException e) {
|
} catch (ExecutionException e) {
|
||||||
throw throwTypedExceptionOrCause(method.getExceptionTypes(), e);
|
throw throwTypedExceptionOrCause(method.getExceptionTypes(), e);
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
|
@ -141,14 +140,16 @@ public class SyncProxy implements InvocationHandler {
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressWarnings("unchecked")
|
@SuppressWarnings("unchecked")
|
||||||
public static Exception throwTypedExceptionOrCause(Class[] exceptionTypes, Exception exception)
|
public static Exception throwTypedExceptionOrCause(Class[] exceptionTypes, Exception exception) throws Exception {
|
||||||
throws Exception {
|
|
||||||
for (Class type : exceptionTypes) {
|
for (Class type : exceptionTypes) {
|
||||||
Throwable throwable = Utils.getFirstThrowableOfType(exception, type);
|
Throwable throwable = Utils.getFirstThrowableOfType(exception, type);
|
||||||
if (throwable != null) {
|
if (throwable != null) {
|
||||||
Throwables.throwCause(exception, true);
|
return (Exception) throwable;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Throwables.propagateIfInstanceOf(exception, IllegalStateException.class);
|
||||||
|
Throwables.propagateIfInstanceOf(exception, AuthorizationException.class);
|
||||||
|
Throwables.propagateIfInstanceOf(exception, ResourceNotFoundException.class);
|
||||||
Throwables.throwCause(exception, true);
|
Throwables.throwCause(exception, true);
|
||||||
return exception;
|
return exception;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue