2015-01-27 4 views
36

Ich habe ein Problem zu verstehen, warum der folgende Code nicht funktioniert.Probleme mit Singletons bei Verwendung von Komponentenabhängigkeiten

Ich habe folgende Projektstruktur:

@Component(modules = CCModule.class) 
public interface CComponent { 
    XXX getXXX(); 
} 

wo

@Module 
public class CCModule { 

    @Provides @Singleton 
    public XXX provide XXX(){ 
     return new XXX(); 
    } 
} 

und

@Component(dependencies = CComponent.class, modules = AAModule.class) 
public interface AComponent { 
    YYY getYYY(); 
} 

wo

class YYY { 
    @Inject 
    public YYY(XXX xxx) { 
     ... 
    } 
} 

ich initialisieren alles wie:

CComponent c_component = Dagger_CComponent.builder().cCModule(new CCModule()).build(); 

AComponent a_component = Dagger_AComponent.builder() 
     .cComponent(c_component) 
     .aAModule(new AAModule()) 
     .build(); 

Sobald ich die folgende Fehlermeldung erhalten Kompilierung stattfindet:

Error:(11, 1) error: com.test.CComponent (unscoped) may not reference scoped bindings: @Provides @Singleton com.test.XXX com.test.CCModule.provideXXX()

Was denn ich bin mit dem Ziel ist eine Komponente Bindungen von anderen Komponenten erben zu haben, haben die gleiche Verweise auf Objekte (Singletons).

Antwort

81

Sie sollten @Singleton zu CComponent Klasse Deklaration setzen.

@Singleton 
@Component(modules = CCModule.class) 
public interface CComponent { 
    XXX getXXX(); 
} 

Erklärung ist in Fehlermeldung: CComponent unscoped ist, @Singleton ein Rahmen ist. Dolch 2 erlaubt es nicht unbeschichteten Komponenten, Module mit Scoped-Bindungen zu verwenden.
Aber jetzt werden Sie die folgende Fehlermeldung erhalten:

AComponent (unscoped) cannot depend on scoped components: 
@Component(dependencies = CComponent.class, modules = AModule.class) 

ohne Bereichseinschränkung Komponenten können nicht scoped Abhängigkeiten aufweisen. Also müssen Sie AComponent Bereich machen. Erstellen Sie dazu benutzerdefinierte AScope Annotation.

@Scope 
@Retention(RetentionPolicy.RUNTIME) 
public @interface AScope { 
} 

und mit Anmerkungen versehen mit ihm AComponent:

@AScope 
@Component(dependencies = CComponent.class, modules = AModule.class) 
public interface AComponent { 
} 

Das sind neue Anforderungen erschienen in neuesten snapshot release. Es wurde in entsprechenden issue diskutiert und kann noch geändert werden.

+0

zu verwenden, nicht zulassen @ Alexander Vasiljev Getestet am letzten Schnappschuss. Funktioniert gut =). Ich habe meine Antwort ein wenig mit benutzerdefinierten AScope-Annotationen aktualisiert. Etwas stimmt nicht mit deinem Code. Zeig es. Übrigens reden wir auf Englisch, das ist keine russische Ressource. –

+0

saubere lösung sir –

0

@Singleton 
@Component(modules = {NameModule.class}) 
public interface NameComponent { 

} 

für die Komponente hinzufügen, weil dagger2 unscoped Komponenten mit scoped Module