스프링은 자바 소프트웨어 개발을 편하게 해주는 오픈소스 프레임워크이다. 스프링의 목적은 애플리케이션 개발의 복잡함을 줄여주고, 효과적으로 대응하게 해주는 것이다.
8.1 POJO 프로그래밍
스프링의 주요 기술인 IoC/DI, AOP, 서비스 추상화는 애플리케이션을 POJO로 개발할 수 있게 해주는 가능기술이라고 불린다.
8.1.1 POJO란 무엇인가?
POJO는 Plain Old Java Object의 첫 글자를 떠서 만든 약자이다. 단순하게 보자면 그냥 평범한 자바 오브젝트라고 할 수 있지만, 좀 더 명확하게 하자면 다음의 세 가지 조건을 충족해야 POJO라고 불릴 수 있다.
- 특정 규약(기술)에 종속되지 않는다.
-> POJO는 자바 언어와 꼭 필요한 API 외에는 종속되지 않아야 한다. - 특정 환경에 종속되지 않는다.
-> 비즈니스 로직을 담은 코드에 HttpServletRequest나 HttpSession, 캐시와 관련된 API가 등장하거나 웹 프레임워크의 클래스를 직접 이용하는 부분이 있다면 그것은 진정한 POJO가 아니다. - 책임과 역할이 분리되고, 필요에 따라 재활용될 수 있어야한다.
-> 객체지향적이어야 한다.
스프링은 사용한다고 객체지향적 POJO 프로그래밍에 대한 부담이 줄어드는 건 아니다. 대신 스프링은 개발자들이 복잡한 엔터프라이즈 기술보다는 이러한 객체지향적인 설계와 개발의 원리에 좀 더 집중할 수 있도록 기회를 준다. 스프링이 제공하는 기술들은 자연스럽게 객체지향적인 설계원리를 따라가도록 이끌어주기도 한다.
8.2 스프링의 기술
POJO 프로그래밍을 손쉽게 할 수 있도록 지원하는 세 가지 가능 기술에 대해 알아보자.

8.2.1 제어의 역전(IoC) / 의존관계 주입(DI)
IoC/DI는 스프링의 가장 기본이 되는 기술이나 스프링의 핵심 개발 원칙이기도 하다. 나머지 두 가지 기술 AOP와 PSA도 IoC/DI에 바탕을 두고 있다. 3대 기술은 아니지만 자주 등장하는 템플릿/콜백 패턴이 적용된 부분도 IoC/DI가 그 핵심 원리다.
왜 두 개의 오브젝트를 분리해서 만들고, 인터페이스를 두고 느슨하게 연결한 뒤, 실제 사용할 대상은 DI를 통해 외부에서 지정하는 것일까? 이는 유연한 확장이 가능하게 하기 위해, 즉 OCP(확장에는 열려있고 변경에는 닫혀있어야 한다.)를 지키기 위해서이다. A->B라는 의존 관계를 갖는 오브젝트 구조에서, B는 자유롭게 변경될 수 있고, B가 변경돼도 A는 아무런 영향을 받지 않고 그대로 유지 가능해야한다.
DI의 활용 방식을 살펴보자.
- 핵심 기능의 변경
DI의 가장 대표적인 적용 방법은 바로 의존 대상의 구현을 바꾸는 것이다. 서비스 오브젝트가 사용하는 DAO의 구현을 JDBC로 했다가 JPA 등으로 변경하는 것을 생각할 수 있다. - 핵심 기능의 동적인 변경
일반적인 DI를 이용한 변경 방법과는 달리, 동적으로 매번 다르게 변경할 수 있다. DI도 기본적으로는 런타임 시 동적으로 의존 오브젝트를 연결해주는 것이긴 하지만, 일단 DI 되고 나면 그 후로는 바뀌지 않는다. 하지만 DI를 잘 활용하면 애플리케이션이 동작하는 중간에 그 의존 대상을 다이내믹하게 변경할 수 있다.
(?? 잘모르겠음) - 부가기능의 추가 (프록시)
데코레이터 패턴처럼, 핵심 기능과 클라이언트 코드에는 전혀 영향을 주지 않으면서 부가적인 기능을 얼마든지 추가할 수 있다. 이러한 구조도 DI로 만들어놨기 때문에 가능한 것이며, OCP가 말하는 확장에 열려 있다는 것은 핵심 기능을 변경해서 쓰는 수준만을 말하는 게 아님을 기억해야한다. - 인터페이스의 변경
클라이언트가 사용하는 인터페이스와 실제 오브젝트 사이에 인터페이스가 일치하지 않는 경우에도 DI가 유용하다. 인터페이스를 구현했으면서 내부에서 실제 오브젝트를 호출해주는 기능을 가진 어댑터 오브젝트를 만들어 클라이언트에 DI해주면 된다. 서비스 추상화(PSA)가 DI를 통해 어댑터 역할을 하는 오브젝트를 이용하게 해준다. 이를 통해서 다른 인터페이스를 가진 로우레벨의 기술을 변경하거나 확장해가면서 사용할 수 있다. - 템플릿과 콜백
반복적으로 등장하지만 항상 고정적인 작업 흐름과 그 사이에서 자주 바뀌는 부분을 분리해서 템플릿과 콜백으로 만들고 이를 DI 원리를 응용하면 코드를 간결하게 만들 수 있다. - 싱글톤과 오브젝트 스코프
DI가 필요한 중요한 이유 중 한 가지는 DI할 오브젝트의 생명주기를 제어할 수 있다는 것이다. DI를 프레임워크로 이용한다는 것은 DI 대상 오브젝트를 컨테이너가 관리한다는 의미이다.
스프링의 DI는 기본적으로 싱글톤으로 오브젝트를 만들어서 사용하게 한다. 단일 싱글톤이 아니라 임의의 생명주기를 갖는 오브젝트가 필요할 때에도 스프링에서는 다양한 스코프를 갖는 오브젝트를 만들어 DI에 사용할 수 있다. - 테스트
여타 오브젝트와 협력해서 동작하는 오브젝트를 효과적으로 테스트하는 방법은 가능한 한 고립시키는 것이다. 의존 오브젝트를 대신해서 스텁 또는 목 오브젝트 같은 테스트 대역을 활용하는데, 이때 DI는 중요한 역할을 한다. DI를 위해 만든 수정자 메소드를 사용하면 테스트 코드 안에서 수동으로 목 오브젝트를 주입할 수 있다.
8.2.2 애스펙트 지향 프로그래밍(AOP)
스프링의 AOP는 스프링이 POJO 프로그래밍을 지원하려는 그 핵심 목적을 위해 중요한 역할을 한다. AOP를 자바 언어에 적용하는 기법은 크게 두 가지로 분류할 수 있다.
- 스프링과 같이 다이내믹 프록시를 사용하는 방법
- 자바 언어의 한계를 넘어서는 언어의 확장을 이용하는 방법
'Coding > 개발 서적' 카테고리의 다른 글
| [토비의 스프링 3.1 Vol 1] 07장.스프링 핵심 기술의 응용 (1) | 2025.05.19 |
|---|---|
| [Real MySQL 8.0 V1] 09장. 옵티마이저와 힌트 (0) | 2025.05.16 |
| [Real MySQL 8.0 V1] 08장. 인덱스 (0) | 2025.05.01 |
| [Real MySQL 8.0 V1] 05장. 트랜잭션과 잠금 (0) | 2025.04.21 |
| [토비의 스프링 3.1 Vol 1] 06장. AOP (1) | 2025.04.16 |