Java 如何重写Springbean定义,但仍然引用被重写的bean?
我试图通过用我的委托服务覆盖原始服务的bean定义来实现委托服务提供者。但是,顾名思义,委托服务需要一个对原始服务的引用来委托调用 在使用原始bean def时,我很难理解如何重写bean定义,而不会遇到循环引用问题 例如:Java 如何重写Springbean定义,但仍然引用被重写的bean?,java,spring,Java,Spring,我试图通过用我的委托服务覆盖原始服务的bean定义来实现委托服务提供者。但是,顾名思义,委托服务需要一个对原始服务的引用来委托调用 在使用原始bean def时,我很难理解如何重写bean定义,而不会遇到循环引用问题 例如: <!-- Original service def in spring-context.xml --> <bean id="service" class="com.mycompany.Service"/> <!-- Overridden de
<!-- Original service def in spring-context.xml -->
<bean id="service" class="com.mycompany.Service"/>
<!-- Overridden definition in spring-plugin-context.xml -->
<bean id="service" class="com.mycompany.DelegatedService"/>
<constructor-arg ref="service"/>
</bean>
这可能吗?您可以创建。因此,现在名为service
的bean将成为原始服务的代理,该服务需要重命名为其他服务。因此,这些更改将仅限于SpringXML,而不会传播到java代码中
<bean id="personTarget" class="com.mycompany.PersonImpl">
<property name="name"><value>Tony</value></property>
<property name="age"><value>51</value></property>
</bean>
<bean id="myAdvisor" class="com.mycompany.MyAdvisor">
<property name="someProperty"><value>Custom string property value</value></property>
</bean>
<bean id="debugInterceptor" class="org.springframework.aop.interceptor.DebugInterceptor">
</bean>
<bean id="person"
class="org.springframework.aop.framework.ProxyFactoryBean">
<property name="proxyInterfaces"><value>com.mycompany.Person</value></property>
<property name="target"><ref local="personTarget"/></property>
<property name="interceptorNames">
<list>
<value>myAdvisor</value>
<value>debugInterceptor</value>
</list>
</property>
</bean>
托尼
51
自定义字符串属性值
com.mycompany.Person
我的顾问
调试拦截器
听起来你在试图重新发明spring AOP。请考虑使用Spring AOP做这个。< /P>
可以通过编程更改现有服务的名称,并使用旧名称创建一个新bean。spring框架中的自动代理代码实现了这一点,您可以看看这一点。在spring框架中对AutoProxy*进行快速代码搜索应该可以达到目的
或者,如果控制客户机站点(消费者),则可以向包装器添加限定符,并使用限定符强制消费者正确实现。包装器可以使用不合格的实现来访问原始实现。
(也可以通过在xml代码中为服务添加另一个bean定义,并使用您控制的限定符将限定符重新装载到原始实现中,您还没有尝试过,但它应该可以工作)您的问题的简短答案是,您不能有两个同名的bean定义。如果尝试,一个将隐藏另一个,并且只有一个定义可用
您的问题的示例似乎表明您正在尝试将原始的服务
bean包装在代理对象中,包装器执行对服务的一些前后处理调用。实现这一点的一种方法是使用SpringAutoProxyCreator
,它可能是一个
这允许您列出要自动代理的bean。指定要应用于目标bean上的调用的拦截器。您将实现这些拦截器来完成您需要完成的工作
Spring将自动为您创建一个委托代理,该代理与以前一样具有bean id服务
,但具有您的附加功能。将“ref”元素的“parent”属性与父容器一起使用。
您可以在Spring文档中找到一个详细的示例:已经写了一篇关于如何很好地做到这一点的博客文章:
使用通配符上下文定义意味着您不需要使用导入
当您想用相同的id重新定义同一个bean时,Parent不起作用。我不能将原始的“服务”bean重命名为其他任何东西,因为它是在spring上下文中定义的,这在我的控制范围之外,在spring中是不可能的。此外,即使有可能,这也是一种不好的做法,如果有人在编写bean时考虑到了特定的功能,并关闭它进行修改,那么最终可能会破坏原有的功能。一个(不好的)解决方法是使用相同的签名定义自己的类,并使用自定义类装入器加载原始类并委托给它。如果你能发布你的最终要求会更好。这个答案是最有用的,尽管我的问题最终无法解决。为了代理该类,它必须由方面编织。因为我试图代理的类已经在另一个类加载器中编译和运行,所以我无法代理它。@Kevin:AnAutoProxyCreator
不代理类,它代理bean。哪个类加载器加载目标类并不重要,代理的是目标对象,Spring实例化了该目标对象。在一个配置中,将其别名为目标bean名称,在另一个配置中,定义注入底层bean的包装器。但这需要事先计划。