Java tutorial
/* * Copyright (c) 2011-2012 by the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package io.dyn.core.handler; import java.lang.reflect.InvocationHandler; import java.lang.reflect.Method; import io.dyn.core.sys.Sys; import org.springframework.beans.BeansException; import org.springframework.context.ApplicationContext; import org.springframework.context.ApplicationContextAware; import org.springframework.context.expression.BeanFactoryResolver; import org.springframework.core.convert.ConversionService; import org.springframework.expression.EvaluationContext; import org.springframework.expression.spel.SpelEvaluationException; import org.springframework.expression.spel.support.StandardEvaluationContext; import org.springframework.util.ClassUtils; /** * @author Jon Brisbin <jon@jbrisbin.com> */ public class GuardedHandlerMethodInvoker implements HandlerMethodInvoker, ApplicationContextAware { //private static final Logger LOG = Logger.logger(GuardedHandlerMethodInvoker.class); private ApplicationContext applicationContext; private ConversionService customConversionService; public ConversionService conversionService() { return customConversionService; } public GuardedHandlerMethodInvoker conversionService(ConversionService conversionService) { this.customConversionService = conversionService; return this; } @Override public void setApplicationContext(ApplicationContext applicationContext) throws BeansException { this.applicationContext = applicationContext; } @Override public Object invoke(HandlerMethod method, Object handler, EvaluationContext evalCtx, Object... args) throws Exception { if (null == evalCtx) { StandardEvaluationContext ec = new StandardEvaluationContext(); if (null != applicationContext) { ec.setBeanResolver(new BeanFactoryResolver(applicationContext)); } evalCtx = ec; } HandlerMethodArgument[] handlerMethodArguments = method.arguments(); int argc = handlerMethodArguments.length; Object[] argv = new Object[argc]; for (int i = 0; i < argc; i++) { HandlerMethodArgument handlerArg = handlerMethodArguments[i]; if (ClassUtils.isAssignable(EvaluationContext.class, handlerArg.targetType())) { argv[i] = evalCtx; } else if (null != handlerArg.valueExpression()) { try { argv[i] = handlerArg.valueExpression().getValue(evalCtx, handlerArg.targetType()); } catch (SpelEvaluationException e) { argv[i] = null; } } else { try { Object o = args[handlerArg.index()]; if (ClassUtils.isAssignable(handlerArg.targetType(), o.getClass())) { argv[i] = o; } else if (null != customConversionService && customConversionService.canConvert(o.getClass(), handlerArg.targetType())) { argv[i] = customConversionService.convert(o, handlerArg.targetType()); } else { argv[i] = Sys.DEFAULT_CONVERSION_SERVICE.convert(o, handlerArg.targetType()); } } catch (IndexOutOfBoundsException e) { } } evalCtx.setVariable(handlerArg.name(), argv[i]); } InvocationHandler invoker = method.invocationHandler(); Method m = method.methodToInvoke(); if (null != method.guard()) { if (method.guard().checkGuard(null, evalCtx)) { if (null != invoker) { try { invoker.invoke(handler, m, argv); } catch (Throwable throwable) { throw new IllegalStateException(throwable); } } else { return m.invoke(handler, argv); } } else { //LOG.debug("Guard expression %s failed", method.guard().expression().getExpressionString()); } } else { if (null != invoker) { try { return invoker.invoke(handler, m, argv); } catch (Throwable throwable) { throw new IllegalStateException(throwable); } } else { return m.invoke(handler, argv); } } return null; } }