일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | |||||
3 | 4 | 5 | 6 | 7 | 8 | 9 |
10 | 11 | 12 | 13 | 14 | 15 | 16 |
17 | 18 | 19 | 20 | 21 | 22 | 23 |
24 | 25 | 26 | 27 | 28 | 29 | 30 |
- 슬픔의 후에
- db
- nginx
- 인덱스
- 말 더듬
- DBMS
- index
- 스위트라떼
- IT
- SQL 처리
- 장범준
- 레이디스코드
- DBMS 구성요소
- 러블리즈
- 오라클 아키텍처
- 핑거스타일
- Inside Of Me
- 천공의 시간
- 신입
- 오라클
- 악보
- 6학년 8반 1분단
- I'm fine thank you
- 데이터베이스
- 아이유
- 봄 사랑 벚꽃 말고
- 니가 참 좋아
- oracle
- 기타
- 개발자
취미로 음악을 하는 개발자
[Spring Boot] 의존 주입 방법 본문
Spring과 Spring Boot의 의존 주입 차이
1) Spring
- bean configuration xml을 이용한 의존 주입
- 자바 코드를 이용한 의존 주입
- 어노테이션을 이용한 의존 주입
2) Spring Boot
- 자바 코드를 이용한 의존 주입
- 어노테이션을 이용한 의존 주입
@SpringBootApplication
: 아래와 같은 기능을 동시에 실행
@Configuration
: 자바 코드로 작성된 클래스를 스프링 설정으로 사용함을 의미
@EnableAutoConfiguration
: Spring Application Context를 만들 때 지정해 둔 설정 값들을 이용하여 자동으로 설정하는 기능을 킴
@ComponetScan
: 지정한 위치 이하에 있는 @Component와 @Configuration이 붙은 클래스를 스캔해서 Bean으로 등록
프로젝트 생성
코드 구현
1 2 3 4 5 | package com.study.springboot.bean; public interface Printer { public void print(String message); } | cs |
1 2 3 4 5 6 7 8 | package com.study.springboot.bean; public class PrinterA implements Printer{ @Override public void print(String message) { System.out.println("Printer A : " + message); } } | cs |
* PrinterB는 A에서 B로만 바꿔주시면 됩니다.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 | package com.study.springboot.bean; public class Member { private String name; private String nickname; private Printer printer; public Member() {} public Member(String name, String nickname, Printer printer) { this.name = name; this.nickname = nickname; this.printer = printer; } public String getName() { return name; } public void setName(String name) { this.name = name; } public String getNickname() { return nickname; } public void setNickname(String nickname) { this.nickname = nickname; } public Printer getPrinter() { return printer; } public void setPrinter(Printer printer) { this.printer = printer; } public void print() { printer.print("Hello " + name + " : " + nickname); } } | cs |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 | package com.study.springboot.bean; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; // 클래스를 스프링 설정으로 사용함 @Configuration public class Config { // 메소드의 리턴 값을 빈 객체로 사용함 @Bean public Member member1() { // Setter Injection (Setter 메소드를 이용한 의존성 주입) Member member1 = new Member(); member1.setName("홍길동"); member1.setNickname("도사"); member1.setPrinter(new PrinterA()); return member1; } @Bean(name="hello") // 별도의 이름으로 Bean 등록 public Member member2() { // COnstructor Injection (생성자를 이용한 의존성 주입) return new Member("전우치", "도사", new PrinterA()); } @Bean public PrinterA printerA() { return new PrinterA(); } @Bean PrinterB printerB() { return new PrinterB(); } // bean : Spring이 IoC 방식으로 관리하는 객체 // beanFactory : 스프링의 IoC를 담당하는 핵심 컨테이너 // Applicationontext : beanFactory를 확장한 IoC 컨테이너 } | cs |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 | package com.study.springboot; import org.springframework.context.ApplicationContext; import org.springframework.context.annotation.AnnotationConfigApplicationContext; import com.study.springboot.bean.Config; import com.study.springboot.bean.Member; import com.study.springboot.bean.Printer; //@SpringBootApplication public class Ex02JavaCodeDiApplication { public static void main(String[] args) { //SpringApplication.run(Ex02JavaCodeDiApplication.class, args); // 1. IoC 컨테이너 생성 ApplicationContext context = new AnnotationConfigApplicationContext(Config.class); // 2. Member Bean 가져오기 Member member1 = (Member)context.getBean("member1"); member1.print(); // 3. Member Bean 가져오기 Member member2 = context.getBean("hello", Member.class); member2.print(); // 4. PrinterB Bean 가져오기 Printer printer = context.getBean("printerB", Printer.class); member1.setPrinter(printer); member1.print(); // 5. 싱글톤인지 확인 if (member1 == member2) System.out.println("동일"); else System.out.println("다른 객체"); } } | cs |
@SpringBootApplication은 자동으로 Bean을 검색하고 등록하므로 잠시 주석처리를 했고
수동으로 작업하면서 결과를 보도록 한다.
1번은 Config.class를 통해 변수 context의 컨테이너를 생성하는 코드다. 실행하면 아래와 같은 결과가 나온다.
1 2 3 4 5 6 7 8 9 10 11 | 22:59:31.108 [main] DEBUG org.springframework.context.annotation.AnnotationConfigApplicationContext - Refreshing org.springframework.context.annotation.AnnotationConfigApplicationContext@5f150435 22:59:31.141 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'org.springframework.context.annotation.internalConfigurationAnnotationProcessor' 22:59:31.402 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'org.springframework.context.event.internalEventListenerProcessor' 22:59:31.405 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'org.springframework.context.event.internalEventListenerFactory' 22:59:31.409 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'org.springframework.context.annotation.internalAutowiredAnnotationProcessor' 22:59:31.410 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'org.springframework.context.annotation.internalCommonAnnotationProcessor' 22:59:31.418 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'config' 22:59:31.426 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'member1' 22:59:31.458 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'hello' 22:59:31.459 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'printerA' 22:59:31.460 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'printerB' | cs |
* 참고로 필자는 처음 실행할 때 bean객체를 찾지 못해서 오류가 떴었는데 이클립스를 재시작하니까 해결되었다.
2번부터 실행하면 각 bean 객체의 메소드를 호출하는데 getBean에 들어가는 파라미터는 bean객체의 메소드 이름을 뜻한다.
참고로 3번의 member2는 'Hello'라는 이름을 사용했기 때문에 'Hello'가 나온 것이고 나머지는 함수의 이름이 출력되었다.
Bean, BeanFactory, ApplicationContext
1) Bean
: Spring이 IoC 방식으로 관리하는 객체 or Spring이 직접 생성과 제어를 담당하는 객체
2) BeanFactory
: Spring의 IoC를 담당하는 핵심 컨테이너를 가리킴
- Bean을 등록, 생성, 조회, 반환하는 기능을 담당
- 이 BeanFactory를 바로 사용하지 않고 이를 확장한 ApplicationContext를 주로 이용
3) ApplicationContext
: BeanFactory를 확장한 IoC 컨테이너
- BeanFactory와 다른 것은 Spring이 제공하는 각종 부가 서비스를 추가로 제공
Annotaiton으로 DI 주입 방법
프로젝트 생성
코드
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 | package com.study.springboot.bean; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Qualifier; import org.springframework.beans.factory.annotation.Value; import org.springframework.stereotype.Component; // 검색된 클래스를 빈으로 등록할 때, 클래스의 첫 글자를 소문자를 바꾼 // 이름을 빈의 이름으로 사용 @Component public class Member { @Value("홍길동") private String name; @Value("도사") private String nickname; @Autowired @Qualifier("printerA") private Printer printer; public Member() {} public Member(String name, String nickname, Printer printer) { this.name = name; this.nickname = nickname; this.printer = printer; } public String getName() { return name; } public void setName(String name) { this.name = name; } public String getNickname() { return nickname; } public void setNickname(String nickname) { this.nickname = nickname; } public Printer getPrinter() { return printer; } public void setPrinter(Printer printer) { this.printer = printer; } public void print() { printer.print("Hello " + name + " : " + nickname); } } | cs |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 | package com.study.springboot.bean; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Qualifier; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.ResponseBody; @Controller public class MyController { @Autowired Member member1; @Autowired @Qualifier("printerB") Printer printer; @Autowired Member member2; @RequestMapping("/") public @ResponseBody String root() { // 1. Member Bean 가져오기 member1.print(); // 2. PrinterB Bean 가져오기 member1.setPrinter(printer); member1.print(); // 3. 싱글톤 확인 if (member1 == member2) System.out.println("동일"); else System.out.println("다른 객체"); return "Annotation 사용하기"; } } | cs |
1 2 3 4 5 6 7 8 9 10 11 | package com.study.springboot.bean; import org.springframework.stereotype.Component; @Component("printerA") public class PrinterA implements Printer{ @Override public void print(String message) { System.out.println("Printer A : " + message); } } | cs |
* PrinterB는 PrinterA에서 A를 B로 바꿔주시면 됩니다.
// application.properties
1 | server.port=8081 | cs |
정상적으로 실행됐다면 아래와 같은 결과가 나올 것이다.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | . ____ _ __ _ _ /\\ / ___'_ __ _ _(_)_ __ __ _ \ \ \ \ ( ( )\___ | '_ | '_| | '_ \/ _` | \ \ \ \ \\/ ___)| |_)| | | | | || (_| | ) ) ) ) ' |____| .__|_| |_|_| |_\__, | / / / / =========|_|==============|___/=/_/_/_/ :: Spring Boot :: (v2.1.6.RELEASE) 2019-07-30 00:08:21.135 INFO 4980 --- [ main] c.s.s.Ex03AnnotationDiApplication : Starting Ex03AnnotationDiApplication on DESKTOP-L60ATLP with PID 4980 (C:\Users\Tom\eclipse-workspace\ex03_AnnotationDI\bin\main started by Tom in C:\Users\Tom\eclipse-workspace\ex03_AnnotationDI) 2019-07-30 00:08:21.139 INFO 4980 --- [ main] c.s.s.Ex03AnnotationDiApplication : No active profile set, falling back to default profiles: default 2019-07-30 00:08:22.650 INFO 4980 --- [ main] o.s.b.w.embedded.tomcat.TomcatWebServer : Tomcat initialized with port(s): 8081 (http) 2019-07-30 00:08:22.683 INFO 4980 --- [ main] o.apache.catalina.core.StandardService : Starting service [Tomcat] 2019-07-30 00:08:22.684 INFO 4980 --- [ main] org.apache.catalina.core.StandardEngine : Starting Servlet engine: [Apache Tomcat/9.0.21] 2019-07-30 00:08:22.840 INFO 4980 --- [ main] o.a.c.c.C.[Tomcat].[localhost].[/] : Initializing Spring embedded WebApplicationContext 2019-07-30 00:08:22.840 INFO 4980 --- [ main] o.s.web.context.ContextLoader : Root WebApplicationContext: initialization completed in 1629 ms 2019-07-30 00:08:23.173 INFO 4980 --- [ main] o.s.s.concurrent.ThreadPoolTaskExecutor : Initializing ExecutorService 'applicationTaskExecutor' 2019-07-30 00:08:23.407 INFO 4980 --- [ main] o.s.b.w.embedded.tomcat.TomcatWebServer : Tomcat started on port(s): 8081 (http) with context path '' 2019-07-30 00:08:23.410 INFO 4980 --- [ main] c.s.s.Ex03AnnotationDiApplication : Started Ex03AnnotationDiApplication in 2.844 seconds (JVM running for 4.461) 2019-07-30 00:08:51.352 INFO 4980 --- [on(9)-127.0.0.1] inMXBeanRegistrar$SpringApplicationAdmin : Application shutdown requested. 2019-07-30 00:08:51.357 INFO 4980 --- [on(9)-127.0.0.1] o.s.s.concurrent.ThreadPoolTaskExecutor : Shutting down ExecutorService 'applicationTaskExecutor' | cs |
@Component 지정된 이름으로 등록이 됨, 파라미터를 주지 않으면 해당 클래스 이름의 첫 글자가 소문자인 같은 이름으로 등록됨.
@Value Setter 역할과 같이 객체가 생성될 때 값을 지정할 수 있음.
@Autowired 자동 주입.
@Qualifier 정확한 이름으로 값을 주고싶을 때 사용
↓ 자세한 것은 이전에 작성했던 포스트에 정리를 한 것이 있으니 참고하면 좋다.
@RequestMapping url에서 파라미터에 해당하는 부분의 값이 들어왔을 때 해당 메소드를 실행
@ResponseBody restapi의 html헤더나 다른 태그가 붙지 않은 순수한 값을 리턴
'공대인 > Spring[Boot]' 카테고리의 다른 글
[Spring Boot] Model 객체 (1) | 2019.07.31 |
---|---|
[Spring Boot] 정적 리소스 (0) | 2019.07.31 |
Spring Boot 개념 정리 시작 (0) | 2019.07.29 |
[Spring] Controller 객체 구현 (2) (0) | 2019.05.28 |
[Spring] Controller 객체 구현 (1) (0) | 2019.05.28 |