이번에는 조회한 빈이 모두 필요할때 한번에 조회하는 방법에 대해 공부해보았다.

 

스프링 빈이 다 필요한 경우가 있다.

예를 들어 할인과 관련된 서비스를 제공할 때 클라이언트가 할인의 종류를 선택할 수 있는것이다.

그렇게 되면 스프링을 사용하면 전략 패턴을 매우 간단하게 구현할 수 있다.

 

package hello.core.autowired.allben;

import hello.core.AutoAppConfig;
import hello.core.discount.DiscountPolicy;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;

import java.util.List;
import java.util.Map;

public class AllBeanTest {

    @Test
    void findAllBean() {
        ApplicationContext ac = new AnnotationConfigApplicationContext(AutoAppConfig.class, DiscountService.class);
    }

    static class DiscountService{
        private final Map<String, DiscountPolicy> policyMap;
        private final List<DiscountPolicy> policies;

        @Autowired
        public DiscountService(Map<String, DiscountPolicy> policyMap, List<DiscountPolicy> policies) {
            this.policyMap = policyMap;
            this.policies = policies;
            System.out.println("policyMap = " + policyMap);
            System.out.println("polices = " + policies);
        }
    }
}

테스트 코드 하나를 작성하고 클래스를 작성하였다.

 

policyMap = {fixDiscountPolicy=hello.core.discount.FixDiscountPolicy@55562aa9, rateDiscountPolicy=hello.core.discount.RateDiscountPolicy@655ef322}
polices = [hello.core.discount.FixDiscountPolicy@55562aa9, hello.core.discount.RateDiscountPolicy@655ef322]

이렇게 확인할 수 있었다.

 

package hello.core.autowired.allben;

import hello.core.AutoAppConfig;
import hello.core.discount.DiscountPolicy;
import hello.core.member.Grade;
import hello.core.member.Member;
import org.assertj.core.api.Assertions;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;

import java.util.List;
import java.util.Map;

public class AllBeanTest {

    @Test
    void findAllBean() {
        ApplicationContext ac = new AnnotationConfigApplicationContext(AutoAppConfig.class, DiscountService.class);

        DiscountService discountService = ac.getBean(DiscountService.class);
        Member member = new Member(1L, "userA", Grade.VIP);
        int discountPrice = discountService.discount(member, 10000,"fixDiscountPolicy");

        Assertions.assertThat(discountService).isInstanceOf(DiscountService.class);
        Assertions.assertThat(discountPrice).isEqualTo(1000);

        int rateDiscountPrice = discountService.discount(member, 20000,"rateDiscountPolicy");
        Assertions.assertThat(rateDiscountPrice).isEqualTo(2000);

    }

    static class DiscountService{
        private final Map<String, DiscountPolicy> policyMap;
        private final List<DiscountPolicy> policies;

        @Autowired
        public DiscountService(Map<String, DiscountPolicy> policyMap, List<DiscountPolicy> policies) {
            this.policyMap = policyMap;
            this.policies = policies;
            System.out.println("policyMap = " + policyMap);
            System.out.println("polices = " + policies);
        }

        public int discount(Member member, int price, String discountCode){
            DiscountPolicy discountPolicy = policyMap.get(discountCode);
            return discountPolicy.discount(member, price);
        }
    }
}

DisCountService는 Map으로 모든 DiscountPolicy를 주입받는다.

이때 fix..와 rate...모두가 주입된다.

discount() 메서드는 discountCode로 fixDiscountPolicy가 넘어오면 map에서 fixDiscountPolicy 스프링 빈을 찾아서

실행한다. 물론 rateDiscountPolicy가 넘어오면 rateDiscountPolicy 스프링 빈을 찾아서 실행한다.

 

굉장히 편하게 스프링이 빈에 등록된 것들을 불러와서

유연한 전략패턴을 발휘할 수 있게 된다.

 

+ Recent posts