Java 使用贡献和重复提供活动

Java 使用贡献和重复提供活动,java,android,dependency-injection,dagger-2,Java,Android,Dependency Injection,Dagger 2,我在向需要此对象的依赖项提供活动对象时遇到问题 我使用Dagger 2.13有一个非常标准的设置,如下所示: AppComponent.java @Singleton @Component(modules = { AndroidInjectionModule.class, AppModule.class, ActivityModule.class }) public interface AppComponent extends AndroidInj

我在向需要此对象的依赖项提供
活动
对象时遇到问题

我使用Dagger 2.13有一个非常标准的设置,如下所示:

AppComponent.java

@Singleton
@Component(modules = {
        AndroidInjectionModule.class,
        AppModule.class,
        ActivityModule.class
})
public interface AppComponent extends AndroidInjector<Appname> {
    @Component.Builder
    interface Builder {
        @BindsInstance
        Builder application(Appname appname);
        AppComponent build();
    }

    void inject(Appname appname);
}
@Module
abstract public class ActivityModule {
    @ContributesAndroidInjector(modules = {MainActivityModule.class, MainActivityFragmentsModule.class})
    abstract MainActivity contributeMainActivity();
}
@Module
public class MainActivityModule {

@Provides
@Singleton
static Billing provideBilling(Context context) {
    return new Billing(context);
}

@Provides
@Singleton
static ActivityCheckout provideActivityCheckout(MainActivity activity, Billing billing) {
    return ActivityCheckout.forActivity(activity, billing);
}
}
@Module
abstract public class MainActivityFragmentsModule {
    @ContributesAndroidInjector
    abstract WelcomeFragment contributeWelcomeFragment();
}
MainActivityModule.java

@Singleton
@Component(modules = {
        AndroidInjectionModule.class,
        AppModule.class,
        ActivityModule.class
})
public interface AppComponent extends AndroidInjector<Appname> {
    @Component.Builder
    interface Builder {
        @BindsInstance
        Builder application(Appname appname);
        AppComponent build();
    }

    void inject(Appname appname);
}
@Module
abstract public class ActivityModule {
    @ContributesAndroidInjector(modules = {MainActivityModule.class, MainActivityFragmentsModule.class})
    abstract MainActivity contributeMainActivity();
}
@Module
public class MainActivityModule {

@Provides
@Singleton
static Billing provideBilling(Context context) {
    return new Billing(context);
}

@Provides
@Singleton
static ActivityCheckout provideActivityCheckout(MainActivity activity, Billing billing) {
    return ActivityCheckout.forActivity(activity, billing);
}
}
@Module
abstract public class MainActivityFragmentsModule {
    @ContributesAndroidInjector
    abstract WelcomeFragment contributeWelcomeFragment();
}
MainActivityFragmentsModule.java

@Singleton
@Component(modules = {
        AndroidInjectionModule.class,
        AppModule.class,
        ActivityModule.class
})
public interface AppComponent extends AndroidInjector<Appname> {
    @Component.Builder
    interface Builder {
        @BindsInstance
        Builder application(Appname appname);
        AppComponent build();
    }

    void inject(Appname appname);
}
@Module
abstract public class ActivityModule {
    @ContributesAndroidInjector(modules = {MainActivityModule.class, MainActivityFragmentsModule.class})
    abstract MainActivity contributeMainActivity();
}
@Module
public class MainActivityModule {

@Provides
@Singleton
static Billing provideBilling(Context context) {
    return new Billing(context);
}

@Provides
@Singleton
static ActivityCheckout provideActivityCheckout(MainActivity activity, Billing billing) {
    return ActivityCheckout.forActivity(activity, billing);
}
}
@Module
abstract public class MainActivityFragmentsModule {
    @ContributesAndroidInjector
    abstract WelcomeFragment contributeWelcomeFragment();
}
当我试图在
WelcomeFragment
中使用
ActivityCheckout
时,我得到一个错误,即无法提供此依赖关系:

错误:(20,8)错误:[dagger.android.androidjector.inject(T)]org.solovyev.android.checkout.ActivityCheckout在没有@inject构造函数或@Provides注释方法的情况下无法提供。

似乎没有提供活动,但我不知道为什么。我试着遵循其中一个教程,其中有相同的设置,可以插入
活动
对象


