【问题标题】:Not getting singletons using Dagger没有使用 Dagger 获得单例
【发布时间】:2015-03-22 13:28:10
【问题描述】:

我刚刚在我当前的 Android 应用程序中开始使用 Dagger,我不确定如何实现我正在寻找的功能(我相信我正在寻找的可能的)。

基本上,我的情况是这样的。我有以下类,我希望它们的实例/注入由 Dagger 管理。我还希望其中一些是单例,由 (1) 指出:

  • CipherFactory - 简单的封装私有工厂
  • CryptoService (1) - 依赖于 CipherFactory
  • SerializationService (1) - 依赖于 Jackson 的 ObjectMapper
  • PlayerApplicationService (1) - 依赖于 SerializationService
  • PlayerRepository (1) - 依赖于 SerializationService、CryptoService

现在,我可以让 Dagger 创建这些服务并适当地注入它们的依赖项;问题是某些类依赖于多个类,并且它通过日志记录语句出现,每次注入时我都会获得 new 个实例。

这是我目前拥有的上述内容,包括 Dagger 模块类:

CryptoService.java

@Singleton
public class CryptoService {
    private final CipherFactory cipherFactory;

    @Inject
    CryptoService(CipherFactory cipherFactory) {
        this.cipherFactory = cipherFactory;
    }
    ...
}   

CryptoServiceModule.java

@Module(
        injects = CryptoService.class,
        complete = true,
        library = true
)
public class CryptoServiceModule {

    @Provides
    @Singleton
    CipherFactory provideCipher() {
        return new CipherFactory();
    }

}

SerializationService.java

@Singleton
public class SerializationService {

    private final ObjectMapper objectMapper;

    @Inject
    SerializationService(ObjectMapper objectMapper) {
        this.objectMapper = objectMapper;
    }
    ...
}

SerializationServiceModule.java

@Module(
        injects = SerializationService.class,
        library = true,
        complete = true
)
public class SerializationServiceModule {

    @Provides
    @Singleton
    ObjectMapper provideMapper() {
        return new ObjectMapper();
    }

}

PlayerApplicationService.java

public class PlayerApplicationService {

    private SerializationService serializationService;

    @Inject
    public PlayerApplicationService(SerializationService serializationService) {
        this.serializationService = serializationService;
    }
    ....
}

PlayerApplicationServiceModule.java

@Module(
        injects = PlayerApplicationService.class,
        includes = {
                SerializationServiceModule.class
        },
        complete = true,
        library = true
)
public class PlayerApplicationServiceModule {
}

PlayerRepository.java

@Singleton
public class PlayerRepository implements Repository<Player> {

    private final SerializationService serializationService;
    private final CryptoService cryptoService;

    @Inject
    public PlayerRepository(SerializationService serializationService, CryptoService cryptoService) {
        this.serializationService = serializationService;
        this.cryptoService = cryptoService;
    }
    ...
}

PlayerRepositoryModule.java

@Module(
        injects = PlayerRepository.class,
        includes = {
                SerializationServiceModule.class,
                CryptoServiceModule.class
        },
        complete = true,
        library = true
)
public class PlayerRepositoryModule {
}

我错过了什么?正如我上面提到的,所有这些东西都工作,看起来我得到了一些依赖项的多个实例(例如SerializationService,它被两个类使用)创建在哪里我只想要/需要一个。

【问题讨论】:

  • 我建议您将所有模块组合成一个注入所有类的大模块。我怀疑 SerializationServiceModule 被创建了两次。例如,SerializationServiceModule.java 创建一个 ObjectMapper,然后 PlayerRepositoryModule.java 创建另一个 ObjectMapper。
  • 感谢您的建议 - 可行。我根据它在下面发布了我的答案。

标签: java android singleton dagger


【解决方案1】:

根据@Andyccs 的评论,我已将所有内容合并到一个应用程序级别的模块类中,并删除了应用程序中的所有其他模块类:

PlayerApplicationModule.java

@Module(
        injects = {
                PlayerApplication.class,
                CryptoService.class,
                SerializationService.class,
                PlayerApplicationService.class
        },
        complete = true,
        library = true
)
public class PlayerApplicationModule {
    private PlayerApplication application;

    public PlayerApplicationModule(PlayerApplication application) {
        this.application = application;
    }

    @Provides
    @Singleton
    public Context provideApplicationContext() {
        return application;
    }

    @Provides
    @Singleton
    public CipherFactory provideCipherFactory() {
        return new CipherFactory();
    }

    @Provides
    @Singleton
    public ObjectMapper provideObjectMapper() {
        return new ObjectMapper();
    }

}

现在一切正常。

【讨论】:

    猜你喜欢
    • 2020-01-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-10-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多