org.springframework.core.DecoratingProxy Java Examples

The following examples show how to use org.springframework.core.DecoratingProxy. You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example #1
Source File: AopProxyUtils.java    From spring-analysis-note with MIT License 6 votes vote down vote up
/**
 * Extract the user-specified interfaces that the given proxy implements,
 * i.e. all non-Advised interfaces that the proxy implements.
 * @param proxy the proxy to analyze (usually a JDK dynamic proxy)
 * @return all user-specified interfaces that the proxy implements,
 * in the original order (never {@code null} or empty)
 * @see Advised
 */
public static Class<?>[] proxiedUserInterfaces(Object proxy) {
	Class<?>[] proxyInterfaces = proxy.getClass().getInterfaces();
	int nonUserIfcCount = 0;
	if (proxy instanceof SpringProxy) {
		nonUserIfcCount++;
	}
	if (proxy instanceof Advised) {
		nonUserIfcCount++;
	}
	if (proxy instanceof DecoratingProxy) {
		nonUserIfcCount++;
	}
	Class<?>[] userInterfaces = new Class<?>[proxyInterfaces.length - nonUserIfcCount];
	System.arraycopy(proxyInterfaces, 0, userInterfaces, 0, userInterfaces.length);
	Assert.notEmpty(userInterfaces, "JDK proxy must implement one or more interfaces");
	return userInterfaces;
}
 
Example #2
Source File: AopProxyUtils.java    From lams with GNU General Public License v2.0 6 votes vote down vote up
/**
 * Extract the user-specified interfaces that the given proxy implements,
 * i.e. all non-Advised interfaces that the proxy implements.
 * @param proxy the proxy to analyze (usually a JDK dynamic proxy)
 * @return all user-specified interfaces that the proxy implements,
 * in the original order (never {@code null} or empty)
 * @see Advised
 */
public static Class<?>[] proxiedUserInterfaces(Object proxy) {
	Class<?>[] proxyInterfaces = proxy.getClass().getInterfaces();
	int nonUserIfcCount = 0;
	if (proxy instanceof SpringProxy) {
		nonUserIfcCount++;
	}
	if (proxy instanceof Advised) {
		nonUserIfcCount++;
	}
	if (proxy instanceof DecoratingProxy) {
		nonUserIfcCount++;
	}
	Class<?>[] userInterfaces = new Class<?>[proxyInterfaces.length - nonUserIfcCount];
	System.arraycopy(proxyInterfaces, 0, userInterfaces, 0, userInterfaces.length);
	Assert.notEmpty(userInterfaces, "JDK proxy must implement one or more interfaces");
	return userInterfaces;
}
 
Example #3
Source File: AopProxyUtils.java    From java-technology-stack with MIT License 6 votes vote down vote up
/**
 * Extract the user-specified interfaces that the given proxy implements,
 * i.e. all non-Advised interfaces that the proxy implements.
 * @param proxy the proxy to analyze (usually a JDK dynamic proxy)
 * @return all user-specified interfaces that the proxy implements,
 * in the original order (never {@code null} or empty)
 * @see Advised
 */
public static Class<?>[] proxiedUserInterfaces(Object proxy) {
	Class<?>[] proxyInterfaces = proxy.getClass().getInterfaces();
	int nonUserIfcCount = 0;
	if (proxy instanceof SpringProxy) {
		nonUserIfcCount++;
	}
	if (proxy instanceof Advised) {
		nonUserIfcCount++;
	}
	if (proxy instanceof DecoratingProxy) {
		nonUserIfcCount++;
	}
	Class<?>[] userInterfaces = new Class<?>[proxyInterfaces.length - nonUserIfcCount];
	System.arraycopy(proxyInterfaces, 0, userInterfaces, 0, userInterfaces.length);
	Assert.notEmpty(userInterfaces, "JDK proxy must implement one or more interfaces");
	return userInterfaces;
}
 
