spring-拦截Bean创建并注入自定义代理
我有一个@Controller
with @Autowired
字段和处理程序方法,我想用自定义注释进行注释。
例如,
@Controllerpublic class MyController{
@Autowired
public MyDao myDao;
@RequestMapping("/home")
@OnlyIfXYZ
public String onlyForXYZ() {
// do something
return "xyz";
}
}
哪里@OnlyIfXYZ
是自定义注释的示例。我当时想我将拦截Controller
bean的创建,传递我自己的CGLIB代理,Spring可以在其上设置属性,例如自动装配字段。
我尝试使用,InstantiationAwareBeanPostProcessor
但是该解决方案效果不佳,因为这postProcessBeforeInstantiation()
会使其余过程短路。我尝试过postProcessAfterInitialization()
,如下所示
public class MyProcessor implements BeanPostProcessor { @Override
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
// Here the bean autowired fields are already set
return bean;
}
@Override
public Object postProcessAfterInitialization(Object aBean, String aBeanName) throws BeansException {
Class<?> clazz = aBean.getClass();
// only for Controllers, possibly only those with my custom annotation on them
if (!clazz.isAnnotationPresent(Controller.class))
return aBean;
Object proxy = Enhancer.create(clazz, new MyMethodInterceptor());
Field[] fields = clazz.getDeclaredFields();
for (Field field : fields) {
field.setAccessible(true);
try {
// get the field and copy it over to the proxy
Object objectToCopy = field.get(aBean);
field.set(proxy, objectToCopy);
} catch (IllegalArgumentException | IllegalAccessException e) {
return aBean;
}
}
return proxy;
}
}
此解决方案使用反射将目标Bean的所有字段复制到代理Bean(根据我的喜好,有点hacky)。但是HttpServletRequest
,HttpServletResponse
如果这些对象不是我要拦截的方法中的参数,则我无法访问和对象。
在Spring填充其属性之前,是否可以在Spring bean创建逻辑中注入另一个回调以注入自己的代理控制器?
该@Autowired
字段也是一个代理,带有注释,@Transactional
因此Spring会对其进行代理。
AOP解决方案很好地拦截了方法调用,但是如果它们还不是方法参数,我找不到找到HttpServletRequest
和HttpServletResponse
对象的方法。
我可能最终会使用HandlerInterceptorAdapter,但我希望我可以使用OOP来做到这一点,以免给不需要它的方法增加开销。
回答:
考虑到您对问题的评论,您需要的只是HandlerInterceptor。
http://static.springsource.org/spring/docs/3.2.x/javadoc-
api/org/springframework/web/servlet/HandlerInterceptor.html
您需要实现该接口并将其添加到您的配置中,例如:
<mvc:interceptors> <bean id="customInterceptor" class="com.example.interceptors.CustomInterceptor"/>
</mvc:interceptors>
该接口提供了preHanlde方法,该方法具有请求,响应和HandlerMethod。要检查该方法是否带有注释,请尝试以下操作:
HandlerMethod method = (HandlerMethod) handler;OnlyIfXYZ customAnnotation = method.getMethodAnnotation(OnlyIfXYZ.class);
以上是 spring-拦截Bean创建并注入自定义代理 的全部内容, 来源链接: utcz.com/qa/433248.html