在Guice中配置多次注射

时间:2012-08-28 12:25:26

标签: dependency-injection guice

在Guice中,我有一个“Panel”类和一个“Controller”类。两者都是相互关联的。控制器有3个子类(比如A,B和C)。我想为程序员提供一种简单的方法来获取Panel的实例,并根据他们的需要注入3个控制器中的一个。

例如,在特定的代码点中,程序员可能希望在注入ControllerA的情况下获取Panel的实例,但在不同的地方,他可能需要带有ControllerB的Panel。

我怎样才能做到这一点?

2 个答案:

答案 0 :(得分:1)

您可以使用绑定注释让用户指定他们想要的注释: http://code.google.com/p/google-guice/wiki/BindingAnnotations

您可以创建这样的注释:

import com.google.inject.BindingAnnotation;
import java.lang.annotation.Target;
import java.lang.annotation.Retention;
import static java.lang.annotation.RetentionPolicy.RUNTIME;
import static java.lang.annotation.ElementType.PARAMETER;
import static java.lang.annotation.ElementType.FIELD;
import static java.lang.annotation.ElementType.METHOD;

@BindingAnnotation @Target({ FIELD, PARAMETER, METHOD }) @Retention(RUNTIME)
public @interface WithClassA{}
@BindingAnnotation @Target({ FIELD, PARAMETER, METHOD }) @Retention(RUNTIME)
public @interface WithClassB{}
...

然后您的用户的构造函数看起来像

@Inject
public MyConstructor(@WithClassA Panel thePanel) {...}

然后当你进行绑定时,你会使用.annotatedWith:

bind(Panel.class)
    .annotatedWith(WithClassA.class)
    .toProvider(ProviderThatReturnsPanelConstructedWithA.class);
bind(Panel.class)
    .annotatedWith(WithClassB.class)
    .toProvider(ProviderThatReturnsPanelConstructedWithB.class);

以防万一,以下是有关如何设置提供商的文档:http://code.google.com/p/google-guice/wiki/ProviderBindings

答案 1 :(得分:1)

我提出了一个可能的解决方案:Guice允许您绑定到提供程序实例,而不仅仅是一个类。因此,您可以使用带有一个参数的构造函数创建一个提供程序,并将其绑定为:

  

bind(Panel.class).annotatedWith(WithClassA.class).toProvider(new MyProvider(“a”))

构造函数的参数类型可以是任何其他类似的,例如枚举或甚至是注释,传入相同的WithClassA.class。

这是保存提供者的好方法。缺点是您不会在提供程序中进行依赖注入,但在这种情况下,这是我可以不用的。