怎样利用Dagger 2注入POJO依赖?

4

我有一个简单的pojo类:

public class MySimpleClass {

    private List<String> mDependency;

    public MySimpleClass (List<String> dependency) {
        mDependency = dependency;
    }
}

我正在尝试使用Dagger 2通过依赖注入创建它。现在,我已经为此编写了一个简单的模块和组件:

@Module
public class MySimpleClassModule {

    @Provides
    MySimpleClass provideMySimpleClass(List<String> dependency) {
        return new MySimpleClass(dependency);
    }
}

@Component(modules={MySimpleClassModule.class})
public interface MySimpleClassComponent {
}

但我不确定如何在每次创建MySimpleClass的新实例时注入List<String>依赖项。 在上述情况下,似乎我实际上需要将List<String>添加到MySimpleClassModule的构造函数中,并在每次需要新的MySimpleClass实例和新的List<String>时使用该模块的新实例。 是这样吗? 在这种特定情况下,它似乎是很多额外开销。
3个回答

3
不,不是这样的。我猜你在使用Dagger时遇到了编译错误,因为从问题描述中不清楚您是否已经有一个提供此字符串列表的模块。
要解决这个问题,您可以简单地执行以下操作:
@Module
public class MySimpleClassModule {

    @Provides
    List<String> provideListDependency() {
        return Arrays.asList("One", "Two");
    }

    @Provides
    MySimpleClass provideMySimpleClass(List<String> dependency) {
        return new MySimpleClass(dependency);
    }
}

如果您认为提供此列表应该是不同模块的一部分,您可以将其移动。主要的事情是,在编译期间,Dagger 能够找到如何获取此依赖项。
如果您不想反复创建此数组,可以将方法标记为 @Singlethon,这样 Dagger 将对其进行缓存。

1
如果您需要定义对象的构造函数,最好使用@Inject构造函数。Dagger 2会自动知道如何实例化对象,因此您不需要在模块中使用@Provides注释的方法。
public class MySimpleClass {

    private List<String> mDependency;

    @Inject
    public MySimpleClass (List<String> dependency) {
        mDependency = dependency;
    }
}

Dagger会认为构造函数的参数是依赖项,并尝试从依赖图中解析它们。请注意,每个类只能有一个@Inject注释的构造函数!如果您无法自行实例化对象(例如Android活动/片段),则需要使用字段注入。
在您的情况下,似乎没有必要将空列表注入到MyClass中。您可以在构造函数中实例化列表。但是,当您想将MyClass注入另一个对象时,它已经在对象图中了。

谢谢,但我觉得那并不能解决问题。在您的方法中,我现在必须声明一个“提供”List<String>依赖项的方式,比如在模块中。因此,每次需要新的MySimpleClass实例时仍然需要实例化一个新的模块。 - Anyonymous2324
现在,如果我按照你的建议进行更改,会出现“错误:java.util.Collection<java.lang.String>不能在没有@Provides注释方法的情况下提供。” - Anyonymous2324
1
就像我说的那样,你并不需要注入你的列表。只需在你的对象中实例化它。 private List mDependency; @Inject public MySimpleClass () { mDependency = new ArrayList<>(); } }``` - plast

0
class A {
    String name;
    @Inject
    A(String name) {
        this.name = name;
    }


    @Component
    interface AComponent {
        A getA();
        @Component.Builder
        interface Builder {
            @BindInstance
            Builder provideName(String name);
            A build();
        }
    }

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接