Android
Dolk 2
Zoeken…
Syntaxis
- @Module
- @Component (afhankelijkheden = {OtherComponent.class}, modules = {ModuleA.class, ModuleB.class})
- DaggerMyComponent.create ()
- DaggerMyComponent.builder (). MyModule (newMyModule ()). Te maken ()
Opmerkingen
Niet te verwarren met dolk per vierkant, de voorloper van dolk 2.
Componenten instellen voor applicatie- en activiteitsinjectie
Een eenvoudige AppComponent
die afhankelijk is van een enkele AppModule
om toepassingsbrede singleton-objecten te bieden.
@Singleton
@Component(modules = AppModule.class)
public interface AppComponent {
void inject(App app);
Context provideContext();
Gson provideGson();
}
Een module om samen met de AppComponent
die zijn singleton-objecten biedt, bijv. Een exemplaar van Gson
om opnieuw te gebruiken in de hele applicatie.
@Module
public class AppModule {
private final Application mApplication;
public AppModule(Application application) {
mApplication = application;
}
@Singleton
@Provides
Gson provideGson() {
return new Gson();
}
@Singleton
@Provides
Context provideContext() {
return mApplication;
}
}
Een subklasse applicatie om dolk en de singleton component in te stellen.
public class App extends Application {
@Inject
AppComponent mAppComponent;
@Override
public void onCreate() {
super.onCreate();
DaggerAppComponent.builder().appModule(new AppModule(this)).build().inject(this);
}
public AppComponent getAppComponent() {
return mAppComponent;
}
}
Nu een activiteitsbereik dat afhankelijk is van de AppComponent
om toegang te krijgen tot de singleton-objecten.
@ActivityScope
@Component(dependencies = AppComponent.class, modules = ActivityModule.class)
public interface MainActivityComponent {
void inject(MainActivity activity);
}
En een herbruikbare ActivityModule
die basisafhankelijkheid biedt, zoals een FragmentManager
@Module
public class ActivityModule {
private final AppCompatActivity mActivity;
public ActivityModule(AppCompatActivity activity) {
mActivity = activity;
}
@ActivityScope
public AppCompatActivity provideActivity() {
return mActivity;
}
@ActivityScope
public FragmentManager provideFragmentManager(AppCompatActivity activity) {
return activity.getSupportFragmentManager();
}
}
Alles bij elkaar zijn we ingesteld en kunnen we onze activiteit injecteren en ervoor zorgen dat we in de hele app dezelfde Gson
gebruiken!
public class MainActivity extends AppCompatActivity {
@Inject
Gson mGson;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
DaggerMainActivityComponent.builder()
.appComponent(((App)getApplication()).getAppComponent())
.activityModule(new ActivityModule(this))
.build().inject(this);
}
}
Aangepaste scopes
@Scope
@Documented
@Retention(RUNTIME)
public @interface ActivityScope {
}
Scopes zijn slechts annotaties en u kunt waar nodig uw eigen scopes maken.
Constructor injectie
Klassen zonder afhankelijkheden kunnen eenvoudig worden gemaakt door dolk.
public class Engine {
@Inject // <-- Annotate your constructor.
public Engine() {
}
}
Deze klasse kan door elke component worden geleverd. Het heeft zelf geen afhankelijkheden en is niet scoped . Er is geen verdere code nodig.
Afhankelijkheden worden als parameters in de constructor aangegeven. Dagger roept de constructor op en levert de afhankelijkheden, zolang deze afhankelijkheden kunnen worden geleverd.
public class Car {
private Engine engine;
@Inject
public Car(Engine engine) {
this.engine = engine;
}
}
Deze klasse kan door elke component worden geleverd, als deze component ook al zijn afhankelijkheden kan bieden - Engine
in dit geval. Omdat de Engine
ook door de constructeur kan worden geïnjecteerd, kan elk onderdeel een Car
.
U kunt constructorinjectie gebruiken wanneer alle afhankelijkheden door de component kunnen worden geleverd. Een component kan een afhankelijkheid bieden, als
- het kan het maken met behulp van constructorinjectie
- een module van het component kan dit bieden
- het kan worden geleverd door de bovenliggende component (als het een
@Subcomponent
) - het kan een object gebruiken dat wordt blootgesteld door een component waarvan het afhankelijk is (afhankelijkheden van componenten)
@Subcomponent gebruiken in plaats van @Component (afhankelijkheden = {...})
@Singleton
@Component(modules = AppModule.class)
public interface AppComponent {
void inject(App app);
Context provideContext();
Gson provideGson();
MainActivityComponent mainActivityComponent(ActivityModule activityModule);
}
@ActivityScope
@Subcomponent(modules = ActivityModule.class)
public interface MainActivityComponent {
void inject(MainActivity activity);
}
public class MainActivity extends AppCompatActivity {
@Inject
Gson mGson;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
((App)getApplication()).getAppComponent()
.mainActivityComponent(new ActivityModule(this)).inject(this);
}
}
Hoe Dagger 2 toe te voegen in build.gradle
Sinds de release van Gradle 2.2 wordt het gebruik van de plug-in android-apt niet meer gebruikt. De volgende methode voor het instellen van Dagger 2 moet worden gebruikt. Gebruik voor oudere versies van Gradle de vorige methode hieronder.
Voor Gradle> = 2.2
dependencies {
// apt command comes from the android-apt plugin
annotationProcessor 'com.google.dagger:dagger-compiler:2.8'
compile 'com.google.dagger:dagger:2.8'
provided 'javax.annotation:jsr250-api:1.0'
}
Voor Gradle <2.2
Om Dagger 2 te gebruiken, is het noodzakelijk om de plug android-apt
toe te voegen, voeg deze toe aan de root build.gradle:
buildscript {
dependencies {
classpath 'com.android.tools.build:gradle:2.1.0'
classpath 'com.neenbedankt.gradle.plugins:android-apt:1.8'
}
}
Dan zou build.gradle van de applicatiemodule moeten bevatten:
apply plugin: 'com.android.application'
apply plugin: 'com.neenbedankt.android-apt'
android {
…
}
final DAGGER_VERSION = '2.0.2'
dependencies {
…
compile "com.google.dagger:dagger:${DAGGER_VERSION}"
apt "com.google.dagger:dagger-compiler:${DAGGER_VERSION}"
}
Referentie: https://github.com/codepath/android_guides/wiki/Dependency-Injection-with-Dagger-2
Een component maken van meerdere modules
Dagger 2 ondersteunt het maken van een component uit meerdere modules. U kunt uw component op deze manier maken:
@Singleton
@Component(modules = {GeneralPurposeModule.class, SpecificModule.class})
public interface MyMultipleModuleComponent {
void inject(MyFragment myFragment);
void inject(MyService myService);
void inject(MyController myController);
void inject(MyActivity myActivity);
}
De twee referentiemodules GeneralPurposeModule
en SpecificModule
kunnen vervolgens als volgt worden geïmplementeerd:
GeneralPurposeModule.java
@Module
public class GeneralPurposeModule {
@Provides
@Singleton
public Retrofit getRetrofit(PropertiesReader propertiesReader, RetrofitHeaderInterceptor headerInterceptor){
// Logic here...
return retrofit;
}
@Provides
@Singleton
public PropertiesReader getPropertiesReader(){
return new PropertiesReader();
}
@Provides
@Singleton
public RetrofitHeaderInterceptor getRetrofitHeaderInterceptor(){
return new RetrofitHeaderInterceptor();
}
}
SpecificModule.java
@Singleton
@Module
public class SpecificModule {
@Provides @Singleton
public RetrofitController getRetrofitController(Retrofit retrofit){
RetrofitController retrofitController = new RetrofitController();
retrofitController.setRetrofit(retrofit);
return retrofitController;
}
@Provides @Singleton
public MyService getMyService(RetrofitController retrofitController){
MyService myService = new MyService();
myService.setRetrofitController(retrofitController);
return myService;
}
}
Tijdens de afhankelijkheidsinjectiefase neemt de component objecten uit beide modules volgens de behoeften.
Deze benadering is zeer nuttig in termen van modulariteit . In het voorbeeld is er een module voor algemene doeleinden die wordt gebruikt om componenten te instantiëren, zoals het Retrofit
object (gebruikt om de netwerkcommunicatie af te handelen) en een PropertiesReader
(belast met de afhandeling van configuratiebestanden). Er is ook een specifieke module die de instantiatie van specifieke controllers en serviceklassen met betrekking tot die specifieke applicatiecomponent afhandelt.