Example #4
Source File: FormattingConversionService.java    From java-technology-stack with MIT License 5 votes vote down vote up
static Class<?> getFieldType(Formatter<?> formatter) {
	Class<?> fieldType = GenericTypeResolver.resolveTypeArgument(formatter.getClass(), Formatter.class);
	if (fieldType == null && formatter instanceof DecoratingProxy) {
		fieldType = GenericTypeResolver.resolveTypeArgument(
				((DecoratingProxy) formatter).getDecoratedClass(), Formatter.class);
	}
	if (fieldType == null) {
		throw new IllegalArgumentException("Unable to extract the parameterized field type from Formatter [" +
				formatter.getClass().getName() + "]; does the class parameterize the <T> generic type?");
	}
	return fieldType;
}
 
Example #5
Source File: GenericConversionService.java    From lams with GNU General Public License v2.0 5 votes vote down vote up
@Override
public void addConverterFactory(ConverterFactory<?, ?> factory) {
	ResolvableType[] typeInfo = getRequiredTypeInfo(factory.getClass(), ConverterFactory.class);
	if (typeInfo == null && factory instanceof DecoratingProxy) {
		typeInfo = getRequiredTypeInfo(((DecoratingProxy) factory).getDecoratedClass(), ConverterFactory.class);
	}
	if (typeInfo == null) {
		throw new IllegalArgumentException("Unable to determine source type <S> and target type <T> for your " +
				"ConverterFactory [" + factory.getClass().getName() + "]; does the class parameterize those types?");
	}
	addConverter(new ConverterFactoryAdapter(factory,
			new ConvertiblePair(typeInfo[0].resolve(), typeInfo[1].resolve())));
}
 
Example #6
Source File: GenericConversionService.java    From lams with GNU General Public License v2.0 5 votes vote down vote up
@Override
public void addConverter(Converter<?, ?> converter) {
	ResolvableType[] typeInfo = getRequiredTypeInfo(converter.getClass(), Converter.class);
	if (typeInfo == null && converter instanceof DecoratingProxy) {
		typeInfo = getRequiredTypeInfo(((DecoratingProxy) converter).getDecoratedClass(), Converter.class);
	}
	if (typeInfo == null) {
		throw new IllegalArgumentException("Unable to determine source type <S> and target type <T> for your " +
				"Converter [" + converter.getClass().getName() + "]; does the class parameterize those types?");
	}
	addConverter(new ConverterAdapter(converter, typeInfo[0], typeInfo[1]));
}
 
Example #7
Source File: AnnotationAwareOrderComparator.java    From lams with GNU General Public License v2.0 5 votes vote down vote up
/**
 * This implementation retrieves an @{@link javax.annotation.Priority}
 * value, allowing for additional semantics over the regular @{@link Order}
 * annotation: typically, selecting one object over another in case of
 * multiple matches but only one object to be returned.
 */
public Integer getPriority(Object obj) {
	Integer priority = null;
	if (obj instanceof Class) {
		priority = OrderUtils.getPriority((Class<?>) obj);
	}
	else if (obj != null) {
		priority = OrderUtils.getPriority(obj.getClass());
		if (priority == null && obj instanceof DecoratingProxy) {
			priority = OrderUtils.getOrder(((DecoratingProxy) obj).getDecoratedClass());
		}
	}
	return priority;
}
 
Example #8
Source File: FormattingConversionService.java    From lams with GNU General Public License v2.0 5 votes vote down vote up
static Class<?> getFieldType(Formatter<?> formatter) {
	Class<?> fieldType = GenericTypeResolver.resolveTypeArgument(formatter.getClass(), Formatter.class);
	if (fieldType == null && formatter instanceof DecoratingProxy) {
		fieldType = GenericTypeResolver.resolveTypeArgument(
				((DecoratingProxy) formatter).getDecoratedClass(), Formatter.class);
	}
	if (fieldType == null) {
		throw new IllegalArgumentException("Unable to extract the parameterized field type from Formatter [" +
				formatter.getClass().getName() + "]; does the class parameterize the <T> generic type?");
	}
	return fieldType;
}
 
Example #9
Source File: GenericConversionService.java    From java-technology-stack with MIT License 5 votes vote down vote up
@Override
public void addConverterFactory(ConverterFactory<?, ?> factory) {
	ResolvableType[] typeInfo = getRequiredTypeInfo(factory.getClass(), ConverterFactory.class);
	if (typeInfo == null && factory instanceof DecoratingProxy) {
		typeInfo = getRequiredTypeInfo(((DecoratingProxy) factory).getDecoratedClass(), ConverterFactory.class);
	}
	if (typeInfo == null) {
		throw new IllegalArgumentException("Unable to determine source type <S> and target type <T> for your " +
				"ConverterFactory [" + factory.getClass().getName() + "]; does the class parameterize those types?");
	}
	addConverter(new ConverterFactoryAdapter(factory,
			new ConvertiblePair(typeInfo[0].toClass(), typeInfo[1].toClass())));
}
 
