SPRING 입문 [ 코드로 배우는 스프링 부트 ]

[스프링 입문] 섹션 4.2 스프링 빈과 의존관계 (자바 코드로 직접 스프링 빈 등록하기)

wlalsu_u 2023. 1. 10. 06:19

4.2.1  자바 코드로 직접 스프링 빈 등록하기

 

스프링 빈을 등록하는 또 다른 방법으로,

자바 코드로 직접 등록하는 방법을 알아보고자 한다.

 

 

과거에는 xml 문서로 설정하였지만,

최근에는 주로 자바 코드를 이용하여 설정한다.

 

 

자바 코드로 직접 스프링 빈을 등록하는 방법은,
정형화 되지 않거나, 상황에 따라 구현 클래스를 변경해야 할 때 사용된다.

 

 

앞선 회원 관리 예제의 가상 시나리오에서,

 

MemoryMemberRepository를 향후 다른 Repository로 변경할 예정이므로,

컴포넌트 스캔 방식 대신 자바 코드로 스프링 빈을 설정하고자 한다.

 

 


 

 

 src  >  main  >  java  >  hello.hellospring  >  service 패키지

 

스프링 빈 등록을 위한 SpringConfig 클래스를 작성한다.

 

 

 

 

이에 앞서, 

 

앞서 섹션 4.1 에서 작성한 @Service / @Repository / @Autowired 애노테이션은 제거한다.

(Controller 클래스 제외)

 

 

+ 참고 ) Controller 는 스프링이 관리하므로, 컴포넌트 스캔으로 올라간다.

 

 

 

 

package hello.hellospring.service;


import hello.hellospring.repository.MemberRepository;
import hello.hellospring.repository.MemoryMemberRepository;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import java.util.List;
import java.util.Optional;

@Configuration
public class SpringConfig {

    @Bean
    public MemberService memberService(){
        return new MemberService(memberRepository());
    }

    @Bean
    public MemberRepository memberRepository(){
        return new MemoryMemberRepository();
    }
}

 

 

 

코드를 하나씩 자세히 살펴보자.

 

 

 

@Configuration

 

- 코드 상단에 작성

 

 

 

@Bean

 

- 스프링에게 넘어갈 때 스프링 빈에 등록하라는 뜻으로 인식

 

- memberService : 멤버 서비스를 이 로직으로 호출하여, 스프링 빈에 등록

                             : 스프링 빈에 저장된 memberRepository 와 연결

 

- memberRepository : 스프링 빈에 등록

 

 

 

 

+ 정리 )

1) Spring 이 뜨면, memberService 와 memberRepository 가 스프링 빈에 등록
2) 등록되어 있는 memberRepository 를 memberService 에 넣어줌
3) Controller 에 Autowired 로 memberService 를 넣어줌

 

 

 

 

main 메소드를 실행하면,

다음과 같이 정상적으로 작동하는 것을 확인할 수 있다.

 

 

 

 

 

 

 


 

4.2.2  DI (Dependency injection)

 

 

1) 필드 주입

 

- @Autowired 를 필드에 작성

 

- 중간에 변경이 불가능하므로, 잘 사용되지 않는다.

 

@Autowired private MemberService memberService;

 

 

 

2) setter 주입

 

- 먼저 생성된 후, setter 가 나중에 memberService 에 들어옴

 

- public 하게 노출되어 있으므로, memberService 가 바뀔 수 있다는 위험이 있음

  ( 의존관계가 실행 중에 동적으로 변하는 경우는 거의 없으므로 좋은 방법이 아님)

 

 

@Autowired
public void setMemberService(MemberService memberService) {
    this.memberService = memberService;
}

 

 

 

 

3) 생성자 주입

 

- 어플리케이션이 조립되는 시점에 한 번 들어 온 후 끝남

 

- 이후 변경 가능 하지 않게 제어할 수 있음

 

- 가장 권장되는 방법

 

 

 

 

+ 추가 )
Autowired 를 이용한 DI 는 스프링이 관리하는 객체에서만 동작
즉, 스프링 빈으로 등록하지 않고, 직접 new로 생성한 객체에서는 동작하지 않음

 

 

 

 

 

 

김영한 '스프링 입문 - 코드로 배우는 스프링 부트, 웹 MVC, DB 접근 기술' 강의를 기반으로 작성하였습니다.

https://www.inflearn.com/course/%EC%8A%A4%ED%94%84%EB%A7%81-%EC%9E%85%EB%AC%B8-%EC%8A%A4%ED%94%84%EB%A7%81%EB%B6%80%ED%8A%B8/dashboard