제7장 가상 호스트

내용 목차

7.1. 개요
7.2. 가상 호스트의 기본 개념
7.2.1. 기본 개념
7.2.2. 기본 가상 호스트
7.2.3. ServletContext 객체와 가상 호스트에 대한 주의 사항
7.3. 가상 호스트 설정
7.3.1. 도메인 이름 등록
7.3.2. WEBMain.xml에 가상 호스트 설정
7.4. 가상 호스트를 통한 Context 요청
7.4.1. URL 매칭에 관한 기본 규칙
7.4.2. URL 매칭의 예

본 장에서는 가상 호스트에 대한 기본 개념, 기본 규칙과 구조, 기본 가상 호스트의 개념 등에 대해 설명한다.

7.1. 개요

JEUS 웹 컨테이너의 새로운 기능은 가상 호스팅이다.

기본적으로, 가상 호스트는 웹 사이트가 다른 Context에게 주어진 Context 경로뿐만 아니라 요청 주소에 있는 도메인 이름에 의해서도 연결될 수 있도록 한다. 이렇게 함으로써 2개 이상의 DNS 이름(예: “www1.foo.com” and “www2.foo.com”)을 하나의 웹 컨테이너에 설정하여 다른 Web Context를 서비스할 수 있다.

가상 호스트는 보기에 따라서 별도의 웹 컨테이너로 보일 수 있다.

7.2. 가상 호스트의 기본 개념

다음 그림은 웹 컨테이너에서 가상 호스트에 관련된 컴포넌트들을 보여주고 있다.

[그림 7.1] JEUS 웹 컨테이너의 가상 호스트 컴포넌트

JEUS 웹 컨테이너의 가상 호스트 컴포넌트


7.2.1. 기본 개념

가상 호스트의 기본적인 개념은 사용자 요청에 포함된 도메인 이름들(예, www.foo.com, www.bar.com)이나 IP 주소(예, 111.111.111.1, 111.111.111.2)에 따라 사용자 요청을 분기하는 것이다. DNS 이름을 사용한 가상 호스트와 IP 주소를 사용한 가상 호스트는 DNS 이름을 통해서 라우팅이 되는지, IP 주소를 통해서 라우팅이 되는지의 차이점을 갖지만, 궁극적인 동작 방법은 동일하다.

가상 호스트 개념의 도입으로 하나의 웹 컨테이너는 여러 도메인 이름을 가진 요청을 처리할 수 있고, 이 요청을 원하는 Context로 보낼 수 있다.

다음 그림은 가상 호스트의 기본 개념을 보여준다.

[그림 7.2] 가상 호스트의 기본적인 개념

가상 호스트의 기본적인 개념


가상 호스트의 규칙

가상 호스트를 구성할 때 적용되어야 할 기본적인 규칙은 다음과 같다.

  • 하나의 가상 호스트는 1개 이상의 DNS 이름이나 IP 주소를 가질 수 있다.

    이것을 우리는 가상 호스트의 네트워크 이름이라고 한다.

  • 가상 호스트에는 유일한 값의 가상 호스트 ID 이름을 부여한다.

    이 이름은 설정 파일 내에서 가상 호스트를 참조하기 위해서 내부적으로 사용되는 이름이다.

  • 가상 호스트는 웹 컨테이너의 Context Group에 설정된다.

    Context Group당 여러 개의 가상 호스트가 존재할 수 있지만, 한 Context Group의 모든 가상 호스트들은 유일한 네트워크 이름(DNS 이름이나 IP 주소)을 가져야 한다.

  • 각각의 가상 호스트는 반드시 하나 이상의 Context와 연계되어 있어야 한다.

    같은 가상 호스트 내의 모든 Context들은 각각 유일한 Context 이름과 경로(URI 요청 경로)를 가지고 있어야 한다. 그러나, 하나의 Context가 다른 여러 개의 가상 호스트에 존재하면 그 경로는 그 모든 가상호스트에서 동일하게 사용할 수도 있다.

다음은 위 규칙을 나타낸 그림이다.

[그림 7.3] Context Group과 가상 호스트, Context 간의 유효한 관계의 예

Context Group과 가상 호스트, Context 간의 유효한 관계의 예


