我有以下代码,在其中我不了解在何处确切创建了EmailService的新实例。我试图检查许多其他的stackoverflow对话,但仍然无法清楚地了解它。

public interface MessageService {
    void sendMessage(String msg, String recipient);
}

@Singleton
public class EmailService implements MessageService {

    @Override
    public void sendMessage(String msg, String recipient) {
        System.out.println("Sending Email to"+recipient+"Msg is:" + msg);
    }
}

public class MyApplication {
    private MessageService service;

    @Inject
    public MyApplication(MessageService service) {
      this.service = service;
    }

    public void sendMessage(String msg, String recipient) {
        this.service.sendMessage(msg, recipient);
    }
}

public class AppInjector extends AbstractModule {

    @Override
    protected void configure() {
      bind(MessageService.class).to(EmailService.class);
    }

}

public class ClientApplication {
    public static void main(String[] args) {
        Injector inj = Guice.createInjector(new AppInjector());
        MyApplication app = inj.getInstance(MyApplication.class);
        app.sendMessage("How are you?", "[email protected]");
    }
}


在此代码中,无处创建类EmailService的新实例,例如(new EmailService())。

最佳答案

Guice通过反射分析了MyApplication的构造函数,发现它依赖于MessageServicepublic MyApplication(MessageService service))。正是由于使用@Inject标记了此构造函数,才采用了该构造函数
Guice尝试找出此接口的绑定。在AppInjector中,您指定MessageService的实现为EmailServicebind(MessageService.class).to(EmailService.class);
EmailService通过Java Reflection API实例化。通过Class.newInstance完成
创建EmailService后,将其作为参数传递给MyApplication.class.newInstance()工厂。


笔记:


默认情况下,如果未指定任何其他构造函数,则存在一个默认的不带参数的构造函数,这就是EmailService没有依赖项的原因。
EmailService实例是单例的,因为它被标记为@Singleton,因此,如果对它有更多依赖性,将注入完全相同的实例
如果要创建binding to instance,可以使用以下代码:bind(MessageService.class).toInstance(new EmailService());
Google库在文档方面总是很丰富。我建议您阅读以下Wiki:google/guice/wiki

09-27 22:44