我有一个模块如下.
@H_404_6@@Module public class AppModule { private final Application app; public AppModule(Application app) { this.app = app; } @Provides @Architecture.ApplicationContext Context provideContext() { return app; } @Provides //scope is not necessary for parameters stored within the module public Context context() { return provideContext(); } @Singleton @Provides Application provideApp() { return app; } @Singleton @Provides SoundsRepository provideSoundsRepository(Context context,SoundsDAO soundsDAO) { return new SoundsRepository(context,soundsDAO); } }
像这样的组件.
@H_404_6@@Singleton @Component(modules = AppModule.class) public interface AppComponent { void inject(Global global); void inject(MainActivity mainActivity); @Architecture.ApplicationContext Context getContext(); Application getApplication(); void inject(PostView postView); void inject(MediaPlayerService mediaPlayerService); }
在活动,片段或服务中,我这样做
@H_404_6@@Inject SoundsRepository soundsRepository; @Override protected void onCreate(...) { //.... ((Global) getApplication()).getComponent().inject(this); }
在SoundsRepository中
@H_404_6@@Singleton public class SoundsRepository { @Inject public SoundsRepository(Context context,SoundsDAO soundsDAO) { this.context = context; this.soundsDAO = soundsDAO; System.out.println(TAG + "INIT"); } // .... }
所以,现在,每当我开始访问注入SoundsRepository的活动或服务时,我得到一个新实例,我的意思是,“SoundsRepository”的构造函数再次触发.
我究竟做错了什么?
编辑:在应用程序类中注入
@H_404_6@public class Global extends MultiDexApplication { protected AppComponent appComponent; private boolean calledAlready = false; @Override public void onCreate() { super.onCreate(); //if (LeakCanary.isInAnalyzerProcess(this)) return; //LeakCanary.install(this); initFirebasePersistance(); appComponent = DaggerAppComponent.builder().appModule(new AppModule(this)).build(); appComponent.inject(this); FrescoUtil.init(getApplicationContext()); } public AppComponent getComponent() { return appComponent; } }
最佳答案
>在您的模块中,您有一个提供SoundsRepository实例的方法 – 很好
>在您的AppComponent中,您缺少:
>在您的AppComponent中,您缺少:
@H_404_6@SoundsRepository soundsRepository();
>在扩展Application / MultidexApplication的Global中,您可以创建DaggerAppComponent – 很好
>在您的其他活动/片段/服务中,只需致电:
@H_404_6@Global application = (Global) getApplication(); SoundsRepository sr = application.getComponent().soundsRepository()
Android保证您只有一个Application(Global)类的实例用于所有其他活动/服务(它有点像单身).
因此,请将您的组件保留在该应用程序类中,并在需要您的类时,调用:(YourApplication)getApplication().getComponent().yourSingleInstanceSomething();
我为您创建并测试了示例代码:https://github.com/zakrzak/StackDaggerTest
Dagger的@Singleton只是一个范围,并不保证返回一个类的单个实例.
据我了解,如果你:
@H_404_6@void inject(PostView postView);
你告诉Dagger,只要你提出请求,就可以在PostView中使用@Provided中的@Provided进行注释:
@H_404_6@@Inject SoundsRepository soundsRepository;
然后dagger只调用@provided方法,在你的情况下返回一个新的SoundRepository实例:
@H_404_6@@Singleton @Provides SoundsRepository provideSoundsRepository(Context ........) { return new SoundsRepository(...); }
这会导致你的问题