Example #10
Source File: GenericConversionService.java    From java-technology-stack with MIT License 5 votes vote down vote up
@Override
public void addConverter(Converter<?, ?> converter) {
	ResolvableType[] typeInfo = getRequiredTypeInfo(converter.getClass(), Converter.class);
	if (typeInfo == null && converter instanceof DecoratingProxy) {
		typeInfo = getRequiredTypeInfo(((DecoratingProxy) converter).getDecoratedClass(), Converter.class);
	}
	if (typeInfo == null) {
		throw new IllegalArgumentException("Unable to determine source type <S> and target type <T> for your " +
				"Converter [" + converter.getClass().getName() + "]; does the class parameterize those types?");
	}
	addConverter(new ConverterAdapter(converter, typeInfo[0], typeInfo[1]));
}
 
Example #11
Source File: AnnotationAwareOrderComparator.java    From java-technology-stack with MIT License 5 votes vote down vote up
/**
 * This implementation retrieves an @{@link javax.annotation.Priority}
 * value, allowing for additional semantics over the regular @{@link Order}
 * annotation: typically, selecting one object over another in case of
 * multiple matches but only one object to be returned.
 */
@Override
@Nullable
public Integer getPriority(Object obj) {
	if (obj instanceof Class) {
		return OrderUtils.getPriority((Class<?>) obj);
	}
	Integer priority = OrderUtils.getPriority(obj.getClass());
	if (priority == null && obj instanceof DecoratingProxy) {
		priority = OrderUtils.getPriority(((DecoratingProxy) obj).getDecoratedClass());
	}
	return priority;
}
 
Example #12
Source File: GenericConversionService.java    From spring-analysis-note with MIT License 5 votes vote down vote up
@Override
public void addConverterFactory(ConverterFactory<?, ?> factory) {
	ResolvableType[] typeInfo = getRequiredTypeInfo(factory.getClass(), ConverterFactory.class);
	if (typeInfo == null && factory instanceof DecoratingProxy) {
		typeInfo = getRequiredTypeInfo(((DecoratingProxy) factory).getDecoratedClass(), ConverterFactory.class);
	}
	if (typeInfo == null) {
		throw new IllegalArgumentException("Unable to determine source type <S> and target type <T> for your " +
				"ConverterFactory [" + factory.getClass().getName() + "]; does the class parameterize those types?");
	}
	addConverter(new ConverterFactoryAdapter(factory,
			new ConvertiblePair(typeInfo[0].toClass(), typeInfo[1].toClass())));
}
 
Example #13
Source File: GenericConversionService.java    From spring-analysis-note with MIT License 5 votes vote down vote up
@Override
public void addConverter(Converter<?, ?> converter) {
	ResolvableType[] typeInfo = getRequiredTypeInfo(converter.getClass(), Converter.class);
	if (typeInfo == null && converter instanceof DecoratingProxy) {
		typeInfo = getRequiredTypeInfo(((DecoratingProxy) converter).getDecoratedClass(), Converter.class);
	}
	if (typeInfo == null) {
		throw new IllegalArgumentException("Unable to determine source type <S> and target type <T> for your " +
				"Converter [" + converter.getClass().getName() + "]; does the class parameterize those types?");
	}
	addConverter(new ConverterAdapter(converter, typeInfo[0], typeInfo[1]));
}
 
Example #14
Source File: AnnotationAwareOrderComparator.java    From spring-analysis-note with MIT License 5 votes vote down vote up
/**
 * This implementation retrieves an @{@link javax.annotation.Priority}
 * value, allowing for additional semantics over the regular @{@link Order}
 * annotation: typically, selecting one object over another in case of
 * multiple matches but only one object to be returned.
 */
