승상의 코딩 블로그

디자인 패턴 - 어댑터 패턴(Adapter Pattern) with 파이썬(python) 본문

Python (파이썬)

디자인 패턴 - 어댑터 패턴(Adapter Pattern) with 파이썬(python)

양승상 2023. 7. 14. 10:19
반응형

어댑터 패턴은 호환되지 않는 인터페이스를 가진 두 객체를 상호작용할 수 있도록 해줍니다.

하나의 객체의 인터페이스를 다른 객체가 원하는 인터페이스로 변환시켜준다고 생각하면 됩니다.

 

최근에는 JSON 형식의 데이터를 많이 썻지만, 예전에는 XML 형식의 데이터를 더 많이 사용했습니다.  

  • JSON 예시
    • { 
      "age": 30,
       "interests": ["reading", "traveling", "music"]
      }
  • XML 예시
    • <user>
         <age>30</age>
         <interests>  
         <interest>reading</interest>
          <interest>music</interest>
          <interest>traveling</interest>
          </interests>
      </user>

만약, JSON 의 데이터의 데이터를 제공받았는데, 사용하려는 라이브러리가 예전꺼라 XML 형식을 사용한다면 어댑터 패턴을 통해 라이브러리를 개선할 수 있습니다.

 

저희는 220V 를 쓰지만, 해외에서는 110V 를 쓰는 곳이 많습니다.

해외에 놀러간다면, 220V 제품을 110V 제품으로 새로 구매하는 것이 아니라, 220V to 110V 변환 어댑터를 구매합니다.

그리고 기존에 사용하는 220V 제품에는 어댑터만 연결하여 사용합니다.

(여기서 중요한 부분 중 하나는 사용하는 220V 제품에는 아무런 변화가 없다는 것입니다.)

 

어댑터 패턴을 코드로 살펴보겠습니다.

class Xml: # 변환하고 싶은 클래스
    def use_xml_data(self):
    	print('xml data')

class Json: # 최종적으로 원하는 클래스
    def use_json_data(self):
        print('use json data')

class XmlToJsonAdapter(Json):
    def __init__(self, xml: Xml):
        self.xml = xml

    def use_json_data(self):
    	# xml 에서 json 형태로 변환해주는 로직이 있음.
        print(f'use json data which is converted from {self.xml.use_xml_data()}')
        
def sendJson(data : Json):
    # sendJson 은 Json 클래스만을 인자로 받음.
    print(f'send {data.use_json_data()}')

if __name__ == "__main__":
    xml = Xml()
    adapter = XmlToJsonAdapter(xml)
    sendJson(adapter)
  1. sendJson 함수를 사용하려고 합니다. 하지만 Json 클래스를 매개변수로 사용하고 Json 의 특정함수(use_json_data) 를 사용하기 때문에 Xml 클래스와 호환되지 않습니다.
  2. Xml 클래스를 sendJson에서 사용하고 싶기 때문에, Json 을 상속받는 XmlToJsonAdapter 를 만듭니다.
    1. 생성자로 Xml(Adaptee) 를 인자로 받게합니다.
    2. 클래스의 use_json_data 를 재정의하여 Xml->Json 변환로직을 추가합니다.
  3. Xml 객체를 XmlToJsonAdapter 에 넣어주면, Xml 클래스도 sendJson 함수를 사용할 수 있습니다.

 

어댑터 패턴을 사용하면 가능한 기존 코드의 수정없이, 상호작용하는 인터페이스를 제공할 수 있습니다.

인터페이스 호환이 안되는데, 코드 수정이 불가한 상황은 많이 존재합니다.

  • 구매해서 사용하는 라이브러리일 경우, 소스코드가 제공되지 않을 수도 있습니다.
  • 레거시 코드일 경우, 코드 변경 자체가 금기시 될 수 도 있습니다. (변경 이후의 사이드 이펙트를 증명할 수 없는 경우가 많음.)
  • 코드 자체가 복잡할 경우, (ex. 의존성 많은 코드) 코드 수정이 어려울 수 있습니다.

 

이야기하다보니 이전에 포스팅한 퍼사드 패턴이랑 유사해보입니다.

2023.07.10 - [Python (파이썬)] - 디자인 패턴 - 퍼사드 패턴(Facade Pattern) with 파이썬(python)

 

디자인 패턴 - 퍼사드 패턴(Facade Pattern) with 파이썬(python)

Facade 는 Oxford 사전에서 아래의 의미를 가집니다. 1. the face of a building 2. an outward appearance that is maintained to conceal a less pleasant or creditable reality. - 먼가 좋지 않아보이는 것을 숨기기 위한 겉모습을

seungsang.tistory.com

퍼사드 패턴은 복잡한 하위 시스템을 통합하여 사용하기 쉬운 새로운 인터페이스를 하는 패턴이고,

어댑터 패턴은 제공된 인터페이스가 상호작용이 되지 않아 기존의 인터페이스를 변경하는 패턴입니다.

 

* 기존의 인터페이스에서 원하는 인터페이스를 위한 어댑터를 만드는 것도 좋은 방법입니다. 하지만 기존의 코드를 수정해서 사용하는 것이 더 쉬울 수도 있습니다. 상황에 따라 이 방식을 적용하는 것이 좋을지 더 좋은 방식은 없을지 고민하는 것 잊지마세요! 

반응형
Comments