[Spring Boot] Spring PSA
이번 포스팅에선 IoC & DI, Spring AOP 와 함께 Spring 의 3대 특징인 Spring PSA 에 대해서 살펴보려고 한다.
Spring PSA 란?
Spring PSA 는 Portable Service Abstraction 의 약자로 휴대용 서비스 추상화라는 의미를 가진다.
우선, 서비스 추상화란 무엇일까? 특정 서비스가 추상화되어있다는 것은 서비스의 내용을 모르더라도 해당 서비스를 이용할 수 있다는 것을 의미한다. 예를 들어, 우리는 JDBC Driver 를 사용해 데이터베이스에 접근하지만 JDBC Driver 가 어떻게 구현되어 있는지는 관심이 없다. 실제 구현부를 추상화 계층으로 숨기고 핵심적인 요소만 개발자에게 제공함으로써 실제 구현부를 모르더라도 해당 서비스를 이용할 수 있도록 하는 것이다.
그러면 이러한 서비스 추상화에 Portable 이 붙으면 무엇을 의미하는지 이야기해보자.
Portable 은 휴대용이라는 의미로 JDBC Driver 의 종류를 비즈니스 로직의 수정없이 언제든지 변경할 수 있는 것을 의미한다. 즉, MySQL Driver 를 사용하다가 어느순간 Oracle Driver 로 변경한다고 해서 프로젝트의 비즈니스 로직에 변화가 없다는 것이다.
이런 기능이 가능한 것은 추상화 계층이 존재하기 때문이다. 모든 JDBC Driver 는 공통적인 인터페이스를 가지고 있기 때문에 해당 인터페이스를 구현하는 어떤 것으로 대체되든 프로젝트에 영향이 없어지는 것이다.
이러한 점에서 Spring PSA 는 확장에는 열려있고 수정에는 닫혀있어야 한다는 OCP 에 대표적인 예시라고 할 수 있다.
Spring PSA 를 왜 사용할까?
위에서도 언급하긴 했지만 서비스를 추상화함으로써 개발자가 실제 구현부를 알지 못하더라도 해당 기능을 사용할 수 있게된다. 즉, 추상화 계층인 인터페이스 API 의 정보를 활용해 해당 서비스의 모든 기능을 이용하면 되는 것이다.
또한, PSA 는 해당 추상화 계층을 구현하는 또 다른 서비스로 언제든지 교체할 수 있게 해준다. 비즈니스 로직의 수정도 없이 말이다.
위에서 잠깐 예시를 든 JDBC Driver 이외의 또 다른 예시를 들어보자면 @Cacheable 어노테이션을 들 수 있다.
비즈니스 로직의 특정 메소드의 결과를 캐싱하고 싶을 때 @Cacheable 어노테이션을 사용한다. 현재 EhCache 를 사용해 로컬캐시를 사용하고 있다고 했을 때 이를 Redis 로 바꾸고 싶다. 그러면 해당 비즈니스 로직을 모두 수정해야할까?
아니다. 단순히 CacheManager 만 EhCacheCacheManager 에서 RedisCacheManager 로 교체해주면 된다.
Spring PSA 의 구현방법
Spring PSA 는 추상화 계층을 추가해 서비스를 추상화하고 여러 서비스를 비즈니스 로직을 수정하지 않고 교체할 수 있도록 하는 것을 의미한다. 즉, 추상화 계층의 핵심사항이다. 그림으로 살펴보자.
핵심은 추상화 계층의 인터페이스인 FlatformTransactionManager 인터페이스를 두고 이를 구현하는 다양한 서비스의 비즈니스 로직을 추상화 해두었다는 것이다. 개발자는 단순히 FlatformTransactionManager 를 선언해서 이용하면 되고 언제든지 이를 구현하는 또 다른 구현체로 바꿀 수 있다.
그럼 내가 JDBC Driver 의 예시에 대해서 살펴보자.
위에서 소개한 두 가지 예시를 통해서 Spring SPA 가 어떻게 맞물려 돌아가는지 이해할 수 있을 것이다.
이외에도 Tomcat 과 Netty 를 의존성만 변경하면 사용할 수 있는 것도 Spring PSA 를 통해 추상화되어있기 때문에 가능하다. 이처럼 Spring PSA 는 복잡한 구현로직을 수정하지 않고도 손쉽게 서비스를 변경할 수 있도록 해준다.
나중에 드는 생각인데..
가장 먼저 소개한 예시인 JDBC Driver 에 대한 것은 Spring PSA 가 아니라 Java 기술이 아닌가..? 라는 생각을 하게 되었다. 예시를 들 때는 @Transactional, @Cacheable 와 같은 예시를 드는 것이 더 적절해 보인다.
JDBC Driver 는 뭔가 비슷하면서 묘하게.. 다른....? 좀 더 고민해봐야겠다!!