위 그림에서 주의깊게 봐야 할 것은 다음과 같다.

  • 2개의 유일한 Context Group이 설정되어 있다.

    클라이언트는 이 2개의 Group을 소켓 포트 번호로 구분한다. 즉, Group A는 “80” 포트를 Group B는 “9999” 포트를 사용한다. Context Group의 웹 서버 리스너는 유일한 포트 번호를 가진다는 것에 유의한다. 자세한 내용은 “제4장 웹 서버 연결과 클러스터링”을 참조한다.

  • Context Group A는 2개의 가상 호스트가 추가되어 있다.

    2개의 가상 호스트는 유일한 네트워크 이름을 가지고 있다.Group B에는 1개의 가상 호스트(“C”)가 추가되어 있다. 이 가상 호스트는 2개의 네트워크 이름을 가지고 있다. "www.bar.com"과 "www.foo.com"이다. 이것은 Context Group 내의 다른 가상 호스트가 동일한 네트워크 이름을 가지고 있지 않기 때문이다.

  • Virtual Host A는 Virtual Host B와 함께 context B를 공유한다.

    이것은 같은 가상 호스트 내에서 Context들이 같은 URI 경로를 가지고 있지 않으면 되기 때문에 올바른 설정이다.

위의 규칙을 통해서 각 Context는 서로 구분되어 설정되었다는 것을 알 수 있다.

가상 호스트의 주된 사용

가상 호스트는 Context가 Context 경로에 의해서가 아닌 실제 DNS 이름이나 IP 주소에 의해 구분되어 사용될 때 사용되어야 한다.

예를 들어 2개의 다른 Context가 하나의 웹 컨테이너에 있고 모두 기본 Context 경로인 “/”에 의해서만 접근 가능해야 한다면, 가상 호스트를 사용하여 하나의 DNS 이름을 첫 번째 Context로, 다른 DNS 이름을 두 번째 Context로 설정하면서, 같은 웹 컨테이너가 2개의 Context를 관리하게 할 수 있다.

다음은 위 개념을 나타낸 그림이다.

[그림 7.4] 웹 컨테이너에서 DNS 이름으로 같은 경로를 가진 Context 사용

웹 컨테이너에서 DNS 이름으로 같은 경로를 가진 Context 사용


위의 그림에서는 2개의 context A, B를 가지고 있다. 2개 모두 하나의 웹 컨테이너에 존재하고 동일한 Context Group과 리스너 그리고 경로(“/”)를 가지고 있다. 차이점은 Context A는 URL http://www.foo.com/이 요청될 때 context B는 URL http://www.bar.com/이 요청될 때 사용된다는 것이다.

7.2.2. 기본 가상 호스트

기본 가상 호스트(Default virtual host)라는 묵시적인 가상 호스트가 존재한다. 이것은 비록 WEBMain.xml에 설정되어 있지 않지만 항상 존재한다. 명시적으로 Context를 가상 호스트에 할당하지 않으면, 이 기본 가상 호스트로 할당된다.

“제6장 Web Context(웹 애플리케이션)”에서 미리 봤듯이, 가상 호스트의 관계를 설정하지 않고 Context를 선언하는 것은 일반적인 일이다. 이런 모든 Context들은 기본 가상 호스트에 속한다고 생각할 수 있다.

기본 가상 호스트의 존재는 JEUS 사용자에게는 보이지 않는다.

7.2.3. ServletContext 객체와 가상 호스트에 대한 주의 사항

Servlet API를 보면 javax.servlet.ServletContext.getContext(java.lang.StringcontextPath)라는 메소드를 볼 수 있다. 이것은 “contextPath” URI에 의해 주어진 Servlet Context 를 리턴한다.

이 메소드는 그 Servlet이 속하는 현재 가상 호스트에 존재하는 Context만을 리턴한다. 유효한 Context가 이 가상 호스트 내에서 존재하지 않으면 기본 가상 호스트에서 찾는다.

이 사항은 Servlet 스펙의 요구 사항이다.

7.3. 가상 호스트 설정

가상 호스트는 WEBMain.xml에 설정된다. 이것을 작동시키기 위해서는 도메인 이름을 등록해야 한다. 그리고 가상 호스트와 Context와의 관계 설정은 JEUSMain.xml<application> 태그를 통해서 이루어진다.

참고

