정상에서 IT를 외치다

[Dagger] Dagger step2 - Cafe 예제 본문

안드로이드

[Dagger] Dagger step2 - Cafe 예제

Black-Jin 2019. 9. 16. 01:26
반응형

안녕하세요. 블랙진입니다.


지난 포스팅에서는 커피 메이커를 만들기 위해서 펌프와 히터를 사용했습니다. 이번 예제에서는 몇가지 사항을 수정해 보겠습니다.


1. 커피메이커는 히터만 있으면 동작합니다.

2. 커피를 갈때는 커피콩을 넣어주어야합니다.

3. 카페 정보를 보여주는 객체가 추가됩니다.


위 정보를 가지고 하나하나 객체를 만들어 보겠습니다.



카페를 구성하는 4가지 요소


CafeInfo


카페 정보를 가지고 있는 객체입니다. 

public class CafeInfo {

private String name;

public CafeInfo(String name) {
this.name = name;
}

public void welcome() {
System.out.println("Welcome " + (name == null ? "" : name));
}
}


 CoffeeMaker


1. CoffeeMaker는 Heater를 사용해 커피를 만듭니다. 커피를 우러낼 때(brew)에는 커피빈을 따로 받아야 됩니다. 

2. 객체의 hashCode()를 로그로 확인하는 것은 대거에 의해 어떤 객체가 잘 주입되었는지 보기 위함 입니다.

public class CoffeeMaker {

private Heater heater;

@Inject
public CoffeeMaker(Heater heater) {
this.heater = heater;
}

public void brew(CoffeeBean coffeeBean) {
if (heater == null) {
System.out.println("heater null");
} else {
System.out.println("brew");
System.out.println("coffeeMaker : " + hashCode() + " , heater : " + heater.hashCode());
System.out.println("coffeeBean name : " + coffeeBean.name() + " , hashCode : " + coffeeBean.hashCode());
}
}
}


CoffeeBean


커피콩입니다.

public class CoffeeBean {

String name() {
return "CoffeeBean";
}
}


Heater


히터입니다.

public class Heater {
}



대거 적용


1. Module


모듈은 필요한 객체를 제공하는 역활을 합니다. 우리는 CafeInfo와 CoffeeBean 그리고 Heater를 제공할 겁니다.

@Module
public class CafeModule {

@Provides
CafeInfo provideCafeInfo() {
return new CafeInfo("BlackJin");
}

@Provides
CoffeeBean provideCoffeeBean() {
return new CoffeeBean();
}

@Provides
Heater provideHeater() {
return new Heater();
}
}



2. Component


컴포넌트는 모듈에서 제공받은 객체를 조합하여 필요한 곳에 주입하는 역활을 합니다. 현재 예제에서는 다음과 같은 역활을 합니다.


1. CafeModule에서  생성한 CafeInfo, CoffeeBean 객체를 반환합니다..

2. CoffeeMaker는 Heater를 생성자 주입을 통해서 받아 생성됩니다. (예제를 보면 CoffeeMaker만 @Inject 하고 있는 것을 확인하실 수 있습니다.)

@Singleton
@Component(modules = CafeModule.class)
public interface CafeComponent {

CafeInfo cafeInfo();

CoffeeBean coffeeBean();

CoffeeMaker coffeeMaker();
}


추가 사항 적용


모듈에서 객체를 사용할 때 계속 생성해서 쓸 객체인지? 재사용해야 되는 객체인지를 정할 수 있습니다. 여기서는 @SingleTon 어노테이션을 사용해 설정할 수 있습니다.

위 예제에서는 CafeInfo, CoffeeMaker, CoffeeBean, Heater 4가지 객체가 있습니다. 여기서 카페는 오직 1개만 있고 카페에 커피 기기나 커피 콩은 여러개가 될 수 있습니다. 그러므로 카페에 @SingleTon 어노테이션을 추가해 줍니다.


1. CafeComponent에 어노테이션을 추가해 줍니다.

@Singleton
@Component(modules = CafeModule.class)
public interface CafeComponent {

//...
}


2. CafeModule에서 CafeInfo에만 어노테이션을 추가해 줍니다.

@Module
public class CafeModule {

@Singleton
@Provides
CafeInfo provideCafeInfo() {
return new CafeInfo("BlackJin");
}

//...
}



사용예제

//카페를 생성합니다.
CafeComponent cafe = DaggerCafeComponent.create();

//생성한 카페 정보를 가져옵니다.
CafeInfo cafeInfo1 = cafe.cafeInfo();
CafeInfo cafeInfo2 = cafe.cafeInfo();

cafeInfo1.welcome();
cafeInfo2.welcome();
System.out.println();

//@SingleTon 이기 때문에 두 객체는 값은 값을 반환합니다.
System.out.println("cafeInfo1 : " + cafeInfo1.hashCode() + " , cafeInfo2 : " + cafeInfo2.hashCode());

CoffeeMaker coffeeMaker1 = cafe.coffeeMaker();
CoffeeMaker coffeeMaker2 = cafe.coffeeMaker();

//같은 카페여도 다른 커피기기를 사용할 수 있으므로 매번 다른 값을 반환합니다.
System.out.println("coffeeMaker1 : " + coffeeMaker1.hashCode() + " , coffeeMaker2 : " + coffeeMaker2.hashCode());

//커피콩 또한 생성할때마다 다른 값을 반환합니다.
CoffeeBean coffeeBean = cafe.coffeeBean();

System.out.println();
coffeeMaker1.brew(coffeeBean);

System.out.println();
coffeeMaker2.brew(coffeeBean);


위 예제를 가지고 다음 포스팅에서는 대거의 좀 더 복잡한 기능들을 살펴보겠습니다.


에제에서 사용한 코드는 깃허브에서 보실 수 있습니다.


객체 그래프




반응형
Comments