我想要做的是抽象,并将抽象作为参数传递。因此,如果有一天出现比改造更好的东西并且我想要切换它,那么这样做很容易。虽然我不知道怎么做。以下是我想要做的基本概述:
public interface ApiClient{
Object getClient()
}
public class RetrofitClient implements ApiClient{
private static Retrofit retrofit = null;
@Override
public Retrofit getClient(){
if(retrofit == null){
OkHttpClient tokenInterceptor = new OkHttpClient.Builder()
.addInterceptor(new NetworkInterceptor())
.build();
retrofit = new Retrofit.Builder()
.baseUrl("www.hello.com")
.addConverterFactory(GsonConverterFactory.create())
.build();
}
}
}
然后我想通过传递ApiClient作为参数来消费它:
public class MyClass{
private ApiClient apiClient;
public MyClass(ApiClient apiClient){
this.apiClient = apiClient;
}
public void getSomeData(){
MyClient client = this.client.create(MyClient.class);
}
}
我需要一些方法将RetrofitClient
注入MyClass
。
请建议一个IOC容器,任何其他替代方案以及我将如何使用它来实现这一目标,谢谢。
此链接提供了更深入的描述,使用C#和Castle Windsor https://github.com/castleproject/Windsor/blob/master/docs/basic-tutorial.md
答案 0 :(得分:0)
在Java中,与在C#中一样,抽象由接口或抽象类表示。
您提出的建议可称为“在接口中包装外部库以允许按配置进行交换”。要做到这一点,你必须检查你想要换出的具体化所暴露的方法,并创建一个与之匹配的新接口。
例如,如果外部库具有以下方法:
public class ExternalLibrary {
void foo() {
//foo implementation
}
void bar() {
//bar implementation
}
}
您将创建一个包装器接口:
public interface FooBarable {
void foo();
void bar();
}
下一步是让您应用中ExternalLibrary
的消费者取决于FooBarable
:
public class MyActivity extends Activity {
FooBar fooBar;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
DaggerFooBarComponent
.builder()
.fooBarModule(new ExternalLibraryModule())
.build()
.inject(this);
}
}
如果您需要为测试模拟交换ExternalLibrary
,则可以按照Dagger 2 User Guide中的测试说明使用测试组件:
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
DaggerTestFooBarComponent
.builder()
.mockFooBarModule(new MockFooBarableModule())
.build()
.inject(this);
}
要了解DI框架/ IOC容器Dagger 2如何处理所有这些,您必须查看user guide和Google Dagger 2 Android app blueprint,因为在上下文中有太多要解释的内容。一个答案。