[복습]
Spring
IOC : Inversion of Control
- 역 제어, 제어의 역행, 제어의 반전
- 기존 제어 방식 vs 제어의 역행(IOC)
- 기존 제어 방식 : 필요 시 생성 - 의존 대상 객체를 사용자가 new 하여 생성하거나, getInstance()를 통해 객체를 생성함
- IOC : 필요 시 IOC 컨테이너가 반환해줌 - 사용자에게 의존 대상 객체를 반환 받음
ex) 여행을 할 때, 항공권이 필요함 (대한항공을 먼저 끊었으나, 일정 변경으로 아시아나로 변경)
- 기존 제어 방식 : 여행자가 대한항공 항공권을 끊었다가, 다시 아시아나 항공권으로 변경함
- IOC 방식 : 여행자는 대행업체를 통해 항공권을 예매함. 대항항공 항공권에서 아시아나 항공권으로 변경은 대행업체에서 변경해줌.
- IOC 방식 사용 이유 : 결합도를 낮추고, 유지 보수성을 향상한다.
- IOC를 활용할 수 있는 것이 DI와 DL(Depency Lookup)이다. : 실무에서 DI를 더 많이 쓴다.
DI : Dependency Injection
의존성 주입, IOC를 실현하기 위함이다.
Maven(메이븐) = Dependency Management
1. 의존성 관리
2. 어플리케이션이 필요한 많은 라이브러리를 일괄적으로 관리
여행을 할 때, 항공권이 필요함 (대한항공을 먼저 끊었으나, 일정 변경으로 아시아나로 변경)
- IOC 방식
: 여행자는 대행업체를 통해 항공권을 예매함. 대항항공 항공권에서 아시아나 항공권으로 변경은 대행업체에서 변경해줌.
이 상황을 코드로 DI를 적용해서, 실현해보자 !
Class Diagram
[ 객체 주요 요소 ]
Spring Container (IOC) ⇔ Spring Config (ioc.xml) | ||
IOC - TestIOC(main) | Person | <<interface>> Ticket |
DI | name | OZTicket (implements Ticket) |
DL | ticket | KETicket (implements Ticket) |
setName(name) | ||
setTicket(ticket) |
IOC : 사용자에게 객체가 반환되는 것
DL : TestIOC.java에서 person객체를 factory.getBean()을 통해, 객체를 찾음
DI : StringContainer (ioc.xml)에 설정파일이 있고, Person 객체를 만들 때, setName(), setTicket()을 통해 값을 주입
[ 실행 순서 ]
1. TestIOC.java
- main 실행
- ioc.xml spring config 생성
2. ioc.xml
- <bean> 에서 Person 객체 생성
- <property> 를 통해 Person 요소 중 name주입 -DI방식
- <property>에서 ticket을 받기 위해, <bean>에서 Ticket 객체 생성 = ticket
- <property> 를 통해 Person 요소 중 ticket 주입 - DI방식
: 주입 시, Person.java에서 setter를 통해 Person 객체가 완성됨
3. TextIOC.java
- DL방식의 getBean()을 통해 Person객체 확보
/model
/Ticket.java <<interface>>
package model;
public interface Ticket {
public void ticketing();
}
name or ticket을 set할 때, Spring IOC Container로부터 주입받는다.
/Person.java
package model;
public class Person {
private String name;
private Ticket ticket;
public String getName() {
return name;
}
/**
* name을 Spring IOC Container로부터 주입받는다.
* (DI:Dependency Injection 방식)
* @param name
*/
public void setName(String name) {
this.name = name;
}
public Ticket getTicket() {
return ticket;
}
/**
* ticket을 Spring IOC Container로부터 주입받는다.
* @param ticket
*/
public void setTicket(Ticket ticket) {
this.ticket = ticket;
}
}
/KETicket.java
package model;
public class KETicket implements Ticket {
@Override
public void ticketing() {
System.out.println("대한항공 티켓을 예매하다.");
}
}
/OZTicket.java
package model;
public class OZTicket implements Ticket {
@Override
public void ticketing() {
System.out.println("아시아나 티켓을 예매하다.");
}
}
/test
/TestIOC.java
package test;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import model.Person;
public class TestIOC {
public static void main(String[] args) {
//Spring IOC Container
//: 시작시점의 spring config(설정파일)인 ioc.xml을 로딩한다.
ClassPathXmlApplicationContext factory
= new ClassPathXmlApplicationContext("ioc.xml");
// DL(Dependency Loopup) 방식으로
// 의존 대상을 검색과정을 통해 확보한다.
Person p = (Person) factory.getBean("person");
// DI : ioc.xml에서 주입을 통해 결과 확보.
System.out.println(p.getName());
p.getTicket().ticketing();
//factory = ioc container 닫기
factory.close();
}
}
SpringBean Configuration file
설정방법
<!-- Spring Container에게 명령하는 부분 -->
<bean id="[getBean의 대상명]" class=[의존대상객체 path] >
<property name="[의존대상객체 path의 attribute]" value="[할당 value]"/>
<property name="[의존대상객체 path의 attribute]" ref="[bean에 할당된 id]"/>
</bean>
<bean id="[property에 할당할 id]" class="[의존대상 객체 path]"></bean>
/ioc.xml
<bean> = DL 방식 (Person객체를 검색하게끔 - TestIOC에서 getBean을 통해 확보)
<property> = DI 방식 (name과 ticket을 주입해줌)
1) name에 아이유, ticket에 model.OZTicket을 넣으면,
TestIOC.java에서 실행 시, 결과가 아래와 같이 나온다.
아이유
아시아나 티켓을 예매하다.
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
<!-- Spring Container에게 명령하는 부분 -->
<!-- <bean id="[getBean의 대상명]" class=[의존대상객체 path] ></bean> -->
<bean id="person" class="model.Person">
<!-- <property name="[[의존대상객체 path의 attribute]" value="[할당 value]"/> -->
<property name="name" value="아이유"/>
<!-- <property name="[[의존대상객체 path의 attribute]" ref="[bean에 할당된 id]"/> -->
<property name="ticket" ref="ticket"/>
</bean>
<bean id="ticket" class="model.OZTicket"></bean>
</beans>
1) name에 아이유, ticket에 model.KETicket을 넣으면,
TestIOC.java에서 실행 시, 결과가 아래와 같이 나온다.
수지
대한항공 티켓을 예매하다.
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
<!-- Spring Container에게 명령하는 부분 -->
<!-- <bean id="[getBean의 대상명]" class=[의존대상객체 path] ></bean> -->
<bean id="person" class="model.Person">
<!-- <property name="[[의존대상객체 path의 attribute]" value="[할당 value]"/> -->
<property name="name" value="수지"/>
<!-- <property name="[[의존대상객체 path의 attribute]" ref="[bean에 할당된 id]"/> -->
<property name="ticket" ref="ticket"/>
</bean>
<bean id="ticket" class="model.KETicket"></bean>
</beans>
'Java Web Programming > 6. Spring | MyBatis' 카테고리의 다른 글
[Spring] 비즈니스 로직 계층 추가 (IOC, DI+DL) (0) | 2020.10.27 |
---|---|
[Spring] 생성자를 통한 DI/DL 적용(constructor-arg) + IOC + maven (0) | 2020.10.27 |
[Spring] 메이븐 maven 형식, Spring IOC 개발단계 (0) | 2020.10.27 |
[Framework/Spring] IOC / DI 의 개념과 활용 (0) | 2020.10.26 |
[Framework/Spring] Eclipse 이클립스에서 Spring 스프링 프레임워크 환경 설정 (0) | 2020.10.26 |