Dagger-为SubComponent Builder设置动态值 [英] Dagger - Setting a Dynamic Value to SubComponent Builder

查看:187
本文介绍了Dagger-为SubComponent Builder设置动态值的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想在构建子组件构建器时为其设置一个值。如果只考虑简单的Dagger 2,我们可以实现以下目标:

  @UserScope 
@Subcomponent(modules = {UserModule .class,ActivityBuilder.class,NewEditQuotationModule.class})

公共接口UserComponent {
NewEditQuotationComponent.Builder getNewEditQuotationComponent();
void inject(UserManager userManager);

@ Subcomponent.Builder
接口Builder {
@ BindsInstance
Builder用户(用户);

UserComponent build();
}}

但是对于Dagger Android,Subcomponent及其关联的构建器由@ContributesAndroidInjector。 Dagger Auto会在当前上下文中自动生成Subcomponent及其生成器。



我想在构建My Dagger Android Subcomponent时设置一些值。我尝试通过以下方法:

  @Subcomponent(modules = NewEditQuotationModule.class)
公共接口NewEditQuotationComponent扩展了AndroidInjector< InquiriesEditNewMainActivity> ; {


@ Subcomponent.Builder
抽象类Builder扩展了AndroidInjector.Builder< InquiriesEditNewMainActivity> ;; {
@BindsInstance
public abstract Builder setName(@Named( My_Name)字符串名称);
}}

@Module
公共抽象类NewEditQuotationModule {
@Binds
@IntoMap
@ActivityKey(InquiriesEditNewMainActivity.class)
抽象的AndroidInjector.Factory< ;?扩展Activity>
bindInquiriesEditNewMainActivityInjectorFactory(NewEditQuotationComponent.Builder builder);

}

我厌倦了通过以下方式构建它:

  AndroidInjector.Builder androidInjector = MyApplication 
.getApplication()
.getAppComponent()
.getApiEndPoint( )
.getApiEndPointComponent()
.getUserManager()
.getUserComponent()
.getNewEditQuotationComponent()。setName( My Name);
androidInjector.seedInstance(this);
androidInjector.build();

但没有成功。
请让我知道


  1. 在构建组件时如何设置一些值?

  2. 在以前的方法中我哪里出错了?


解决方案

dagger.android 的工作原理是在 onCreate 中自动创建您的组件,由于Android是允许自己创建活动。预先创建AndroidInjector无效;



正如我试图通过重复提问投票指出的那样,设置模块实例或<$ c $的唯一方法是dagger.android中的c> @BindsInstance 值由 AndroidInjector.Builder 中替代 seedInstance 方法作为您的 @ Subcomponent.Builder 也是如此。



尽管您始终可以将数据存储在 @Singleton中,但您可以将这些值从Activity实例中拉出并进行设置。



(ApplicationComponent范围的)对象或VM全局变量,您正在尝试通过正确地将数据从Activity传递到Activity而不设置全局状态来做正确的事情。 我认为这是正确的方法,但您的解决方案可能不会涉及显式构造AndroidInjector 。相反,通过Extras捆绑包传递数据,这是将参数和其他数据传输到Activity中的一种惯用方式;然后可以通过将数据从 seedInstance getIntent()。getExtras()中拉出,将其插入到图形中$ c>,因为 getIntent()应该在<$ c之前填充$ c> onCreate(Bundle)运行


I want to set a value to my sub-component builder at the time of building it. If simple Dagger 2 is concerned, we can achieve like following:

@UserScope
@Subcomponent(modules = {UserModule.class, ActivityBuilder.class, NewEditQuotationModule.class})

public interface UserComponent {
NewEditQuotationComponent.Builder getNewEditQuotationComponent();
void inject(UserManager userManager);

@Subcomponent.Builder
interface Builder {
    @BindsInstance
    Builder user(User user);

    UserComponent build();
}}

But In case of Dagger Android, Subcomponent and its associated builder is handled by @ContributesAndroidInjector. Dagger Auto generate Subcomponent and its builder even its implementation with the current context.

I want to set some value at the time of building My Dagger Android Subcomponent. I tried by following approach:

 @Subcomponent(modules = NewEditQuotationModule.class)
    public interface NewEditQuotationComponent extends AndroidInjector<InquiriesEditNewMainActivity> {


    @Subcomponent.Builder
    abstract class Builder extends AndroidInjector.Builder<InquiriesEditNewMainActivity> {
        @BindsInstance
        public abstract Builder setName(@Named("My_Name") String name);
    }}

        @Module
    public abstract class NewEditQuotationModule {
        @Binds
        @IntoMap
        @ActivityKey(InquiriesEditNewMainActivity.class)
        abstract AndroidInjector.Factory<? extends Activity>
        bindInquiriesEditNewMainActivityInjectorFactory(NewEditQuotationComponent.Builder builder);

    }

I tired to build it by following way:

AndroidInjector.Builder androidInjector = MyApplication
                .getApplication()
                .getAppComponent()
                .getApiEndPoint()
                .getApiEndPointComponent()
                .getUserManager()
                .getUserComponent()
                .getNewEditQuotationComponent().setName("My Name");
        androidInjector.seedInstance(this);
        androidInjector.build();

But not succeed. Please let me know

  1. How can I set some value at the time of building my component?
  2. Where am I wrong in the previous approach?

解决方案

dagger.android works by automatically creating your component in onCreate, and needs to work this way because Android is allowed to create your Activity on its own. Pre-creating your AndroidInjector will not work; that is what's wrong with your previous approach.

As I tried to indicate through a duplicate-question vote, the only way for you to set module instance or @BindsInstance values in dagger.android is by overriding the seedInstance method in the AndroidInjector.Builder that serves as your @Subcomponent.Builder as well. This will let you pull values out of the Activity instance and set them in your Activity graph.

Though you could always stash data in a @Singleton (ApplicationComponent-scoped) object or VM global variable, you are trying to do the right thing by passing data carefully from Activity to Activity without setting global state. I think this is the right approach, but also that your solution probably will not involve constructing an AndroidInjector explicitly. Instead, pass your data through the extras bundle, which is an idiomatic way of transferring parameters and other data into Activities; you can then insert that data into your graph by pulling it out of getIntent().getExtras() on your Activity instance in seedInstance, since getIntent() should be populated by the time onCreate(Bundle) runs.

这篇关于Dagger-为SubComponent Builder设置动态值的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