Spring如何知道需要注入代理对象的位置?

sup*_*sky 5 java spring

根据我的印象,RmiProxyFactoryBean应该生成一个代理对象实例,该实例的类型AccountService将在以下代码中注入实例的accountService属性SimpleObject.

我不明白为什么XML文件似乎指示Spring向对象实例的属性注入RmiProxyFactoryBean类型accountServiceSimpleObject对象?我期待XML文件中的显式指令告诉Spring如何AccountServiceRmiProxyFactoryBean实例获取实例而不是注入RmiProxyFactoryBean实例.我发现这令人困惑.

public class SimpleObject {

    private AccountService accountService;

    public void setAccountService(AccountService accountService) {
        this.accountService = accountService;
    }
}


<bean class="example.SimpleObject">
    <property name="accountService" ref="accountService"/>
</bean>

<bean id="accountService" class="org.springframework.remoting.rmi.RmiProxyFactoryBean">
    <property name="serviceUrl" value="rmi://HOST:1199/AccountService"/>
    <property name="serviceInterface" value="example.AccountService"/>
</bean>
Run Code Online (Sandbox Code Playgroud)

来源: http ://static.springsource.org/spring/docs/2.5.x/reference/remoting.html(见17.2.2.)

谢谢

lee*_*d00 5

因为Proxy Beans包装有问题的对象,所以它们假装是被调用的接口(然后实际调用该接口).

RmiProxyFactoryBean返回一个代理对象,这样当你的代码认为它正在你的example.AccountService类上调用一个方法时,它实际上是在一个bean上调用的,其接口与你的example.AccountService接口一样,如下所示:

<bean id="accountService" class="org.springframework.remoting.rmi.RmiProxyFactoryBean">
    ...
    <property name="serviceInterface" value="example.AccountService"/>
</bean>
Run Code Online (Sandbox Code Playgroud)

假设在接口上有一个方法叫做example.AccountService.reconcile(Long amount)(仅为了示例)...

如果你通常调用它,调用它的方法只会将它推入堆栈.但是如果exam​​ple.AccountService对象是从上面的RmiProxyFactoryBean返回的,它将被包装在代理bean中.这个代理bean在其中有一个方法,它也被命名reconcile并且还有一个参数Long amount,这使得它与example.AccountService它包装的原始bean 无法区分.这样,代理bean可以拥有它在实际example.AccountService.reconcile(Long amount)方法中的代码之前,之后或代替它运行的代码.

代理bean来自一种完全不同的编程方式,称为面向方面编程(AOP),它处理交叉问题; 即代码似乎不符合正常OOP分离关注的范围.其中一些问题是例如事务划分,安全性和日志记录.

您似乎在上面手动执行此操作,但有时在运行时使用SpringAOP编写这些内容更容易,SpringAOP具有用于选择代理bean并将其应用于现有代码的语言.

但是,请注意编程接口而不是编程到只是类.


pap*_*pap 2

更简洁的说法是实现RmiProxyFactoryBean接口FactoryBean。实现该接口会指示 Spring bean 工厂该类本身就是一个工厂,从而导致 Spring 调用getObject()该类上的方法并将结果作为 bean 返回,而不是创建该类本身的实例并返回。

所以,简短的回答,它是 Spring 的内置机制。