Dagger2 기초 부터

Dagger2 활용을 위하여

0. 내가 생각하는 시나리오

  • 기능이 있거나 구조체로 사용하는 클래스를 만든다.
  • 어노테이션을 이용해서 원하는곳에서 사용 가능하게 한다.
  • 싱글톤으로 구현된 스태틱 클래스를 들을 편하게 가져다 쓰는 느낌으로

1. 그래들 설정

  • 다른곳은 너무 어렵게 되어 있습니다.

      compile 'com.google.dagger:dagger:2.7'
      annotationProcessor 'com.google.dagger:dagger-compiler:2.7'
    

2. 따라하기

  • 개 이름이 있는 클래스를 생성한다.

java public class Dog { public String getName() { return "멈뭄미"; } }

  • 개 클래스를 제공할 모듈을 만든다.
  • 개 클래스를 반환한 함수를 메소드를 만들고 어노테이션으로 @Provides 추가 한다.
  • 클래스에는 @Module 을 어노테이션을 입력한다.

java @Module public class SampleModule { @Provides Dog provideDog() { return new Dog(); } }

  • 모듈을 사용할 인터페이스를 만든다.
  • inject 메소드를 만들어야 한다.

java @Component(modules = SampleModule.class) public interface SampleComponent { void inject(MainActivity activity); }

  • 액티비티에 의존성을 주입시켜 개 이름을 출력해 보자
  • 아래 내용을 진행하기 전에 make 를 한번 진행해야 DaggerSampleComponent 를 사용할 수 있습니다.
  • new Dog 를 안했지만 “멈뭄미” 를 출력 가능합니다.
  • 즉 Dog 를 주입 시켰습니다.
  • 가장 기본 적인 필드 인젝션 입니다.

```java public class MainActivity extends AppCompatActivity { // 인스턴스가 주입되는 필드 @Inject Dog dog;

  @Override
  protected void onCreate(Bundle savedInstanceState) {
      super.onCreate(savedInstanceState);
      setContentView(R.layout.activity_main);

      // SampleComponent로부터 DaggerSampleComponent 가 자동 생성되므로, 그것을 사용하여 SampleComponent를 만듭니다.
      SampleComponent component = DaggerSampleComponent.builder()
              // 사용하는 Module 인스턴스를 지정합니다.
              // (여기서 deprecated 될 수 있지만, 일단 모든 코드를 작성하고 빌드하면 사라질 것입니다)
              .sampleModule(new SampleModule())
              .build();

      // 의존 주입을 실행합니다
      component.inject(this);

      String name = dog.getName();

      Log.d("MainActivity", name);

  }
}   ```
  • 생성자 인젝션
  • 생성자에서 개 클래스를 입력 받기 위해서 아래 처럼 클래스를 작성합니다.

```java public class Owner {

  private Dog dog;

  @Inject
  public Owner(Dog dog) {
      this.dog = dog;
  }

  public String getPetName() {
      return dog.getName();
  }
}   ```
  • MainActivity 에서 변경 내용은 아래 처럼 인젝트 내용만 변경해 주면 됩니다.

java @Inject Owner owner;

3. 인터페이스를 이용하여 좀더 편하게 주입을 변경하기

  • 지금까지 사용한 것은 구현 클래스였지만, 다음은 interface를 사용하도록 변경합니다.

```java public interface Pet { String getName(); }

public class Dog implements Pet {

  @Override
  public String getName() {
      return "포치";
  }
}

@Module
public class SampleModule {

  @Provides
  Pet providePet() {
      return new Dog();
  }
}

public class Owner {

  private Pet pet;

  @Inject
  public Owner(Pet pet) {
      this.pet = pet;
  }

  public String getPetName() {
      return pet.getName();
  }
}   ```
  • 구현 클래스가 아닌 인터페이스로만 의존성을 변경하였습니다.
  • 여러가지 컴포넌트를 이용해서 주입을 변경해도 되지만 그래들에서 제공하는 플래버를 이용해 보겠습니다.

4. Build Variants 를 이용해서 주입을 변경해보자

  • 테스트 또는 저장소 변경등을 쉽게 할 수 있다.
  • 그래들 변경

gradle flavorDimensions "mode" productFlavors { dog { dimension "mode" } cat { dimension "mode" } }

  • src 폴더 아래 dog/java ,cat/java 폴더 생성(패키지 이름까지 동일하게 처리 해야 한다.)
  • View → Tool Windows → Build Variants에서 추가된 내용을 확인 할 수 있다.
  • main 폴더의 sampleModule 를 제거 한다.
  • cat, dog 폴더에 각각 추가한다.
  • 플래버 변경 만으로 원하는 인터페이스 모듈 주입 가능합니다.

PyeongHo

즐겁게 또 즐겁게