: ๊ฐ์ฒด(Bean)๋ฅผ ์์ฑ ๋ฐ ๊ด๋ฆฌํ๊ณ ์์กด์ฑ์ ์ฃผ์
ํ๋ ์ญํ
์ฌ๊ธฐ์ ์ด ๋น์ ๋ง๋๋ ๊ฒ์ ๋ด๋น์๋ ๋ฐ๋ก ์คํ๋ง ์ปจํ
์ด๋์ใ
: Spring ์ปจํ
์ด๋๊ฐ ๊ด๋ฆฌํ๋ ๊ฐ์ฒด
โ ์๋๋ ๊ทธ๋ฅ ์๋ฐ ๊ฐ์ฒด๊ฐ ์คํ๋ง์ ๋ง๋์ ์คํ๋ง์ด ์ด ๊ฐ์ฒด๋ฅผ ๊ด๋ฆฌํ๊ฒ ๋๋ฉด์ ๊ทธ ์๊ฐ๋ถํฐ ๊ฐ์ฒด๊ฐ ์๋๋ผ ๋น์ด ๋๋ ๊ฒ!
(new ํค์๋๋ฅผ ์ฐ์ง ์๊ณ ๋ ์ฌ์ฉํ ์ ์๋ค)
< Spring Bean์ ํน์ง >
1. Spring ์ปจํ ์ด๋์ ์ํด ์์ฑ๋๊ณ ๊ด๋ฆฌ๋๋ค.
2. ๊ธฐ๋ณธ์ ์ผ๋ก Singleton์ผ๋ก ์ค์ ๋๋ค.
3. ์์กด์ฑ ์ฃผ์ (DI)์ ํตํด ๋ค๋ฅธ ๊ฐ์ฒด๋ค๊ณผ ์์กด ๊ด๊ณ๋ฅผ ๋งบ์ ์ ์๋ค.
4. ์์ฑ, ์ด๊ธฐํ, ์ฌ์ฉ, ์๋ฉธ์ ์๋ช ์ฃผ๊ธฐ๋ฅผ ๊ฐ์ง๋ค.
Bean์ ํญ์ ์ฑ๊ธํค
์๋ ๋น ๋ฑ๋ก์ด ์๋ ๋น ๋ฑ๋ก์ ์ค๋ฒ๋ผ์ด๋ฉ ํด์ ์ฐ์ ๊ถ
-> ์ข ๋ ์์ธํ ์์ฑ๋ ๋น์ด ์ฐ์ ์ผ๋ก ์คํ๋๋ค๊ณ ์๊ฐํ๋ฉด๋จ์ฌ
๋น์ ์ฐ๋ฉด ๊ฒฐํฉ๋๋ฅผ ๋ฎ์ถ๊ณ ์์ง๋๋ฅผ ๋์ฌ์ ๋
๋ฆฝ์ฑ์ ๋์ผ ์ ์์ผ
singletonํจํด์ ๊ฐ์ง๋๋ฐ ์ด๊ฑฐ ๋๋ถ์ ์ฌ๊ธฐ์ ๊ธฐ์ ๋ง ํ๋์ ๊ฐ์ฒด๋ฅผ ๊ณต์ ํด๊ฐ์ง๊ณ ๋ง ์ธ์์์
์์กด์ฑ ์ฃผ์ (DI)๊ณผ ์ ์ด์ ์ญ์ (IoC)์ ํตํด ๋ค๋ฅธ ๊ฐ์ฒด๋ค๊ณผ ์์กด ๊ด๊ณ๋ฅผ ๋งบ์ ์ ์๋ค
: ๊ฐ์ฒด์ ์์ฑ๊ณผ ๊ด๋ฆฌ ๊ถํ์ ๊ฐ๋ฐ์๊ฐ ์๋ Spring ์ปจํ
์ด๋๊ฐ ๋ด๋นํ๋ ๊ฒ
์ฆ, ์คํ๋ง์ด ๊ฐ์ฒด๋ฅผ ๋์ ๊ด๋ฆฌํ๊ฒ ํ๋ ๊ฒ
: Spring์ด ๊ฐ์ฒด ๊ฐ์ ์์กด์ฑ์ ์๋์ผ๋ก ์ฃผ์
ํด์ฃผ๋ ๊ฒ
์คํ๋ง์ด ์๋ง์ ๊ฐ์ฒด๋ฅผ ์์์ ๊ฐ์ ธ๋ค ์(ํด๋น ๊ฐ์ฒด๋ฅผ ์ง์ ์์ฑ(new)ํ์ง ์๊ณ Spring์ด ์ฃผ์
)
โ ๊ฐ์ฒด๋ฅผ ์ง์ ๋ง๋ค ํ์ ์์ด, ํ์ํ ๊ณณ์์ "์ด๊ฑฐ ์ฃผ์ธ์!" ํ๋ฉด ๋จ!
โ ์คํ๋ง์ด ๊ด๋ฆฌํ๋ ๊ฐ์ฒด๋ฅผ ํ์ํ ๊ณณ์ ์๋์ผ๋ก ๋ฃ์ด์ฃผ๋ ๊ฒ" (IoC์ ํ ๋ฐฉ์)
๊ฐ๋ฐ์๊ฐ ์ด ๋ฌด์จ ๊ฐ์ฒด ํ์ํ๋ค~ ํ๋ฉด ์์์ ๊ทธ๊ฑฐ์ ๋ง๋ ๊ฐ์ฒด ๊ฐ์ ธ์๊ฐ์ง๊ณ ๋ง๋ ๊ฐ์ฒด๋ฅผ ๋ฃ์ด์ค
๐ก ์ฅ์
- ์ ์ง๋ณด์๊ฐ ์ฌ์
- ๊ฒฐํฉ๋๋ฅผ ๋ฎ์ถ์ด ๋ ๋ฆฝ์ฑ์ ๋์ฌ์ค
IoC๋ ๋ ํฐ ๊ฐ๋
DI๋ IoC๋ฅผ ๊ตฌํํ๋ ๋ฐฉ๋ฒ ์ค ํ๋
๐ญ ๋น์ ํ์๋ฉด...
IoC = "ํ์ฌ๊ฐ ์ง์(๊ฐ์ฒด) ๊ด๋ฆฌ๋ฅผ ์ง์ ์ ํ๊ณ , HR(์คํ๋ง)์ด ๊ด๋ฆฌํ๊ฒ ๋งก๊ธฐ๋ ๊ฒ"
DI = "HR(์คํ๋ง)์ด ๊ฐ ๋ถ์์ ํ์ํ ์ง์(๊ฐ์ฒด)์ ์๋์ผ๋ก ๋ฐฐ์นํด ์ฃผ๋ ๊ฒ"
โ IoC โ ๊ฐ๋ฐ์๊ฐ ์ง์ ๊ฐ์ฒด๋ฅผ ๋ง๋ค์ง ์๊ณ , ์คํ๋ง์ด ์์์ ๊ด๋ฆฌ!
โ DI โ ๊ฐ๋ฐ์๊ฐ ์ง์ new ์ ํด๋, ํ์ํ ๊ฐ์ฒด๋ฅผ ์คํ๋ง์ด ์๋์ผ๋ก ์ฃผ์ !
: Spring์ด ํน์ ํจํค์ง ๋ด์์ Annotation(@Component, @Service, @Repository ๋ฑ)์ด ๋ถ์ ํด๋์ค๋ฅผ ์๋์ผ๋ก ๊ฒ์ํ๊ณ , ์ด๋ฅผ Bean์ผ๋ก ๋ฑ๋กํ๋ ๊ธฐ๋ฅ
์ด์ ํฌ๋ ํ๋ก์ ํธ๋ฅผ ๋ง๋ค๋ ํด๋์ค๋ณ๋ก @Repository @Conroller @Servie ๋ฑ์ ์ด๋
ธํ
์ด์
์ ๋ถ์ฌ์คฌ์๋ค.
์ด ์ด๋
ธํ
์ด์
์ ํตํด Spring์ด ๊ฐ ํด๋์ค๋ฅผ ๊ฐ๊ฐ์ ๋ง๋ ๋น์ผ๋ก ์๋ ๋ฑ๋กํ์๋ค
๐
ComponentScan๋๋ถ์ ๋ค๊ฐ ์ง์ Bean ๋ฑ๋ก์ ํ์ง ์์๋, Spring์ด ์ด๋ ธํ ์ด์ ์ด ๋ถ์ ํด๋์ค๋ค์ ์ฐพ์์ ์๋์ผ๋ก ๋น์ผ๋ก ๊ด๋ฆฌ!
๊ทธ๋ฌ๋๊น @Service ๊ฐ์ ๊ฑธ ๋ฌ์๋๊ธฐ๋ง ํ๋ฉด, ์คํ๋ง "์ ์ด๊ฑฐ Bean์ผ๋ก ๋ฑ๋กํ๋ผ๋๊ฑฐ๊ตฐ ใ " ํ๊ณ ์์์ ์ฒ๋ฆฌํ๋๊ฑฐ~~~ ์งฑํธํ์ฃ ?
: ํน์ ํจํค์ง๋ฅผ ์ค์บํ ๋ ์ฌ์ฉ, ๋ฐฐ์ด๋ก ์ฌ๋ฌ๊ฐ๋ฅผ ์ ์ธํ ์ ์๋ค.
์ฌ๋ฌ๊ฐ์ ํจํค์ง๊ฐ ์กด์ฌํ ๋, ์คํ๋ง์ด ์ด๋ค ํจํค์ง์์ ์ด๋ค ์ด๋
ธํ
์ด์
์ ์ฝ์ด์ผํ ์ง ํผ๋์ค๋ฝ์์? ๊ทธ๋ basePackges๋ฅผ ์ฌ์ฉํด์ ์ด๋ค ํจํค์ง์ ์๋ ๊ฒ๋ค์ ์ฌ์ฉํ ๊ฑด์ง ์ง์ ํด์ค ์ ์๋ค~~
- ์์: @ComponentScan(basePackages = {"com.example", "com.another"})
@ComponentScan์ด ์ง์ ๋ ํจํค์ง๋ฅผ ํ์๐ ComponentScan = "์ฐฝ๊ณ ์์ ์ฌ๋ฃ(๋น)๋ฅผ ๋ฏธ๋ฆฌ ์ฐพ์ ์ค๋นํ๋ ๊ด๋ฆฌ์"
๐จโ๐ณ DI = "์ํ๊ฐ ํ์ํ ์ฌ๋ฃ๋ฅผ ์์ฒญํ๋ฉด ์๋์ผ๋ก ์ ๊ณต"
โ ๊ฐ๋ฐ์๋ ์ง์ ๊ฐ์ฒด๋ฅผ ๋ง๋ค ํ์ ์์ด, ํ์ํ ๊ณณ์์ ์์ฒญ๋ง ํ๋ฉด ๋!! ๐๐ฅ
โญ๏ธ
@Autowired: ์์กด์ฑ์ ์๋์ผ๋ก ์ฃผ์ ํ ๋ ์ฌ์ฉํ๋ Annotation
๊ฐ์ฅ ๊ถ์ฅ๋๋ ๋ฐฉ์์ด๋ค
์์ฑ์๋ก ๊ฐ์ฒด๋ฅผ ๋ฐ์์ ์ฃผ์
ํ๋ ๋ฐฉ์
๊ฐ์ฅ ์์ ์ ์ด๊ณ , ๋ถ๋ณ์ฑ์ ๋ณด์ฅํ ์ ์์ด์ ์ถ์ฒ๋๋ค
@Service
public class OrderService {
private final PaymentService paymentService;
@Autowired // ๐ฅ ์์ฑ์ ์ฃผ์
public OrderService(PaymentService paymentService) {
this.paymentService = paymentService;
}
}
ํ๋์ final ์ ์์ฑ์ ์ฃผ์
๋ฐฉ์๋ง ์ฌ์ฉํ ์ ์๋ค.
:final ํ๋๋ฅผ ๋ชจ์์ ์์ฑ์๋ฅผ ์๋์ผ๋ก ๋ง๋ค์ด ์ฃผ๋ ์ญํ
Annotation Processor ๊ฐ ๋์ โ ์ปดํ์ผ ์์ ์ ์๋์ผ๋ก ์์ฑ์ ์ฝ๋ ์์ฑ
@Component
@RequiredArgsConstructor //โญ๏ธ ์์ฑ์ ์๋ ์ฃผ์
public class MyApp {
private final MyService myService;
public void run() {
myService.doSomething();
}
}
์ด๋, ํ๋์ final ํค์๋๋ ํ์!
โ ๋ฌด์กฐ๊ฑด ๊ฐ์ด ์๋๋ก ๋ง๋ค์ด์ค๋ค
Spring์์ Validation์ ํด๋ผ์ด์ธํธ ์์ฒญ ๋ฐ์ดํฐ๊ฐ ์ ํจํ์ง ํ์ธํ๋ ๊ณผ์ !
โ ์๋ชป๋ ๋ฐ์ดํฐ๋ก ์ธํด ๋ฐ์ํ ์ ์๋ ์ค๋ฅ๋ฅผ ๋ฐฉ์งํ๊ณ , ์ฌ์ฉ์ ๊ฒฝํ์ ํฅ์
๋ฏธ๋ฆฌ ์ ํด๋์ ์ฌํญ์ ๋ถํฉํ๋์ง ๊ฒ์ฆํ๋ ๊ฒ์ธ๋ฐ,
์๋ฅผ ๋ค์ด ์๋น ๋ฉ๋ดํ์ ์๋ ๋ฉ๋ด๋ฅผ ์ฃผ๋ฌธํ ์ ์๋ ๊ฒ์ฒ๋ผ, ํน์ ๋ฐ์ดํฐ ํ์๊ณผ ๊ฐ์ ์ ํจ์ฑ์ ๊ฒ์ฌํ๋๊ฒ!
โ ์ ํด์ผํ ๊น?
- ์๋ชป๋ ์ ๋ ฅ๊ฐ์ผ๋ก ์ธํด ์๋ฒ ์ค๋ฅ๊ฐ ๋ฐ์ํ๋ฉด ์ฌ์ฉ์ ๊ฒฝํ์ด ๋๋น ์ง
- ์ค๋ฅ ๋ฐ์ ์ ์์ฑ ์ค์ด๋ ๋ฐ์ดํฐ๊ฐ ์ด๊ธฐํ๋๋ฉด ๋ถํธํจ์ด ํผ
- ์ ์ ํ ๊ฒ์ฆ์ ํตํด ์ค๋ฅ๋ฅผ ๋ฐฉ์งํ๊ณ , ์ฌ์ฉ์์๊ฒ ๋ช ํํ ํผ๋๋ฐฑ์ ์ ๊ณตํด์ผ ํจ
ํ๋ก ํธ์๋ / ์๋ฒ / ๋ฐ์ดํฐ๋ฒ ์ด์ค ๊ฒ์ฆ 3๊ฐ์ง๊ฐ ์๋๋ฐ ์ด ์ค์์๋
์๋ฒ ๊ฒ์ฆ์ด ํ์์ด๋ค
โ API์์ ๋ฐ์ดํฐ ์ ํจ์ฑ ๊ฒ์ฌ ์ํ
โ ๊ฒ์ฆ ์คํจ ์ ์ ์ ํ ์๋ต์ ๋ฐํํด์ผ ํจ
: Validation ์ค๋ฅ๋ฅผ ์ ์ฅํ๋ ๊ฐ์ฒด
@ModelAttribute ๋ก ์ ๋ฌ๋ ๋ฐ์ดํฐ์์ ๊ฒ์ฆ ์ค๋ฅ๊ฐ ๋ฐ์ํ๋ฉด BindingResult ๊ฐ ์ด๋ฅผ ๋ณด๊ด!
๐ ๋ง์ฝ BindingResult๊ฐ ์์ผ๋ฉด?
์์ฒญ ๋ฐ์ดํฐ ๋ฐ์ธ๋ฉ ์คํจ ์ 400 Bad Request ๋ฐ์
์ปจํธ๋กค๋ฌ๊ฐ ํธ์ถ๋์ง ์๊ณ , ์์ธ๊ฐ ๋ฐ์ํ์ฌ ์ค๋ฅ ํ์ด์ง๋ก ์ด๋
๐ BindingResult๊ฐ ์์ผ๋ฉด!!!!
@ModelAttribute ๋ฐ์ธ๋ฉ ์ค๋ฅ ๋ฐ์ ์, BindingResult๊ฐ ์ค๋ฅ ์ ๋ณด ์ ์ฅ
์ปจํธ๋กค๋ฌ๊ฐ ์ ์์ ์ผ๋ก ํธ์ถ, ๊ฒ์ฆ ์ค๋ฅ๊ฐ ๋ฐ์ํ ํ๋๋ฅผ ์ ์ธํ ๋๋จธ์ง ๊ฐ์ด ๋ฐ์ธ๋ฉ
๐ BindingResult๋ ๊ฒ์ฆํ ๊ฐ์ฒด ๋ค์ ์์นํด์ผ๋ง ํจ
โก๏ธ ์ด๋ฌํ ๊ฒ์ฆ์ ํตํด ์ฌ์ฉ์ ๊ฒฝํ ํฅ์ ๋ฐ ์ค๋ฅ ๋ฐฉ์ง ๊ฐ๋ฅ