자세한 내용은 "JEUS Server 안내서"를 참조한다. WebAdmin을 사용하여 WEBMain.xml에 가상 호스트를 설정하려면 "JEUS WebAdmin 안내서"의 Context Group 설정 장을 참고한다.

7.3.1. 도메인 이름 등록

복수의 DNS 이름 또는 IP 주소를 가상 호스트에 사용하기 위해서는 DNS 이름을 등록해야 한다.

등록 방법에는 2가지 선택 사항이 있다.

  • DNS 서버에 웹 컨테이너의 리스너 또는 웹 서버 IP 주소 아래의 모든 DNS 이름을 등록한다.

    (예: www.foo.com과 www.bar.com)

  • 서버의 “hosts” 파일에 네트워크 이름과 IP 주소를 추가한다.

    Windows 2000에서는 c:\WINNT\system32\drivers\etc\hosts에 hosts 파일이 있다. UNIX의 경우는 /etc에 hosts 파일이 있다. 이 파일에 www.foo.com과 www.bar.com 호스트를 다음과 같이 등록한다.

    111.111.111.1   www.foo.com
    111.111.111.2   www.bar.com

7.3.2. WEBMain.xml에 가상 호스트 설정

WEBMain.xml에 가상 호스트를 설정하기 위하여 <context-group><virtual-host> 태그를 추가한다.

다음은 “7.2. 가상 호스트의 기본 개념”[그림 7.3]을 설정한 예이다.

다음의 예제에서 ContextGroup B의 가상 호스트 “C”가 어떻게 2개의 hostname을 가지는지 주의깊게 확인한다.

[예 7.1] 가상 호스트 설정 : <<WEBMain.xml>>

<web-container xmlns="http://www.tmaxsoft.com/xml/ns/jeus">
    . . .
    <context-group>
        <group-name>A</group-name>
        <virtual-host>
            <virtual-host-name>A</virtual-host-name>
            <host-list>www.foo.com</host-list>
        </virtual-host>
        <virtual-host>
            <virtual-host-name>B</virtual-host-name>
            <host-list>www.bar.com</host-list>
        </virtual-host>
        <webserver-connection>
            . . .
        </webserver-connection>
        . . .
    </context-group>
    <context-group>
        <group-name>B</group-name>
        <virtual-host>
            <virtual-host-name>C</virtual-host-name>
            <host-list>www.foo.com</host-list >
            <host-list>www.bar.com</host-list >
        </virtual-host>
        <webserver-connection>
            . . .
        </webserver-connection>
        . . .
    </context-group>
    . . .
</web-container>


다음은 설정 태그에 대한 설명이다.

  • <virtual-host>

    태그설명
    <virtual-host-name>

    가상 호스트를 참조하기 위해 내부적으로 사용하는 이름이다.

    여기에 "__DEFAULT_HOST__"를 사용해서는 안 된다. 이것은 기본 가상 호스트를 위해 사용되는 것이기 때문이다.

    <host-list>DNS 이름 또는 IP 주소를 포함하는 복수 개의 태그이다. 같은 Context Group에는 유일한 hostname만이 올 수 있다.

참고

이름 “A”, “B”, “C”는 간략성을 위해 표현되었다. 실제 환경에서는 의미 있는 이름이 사용되어야 한다.

7.4. 가상 호스트를 통한 Context 요청

본 절에서는 가상 호스트 내에 존재하는 Context를 접근하기 위해 URL을 요청하는 방법에 대해서 설명한다. URL 매칭에 대한 일반적인 규칙에 대해 알아보고 예를 들어 이를 설명한다.

7.4.1. URL 매칭에 관한 기본 규칙

가상 호스트를 통한 Context 요청을 하기 위해서 URL의 매칭 정보를 생성해야 한다.

다음의 4가지 규칙은 사용자가 제공하는 요청 내의 URL이 가상 호스트가 존재하는 환경에서의 특정 Context와 매칭되는지 결정한다.

  1. 사용자의 URL 요청 경로가 실제 Context에 매칭되는 기본적인 규칙은(가상 호스트의 사용 여부에 상관없이) 다음과 같다.

    도메인 이름(예: www.foo.com) 이후의 URI 부분을, 등록된 Context 중에서 가장 긴 Context URI 경로에 매칭한다. 만약 매칭이 발견되면 그 Context를 사용한다.

  2. 가상 호스트가 설정되어 있으면, 먼저 사용자의 URL에 있는 도메인 이름을 등록된 모든 가상 호스트의 네트워크 이름에 매칭시킨다. 그 후에 이 가상 호스트에 설정된 모든 Context들을 찾는다. 마지막으로, 위의 규칙 1을 이 Context에 적용시킨다.

  3. 규칙 2에서 Context가 발견되지 않았으면 기본 가상 호스트에 규칙 1을 적용시킨다.

  4. 기본 가상 호스트에도 Context가 발견되지 않으면, 기본 Context가 규칙 1에 적용된다.