@Override
@Nullable
public Integer getPriority(Object obj) {
	if (obj instanceof Class) {
		return OrderUtils.getPriority((Class<?>) obj);
	}
	Integer priority = OrderUtils.getPriority(obj.getClass());
	if (priority == null  && obj instanceof DecoratingProxy) {
		return getPriority(((DecoratingProxy) obj).getDecoratedClass());
	}
	return priority;
}
 
Example #15
Source File: AnnotationAwareOrderComparator.java    From spring-analysis-note with MIT License 5 votes vote down vote up
@Nullable
private Integer findOrderFromAnnotation(Object obj) {
	AnnotatedElement element = (obj instanceof AnnotatedElement ? (AnnotatedElement) obj : obj.getClass());
	MergedAnnotations annotations = MergedAnnotations.from(element, SearchStrategy.EXHAUSTIVE);
	Integer order = OrderUtils.getOrderFromAnnotations(element, annotations);
	if (order == null && obj instanceof DecoratingProxy) {
		return findOrderFromAnnotation(((DecoratingProxy) obj).getDecoratedClass());
	}
	return order;
}
 
Example #16
Source File: FormattingConversionService.java    From spring-analysis-note with MIT License 5 votes vote down vote up
static Class<?> getFieldType(Formatter<?> formatter) {
	Class<?> fieldType = GenericTypeResolver.resolveTypeArgument(formatter.getClass(), Formatter.class);
	if (fieldType == null && formatter instanceof DecoratingProxy) {
		fieldType = GenericTypeResolver.resolveTypeArgument(
				((DecoratingProxy) formatter).getDecoratedClass(), Formatter.class);
	}
	if (fieldType == null) {
		throw new IllegalArgumentException("Unable to extract the parameterized field type from Formatter [" +
				formatter.getClass().getName() + "]; does the class parameterize the <T> generic type?");
	}
	return fieldType;
}
 
Example #17
Source File: JdkDynamicAopProxy.java    From spring-analysis-note with MIT License 4 votes vote down vote up
/**
 * Implementation of {@code InvocationHandler.invoke}.
 * <p>Callers will see exactly the exception thrown by the target,
 * unless a hook method throws an exception.
 */
@Override
@Nullable
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
	// 注释 8.12 jdk 动态代理重载的 invoke 方法
	MethodInvocation invocation;
	Object oldProxy = null;
	boolean setProxyContext = false;

	TargetSource targetSource = this.advised.targetSource;
	Object target = null;

	try {
		// 处理 equals 方法
		if (!this.equalsDefined && AopUtils.isEqualsMethod(method)) {
			// The target does not implement the equals(Object) method itself.
			return equals(args[0]);
		}
		else if (!this.hashCodeDefined && AopUtils.isHashCodeMethod(method)) {
			// The target does not implement the hashCode() method itself.
			return hashCode();
		}
		else if (method.getDeclaringClass() == DecoratingProxy.class) {
			// There is only getDecoratedClass() declared -> dispatch to proxy config.
			return AopProxyUtils.ultimateTargetClass(this.advised);
		}
		else if (!this.advised.opaque && method.getDeclaringClass().isInterface() &&
				method.getDeclaringClass().isAssignableFrom(Advised.class)) {
			// Service invocations on ProxyConfig with the proxy config...
			return AopUtils.invokeJoinpointUsingReflection(this.advised, method, args);
		}

		Object retVal;

		if (this.advised.exposeProxy) {
			// Make invocation available if necessary.
			oldProxy = AopContext.setCurrentProxy(proxy);
			setProxyContext = true;
		}

		// Get as late as possible to minimize the time we "own" the target,
		// in case it comes from a pool.
		target = targetSource.getTarget();
		Class<?> targetClass = (target != null ? target.getClass() : null);

		// Get the interception chain for this method.
		// 获取此方法的拦截链
		List<Object> chain = this.advised.getInterceptorsAndDynamicInterceptionAdvice(method, targetClass);

		// Check whether we have any advice. If we don't, we can fallback on direct
		// reflective invocation of the target, and avoid creating a MethodInvocation.
		// 检查我们是否有任何切面逻辑。如果我们不这样做,我们可以回退直接反射调用目标,并避免创建 MethodInvocation。
		if (chain.isEmpty()) {
			// We can skip creating a MethodInvocation: just invoke the target directly
			// Note that the final invoker must be an InvokerInterceptor so we know it does
			// nothing but a reflective operation on the target, and no hot swapping or fancy proxying.
			Object[] argsToUse = AopProxyUtils.adaptArgumentsIfNecessary(method, args);
			retVal = AopUtils.invokeJoinpointUsingReflection(target, method, argsToUse);
		}
		else {
			// We need to create a method invocation...
			// 将拦截器封装在 ReflectiveMethodInvocation,便于使用 proceed 执行拦截器
			invocation = new ReflectiveMethodInvocation(proxy, target, method, args, targetClass, chain);
			// Proceed to the joinpoint through the interceptor chain.
			// 执行拦截器链
			retVal = invocation.proceed();
		}

		// Massage return value if necessary.
		Class<?> returnType = method.getReturnType();
		if (retVal != null && retVal == target &&
				returnType != Object.class && returnType.isInstance(proxy) &&
				!RawTargetAccess.class.isAssignableFrom(method.getDeclaringClass())) {
			// Special case: it returned "this" and the return type of the method
			// is type-compatible. Note that we can't help if the target sets
			// a reference to itself in another returned object.
			retVal = proxy;
		}
		else if (retVal == null && returnType != Void.TYPE && returnType.isPrimitive()) {
			throw new AopInvocationException(
					"Null return value from advice does not match primitive return type for: " + method);
		}
		return retVal;
	}
	finally {
		if (target != null && !targetSource.isStatic()) {
			// Must have come from TargetSource.
			targetSource.releaseTarget(target);
		}
		if (setProxyContext) {
			// Restore old proxy.
			AopContext.setCurrentProxy(oldProxy);
		}
	}
}
 