我正在使用
DaggerApplication
DaggerAppCompativity
DaggerFragment
,虽然我不确定它会如何/为什么显示您显示的错误,但您在@Singleton范围下错误注册了活动范围内的内容。请注意,您发布的错误消息抱怨未提供ActivityCheckout;如果无法提供您的活动,您可能会发现一条关于缺少MainActivity的错误消息

我的直觉是编译中有多个错误,但您只发布了最后一个错误,而之前的错误表明您无法将@Singleton绑定安装到@ContributesAndroidInjector默认创建的非作用域子组件中。因此,Dagger忽略了@Provides方法,您将得到您得到的错误

@Provides
@Singleton  // BAD: If this is Singleton, it will outlive and leak MainActivity.
            // Dagger will complain about mismatched scopes, but it's right:
            // It doesn't make sense for ActivityCheckout to be @Singleton.
static ActivityCheckout provideActivityCheckout(
    MainActivity activity, Billing billing) {
  return ActivityCheckout.forActivity(activity, billing);
}
相反,创建特定于活动的范围,这表示每个活动都有自己的范围

@Retention(RetentionPolicy.RUNTIME)    // Not used at runtime, but JSR-330
@Scope                                 // requires that @Scopes are kept at RUNTIME.
public @interface ActivityScope {}     // PerActivity is also a good name.
现在用它标记@ContributesAndroidInjector,以便生成的子组件具有该范围:

@ContributesAndroidInjector(
    modules = {MainActivityModule.class, MainActivityFragmentsModule.class})
@ActivityScope
abstract MainActivity contributeMainActivity();
以及您的绑定,因此它们与活动组件的生存期相匹配:

@Module public class MainActivityModule {
  // I'm assuming this is actually activity scoped, but if it's truly singleton,
  // leave it @Singleton and move it to AppModule.
  @Provides
  @ActivityScope
  static Billing provideBilling(Context context) {
    return new Billing(context);
  }

  @Provides
  @ActivityScope
  static ActivityCheckout provideActivityCheckout(
      MainActivity activity, Billing billing) {
    return ActivityCheckout.forActivity(activity, billing);
  }
}

虽然我不确定它将如何/为什么显示您显示的错误,但您在@Singleton scope下错误注册了活动范围的内容。请注意,您发布的错误消息抱怨未提供ActivityCheckout;如果无法提供您的活动,您可能会发现一条关于缺少MainActivity的错误消息

我的直觉是编译中有多个错误,但您只发布了最后一个错误,而之前的错误表明您无法将@Singleton绑定安装到@ContributesAndroidInjector默认创建的非作用域子组件中。因此,Dagger忽略了@Provides方法,您将得到您得到的错误

@Provides
@Singleton  // BAD: If this is Singleton, it will outlive and leak MainActivity.
            // Dagger will complain about mismatched scopes, but it's right:
            // It doesn't make sense for ActivityCheckout to be @Singleton.
static ActivityCheckout provideActivityCheckout(
    MainActivity activity, Billing billing) {
  return ActivityCheckout.forActivity(activity, billing);
}
相反,创建特定于活动的范围,这表示每个活动都有自己的范围

@Retention(RetentionPolicy.RUNTIME)    // Not used at runtime, but JSR-330
@Scope                                 // requires that @Scopes are kept at RUNTIME.
public @interface ActivityScope {}     // PerActivity is also a good name.
现在用它标记@ContributesAndroidInjector,以便生成的子组件具有该范围:

@ContributesAndroidInjector(
    modules = {MainActivityModule.class, MainActivityFragmentsModule.class})
@ActivityScope
abstract MainActivity contributeMainActivity();
以及您的绑定,因此它们与活动组件的生存期相匹配:

@Module public class MainActivityModule {
  // I'm assuming this is actually activity scoped, but if it's truly singleton,
  // leave it @Singleton and move it to AppModule.
  @Provides
  @ActivityScope
  static Billing provideBilling(Context context) {
    return new Billing(context);
  }

  @Provides
  @ActivityScope
  static ActivityCheckout provideActivityCheckout(
      MainActivity activity, Billing billing) {
    return ActivityCheckout.forActivity(activity, billing);
  }
}