Java 如何使用匕首重新注入特定对象
在我的应用程序中,我有两种模式:演示模式和真实模式。在演示模式下,我使用另一个类模拟服务器通信:Java 如何使用匕首重新注入特定对象,java,android,dependency-injection,dagger,Java,Android,Dependency Injection,Dagger,在我的应用程序中,我有两种模式:演示模式和真实模式。在演示模式下,我使用另一个类模拟服务器通信: @Module(...) public class CommunicationModule { @Provides @Singleton CommunicationWrapper provideNetworkBusWrapper(Application app) { boolean isDebug = ((MyApplication) app).isDebug();
@Module(...)
public class CommunicationModule {
@Provides @Singleton CommunicationWrapper provideNetworkBusWrapper(Application app) {
boolean isDebug = ((MyApplication) app).isDebug();
CommunicationWrapper result = null;
if (isDebug) {
result = new DemoWrapper(app);
} else {
result = new NetworkWrapper(app);
}
return result;
}
}
现在,在一个特定的用户操作之后,我想重新初始化这个依赖项。是否可以在不重建整个对象图的情况下执行此操作 这篇评论是关于匕首1的
我不确定它是否对你有帮助,但你分析过吗?
根据我的分析,他在调试模式下添加了两个图形(标准模块和调试模块)。调试模块可以覆盖标准模块的功能(在运行时),但我还并没有找到它的具体实现位置。在这个应用程序中,它是由菜单中的按钮提供的-也许你会发现它更快(我对gradle有一些问题)这个评论是关于Dagger 1的
我不确定它是否对你有帮助,但你分析过吗?
根据我的分析,他在调试模式下添加了两个图形(标准模块和调试模块)。调试模块可以覆盖标准模块的功能(在运行时),但我还并没有找到它的具体实现位置。在这个应用程序中,它是由菜单中的按钮提供的-也许你会发现它更快(我对gradle有一些问题)你可以重新注入对象,以便根据你的标志更改实现。只需从提供方法中删除@Singleton
注释
下面是一个示例代码:
public class SomeActivity extends Activity {
@Inject CommunicationWrapper mCommunicationWrapper;
@Override
protected void onCreate(Bundle savedInstanceState) {
((MyApplication) getApplication()).inject(this);
// using NetworkWrapper
...
}
public void userActionHandler(){
((MyApplication) getApplication()).setDebug(true);
((MyApplication) getApplication()).inject(this);
// using DemoWrapper
...
}
记住,类的所有依赖项都将被重新注入。您可以重新注入对象,以便根据您的标志更改实现。只需从提供方法中删除@Singleton
注释
下面是一个示例代码:
public class SomeActivity extends Activity {
@Inject CommunicationWrapper mCommunicationWrapper;
@Override
protected void onCreate(Bundle savedInstanceState) {
((MyApplication) getApplication()).inject(this);
// using NetworkWrapper
...
}
public void userActionHandler(){
((MyApplication) getApplication()).setDebug(true);
((MyApplication) getApplication()).inject(this);
// using DemoWrapper
...
}
请记住,该类的所有依赖项都将被重新注入。若要有2个版本,您可以有条件地包括,但希望在其他一些变化的条件下交换,您可以从singleton提供2种类型,然后从提供到您的依赖项,而不使用singleton
// DemoWrapper.java
@Singleton // Alternatively, you could add provides methods for the wrapper types and annotate those with @Singleton
class DemoWrapper { ... }
// NetworkWrapper.java
@Singleton
class NetworkWrapper { ... }
// CommunicationModule.java
@Module(
...,
injects = {
DemoWrapper.class,
NetworkWrapper.class
}
)
public class CommunicationModule {
@Provides
CommunicationWrapper provideNetworkBusWrapper(Application app, DemoWrapper demo, NetworkWrapper network) {
boolean isDebug = ((MyApplication) app).isDebug();
return isDebug ? demo : network;
}
}
要有2个有条件地包含的版本,但要在其他一些变化的条件下交换,可以从singleton提供2种类型,然后从提供到依赖项,而不提供singleton
// DemoWrapper.java
@Singleton // Alternatively, you could add provides methods for the wrapper types and annotate those with @Singleton
class DemoWrapper { ... }
// NetworkWrapper.java
@Singleton
class NetworkWrapper { ... }
// CommunicationModule.java
@Module(
...,
injects = {
DemoWrapper.class,
NetworkWrapper.class
}
)
public class CommunicationModule {
@Provides
CommunicationWrapper provideNetworkBusWrapper(Application app, DemoWrapper demo, NetworkWrapper network) {
boolean isDebug = ((MyApplication) app).isDebug();
return isDebug ? demo : network;
}
}
在那个应用程序中,他只是重建了整个对象图。我认为这是另一种方式。据我所知,这不是真的——他为调试模式构建了更大的图形,并为模拟模式重新注入ApplicationContainer(DebugAppContainer)的模拟实现。在我看来,这不是重建图表。是的,活动被破坏了,但图形仍然是一样的。调试它比我想象的要困难得多。你是对的——即使在日志中我也可以看到“buildObjectGraphHandInject()”通知,每次我在那个应用程序中更改“Endpoint”时,他都会重建整个对象图。我认为这是另一种方式。据我所知,这不是真的——他为调试模式构建了更大的图形,并为模拟模式重新注入ApplicationContainer(DebugAppContainer)的模拟实现。在我看来,这不是重建图表。是的,活动被破坏了,但图形仍然是一样的。调试它比我想象的要困难得多。您是对的-即使在日志中,我也可以观察“buildObjectGraphHandInject()”通知,每次更改“Endpoint”时,问题是我希望在多个对象之间共享CommunicationWrapper实例。所以我需要它是单例的,为什么不在模块中保留一个DemoWrapper
和NetworkWrapper
的实例呢?我认为你对DI库的要求太高了。如果您需要一些不常见的东西,您必须自己实现它(比如返回singleton而不是使用@singleton
)。我们如何确定在调用inject()的同一代码上需要NetworkWrapper或DemoWrapper实例。问题是我想在多个对象之间共享CommunicationWrapper实例。所以我需要它是单例的,为什么不在模块中保留一个DemoWrapper
和NetworkWrapper
的实例呢?我认为你对DI库的要求太高了。如果你需要一些不常见的东西,你必须自己实现(比如返回singleton而不是使用@singleton
)。我们如何决定在调用inject()的同一代码上需要NetworkWrapper或DemoWrapper实例。我相信测试和调试构建变量在isDebug()中都会返回true;你在两者之间切换的条件可以是你喜欢的任何条件。共享首选项、应用程序调试模式或BuildConfig.Flavor
。我相信测试和调试构建变量在isDebug()中都会返回true;你在两者之间切换的条件可以是你喜欢的任何条件。共享首选项、应用程序调试模式或BuildConfig.Flavor
。