인프런 커뮤니티 질문&답변

지성 장님의 프로필 이미지

작성한 질문수

스프링 MVC 1편 - 백엔드 웹 개발 핵심 기술

스프링 MVC 전체 구조

스프링 MVC 어댑터의 활용

해결된 질문

작성

·

594

1

학습하는 분들께 도움이 되고, 더 좋은 답변을 드릴 수 있도록 질문전에 다음을 꼭 확인해주세요.

1. 강의 내용과 관련된 질문을 남겨주세요.
2. 인프런의 질문 게시판과 자주 하는 질문(링크)을 먼저 확인해주세요.
(자주 하는 질문 링크: https://bit.ly/3fX6ygx)
3. 질문 잘하기 메뉴얼(링크)을 먼저 읽어주세요.
(질문 잘하기 메뉴얼 링크: https://bit.ly/2UfeqCG)

질문 시에는 위 내용은 삭제하고 다음 내용을 남겨주세요.
=========================================
[질문 템플릿]
1. 강의 내용과 관련된 질문인가요? (예/아니오)
2. 인프런의 질문 게시판과 자주 하는 질문에 없는 내용인가요? (예/아니오)
3. 질문 잘하기 메뉴얼을 읽어보셨나요? (예/아니오)

[질문 내용]

스프링 MVC에 대해서 공부하다가 문득 궁금한 것이 생겼습니다. 스프링 MVC의 구조 중에 어댑터 패턴을 이용해 다양한 컨트롤러를 호환해서 핸들러를 반환한다고 했는데, 솔직하게 어떤 기능은 하는지 알겠으나 감이 잘 오지 않습니다.

실무에서 어댑터를 어떻게 활용하는지에 대해서 궁금증이 생겼습니다. 사실 이미 버전이 다른 컨트롤러를 어댑터를 통해서 핸들러를 찾아서 호출하는 것을 예제로 공부해 보았지만, 저에게는 조금 보충이 필요하다는 생각이 들어서 한번 질문 남겨봅니다.

답변 1

4

김영한님의 프로필 이미지
김영한
지식공유자

안녕하세요. 지성 장님

어댑터 패턴의 간단한 예제를 들어볼게요. 상황은 이렇습니다: 이미 작성된 코드가 있고, 이 코드에서 사용하는 인터페이스와 새로운 시스템에서 사용하는 인터페이스가 서로 다릅니다. 어댑터 패턴을 이용해 기존 코드를 수정하지 않고 새로운 시스템에 적용해봅시다.

예를 들어, 다음과 같은 두 가지 인터페이스가 있다고 가정해봅시다.

// 기존 인터페이스
interface OldInterface {
    void oldMethod();
}

// 새로운 인터페이스
interface NewInterface {
    void newMethod();
}

기존 시스템에서는 OldInterface를 사용한 클래스가 있습니다.

class OldSystemClass implements OldInterface {
    @Override
    public void oldMethod() {
        System.out.println("Old method executed.");
    }
}

이제 새로운 시스템에서는 NewInterface를 사용해야 합니다. 이때 어댑터 패턴을 사용하여 기존의 OldSystemClass를 새로운 시스템에 적용할 수 있습니다. 어댑터 클래스를 다음과 같이 작성해봅시다.

class Adapter implements NewInterface {
    private OldInterface oldInterface;

    public Adapter(OldInterface oldInterface) {
        this.oldInterface = oldInterface;
    }

    @Override
    public void newMethod() {
        oldInterface.oldMethod();
    }
}

이제 새로운 시스템에서 어댑터를 사용하여 기존의 OldSystemClass를 활용할 수 있습니다.

public class Main {
    public static void main(String[] args) {
        OldSystemClass oldSystemClass = new OldSystemClass();
        NewInterface adapted = new Adapter(oldSystemClass);
        adapted.newMethod(); // 출력: Old method executed.
    }
}

위 예제에서 볼 수 있듯이, 어댑터 패턴을 사용하면 기존 코드를 수정하지 않고도 새로운 시스템에 적용할 수 있습니다. 이를 통해 코드 재사용성과 유지 보수성을 향상시킬 수 있습니다.

 

추가로 스프링 MVC에서 어댑터 패턴은 다양한 컨트롤러 구현체를 동일한 인터페이스로 처리할 수 있도록 돕는 역할을 합니다. 어댑터 패턴은 기존 클래스의 인터페이스를 변경하지 않고도 그 클래스와 다른 인터페이스를 가진 클래스와 협업할 수 있게 해주는 구조 패턴입니다. 스프링 MVC에서는 이를 통해 다양한 종류의 컨트롤러를 하나의 인터페이스로 통합하여 관리할 수 있습니다.

실무에서 어댑터 패턴은 다음과 같은 상황에서 유용하게 활용됩니다:

  1. 라이브러리나 외부 시스템과의 호환성: 외부 라이브러리나 시스템과 연동할 때 해당 라이브러리나 시스템이 제공하는 인터페이스와 호환되지 않는 경우가 있습니다. 이때 어댑터 패턴을 사용하여 다양한 인터페이스를 통합하여 사용할 수 있습니다.

  2. 기존 코드 재사용: 기존에 작성된 코드가 있고, 이를 새로운 시스템에서 사용하고자 할 때 인터페이스가 다른 경우가 발생할 수 있습니다. 어댑터 패턴을 사용하여 기존 코드를 수정하지 않고도 새로운 시스템에 적용할 수 있습니다.

  3. 기능 확장: 기능 확장이 필요한 경우, 어댑터 패턴을 통해 추가적인 기능을 구현할 수 있습니다. 즉, 기존 코드를 수정하지 않고 새로운 기능을 추가할 수 있게 도와줍니다.

스프링 MVC에서 어댑터 패턴의 대표적인 예는 HandlerAdapter 인터페이스입니다. 이 인터페이스를 구현하는 클래스들은 서로 다른 종류의 컨트롤러를 처리할 수 있게 해주며, 어플리케이션에 등록된 여러 가지 HandlerAdapter들 중 적절한 것을 선택하여 요청을 처리할 수 있습니다. 이를 통해 프레임워크의 유연성이 높아지며, 다양한 컨트롤러 구현체를 효율적으로 관리할 수 있습니다.

감사합니다.

지성 장님의 프로필 이미지
지성 장
질문자

친절한 설명 정말 감사합니다.

그러면 어댑터 패턴을 사용하는 이유는 다양한 인터페이스들을 호환하기 위해 사용한다라고 이해하면 되는 건가요?

추가로 실무에서 어댑터가 실제로 어떻게 활용되고 있는지 알고 싶습니다.

김영한님의 프로필 이미지
김영한
지식공유자

안녕하세요. 지성 장님

인터페이스로 딱 맞게 떨어지면 어댑터가 필요하지 않는데, 인터페이스로 딱 맞아 떨어지지 않을 때 어댑터 패턴으로 끼워 맞출 수 있습니다.

예를 들어서 외부 라이브러리를 사용하는데, 해당 라이브러리가 우리쪽 기준과 맞지 않을 때 어댑터를 통해서 우리쪽 기준에 맞도록 맞출 수 있습니다.

중간에 어댑터가 복잡한 역할을 대신 해주는 것이지요.

쉽게 설명드리자면 인터페이스가 220V에 맞는 전원 코드라고 한다면 서로 인터페이스를 맞추기 때문에 국내에서는 아무런 문제 없이 전기를 사용할 수 있습니다. 그런데 해외 제품을 구매하거나 해외에 나가면 110V 제품이 존재하는데요. 이 경우에는 중간에 전원 어댑터(돼지코 등이 떠오르네요)를 사용해서 문제를 해결할 수 있습니다.

이런 패턴은 정해진 용도가 딱 있다기 보다는 실무에서는 이렇게 잘 맞지 않은 경우에 어댑터를 사용해서 문제를 해결할 수 있습니다.

감사합니다.