본문 바로가기

IT/헤드퍼스트 디자인패턴

[디자인패턴] 프록시 패턴 Proxy pattern

안녕하세요 남갯입니다


오늘은 프록시 패턴에 대해 포스팅해보려고합니다.


사건의 발단

이전시간에 진행했던 뽑기 기계의 재고와 현재상태를 알아낼 수 있도록 해달라는 부탁이 왔습니다.


위치를 알아낼 수 있는 코드를 만들기 위해 


class GumballMachine(val location: String, val count: Int) {

}


이와같이 생성하고


class GumballMonitor(val machine: GumballMachine) {

fun report() {
println("뽑기 기계 위치: ${machine.location}")
println("현재 재고: ${machine.count}")
}

}


모니터 클래스를 생성해서 기계의 상태를 가져오는것을 만들었습니다.


fun main() {
val count = 10;
val gumballMachine: GumballMachine = GumballMachine("서울", 10)
val monitor = GumballMonitor(gumballMachine)
}


이와같이 테스트를 했더니 잘 나오는것을 확인했습니다.



사건의 발단2

하지만 발주처에서는 가만히 두지를 않겠죠? 부정확하게 말했었다고 뽑기 기계를 원격으로 모니터링하고 싶었다라는 내용이였다고 합니다. 모니터링 기능을 위해서 네트워크 연결도 했다고 수정해달라고 하네요.. 띱빡..


원격프록시를 이용하자!

조와 짐과 프랭크는 고민을 하다가 원격프록시를 통해 뽑기기계에 대한 래퍼런스를 넘겨주기로 했습니다.


원격프록시와 로컬 대변자란?

- 원격 프록시는 원격 객체에 대한 로컬 대변자 역할을 합니다. 원격 객체란 다른 주소공간에서 돌아가고 있는 원격객체를 뜻합니다.

- 로컬대변자는 어떤 메소드를 호출하면 다른 원격 객체한테 그 메소드 호출을 전달해주는 역할을 맡고 있는 객체를 로컬 대변자라고 생각하면 됩니다.


RMI

RMI라는 자바의 원격 메소드 호출을 이용하게 되면 원격 JVM에 있는 객체를 찾아서 그 메소드를 호출 가능합니다.

*RMI 용어 클라이언트 보조객체는 Stub , 서비스의 보조객체는 skeleton 이라고 부릅니다,


원격서비스 만들기

원격 서비스를 만들기위한 다섯 가지의 단계를 살펴보겠습니다.


1. 원격 인터페이스 만들기 : 원격 인터페이스에서는 클라이언트에서 원격으로 호출할 수 있는 메소드를 정의합니다. 클라이언트에서 이 인터페이스를 서비스 클래스형식으로 사용합니다. 스터브와 실제서비스에서는 모두 이 인터페이스를 구현해야합니다.


2. 서비스 구현클래스만들기 : 실제 작업을 처리하는 클래스입니다. 원격 인터페이스에서 정의한 원격 메소드를 실제 구현한 코드가 들어있는 부분입니다. 나중에 클러이언트에서 이 객체에 있는 메소드를 호출하게 됩니다. (ex gumballMachine)


3. rmic를 이용하여 스터브와 스켈레톤 만들기 : 클라이언트 서비스 '보조객체'를 생성합니다. 우리가 직접 이 클래스들을 만들거나, 클래스를 만들기 위한 소스코드를 건드릴 필요는 전혀 없습니다. jdk에 포함되어 있는 rmic툴을 실행시키면 자동으로 만들어집니다.


4. RMI 레지스트리를 실행시킵니다.  : rmiregistry는 전화번호부랑 비슷하다고 보면 됩니다. 클라이언트에서는 이 레지스트리로부터 프록시를 받아갈 수 있습니다.


5. 원격 서비스 시작 : 서비스 객체를 가동시킵니다. 서비스를 구현한 클래스에서 서비스의 인스턴스를 만들고 그 인스턴스를 RMI 레지스트리에 등록합니다. 일단 RMI 레지스트리에 등록되고 나면 클라이언트에서 그 서비스를 사용할 수 있습니다.



........