Dagger 依赖项单独注入,同时@IntoSet 注入。我该如何实施?

问题描述 投票:0回答:1

我正在学习 Dagger。我是 Spring 的前用户。我注意到的一件事是我必须用

@IntoSet
注释每个 bean,才能将某种类型的 bean 作为集合注入。在 Spring 中,我会直接声明
Set<MyBeanClass>
作为自动装配方法或构造函数中的参数,并且框架会自行解决所有问题(当然,“框架为您解决问题”并不总是一个优势)

但是,

@IntoSet
有时会弄坏东西。这是 MRE:

package myown;

import dagger.Component;

import javax.inject.Named;
import javax.inject.Singleton;
import java.util.Set;

@Component(modules = {PersonModule.class})
@Singleton
public interface PersonComponent {
    Person getJane();
}
package myown;

import dagger.Module;
import dagger.Provides;
import dagger.multibindings.IntoSet;

import javax.inject.Singleton;

@Module(includes = PetModule.class)
public class PersonModule {
    @IntoSet
    @Singleton
    @Provides
    public Person jane(Pet pet) {
        return new PetOwner("Jane", pet);
    }
}
package myown;

import dagger.Module;
import dagger.Provides;

import javax.inject.Singleton;

@Module
public class PetModule {
    @Provides
    @Singleton
    Pet getPet() {
        return new Pet("Puffy");
    }
}
package myown;

public class Person {
    private final String name;

    public Person(String name) {
        this.name = name;
    }
}
package myown;

public class PetOwner extends Person {
    private final Pet pet;

    public PetOwner(String name, Pet pet) {
        super(name);
        this.pet = pet;
    }
}
package myown;

public class Pet {
    private final String name;

    public Pet(String name) {
        this.name = name;
    }
}

尝试构建它,你会得到:

java: [Dagger/MissingBinding] myown.Person cannot be provided without an @Inject constructor or an @Provides-annotated method.
      myown.Person is provided at
          myown.PersonComponent.getJane()

但是,如果您注释掉

@IntoSet
并尝试重建它,一切都很好

要明确的是,我希望

jane
能够直接注入 作为所有
Set
的注入
Person
的一部分(想象一下,有
jack
john
等)好吧 -- 也用
@IntoSet
)

进行注释

为什么会发生这种情况,有解决方案/解决方法吗?

java dagger
1个回答
0
投票

当您提供 @IntoSet 时,它只会在您的 Set 中。不能直接注入‘Jane’

如果您想专门注入 Jane,您可以为 Jane 提供命名注释或子类型,然后使用 @IntoSet 再次绑定或提供它

@Module(includes = PetModule.class)
public class PersonModule {
    @Singleton
    @Provides
    @Named("Jane")
    public Person jane(Pet pet) {
        return new PetOwner("Jane", pet);

    @Provides
    @IntoSet
    public Person janeIntoSet(@Named("Jane") jane: Person) {
        return jane;
    }
}

有多种方法可以实现它。请参阅https://dagger.dev/dev-guide/multibindings.html

Spring 的区别在于它在运行时计算出来,而 dagger 中的所有内容都是编译时生成的。所以这里没有猜测、投射或反思。它需要在编译时就全部清楚。

© www.soinside.com 2019 - 2024. All rights reserved.