Example #18
Source File: AopProxyUtils.java    From java-technology-stack with MIT License 4 votes vote down vote up
/**
 * Determine the complete set of interfaces to proxy for the given AOP configuration.
 * <p>This will always add the {@link Advised} interface unless the AdvisedSupport's
 * {@link AdvisedSupport#setOpaque "opaque"} flag is on. Always adds the
 * {@link org.springframework.aop.SpringProxy} marker interface.
 * @param advised the proxy config
 * @param decoratingProxy whether to expose the {@link DecoratingProxy} interface
 * @return the complete set of interfaces to proxy
 * @since 4.3
 * @see SpringProxy
 * @see Advised
 * @see DecoratingProxy
 */
static Class<?>[] completeProxiedInterfaces(AdvisedSupport advised, boolean decoratingProxy) {
	Class<?>[] specifiedInterfaces = advised.getProxiedInterfaces();
	if (specifiedInterfaces.length == 0) {
		// No user-specified interfaces: check whether target class is an interface.
		Class<?> targetClass = advised.getTargetClass();
		if (targetClass != null) {
			if (targetClass.isInterface()) {
				advised.setInterfaces(targetClass);
			}
			else if (Proxy.isProxyClass(targetClass)) {
				advised.setInterfaces(targetClass.getInterfaces());
			}
			specifiedInterfaces = advised.getProxiedInterfaces();
		}
	}
	boolean addSpringProxy = !advised.isInterfaceProxied(SpringProxy.class);
	boolean addAdvised = !advised.isOpaque() && !advised.isInterfaceProxied(Advised.class);
	boolean addDecoratingProxy = (decoratingProxy && !advised.isInterfaceProxied(DecoratingProxy.class));
	int nonUserIfcCount = 0;
	if (addSpringProxy) {
		nonUserIfcCount++;
	}
	if (addAdvised) {
		nonUserIfcCount++;
	}
	if (addDecoratingProxy) {
		nonUserIfcCount++;
	}
	Class<?>[] proxiedInterfaces = new Class<?>[specifiedInterfaces.length + nonUserIfcCount];
	System.arraycopy(specifiedInterfaces, 0, proxiedInterfaces, 0, specifiedInterfaces.length);
	int index = specifiedInterfaces.length;
	if (addSpringProxy) {
		proxiedInterfaces[index] = SpringProxy.class;
		index++;
	}
	if (addAdvised) {
		proxiedInterfaces[index] = Advised.class;
		index++;
	}
	if (addDecoratingProxy) {
		proxiedInterfaces[index] = DecoratingProxy.class;
	}
	return proxiedInterfaces;
}
 
