그래서 현재 Dagger을 사용하기 위해 Android 앱을 다시 디자인하고 있습니다. 내 응용 프로그램은 크고 복잡하며 최근에 다음 시나리오를 보았습니다.생성자 의존성 주입에 대거 사용
Object A는 완벽한 인젝션 후보 인 특수 DebugLogger 인스턴스가 필요합니다. 로그 작성기를 돌아 다니는 대신 A의 생성자를 통해 주입 할 수 있습니다. 이 모양은 다음과 같습니다.
class A
{
private DebugLogger logger;
@Inject
public A(DebugLogger logger)
{
this.logger = logger;
}
// Additional methods of A follow, etc.
}
지금까지는 이것이 합리적입니다. 그러나 A는 그렇게 일을 단검의 방법에 따라, (A)의 여러 인스턴스를 구축 할 수 있어야 다른 클래스 B로 구축 할 필요가있다, 나는 간단한 B에 Provider<A>
를 주입 :
class B
{
private Provider<A> aFactory;
@Inject
public B(Provider<A> aFactory)
{
this.aFactory = aFactory;
}
}
좋아, 좋은 지금까지. 그러나 잠깐, 갑자기 A는 그 구성에 필수적인 "양"이라는 정수와 같은 추가 입력이 필요합니다. 이제 A에 대한 내 생성자는 다음과 같이 표시되어야합니다.
@Inject
public A(DebugLogger logger, int amount)
{
...
}
갑자기이 새 매개 변수가 주입을 방해합니다. 더욱이 이것이 작동했다하더라도 내가 잘못하지 않는 한 제공자로부터 새로운 인스턴스를 검색 할 때 "양"을 전달할 수있는 방법이 없습니다. 내가 여기서 할 수있는 일이 몇 가지 있는데, 나의 질문은 어느 것이 최고인가?
생성자 다음에 호출 될 것으로 예상되는 setAmount()
메서드를 추가하여 A를 리팩토링 할 수 있습니다. 그러나 이것은 "양"이 채워질 때까지 A의 생성을 지연 시키므로 추악합니다. "amount"와 "frequency"라는 두 개의 매개 변수가 있다면 두 개의 setter가 생겨 복잡한 두 세터가 호출 재개 후의 구성을 확인하려면, 또는 그런 것처럼, 혼합으로 아직 세 번째 방법을 추가해야합니다 :
(Somewhere in B):
A inst = aFactory.get();
inst.setAmount(5);
inst.setFrequency(7);
inst.doConstructionThatRequiresAmountAndFrequency();
다른 대안은 내가 생성자를 사용하지 않는 것이있다 기반 주입 및 필드 기반 주입으로 이동합니다. 하지만 지금은 밭을 공개해야합니다. 내 수업의 내부 데이터를 다른 수업에 공개해야 할 의무가 있기 때문에 이것은 나에게 잘 맞지 않습니다.
지금까지 내가 생각할 수있는 유일한 다소 우아한 솔루션과 같이, 공급자에 대한 필드 기반의 주사를 사용하는 것입니다
class A
{
@Inject
public Provider<DebugLogger> loggerProvider;
private DebugLogger logger;
public A(int amount, int frequency)
{
logger = loggerProvider.get();
// Do fancy things with amount and frequency here
...
}
}
에도 여전히 나는 '이후이 타이밍에 대해 확실 해요 Dagger가 생성자가 호출되기 전에 공급자를 삽입 할 것인지 확실하지 않습니다.
더 좋은 방법이 있습니까? Dagger가 작동하는 방식에 대해 뭔가 빠져 있습니까?
빠른 응답 감사합니다. 설명 된 팩터 리 패턴은 최상의 접근 방법처럼 보입니다. 또한 Dagger가 개인 필드 주입을 지원하면 쉽게 달성하려는 것을 허용 할 수 있다고 생각했습니다. Dagger의 독창적 인 디자인의 일부가 아닌 이유가 궁금합니다. 대거가 반사를 사용하여 주사한다고 가정합니다. 그렇다면 사적인 필드는 문제가되지 않습니다. – Alex
대거 (dagger)는 반사에 빠지 긴하지만 그것은 주된 주입 방법이 아닙니다. 필드를 직접 설정하거나 생성자를 호출하는 코드를 생성합니다. 따라서 소스 트리에서 다른 코드와 마찬가지로 작동하며 'private'멤버에 액세스 할 수 없습니다. –
그리고 일부 보안 관리자는 클래스의 액세스 가능성 변경에 의존하는 리플렉션을 중단합니다. –