代码之家  ›  专栏  ›  技术社区  ›  Steffen

我可以用Dagger 2提供MembersInjector的实现吗?

  •  0
  • Steffen  · 技术社区  · 6 年前

    我想用Dagger-2取代Guice。到目前为止,一切看起来都很好,但有一件事我找不到惯用的解决方案。

    假设我有一个无法扩展的类,并且无法控制代码。此外,我无法创建该类的实例。实例将由另一个框架创建,但不会初始化。我被 MembersInjector<T> 接口,但它似乎只处理带有注释的类。我正在寻找一种方法来实现 MemebersInjector<Type> (参见下面的示例代码)。

    final class Type {
      A a;
      B b;
    
      public Type() {
      }
    
      public void initialize(A a, B b) {this.a=a; this.b=b};
    } 
    

    我的组件和模块可以提供 A B .

    我要找的是

    @Component(modules = MyModule.class)
    interface MyComponent {
      Type inject(Type t);
    }
    

    @Component(modules = MyModule.class)
    interface MyComponent {
      MembersInjector<Type> getTypeInjector();
    }
    

    以及提供我自己的实现 MembersInjector .

    我试过这样的

    @Module
    class MyModule {
      @Provides
      MembersInjector<Type> provideTypeInjector(A a, B b) {
        return instance -> {
          instance.initialize(a, b);
        }
      }
    }
    

    但Dagger-2对此并不满意。

    你知道怎么做吗?

    1 回复  |  直到 6 年前
        1
  •  1
  •   Jeff Bowman    6 年前

    我认为除了创建自己的POJO之外,没有一种惯用的方法可以做到这一点,这可能很好。

    @组件的值 inject(T) 方法或 MembersInjector<T> 事实就是这样 如何请求Dagger基于的对象 T @Inject 注释 . 如果Dagger没有扫描类并为您生成对象,那么您将负责填充对象,因此您最好编写自己的初始值设定项。

    class YourTypeInitializer { // nothing to extend or implement
      private final Provider<A> aProvider;
      private final Provider<B> bProvider;
    
      @Inject YourTypeInitializer(Provider<A> aProvider, Provider<B> bProvider) {
        this.aProvider = aProvider;
        this.bProvider = bProvider;
      }
    
      public YourType inject(YourType instance) {
        instance.initialize(aProvider.get(), bProvider.get());
        return instance;  // for convenience
      }
    }
    

    或现场注入:

    class YourTypeInitializer {
      @Inject Provider<A> aProvider;
      @Inject Provider<B> bProvider;
      @Inject YourTypeInitializer() {}
    
      public YourType inject(YourType instance) {
        instance.initialize(aProvider.get(), bProvider.get());
        return instance;  // for convenience
      }
    }
    

    然后,而不是注射 MembersInjector<YourType> ,只需注入 YourTypeInitializer ; 而不是打电话 yourComponent.inject(yourTypeInstance) ,只需打电话 yourComponent.getYourTypeInitializer().inject(yourTypeInstance) . 这有点陈词滥调,但没有 @注入 作为替代品,Dagger几乎无法为您提供任何注释。