7.4.2. URL 매칭의 예

다음은 WEBMain.xml의 가상 호스트 설정의 예이다.

[예 7.2] 가상 호스트의 설정 : <<WEBMain.xml>>

<web-container xmlns="http://www.tmaxsoft.com/xml/ns/jeus">
    . . .
    <context-group>
        <group-name>MyGroup</group-name>
        <virtual-host>
            <virtual-host-name>vhost1</virtual-host-name>
            <host-list>www1.foo.com</host-list>
        </virtual-host>
        <virtual-host>
            <virtual-host-name>vhost2</virtual-host-name>
            <host-list >www2.foo.com</host-list>
            <host-list >www3.foo.com</host-list>
        </virtual-host>
        <webserver-connection>
            . . .
        </webserver-connection>
        . . .
    </context-group>
    . . .
</web-container>


다음은 JEUSMain.xml의 가상 호스트 설정의 예이다. JEUS_HOME은 "c:\jeus6"로 가정한다.

[예 7.3] 가상 호스트의 설정 : <<JEUSMain.xml>>

<jeus-system xmlns="http://www.tmaxsoft.com/xml/ns/jeus">
    <node>
        <name>tmax1</name>
        . . .
    </node>
    <application>
        <name>vhost1ctx1</name>
        <path>
            c:\jeus6\webhome\app_home\vhost1ctx1
        </path>
        <deployment-target>
            <target>
                <engine-container-name>
                    tmax1_container1
                </engine-container-name>
                <web-context-group>
                    <name>MyGroup</name>
                    <virtual-host-name>vhost1</virtual-host-name>
                </web-context-group>
            </target>
        </deployment-target>
        <deployment-type>COMPONENT</deployment-type>
        <web-component/>
    </application>
    
    <application>
        <name>vhost1ctx2</name>
        <path>
            c:\jeus6\webhome\app_home\vhost1ctx2
        </path>
        <deployment-target>
            <target>
                <engine-container-name>
                    tmax1_container1
                </engine-container-name>
                <web-context-group>
                    <name>MyGroup</name>
                    <virtual-host-name>vhost1</virtual-host-name>
                </web-context-group>
            </target>
        </deployment-target>
        <deployment-type>COMPONENT</deployment-type>
        <web-component/>
    </application>
    
    <application>
        <name>vhost2ctx1</name>
        <path>
            c:\jeus6\webhome\app_home\vhost2ctx1
        </path>
        <deployment-target>
            <target>
                <engine-container-name>
                    tmax1_container1
                </engine-container-name>
                <web-context-group>
                    <name>MyGroup</name>
                    <virtual-host-name>vhost2</virtual-host-name>
                </web-context-group>
            </target>
        </deployment-target>
        <deployment-type>COMPONENT</deployment-type>
        <web-component/>
    </application>
    
    <application>
        <name>vhost2ctx2</name>
        <path>
            c:\jeus6\webhome\app_home\vhost2ctx2
        </path>
        <deployment-target>
            <target>
                <engine-container-name>
                    tmax1_container1
                </engine-container-name>
                <web-context-group>
                    <name>MyGroup</name>
                    <virtual-host-name>vhost2</virtual-host-name>
                </web-context-group>
            </target>
        </deployment-target>
        <deployment-type>COMPONENT</deployment-type>
        <web-component/>
    </application>
    
    <application>
        <name>default1</name>
        <path>
            c:\jeus6\webhome\app_home\default1
        </path>
        <deployment-target>
            <target>
                <engine-container-name>
                    tmax1_container1
                </engine-container-name>
                <web-context-group>
                    <name>MyGroup</name>
                </web-context-group>
            </target>
        </deployment-target>
        <deployment-type>COMPONENT</deployment-type>
        <web-component/>
    </application>
    
    <application>
        <name>default2</name>
        <path>
          c:\jeus6\webhome\app_home\default2
        </path>
        <deployment-target>
            <target>
                <engine-container-name>
                    tmax1_container1
                </engine-container-name>
                <web-context-group>
                    <name>MyGroup</name>
                </web-context-group>
            </target>
        </deployment-target>
        <deployment-type>COMPONENT</deployment-type>
        <web-component/>
    </application>
    
    <application>
        <name>default3</name>
        <path>
            c:\jeus6\webhome\app_home\default3
        </path>
        <deployment-target>
            <target>
                <engine-container-name>
                    tmax1_container1
                </engine-container-name>
                <web-context-group>
                    <name>MyGroup</name>
                </web-context-group>
            </target>
        </deployment-target>
        <deployment-type>COMPONENT</deployment-type>
        <web-component/>
    </application>
