💡 프록시(Proxy) = 크로스컷팅 관심사(Cross-Cutting Concern)를 제공
프록시 패턴(Proxy Pattern)은 대리 객체를 통해 원래 객체에 대한 접근을 제어하는 디자인 패턴입니다. 이 패턴은 주로 크로스컷팅 관심사(Cross-Cutting Concern)를 처리하는 데 사용됩니다.
크로스컷팅 관심사(Cross-Cutting Concern):
- 크로스컷팅 관심사는 애플리케이션의 주요 비즈니스 로직과는 직접적인 관련이 없지만, 다양한 모듈에서 반복적으로 나타나는 공통 기능을 말합니다. 대표적인 예로 로그 기록, 트랜잭션 관리, 보안 검사, 캐싱, 모니터링 등이 있습니다.
- 이러한 기능을 각 비즈니스 로직에 직접 포함시키는 대신, 프록시를 사용하여 비즈니스 로직에 영향 없이 해당 기능을 추가할 수 있습니다. 이를 통해 모듈 간의 관심사 분리가 가능해집니다.
프록시의 역할:
- 프록시는 원래 객체를 감싸고 있으며, 객체에 접근할 때 추가적인 작업(크로스컷팅 관심사)을 수행할 수 있습니다.
- 예를 들어, 데이터베이스 작업 전후에 트랜잭션을 처리하거나, 메서드 호출 전후에 로그를 기록할 수 있습니다. 이 작업은 실제 비즈니스 로직을 수행하는 원래 객체에는 영향을 미치지 않습니다.
예시: 스프링 AOP(Aspect-Oriented Programming)와 프록시
스프링 프레임워크에서는 AOP(Aspect-Oriented Programming)를 통해 프록시를 사용하여 크로스컷팅 관심사를 처리합니다. 예를 들어, 특정 메서드 실행 전후로 로깅을 하거나, 메서드 실행 시 트랜잭션 처리를 추가하는 등의 작업을 프록시를 통해 수행할 수 있습니다.
public class ServiceProxy implements MyService {
private MyService target;
public ServiceProxy(MyService target) {
this.target = target;
}
@Override
public void doSomething() {
System.out.println("Logging before method call");
target.doSomething(); // 실제 비즈니스 로직 호출
System.out.println("Logging after method call");
}
}
위 예시에서는 프록시 객체가 원래의 MyService
객체를 감싸고 있으며, 메서드 실행 전후에 로깅 작업을 추가하고 있습니다. 이렇게 크로스컷팅 관심사를 처리할 수 있습니다.
💡 어댑터(Adapter) = 특정 기능을 추가
어댑터 패턴(Adapter Pattern)은 호환되지 않는 인터페이스를 가진 객체들 사이에 상호작용을 가능하게 하는 디자인 패턴입니다. 즉, 어댑터는 기존의 인터페이스에 특정 기능을 추가하여 새로운 요구사항을 충족할 수 있도록 도와줍니다.
어댑터의 역할:
- 어댑터는 기존 클래스 또는 인터페이스를 변경하지 않고, 다른 형식의 객체와 통신할 수 있도록 새로운 기능을 추가합니다.
- 즉, 호환되지 않는 인터페이스나 기존 기능에 새로운 기능을 덧붙여서 작동하도록 만듭니다. 이를 통해 새로운 클라이언트가 기존 클래스를 사용할 수 있도록 합니다.
예시: 어댑터 패턴
// 기존 인터페이스
public interface OldInterface {
void oldMethod();
}
// 새로운 인터페이스
public interface NewInterface {
void newMethod();
}
// 어댑터 클래스
public class Adapter implements NewInterface {
private OldInterface oldInterface;
public Adapter(OldInterface oldInterface) {
this.oldInterface = oldInterface;
}
@Override
public void newMethod() {
System.out.println("New method call");
oldInterface.oldMethod(); // 기존 메서드 호출
}
}
위 코드에서 어댑터는 기존의 OldInterface
를 감싸고 있으며, 새로운 요구사항에 맞는 NewInterface
를 구현합니다. 이를 통해 기존 클래스를 수정하지 않고 새로운 기능을 추가하는 것이 가능합니다.
어댑터 패턴의 활용:
- 기존 시스템을 변경하지 않고, 새로운 기능을 유연하게 추가해야 할 때 사용됩니다. 예를 들어, 새로운 데이터베이스나 파일 시스템을 사용하는 경우, 기존 인터페이스에 대한 호환성을 유지하면서 새로운 기능을 덧붙이는 데 어댑터 패턴이 유용합니다.
💡 프록시와 어댑터의 차이점
특징 | 프록시(Proxy) | 어댑터(Adapter) |
---|---|---|
주된 목적 | 기존 객체에 추가적인 기능(크로스컷팅 관심사) 제공 | 호환되지 않는 인터페이스 간의 호환성 추가 |
동작 방식 | 원래 객체를 감싸고, 그 전후에 추가 작업 수행 | 기존 객체와 호환성 유지하며 새로운 인터페이스 구현 |
사용 사례 | AOP, 보안 검사, 트랜잭션, 로깅 등 | 기존 시스템에 새로운 기능 추가, 인터페이스 통합 |
영향을 받는 객체 | 원래 객체에 간접적으로 접근 | 기존 객체에 변화를 주지 않고 새로운 인터페이스로 감싸줌 |
결론
- 프록시 패턴은 객체를 대리하여 크로스컷팅 관심사(트랜잭션 관리, 로깅, 보안 등)를 처리하는 데 사용되며, 주로 AOP 같은 기술에서 활용됩니다.
- 어댑터 패턴은 호환되지 않는 인터페이스를 호환 가능하게 만들고, 기존 객체에 새로운 기능을 추가하는 역할을 합니다. 기존 시스템을 변경하지 않고 새로운 기능을 추가할 때 유용합니다.
'Spring Framework' 카테고리의 다른 글
XMLHttpRequest(XHR) - 비동기 자바스크립트 (3) | 2024.10.14 |
---|---|
@Valid와 @Validated (0) | 2024.10.14 |
스프링 웹 MVC (0) | 2024.10.08 |
필터와 밸브 (0) | 2024.10.08 |
AJP 커넥터 (1) | 2024.10.08 |