首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Dagger2多重绑定[dagger.android.AndroidInjector.inject(T)]发现了一个依赖周期:

Dagger2多重绑定[dagger.android.AndroidInjector.inject(T)]发现了一个依赖周期:
EN

Stack Overflow用户
提问于 2018-08-20 10:58:01
回答 2查看 854关注 0票数 1

我正在尝试复制ViewModelFactory为我的演示者类所做的事情,下面是我的Dagger2代码

代码语言:javascript
复制
public class App extends DaggerApplication { //Support import
    @Override
    protected AndroidInjector<? extends DaggerApplication> applicationInjector() {
        return DaggerAppComponent.builder().create(this);
    }
}


@Documented
@Target({ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@MapKey
public @interface PresenterKey {
    Class<? extends PresenterClass> value();
}

    @Module
public abstract class PresenterModule {

    @Binds
    @IntoMap
    @PresenterKey(AuthPresenterImpl.class)
    abstract PresenterClass bindsAuthPresenterImpl(AuthPresenterImpl authViewModel);

    @Binds
    abstract PresenterFactory bindsPresenterFactory(PresenterFactory viewModelFactory);
}


@Singleton
public class PresenterFactory {
    private final Map<Class<? extends PresenterClass>, Provider<PresenterClass>> creators;

    @Inject
    public PresenterFactory(Map<Class<? extends PresenterClass>, Provider<PresenterClass>> creators) {
        this.creators = creators;
    }

    @SuppressWarnings("unchecked")
    public <T extends PresenterClass> T create(Class<T> modelClass) {
        Provider<? extends PresenterClass> creator = creators.get(modelClass);
        if (creator == null) {
            for (Map.Entry<Class<? extends PresenterClass>, Provider<PresenterClass>> entry : creators.entrySet()) {
                if (modelClass.isAssignableFrom(entry.getKey())) {
                    creator = entry.getValue();
                    break;
                }
            }
        }
        if (creator == null) {
            throw new IllegalArgumentException("unknown model class " + modelClass);
        }
        try {
            return (T) creator.get();
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }
}

当我试图构建时,我得到的错误是

代码语言:javascript
复制
    import in.silentsudo.authflow.di.modules.DaggerAppComponent;
                                        ^
  symbol:   class DaggerAppComponent
  location: package in.silentsudo.authflow.di.modules
/path/to/project/app/src/main/java/in/silentsudo/authflow/di/modules/AppComponent.java:17: error: [Dagger/BindingCycle] [dagger.android.AndroidInjector.inject(T)] Found a dependency cycle:
public interface AppComponent extends AndroidInjector<AuthFlow> {
       ^
      in.silentsudo.authflow.viewmodels.PresenterFactory is injected at
          in.silentsudo.authflow.di.modules.PresenterModule.bindsPresenterFactory(presenterFactory)
      in.silentsudo.authflow.viewmodels.PresenterFactory is injected at
          in.silentsudo.authflow.AbstractActivity.factory
      in.silentsudo.authflow.auth.AuthActivity is injected at
          dagger.android.AndroidInjector.inject(T)
  component path: in.silentsudo.authflow.di.modules.AppComponent ? in.silentsudo.authflow.di.modules.ActivityModule_BindsAuthActivity.AuthActivitySubcomponent
2 errors

我是不是做错了什么傻事,请帮帮忙,

编辑:

混凝土级

代码语言:javascript
复制
public class AuthPresenterImpl extends AbstractPresenter {

    @Inject
    public AuthPresenterImpl(AuthApi api) {

    }
}
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2018-08-22 09:32:52

我设法解决了这个问题,依赖问题就在这一行。

代码语言:javascript
复制
@Binds
abstract PresenterFactory bindsPresenterFactory(PresenterFactory viewModelFactory);

在这里,我需要返回一个引用,并提供该引用的具体实现者。工作上的变化如下:

代码语言:javascript
复制
public interface PresenterFactory {
    /**
     * Creates a new instance of the given {@code Class}.
     * <p>
     *
     * @param modelClass a {@code Class} whose instance is requested
     * @param <T>        The type parameter for the ViewModel.
     * @return a newly created ViewModel
     */
    @NonNull
    <T extends PresenterClass> T create(@NonNull Class<T> modelClass);
}

具体实现者

代码语言:javascript
复制
@Singleton
public class PresenterFactoryImpl implements PresenterFactory {
    private final Map<Class<? extends PresenterClass>, Provider<PresenterClass>> creators;

    @Inject
    public PresenterFactoryImpl(Map<Class<? extends PresenterClass>, Provider<PresenterClass>> creators) {
        this.creators = creators;
    }

    @SuppressWarnings("unchecked")
    @Override
    public <T extends PresenterClass> T create(Class<T> modelClass) {
        Provider<? extends PresenterClass> creator = creators.get(modelClass);
        if (creator == null) {
            for (Map.Entry<Class<? extends PresenterClass>, Provider<PresenterClass>> entry : creators.entrySet()) {
                if (modelClass.isAssignableFrom(entry.getKey())) {
                    creator = entry.getValue();
                    break;
                }
            }
        }
        if (creator == null) {
            throw new IllegalArgumentException("unknown model class " + modelClass);
        }
        try {
            return (T) creator.get();
        } catch (Exception e) {
            e.printStackTrace();
            throw new RuntimeException(e);
        }
    }
}

以及如何在PresenterModule中定义

代码语言:javascript
复制
@Module
public abstract class PresenterModule {

    @Binds
    @IntoMap
    @PresenterKey(AuthPresenterImpl.class)
    abstract PresenterClass bindsAuthPresenterImpl(AuthPresenterImpl authViewModel);

    @Binds
    abstract PresenterFactory bindsPresenterFactory(PresenterFactoryImpl viewModelFactory);
}
票数 0
EN

Stack Overflow用户

发布于 2018-08-22 07:40:46

下面是您的依赖周期:

代码语言:javascript
复制
@Binds
@IntoMap
@PresenterKey(PresenterClass.class)
abstract PresenterClass bindsAuthPresenterClass(PresenterClass authViewModel);

您必须通过这样的具体实现:

代码语言:javascript
复制
@Binds
@IntoMap
@PresenterKey(ConcretePresenterClass.class)
abstract PresenterClass bindsAuthPresenterClass(ConcretePresenterClass authViewModel);

参考Dagger 2 - Why is this a dependency cycle?

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/51929258

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档