将依赖项注入 Singleton Dagger 2.11

Inject dependencies into Singleton Dagger 2.11

我有应用程序级范围的单例 类 TaskRepositoryAppConfig,它们具有单例类型的依赖性。在我的 activity 中,注入了 TaskRepository 的实例,但它的所有字段都是空的。

申请Class

public class MVPApplication extends Application implements HasActivityInjector {

    @Inject
    DispatchingAndroidInjector<Activity> activityDispatchingAndroidInjector;

    @Inject
    TasksRepository tasksRepository;

    @Inject
    AppConfig appConfig;

    private static MVPApplication instance;

    @Override
    public void onCreate() {
        super.onCreate();
        instance = this;
        Realm.init(this);
        DaggerAppComponent
                .builder()
                .application(this)
                .realmBuilder(Realm.getDefaultInstance())
                .build()
                .inject(this);
    }

    @Override
    public DispatchingAndroidInjector<Activity> activityInjector() {
        return activityDispatchingAndroidInjector;
    }
}

应用组件

@Singleton
@Component(modules = {
        AndroidInjectionModule.class,
        AppModule.class,
        ActivityBindingModule.class})
public interface AppComponent extends AndroidInjector<DaggerApplication> {

    @Component.Builder
    interface Builder {

        @BindsInstance
        Builder application(Application application);

        @BindsInstance
        Builder realmBuilder(Realm realm);

        AppComponent build();
    }

    void inject(MVPApplication application);

    TasksRepository getRepository();

    AppConfig getAppConfig();

}

AppModule

@Singleton
@Module
public class AppModule {

@Provides
@Singleton
TasksRepository provideTasksRepository() {
    return new TasksRepository();
}

@Provides
@Singleton
AppConfig provideAppConfig() {
    return new AppConfig();
}
}

任务库Class

@Singleton
public class TasksRepository implements RepositoryDatasource {

@Inject
Context mContext;

@Inject
AppConfig appConfig; //Singleton

@Inject
Realm realm; //Singleton

   //There is no constructor. Only public functions using fields

}

AppConfig Class

@Singleton
public class AppConfig {

    @Inject
    Context mContext;

   //There is no constructor. Only public functions using fields
}

请强调我的错误...任何帮助将不胜感激。谢谢!

Dagger 2 有两种主要的注入类型 - 字段注入和构造函数注入。字段注入是你注释 class 的字段,如 Activity 或带有 @Inject 的片段,然后显式请求从 Dagger 2 组件注入:

 class MainActivity extends AppCompatActivity {

     @Inject TasksRepository tasksRepository;

     public void onCreate(Bundle savedInstanceState) {
         super.onCreate(savedInstanceState);
         AndroidInjector.inject(this); //explicit request for injection
     }
 }

请注意,在 onCreate 的第 2 行中没有明确的注入请求,字段 tasksRespository 将保持 null

对于classes实例化的AndroidOS像Activity或者Application字段注入是合适的。对于其他人,包括您的存储库,最好使用构造函数注入。为什么?测试时,您可以通过构造函数和存根行为传入测试替身,或验证测试替身。

因此,要使其正常工作,您应该重构 TasksRepository 以使用构造函数注入:

@Singleton
public class TasksRepository implements RepositoryDatasource {

    private final Context context;
    private final AppConfig appConfig; 
    private final Realm realm;

    @Inject
    TasksRepository(Context context, AppConfig appConfig, Realm realm) {
        this.context = context;
        this.appConfig = appConfig;
        this.realm = realm;
    }

请注意,此步骤将突出显示您在设置对象图时所犯的任何错误。因此,如果 Dagger 2 无法在 TasksRepository 的构造函数中提供 3 个参数中的任何一个,它将通过编译时消息通知您。