</jeus-system>


마지막으로 각각의 애플리케이션에 따른 jeus-web-dd.xml 파일에 대한 예이다.

[예 7.4] vhost1ctx1 : <<jeus-web-dd.xml>>

<?xml version="1.0"?>
<jeus-web-dd  xmlns="http://www.tmaxsoft.com/xml/ns/jeus">
        <context-path>/vpath1</context-path>
        <enable-jsp>true</enable-jsp>
</jeus-web-dd>


[예 7.5] vhost1ctx2 : <<jeus-web-dd.xml>>

<?xml version="1.0"?>
<jeus-web-dd  xmlns="http://www.tmaxsoft.com/xml/ns/jeus">
        <context-path>/vpath2</context-path>
        <enable-jsp>true</enable-jsp>
</jeus-web-dd>


[예 7.6] vhost2ctx1 : <<jeus-web-dd.xml>>

<?xml version="1.0"?>
<jeus-web-dd  xmlns="http://www.tmaxsoft.com/xml/ns/jeus">
        <context-path>/vpath3</context-path>
        <enable-jsp>true</enable-jsp>
</jeus-web-dd>


[예 7.7] vhost2ctx2 :<<jeus-web-dd.xml>>

<?xml version="1.0"?>
<jeus-web-dd  xmlns="http://www.tmaxsoft.com/xml/ns/jeus">
        <context-path>/vpath3/subdir</context-path>
        <enable-jsp>true</enable-jsp>
</jeus-web-dd>


[예 7.8] default1 : <<jeus-web-dd.xml>>

<?xml version="1.0"?>
<jeus-web-dd  xmlns="http://www.tmaxsoft.com/xml/ns/jeus">
        <context-path>/default1</context-path>
        <enable-jsp>true</enable-jsp>
</jeus-web-dd>


[예 7.9] default2 :<<jeus-web-dd.xml>>

<?xml version="1.0"?>
<jeus-web-dd  xmlns="http://www.tmaxsoft.com/xml/ns/jeus">
        <context-path>/default2</context-path>
        <enable-jsp>true</enable-jsp>
</jeus-web-dd>


[예 7.10] default3 : <<jeus-web-dd.xml>>

<?xml version="1.0"?>
<jeus-web-dd  xmlns="http://www.tmaxsoft.com/xml/ns/jeus">
        <context-path>/vpath3</context-path>
        <enable-jsp>true</enable-jsp>
</jeus-web-dd>


다음의 예는 위의 설정을 기반으로 하였을 때 어떤 context(“default1”, “default2”, “default3”, “vhost1ctx1”, “vhost1ctx2”, “vhost2ctx1”, “vhost2ctx2”, default context)가 주어진 URL 요청에 매칭되는지 보여준다.

http://www1.foo.com/vpath2/test.jsp 
      vhost1ctx2
http://www1.foo.com/default2/test.jsp
      default2 (in default virtual host)
http://www.foo.com/vpath3/test.jsp
      default3 (in default virtual host)
http://www2.foo.com/vpath3/test.jsp
      vhost2ctx1
http://www3.foo.com/vpath3/subdir/test.jsp
      vhost2ctx2
http://www.foo.com/default1/test.jsp
      default1 (in default virtual host)

참고

위의 예는 단지 개념을 설명하기 위한 것이다. 실제 설정에서는 좀 더 주의해야 한다.