2016-11-22 1 views
13

CoreModule에서 제공하는 클래스의 인스턴스를 삽입하기 위해 @Singleton 범위를 사용하여 CoreComponent 광고를 정의하는 Core Android 라이브러리가 있습니다.단검 2 : 여러 구성 요소간에 동일한 인스턴스를 다른 라이브러리 모듈에서 동일한 범위로 제공하십시오.

@Singleton 
@Component(modules = {CoreModule.class}) 
public interface CoreComponent { 
    void inject(SomeClass target); 
} 

@Module 
public class CodeModule { 
    @Singleton 
    @Provides 
    CoreRepository provideCoreRepository() { 
     return new CoreRepositoryImpl(); 
    } 
} 

나는 핵심 라이브러리에 의존하고 다른 구성 요소를 사용하는 다른 안드로이드 라이브러리에서 동일한 @Singleton의 인스턴스에 액세스하고 싶습니다.

@Singleton 
@FooScope 
@Component(modules = {CoreModule.class, FooModule.class}) 
public interface FooComponent { 
    void inject(SomeActivity target); 
} 

public class FooActivity extends AppCompatActivity { 
    @Inject 
    public CoreRepository repo; 

    @Override 
    protected void onCreate(@Nullable Bundle savedInstanceState) { 
     injectDependencies(); 
     super.onCreate(savedInstanceState); 
    } 
    [...] 
} 

위의 코드는 빌드되지만 @Singleton 범위는 구성 요소에 대해 "로컬"입니다. 즉, CoreComponent와 FooComponent에 대한 두 개의 싱글 톤 인스턴스가 있습니다.

Android Application 
├── Foo Library 
| └── Core Library 
├── Bar Library 
| └── Core Library 
· 
· 
· 
└── Core Library 

나는 최선의 해결책은 코어 도서관은 다른 도서관의 가시성이 없기 때문에 불행히도, 가능하지 않는 것, 하위 구성 요소를 사용하고 있지만되어야한다고 생각합니다.

클래스가 동일한 범위로 주석을 달면 구성 요소간에 한 클래스의 동일한 인스턴스를 대거와 공유 할 수있는 다른 방법이 있습니까?

@Singleton 
@Component(modules = {CoreModule.class}) 
public interface CoreComponent { 
    CoreRepository coreRepository(); 
} 

응용 프로그램 내부의이 싱글 범위의 구성 요소에 대한 참조를 만듭니다 : -

+2

당신이 [구성 요소 종속성]로 봤어 당신에 삽입 할 수 (http://stackoverflow.com/q/29587130/1426891) 아직? [Javadoc] (https://google.github.io/dagger/api/latest/dagger/Component.html#component-dependencies) 여기를 참고하고 CoreComponent에 몇 가지 엑스트라 접근 메소드를 명시 적으로 추가해야 할 수도 있습니다. FooComponent가 호출 할 수 있습니다. –

+0

Checkout https://stackoverflow.com/questions/27036933/how-to-set-up-dagger-dependency-injection-from-scratch-in-android-project 여기에는 범위와 종속 구성 요소를 사용하는 예가 있습니다. –

답변

15

당신의 CoreComponent에서 주사 부위를 제거는 지금 종속 구성 요소 CoreRepository에 대한 바인딩을 노출의 유일한 기능이

@Scope 
@Retention(RetentionPolicy.RUNTIME) public @interface PerActivity {} 
:
public class MyApplication extends Application { 
    private final CoreComponent coreComponent; 

    @Override 
    public void onCreate() { 
     super.onCreate(); 
     coreComponent = DaggerCoreComponent 
          .coreModule(new CoreModule()) 
          .build(); 
    } 

    public static CoreComponent getCoreComponent(Context context) { 
     return ((MyApplication) context.getApplicationContext()).coreComponent; 
    } 
} 

새로운 좁은 범위 만들기

는 주사 부위에 완전이 범위를 추적하는 새 구성 요소를 만들기 당신이 원하는 :

@PerActivity 
@Component(dependencies = {CoreComponent.class}) 
public interface ActivityComponent { 
    void inject(FooActivity activity); 

    void inject(BarActivity activity); 
} 

당신이 주사 부위에이 활동 범위의 구성 요소에 액세스 할 때 빌더에 CoreComponent의 인스턴스를 제공해야합니다 . 지금 당신은 Activity

public class FooActivity extends AppCompatActivity { 
     @Inject 
     public CoreRepository repo; 

     @Override 
     protected void onCreate(@Nullable Bundle savedInstanceState) { 
      super.onCreate(savedInstanceState); 
      CoreComponent coreComponent = MyApplication.getCoreComponent(this); 
      DaggerActivityComponent.builder() 
       .coreComponent(coreComponent) 
       .build() 
       .inject(this); 
     } 
    } 
} 
+0

안녕하세요. 많이! 이것은 내가 필요한 것입니다! 코어 라이브러리 내부에 CoreRepository를 주입해야하기 때문에 내가 다르게하고있는 유일한 방법은 또한 CoreComponent에 주입 방법을 유지하는 것입니다. 좋지 않아? 코어 라이브러리 내부에서 사용하기 위해 종속성을 가진 새 구성 요소를 만들고 주입없이 CoreComponent를 그대로 두어야합니까? –

+1

CoreLibrary의 종속성에 대해 원하는 범위에 따라 다릅니다. 만약 당신이 그때 아마 괜찮아 애플 리케이션 싱글 톤을 원한다면. 그러나 나는 개인적으로 주사 부위의 범위를 추적하는 구성 요소를 갖고 싶다. –

+0

한 가지 더 질문 : 한 가지 구성 요소에 대해 하나의 범위가 지정된 종속성을 가질 수 없다는 사실을 알고 있다면 여러 범위 종속성과 함께 작동하도록하는 방법이 있습니까? ?예를 들어, @Singleton 범위가 지정된 구성 요소가있는 여러 라이브러리가 있고 Singleton 인스턴스를 내 ActivityComponent와 공유 할 수 있기를 원합니다. 라이브러리는 독립적이며 서로를 볼 수 없습니다. –

관련 문제