Example #19
Source File: JdkDynamicAopProxy.java    From java-technology-stack with MIT License 4 votes vote down vote up
/**
 * Implementation of {@code InvocationHandler.invoke}.
 * <p>Callers will see exactly the exception thrown by the target,
 * unless a hook method throws an exception.
 */
@Override
@Nullable
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
	MethodInvocation invocation;
	Object oldProxy = null;
	boolean setProxyContext = false;

	TargetSource targetSource = this.advised.targetSource;
	Object target = null;

	try {
		if (!this.equalsDefined && AopUtils.isEqualsMethod(method)) {
			// The target does not implement the equals(Object) method itself.
			return equals(args[0]);
		}
		else if (!this.hashCodeDefined && AopUtils.isHashCodeMethod(method)) {
			// The target does not implement the hashCode() method itself.
			return hashCode();
		}
		else if (method.getDeclaringClass() == DecoratingProxy.class) {
			// There is only getDecoratedClass() declared -> dispatch to proxy config.
			return AopProxyUtils.ultimateTargetClass(this.advised);
		}
		else if (!this.advised.opaque && method.getDeclaringClass().isInterface() &&
				method.getDeclaringClass().isAssignableFrom(Advised.class)) {
			// Service invocations on ProxyConfig with the proxy config...
			return AopUtils.invokeJoinpointUsingReflection(this.advised, method, args);
		}

		Object retVal;

		if (this.advised.exposeProxy) {
			// Make invocation available if necessary.
			oldProxy = AopContext.setCurrentProxy(proxy);
			setProxyContext = true;
		}

		// Get as late as possible to minimize the time we "own" the target,
		// in case it comes from a pool.
		target = targetSource.getTarget();
		Class<?> targetClass = (target != null ? target.getClass() : null);

		// Get the interception chain for this method.
		List<Object> chain = this.advised.getInterceptorsAndDynamicInterceptionAdvice(method, targetClass);

		// Check whether we have any advice. If we don't, we can fallback on direct
		// reflective invocation of the target, and avoid creating a MethodInvocation.
		if (chain.isEmpty()) {
			// We can skip creating a MethodInvocation: just invoke the target directly
			// Note that the final invoker must be an InvokerInterceptor so we know it does
			// nothing but a reflective operation on the target, and no hot swapping or fancy proxying.
			Object[] argsToUse = AopProxyUtils.adaptArgumentsIfNecessary(method, args);
			retVal = AopUtils.invokeJoinpointUsingReflection(target, method, argsToUse);
		}
		else {
			// We need to create a method invocation...
			invocation = new ReflectiveMethodInvocation(proxy, target, method, args, targetClass, chain);
			// Proceed to the joinpoint through the interceptor chain.
			retVal = invocation.proceed();
		}

		// Massage return value if necessary.
		Class<?> returnType = method.getReturnType();
		if (retVal != null && retVal == target &&
				returnType != Object.class && returnType.isInstance(proxy) &&
				!RawTargetAccess.class.isAssignableFrom(method.getDeclaringClass())) {
			// Special case: it returned "this" and the return type of the method
			// is type-compatible. Note that we can't help if the target sets
			// a reference to itself in another returned object.
			retVal = proxy;
		}
		else if (retVal == null && returnType != Void.TYPE && returnType.isPrimitive()) {
			throw new AopInvocationException(
					"Null return value from advice does not match primitive return type for: " + method);
		}
		return retVal;
	}
	finally {
		if (target != null && !targetSource.isStatic()) {
			// Must have come from TargetSource.
			targetSource.releaseTarget(target);
		}
		if (setProxyContext) {
			// Restore old proxy.
			AopContext.setCurrentProxy(oldProxy);
		}
	}
}
 
