[Structural Patterns] - Facade

Lee Jeong Min·2022년 1월 10일
0

디자인 패턴

목록 보기
11/23
post-thumbnail

의도

파사드는 라이브러리, 프레임워크 또는 기타 복잡한 클래스 집합에 대한 단순하지만 제한된 인터페이스를 제공하는 Structural design pattern이다.

파사드는 애플리케이션 전반적인 복잡성을 줄여주기도 하며 원하지 않는 의존성을 한 곳으로 이동시키는 데도 도움이 된다.

문제

정교한 라이브러리나 프레임워크에 속하는 광범위한 객체 집합에서 코드가 작동하도록 해야 한다고 생각해 보자. 일반적으로 이러한 모든 객체를 초기화하고, 종속성을 추적하고, 메서드를 올바른 순서로 실행하는 등의 작업이 필요하다.

해결책

파사드는 많은 이동 부품을 포함하는 복잡한 하위 시스템에 단순한 인터페이스를 제공하는 클래스이다. 파사드는 서브 시스템과 직접 연동하는 것에 비해 제한된 기능을 제공할 수 있다. 하지만 고객이 진정으로 신경 쓰는 기능만 포함하고 있다.

파사드를 갖추는 것은 수십 개의 기능이 있는 정교한 라이브러리와 당신의 앱을 통합해야 할 때 편리하지만, 기능적인 부분이 조금 필요하다.

예를들어 고양이와 함께 찍은 재미있는 영상을 소셜 미디어에 업로드하는 앱은 잠재적으로 전문 비디오 변환 라이브러리를 사용할 수 있다. 그러나 실제로 필요한 것은 단일 메서드 encode(filename, format)의 클래스이다. 그런 클래스를 만들고 영상 변환 라이브러리와 연결하면 첫 번째 파사드가 나온다.

현실 유사성

전화로 주문하는 중이다.

당신이 전화 주문을 하기 위해 상점에 전화를 걸 때, 교환원은 상점의 모든 서비스와 부서에 대한 당신의 파사드(정면, 겉모습)이다. 교환원은 당신에게 주문 시스템, 결제 게이트웨이, 그리고 다양한 배송 서비스에 대한 간단한 음성 인터페이스를 제공한다.

구조

  1. 파사드는 서브시스템 기능의 특정 부분에 대한 편리한 액세스를 제공한다. 고객의 요청을 어디로 지시해야 하는지, 모든 이동 부품을 어떻게 작동해야 하는지 알고 있다.

  2. 다른 복잡한 구조를 만들 수 있는 관련 없는 기능이 있는 단일 파사드를 오염시키지 않도록 추가 파사드 클래스를 작성할 수 있다. 추가 파사드는 클라이언트와 다른 파사드 모두 사용할 수 있다.

  3. 복잡한 하위 시스템 수십 개의 다양한 객체로 구성된다. 이들 모두가 의미 있는 작업을 수행하도록 하려면 객체를 올바른 순서로 초기화하고 적절한 형식으로 데이터를 제공하는등 하위 시스템의 구현 세부 정보를 깊이 살펴봐야 한다.
    하위 시스템 클래스는 파사드의 존재를 인식하지 못한다. 시스템 내에서 작동하며 서로 직접 작동한다.

  4. 클라이언트는 서브시스템 객체를 직접 호출하는 대신 파사드를 사용한다.

적용가능성

  • 복잡한 하위 시스템에 대한 제한적이지만 간단한 인터페이스가 필요한 경우 파사드 패턴을 사용한다.

  • 하위 시스템을 레이어로 구조화하려면 파사드를 사용한다.

장단점

장점

  • 코드를 하위 시스템의 복잡성에서 분리할 수 있다.

단점

  • 파사드는 앱의 모든 클래스와 결합된 God Object가 될 수 있다.

God Object는 객체지향 프로그래밍에서 많은 수의 구별된 유형을 참조하거나 관련 없는 메서드를 모두 조합한 객체이다.

Facade in TypeScript

TypeScript의 패턴 사용

복잡도: ★☆

인기: ★★☆

사용 예: 파사드 패턴은 TS로 작성된 앱에서 일반적으로 사용도니다. 특히 복잡한 라이브러리와 API로 작업할 때 편리하다.

식별: 파사드는 인터페이스가 단순한 클래스에서 인식할 수 있지만 대부분의 작업을 다른 클래스에 위임한다. 일반적으로 파사드는 그들이 사용하는 물체의 전체 수명 주기를 관리한다.

index.ts

// 파사드 클래스는 몇몇의 하나 혹은 서브시스템의 복잡한 로직의 간단한 인터페이스를 제공한다.
// 파사드는 서브시스템 이내의 적절한 객체에 클라이언트의 요청을 위임한다.
// 이 모든 것들은 클라이언트를 서브시스템의 복잡성으로부터 방어해준다.
class Facade {
  protected subsystem1: Subsystem1;

  protected subsystem2: Subsystem2;

  // 응용 프로글매의 필요에 따라 파사드에 기존 하위 시스템 객체를 제공하거나 파사드가
  // 자체적으로 만들도록 강제할 수 있다.
  constructor(subsystem1: Subsystem1 = null, subsystem2: Subsystem2 = null) {
    this.subsystem1 = subsystem1 || new Subsystem1();
    this.subsystem2 = subsystem2 || new Subsystem2();
  }

  // 파사드 메서드는 서브시스템의 정교한 기능들의 편리한 단축키 이다.
  public operation(): string {
    let result = 'Facade initializes subsystems:\n';
    result += this.subsystem1.operation1();
    result += this.subsystem2.operation1();
    result += 'Facade orders subsystems to perform this action:\n';
    result += this.subsystem1.operationN();
    result += this.subsystem2.operationZ();

    return result;
  }
}

// SubSystem은 파사드나 클라이언트로부터 직접 요청을 수락할 수 있다.
class Subsystem1 {
  public operation1(): string {
    return 'Subsystem1: Ready!\n';
  }

  public operationN(): string {
    return 'Subsystem1: Go!\n';
  }
}

// 몇몇의 파사드들은 동시에 여러개의 서브시스템들과 작업을 할 수 있다.
class Subsystem2 {
  public operation1(): string {
    return 'Subsystem2: Get ready!\n';
  }

  public operationZ(): string {
    return 'Subsystem2: Fire!';
  }
}

function clientCode(facade: Facade) {
  console.log(facade.operation());
}

const subsystem1 = new Subsystem1();
const subsystem2 = new Subsystem2();
const facade = new Facade(subsystem1, subsystem2);
clientCode(facade);

결과

요약

파사드는 복잡한 서브 시스템을 간단하게 제어할 수 있는 제한된 인터페이스를 제공한다. 이를 통해 클라이언트는 하위 시스템들에 대한 자세한 정보 없이 필요한 부분만 호출하여 편리하게 기능을 사용할 수 있다.

참고 사이트

profile
It is possible for ordinary people to choose to be extraordinary.

0개의 댓글