开发者

How do I bind a specific parameter to an instance of a custom annotation?

How do I make the following work using Guice?

// The Guice 开发者_运维百科Module configuration
void configure() {
  // The following won't compile because HelpTopicId is abstract.
  // What do I do instead?
  bind(new TypeLiteral<String>(){}).
      annotatedWith(new HelpTopicId("A")).toInstance("1");
  bind(new TypeLiteral<String>(){}).
      annotatedWith(new HelpTopicId("B")).toInstance("2");
}

public @interface HelpTopicId {
  public String helpTopicName();
}

public class Foo {
  public Foo(@HelpTopicId("A") String helpTopicId) {
    // I expect 1 and not 2 here because the actual parameter to @HelpTopicId is "A"
    assertEquals(1, helpTopicId);
  }
}


Probably the simplest way to do this would be to use @Provides methods:

@Provides @HelpTopicId("A")
protected String provideA() {
  return "1";
}

Alternatively, you could create an instantiable implementation of the HelpTopicId annotation/interface similar to the implementation of Names.named (see NamedImpl). Be aware that there are some special rules for how things like hashCode() are implemented for an annotation... NamedImpl follows those rules.

Also, using new TypeLiteral<String>(){} is wasteful... String.class could be used in its place. Furthermore, for String, int, etc. you should typically use bindConstant() instead of bind(String.class). It's simpler, requires that you provide a binding annotation, and is limited to primitives, Strings, Class literals and enums.


Constructor Foo(String) has to be annotated with @Inject.

Instead of using your own HelpTopicId annotation, you should try with Guice Named annotation.

void configure() {
  bind(new TypeLiteral<String>(){}).annotatedWith(Names.named("A")).toInstance("1");
  bind(new TypeLiteral<String>(){}).annotatedWith(Names.named("B")).toInstance("2");
}

public class Foo {
  @Injected
  public Foo(@Named("A") String helpTopicId) {
    assertEquals("1", helpTopicId);
  }
}

If you want to roll out your own implementation of @Named interface, take a look at the Guice's implementation in the package com.google.inject.name.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