Example #20
Source File: JdkDynamicAopProxy.java    From lams with GNU General Public License v2.0 4 votes vote down vote up
/**
 * Implementation of {@code InvocationHandler.invoke}.
 * <p>Callers will see exactly the exception thrown by the target,
 * unless a hook method throws an exception.
 */
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
	MethodInvocation invocation;
	Object oldProxy = null;
	boolean setProxyContext = false;

	TargetSource targetSource = this.advised.targetSource;
	Class<?> targetClass = null;
	Object target = null;

	try {
		if (!this.equalsDefined && AopUtils.isEqualsMethod(method)) {
			// The target does not implement the equals(Object) method itself.
			return equals(args[0]);
		}
		else if (!this.hashCodeDefined && AopUtils.isHashCodeMethod(method)) {
			// The target does not implement the hashCode() method itself.
			return hashCode();
		}
		else if (method.getDeclaringClass() == DecoratingProxy.class) {
			// There is only getDecoratedClass() declared -> dispatch to proxy config.
			return AopProxyUtils.ultimateTargetClass(this.advised);
		}
		else if (!this.advised.opaque && method.getDeclaringClass().isInterface() &&
				method.getDeclaringClass().isAssignableFrom(Advised.class)) {
			// Service invocations on ProxyConfig with the proxy config...
			return AopUtils.invokeJoinpointUsingReflection(this.advised, method, args);
		}

		Object retVal;

		if (this.advised.exposeProxy) {
			// Make invocation available if necessary.
			oldProxy = AopContext.setCurrentProxy(proxy);
			setProxyContext = true;
		}

		// May be null. Get as late as possible to minimize the time we "own" the target,
		// in case it comes from a pool.
		target = targetSource.getTarget();
		if (target != null) {
			targetClass = target.getClass();
		}

		// Get the interception chain for this method.
		List<Object> chain = this.advised.getInterceptorsAndDynamicInterceptionAdvice(method, targetClass);

		// Check whether we have any advice. If we don't, we can fallback on direct
		// reflective invocation of the target, and avoid creating a MethodInvocation.
		if (chain.isEmpty()) {
			// We can skip creating a MethodInvocation: just invoke the target directly
			// Note that the final invoker must be an InvokerInterceptor so we know it does
			// nothing but a reflective operation on the target, and no hot swapping or fancy proxying.
			Object[] argsToUse = AopProxyUtils.adaptArgumentsIfNecessary(method, args);
			retVal = AopUtils.invokeJoinpointUsingReflection(target, method, argsToUse);
		}
		else {
			// We need to create a method invocation...
			invocation = new ReflectiveMethodInvocation(proxy, target, method, args, targetClass, chain);
			// Proceed to the joinpoint through the interceptor chain.
			retVal = invocation.proceed();
		}

		// Massage return value if necessary.
		Class<?> returnType = method.getReturnType();
		if (retVal != null && retVal == target &&
				returnType != Object.class && returnType.isInstance(proxy) &&
				!RawTargetAccess.class.isAssignableFrom(method.getDeclaringClass())) {
			// Special case: it returned "this" and the return type of the method
			// is type-compatible. Note that we can't help if the target sets
			// a reference to itself in another returned object.
			retVal = proxy;
		}
		else if (retVal == null && returnType != Void.TYPE && returnType.isPrimitive()) {
			throw new AopInvocationException(
					"Null return value from advice does not match primitive return type for: " + method);
		}
		return retVal;
	}
	finally {
		if (target != null && !targetSource.isStatic()) {
			// Must have come from TargetSource.
			targetSource.releaseTarget(target);
		}
		if (setProxyContext) {
			// Restore old proxy.
			AopContext.setCurrentProxy(oldProxy);
		}
	}
}
 
Example #21
Source File: AopProxyUtils.java    From lams with GNU General Public License v2.0 4 votes vote down vote up
/**
 * Determine the complete set of interfaces to proxy for the given AOP configuration.
 * <p>This will always add the {@link Advised} interface unless the AdvisedSupport's
 * {@link AdvisedSupport#setOpaque "opaque"} flag is on. Always adds the
 * {@link org.springframework.aop.SpringProxy} marker interface.
 * @param advised the proxy config
 * @param decoratingProxy whether to expose the {@link DecoratingProxy} interface
 * @return the complete set of interfaces to proxy
 * @since 4.3
 * @see SpringProxy
 * @see Advised
 * @see DecoratingProxy
 */
static Class<?>[] completeProxiedInterfaces(AdvisedSupport advised, boolean decoratingProxy) {
	Class<?>[] specifiedInterfaces = advised.getProxiedInterfaces();
	if (specifiedInterfaces.length == 0) {
		// No user-specified interfaces: check whether target class is an interface.
		Class<?> targetClass = advised.getTargetClass();
		if (targetClass != null) {
			if (targetClass.isInterface()) {
				advised.setInterfaces(targetClass);
			}
			else if (Proxy.isProxyClass(targetClass)) {
				advised.setInterfaces(targetClass.getInterfaces());
			}
			specifiedInterfaces = advised.getProxiedInterfaces();
		}
	}
	boolean addSpringProxy = !advised.isInterfaceProxied(SpringProxy.class);
	boolean addAdvised = !advised.isOpaque() && !advised.isInterfaceProxied(Advised.class);
	boolean addDecoratingProxy = (decoratingProxy && !advised.isInterfaceProxied(DecoratingProxy.class));
	int nonUserIfcCount = 0;
	if (addSpringProxy) {
		nonUserIfcCount++;
	}
	if (addAdvised) {
		nonUserIfcCount++;
	}
	if (addDecoratingProxy) {
		nonUserIfcCount++;
	}
	Class<?>[] proxiedInterfaces = new Class<?>[specifiedInterfaces.length + nonUserIfcCount];
	System.arraycopy(specifiedInterfaces, 0, proxiedInterfaces, 0, specifiedInterfaces.length);
	int index = specifiedInterfaces.length;
	if (addSpringProxy) {
		proxiedInterfaces[index] = SpringProxy.class;
		index++;
	}
	if (addAdvised) {
		proxiedInterfaces[index] = Advised.class;
		index++;
	}
	if (addDecoratingProxy) {
		proxiedInterfaces[index] = DecoratingProxy.class;
	}
	return proxiedInterfaces;
}
 
Example #22
Source File: AopProxyUtils.java    From spring-analysis-note with MIT License 4 votes vote down vote up
/**
 * Determine the complete set of interfaces to proxy for the given AOP configuration.
 * <p>This will always add the {@link Advised} interface unless the AdvisedSupport's
 * {@link AdvisedSupport#setOpaque "opaque"} flag is on. Always adds the
 * {@link org.springframework.aop.SpringProxy} marker interface.
 * @param advised the proxy config
 * @param decoratingProxy whether to expose the {@link DecoratingProxy} interface
 * @return the complete set of interfaces to proxy
 * @since 4.3
 * @see SpringProxy
 * @see Advised
 * @see DecoratingProxy
 */
static Class<?>[] completeProxiedInterfaces(AdvisedSupport advised, boolean decoratingProxy) {
	Class<?>[] specifiedInterfaces = advised.getProxiedInterfaces();
	if (specifiedInterfaces.length == 0) {
		// No user-specified interfaces: check whether target class is an interface.
		Class<?> targetClass = advised.getTargetClass();
		if (targetClass != null) {
			if (targetClass.isInterface()) {
				advised.setInterfaces(targetClass);
			}
			else if (Proxy.isProxyClass(targetClass)) {
				advised.setInterfaces(targetClass.getInterfaces());
			}
			specifiedInterfaces = advised.getProxiedInterfaces();
		}
	}
	boolean addSpringProxy = !advised.isInterfaceProxied(SpringProxy.class);
	boolean addAdvised = !advised.isOpaque() && !advised.isInterfaceProxied(Advised.class);
	boolean addDecoratingProxy = (decoratingProxy && !advised.isInterfaceProxied(DecoratingProxy.class));
	int nonUserIfcCount = 0;
	if (addSpringProxy) {
		nonUserIfcCount++;
	}
	if (addAdvised) {
		nonUserIfcCount++;
	}
	if (addDecoratingProxy) {
		nonUserIfcCount++;
	}
	Class<?>[] proxiedInterfaces = new Class<?>[specifiedInterfaces.length + nonUserIfcCount];
	System.arraycopy(specifiedInterfaces, 0, proxiedInterfaces, 0, specifiedInterfaces.length);
	int index = specifiedInterfaces.length;
	if (addSpringProxy) {
		proxiedInterfaces[index] = SpringProxy.class;
		index++;
	}
	if (addAdvised) {
		proxiedInterfaces[index] = Advised.class;
		index++;
	}
	if (addDecoratingProxy) {
		proxiedInterfaces[index] = DecoratingProxy.class;
	}
	return proxiedInterfaces;
}