본문 바로가기

운영체제/Windows

[Windows] WSFC에서 IIS 클러스터링

반응형

개요

Windows Server Failover Cluster(WSFC) 에서 IIS 클러스터링 방법에 대해서 설명한다.

구성환경

Windows Server 2016

사전구성

1. Windows Server Failover Clustering(WSFC) 기능 설치

2. IIS 설치

3. 공유 볼륨 구성

 

구성 순서

1. IIS 공유 구성을 사용할 파일 공유 설정

2. 클러스터 노드에서 IIS 공유 구성을 구성합니다

3. 모든 클러스터 노드에서 IIS 오프 라인 파일 공유 구성 위한 구성

4. 관련된 응용 프로그램 풀, 웹 사이트등을 구성하고 하나의 클러스터 노드에서 해당 콘텐츠의 위치를 지정 합니다.

5. 장애 조치 클러스터 관리자에서 일반 스크립트를 만들어 웹 사이트에 대 한 높은 가용성 구성

구성도

 

1. IIS 구성을 사용할 파일 공유 설정

 1.1 adsvr1 서버에 공유 폴더 구성

    - 사용자 생성 : iisuser   

    - 공유 폴더 이름 : iisConfig

    - 공유 폴더는 클러스터의 외부 서버에 생성

 1.2 모든 클러스터 노드에서 파일 공유 탐색할 수 있는지 확인 합니다. 파일 공유 경로 \\파일 < 서버 >\< 공유 >.

 

2. 클러스터 노드에서 IIS 공유 구성을 합니다.

 2.1 클러스터 노드 중 하나에서 파일 공유로 공유 구성 내보내기:

 2.2 클러스터의 모든 노드에서 공유 구성 활성화

 

3. 모든 클러스터 노드에서 IIS 오프 라인 파일 공유 구성 위한 구성

 *** 클러스터 구성시 구성파일이 네트워크상에 위치하기 때문에 오프라인 상태에서도 지속적으로 읽고/쓰기 위하여 오프라인 파일관리 필요 

 3.1 오프라인 파일 사용 활성화 

 제이판 > 동기화 센터 > 오프라인 파일 관리

 3.2 시스템 리부팅( 오프라인 파일 사용을 활성화 하기 위해서 시스템 리부팅 필요)

 3.3 항상 오프라인 사용 가능 활성화

 3.4 IIS 구성 동기화 일정 추가

  단계 1) 동기화 파트너 관계 보기 > 오프라인 파일 > 오프라인 일정

  단계 2) 오프라인 파일 선택 및 동기화 일정 선택

  단계 3) 동기화 일정

 

4. 관련된 응용 프로그램 풀, 웹 사이트등을 구성하고 하나의 클러스터 노드에서 해당 콘텐츠의 위치를 지정 합니다.

 ** 클러스터 디스크 리소스(공유볼륨)를 소유 하는 클러스터 노드에서 구성

 

5. 장애 조치 클러스터 관리자에서 일반 스크립트를 만들어 웹 사이트에 대한 높은 가용성 구성

 5.1 모든 노드에 웹 사이트에 대 한 웹 사이트 및 응용 프로그램 풀을 모니터링 하는 일반 스크립트 리소스 설정

 각 클러스터 노드에서 %Windows%\System32\inetsrv\Clusweb10.vbs 파일생성 및  고가용성 구성을 위한 일반 스크립트 파일의 내용 복사(이글  끝에 고가용성 구성을 위한 일반 스크립트 내용 참조).

기본적으로 이 스크립트는 "기본 웹 사이트"라는 웹 사이트와 "DefaultAppPool"이라는 응용 프로그램 풀을 모니터링합니다. 이것이 올바른 웹 사이트 및 응용 프로그램 풀이 아닌 경우 SITE_NAME 및 APP_POOL_NAME 변수를 변경하십시오. 스크립트의 동일한 웹 사이트 및 응용 프로그램 풀이 모든 클러스터 노드에 존재하는지 확인하십시오. 이름은 대소 문자를 구분합니다.

 5.2 장애처리 클러스터 관리자에서 역할 구성

  단계 1) 역할 선택 - 일반 스크립트 선택

  단계 2) 스크립트 파일 경로 지정

  단계 3) 클라이언트 액세스 지점 설정

   단계 4)  저장소  선택

     - 웹 사이트 콘텐츠 파일이 상주하는 클러스터 공유 디스크를 선택

  단계 5) 확인 및 요약

 

참조 사이트 : https://support.microsoft.com/ko-kr/help/970759/configure-iis-world-wide-web-publishing-service-in-failover-cluster

참고

- 서버 인증서는 로컬 서버의 레지스트리에 등록되기 때문에 인증서는 모든 노드에서 작업을 해줘야 한다.

- 고가용성 구성을 위한 일반 스크립트 파일(C:\Windows\system32\inetsvc\Cluswin10.vbs)

'<begin script sample>


'This script provides high availability for IIS websites
'By default, it monitors the "Default Web Site" and "DefaultAppPool"
'To monitor another website, change the SITE_NAME below
'To monitor another application pool, change the APP_POOL_NAME below
'More thorough and application-specific health monitoring logic can be added to the script if needed

Option Explicit

DIM SITE_NAME
DIM APP_POOL_NAME
Dim START_WEB_SITE
Dim START_APP_POOL
Dim SITES_SECTION_NAME
Dim APPLICATION_POOLS_SECTION_NAME
Dim CONFIG_APPHOST_ROOT
Dim STOP_WEB_SITE


'Note:
'Replace this with the site and application pool you want to configure high availability for
'Make sure that the same website and application pool in the script exist on all cluster nodes. Note that the names are case-sensitive.
SITE_NAME = "Default Web Site"
APP_POOL_NAME = "DefaultAppPool"

START_WEB_SITE = 0
START_APP_POOL = 0
STOP_WEB_SITE  = 1
SITES_SECTION_NAME = "system.applicationHost/sites"
APPLICATION_POOLS_SECTION_NAME = "system.applicationHost/applicationPools"
CONFIG_APPHOST_ROOT = "MACHINE/WEBROOT/APPHOST"

'Helper script functions


'Find the index of the website on this node
Function FindSiteIndex(collection, siteName)

    Dim i

    FindSiteIndex = -1    

    For i = 0 To (CInt(collection.Count) - 1)
        If collection.Item(i).GetPropertyByName("name").Value = siteName Then
            FindSiteIndex = i
            Exit For
        End If 
    Next

End Function


'Find the index of the application pool on this node
Function FindAppPoolIndex(collection, appPoolName)

    Dim i

    FindAppPoolIndex = -1    

    For i = 0 To (CInt(collection.Count) - 1)
        If collection.Item(i).GetPropertyByName("name").Value = appPoolName Then
            FindAppPoolIndex = i
            Exit For
        End If 
    Next

End Function

'Get the state of the website
Function GetWebSiteState(adminManager, siteName)

    Dim sitesSection, sitesSectionCollection, siteSection, index, siteMethods, startMethod, executeMethod
    Set sitesSection = adminManager.GetAdminSection(SITES_SECTION_NAME, CONFIG_APPHOST_ROOT)
    Set sitesSectionCollection = sitesSection.Collection

    index = FindSiteIndex(sitesSectionCollection, siteName)
    If index = -1 Then
        GetWebSiteState = -1
    End If    

    Set siteSection = sitesSectionCollection(index)

    GetWebSiteState = siteSection.GetPropertyByName("state").Value

End Function

'Get the state of the ApplicationPool
Function GetAppPoolState(adminManager, appPool)

    Dim configSection, index, appPoolState

    set configSection = adminManager.GetAdminSection(APPLICATION_POOLS_SECTION_NAME, CONFIG_APPHOST_ROOT)
    index = FindAppPoolIndex(configSection.Collection, appPool)

    If index = -1 Then
        GetAppPoolState = -1
    End If    

    GetAppPoolState = configSection.Collection.Item(index).GetPropertyByName("state").Value
End Function


'Start the w3svc service on this node
Function StartW3SVC()

    Dim objWmiProvider
    Dim objService
    Dim strServiceState
    Dim response

    'Check to see if the service is running
    set objWmiProvider = GetObject("winmgmts:/root/cimv2")
    set objService = objWmiProvider.get("win32_service='w3svc'")
    strServiceState = objService.state

    If ucase(strServiceState) = "RUNNING" Then
        StartW3SVC = True
    Else
        'If the service is not running, try to start it
        response = objService.StartService()

        'response = 0  or 10 indicates that the request to start was accepted
        If ( response <> 0 ) and ( response <> 10 ) Then
            StartW3SVC = False
        Else
            StartW3SVC = True
        End If
    End If
    
End Function


'Start the application pool for the website
Function StartAppPool()

    Dim ahwriter, appPoolsSection, appPoolsCollection, index, appPool, appPoolMethods, startMethod, callStartMethod
    Set ahwriter = CreateObject("Microsoft.ApplicationHost.WritableAdminManager")

    Set appPoolsSection = ahwriter.GetAdminSection(APPLICATION_POOLS_SECTION_NAME, CONFIG_APPHOST_ROOT)       
    Set appPoolsCollection = appPoolsSection.Collection

    index = FindAppPoolIndex(appPoolsCollection, APP_POOL_NAME)
    Set appPool = appPoolsCollection.Item(index)
    
    'See if it is already started
    If appPool.GetPropertyByName("state").Value = 1 Then
        StartAppPool = True
        Exit Function
    End If

    'Try To start the application pool
    Set appPoolMethods = appPool.Methods
    Set startMethod = appPoolMethods.Item(START_APP_POOL)
    Set callStartMethod = startMethod.CreateInstance()
    callStartMethod.Execute()
    
    'If started return true, otherwise return false
    If appPool.GetPropertyByName("state").Value = 1 Then
        StartAppPool = True
    Else
        StartAppPool = False
    End If

End Function


'Start the website
Function StartWebSite()

    Dim ahwriter, sitesSection, sitesSectionCollection, siteSection, index, siteMethods, startMethod, executeMethod
    Set ahwriter = CreateObject("Microsoft.ApplicationHost.WritableAdminManager")
    Set sitesSection = ahwriter.GetAdminSection(SITES_SECTION_NAME, CONFIG_APPHOST_ROOT)
    Set sitesSectionCollection = sitesSection.Collection

    index = FindSiteIndex(sitesSectionCollection, SITE_NAME)
    Set siteSection = sitesSectionCollection(index)

    if siteSection.GetPropertyByName("state").Value = 1 Then
        'Site is already started
        StartWebSite = True
        Exit Function
    End If

    'Try to start site
    Set siteMethods = siteSection.Methods
    Set startMethod = siteMethods.Item(START_WEB_SITE)
    Set executeMethod = startMethod.CreateInstance()
    executeMethod.Execute()

    'Check to see if the site started, if not return false
    If siteSection.GetPropertyByName("state").Value = 1 Then
        StartWebSite = True
    Else
        StartWebSite = False
    End If

End Function


'Stop the website
Function StopWebSite()

    Dim ahwriter, sitesSection, sitesSectionCollection, siteSection, index, siteMethods, startMethod, executeMethod, autoStartProperty
    Set ahwriter = CreateObject("Microsoft.ApplicationHost.WritableAdminManager")
    Set sitesSection = ahwriter.GetAdminSection(SITES_SECTION_NAME, CONFIG_APPHOST_ROOT)
    Set sitesSectionCollection = sitesSection.Collection

    index = FindSiteIndex(sitesSectionCollection, SITE_NAME)
    Set siteSection = sitesSectionCollection(index)

    'Stop the site
    Set siteMethods = siteSection.Methods
    Set startMethod = siteMethods.Item(STOP_WEB_SITE)
    Set executeMethod = startMethod.CreateInstance()
    executeMethod.Execute()

End Function



'Cluster resource entry points. More details here:
'http://msdn.microsoft.com/en-us/library/aa372846(VS.85).aspx

'Cluster resource Online entry point
'Make sure the website and the application pool are started
Function Online( )

    Dim bOnline
    'Make sure w3svc is started
    bOnline = StartW3SVC()

    If bOnline <> True Then
        Resource.LogInformation "The resource failed to come online because w3svc could not be started."
        Online = False
        Exit Function
    End If


    'Make sure the application pool is started
    bOnline = StartAppPool()
    If bOnline <> True Then
        Resource.LogInformation "The resource failed to come online because the application pool could not be started."
        Online = False
        Exit Function
    End If


    'Make sure the website is started
    bOnline = StartWebSite()
    If bOnline <> True Then
        Resource.LogInformation "The resource failed to come online because the web site could not be started."
        Online = False
        Exit Function
    End If

    Online = true 

End Function

 
'Cluster resource offline entry point
'Stop the website
Function Offline( )

    StopWebSite()
    Offline = true

End Function


'Cluster resource LooksAlive entry point
'Check for the health of the website and the application pool
Function LooksAlive( )

    Dim adminManager, appPoolState, configSection, i, appPoolName, appPool, index

    i = 0
    Set adminManager  = CreateObject("Microsoft.ApplicationHost.AdminManager")
    appPoolState = -1

    'Get the state of the website
    if GetWebSiteState(adminManager, SITE_NAME) <> 1 Then
        Resource.LogInformation "The resource failed because the " & SITE_NAME & " web site is not started."
        LooksAlive = false
        Exit Function
    End If


    'Get the state of the Application Pool
     if GetAppPoolState(adminManager, APP_POOL_NAME) <> 1 Then
         Resource.LogInformation "The resource failed because Application Pool " & APP_POOL_NAME & " is not started."
         LooksAlive = false  
 Exit Function
     end if

     '  Web site and Application Pool state are valid return true
     LooksAlive = true
End Function


'Cluster resource IsAlive entry point
'Do the same health checks as LooksAlive
'If a more thorough than what we do in LooksAlive is required, this should be performed here
Function IsAlive()   

    IsAlive = LooksAlive

End Function


'Cluster resource Open entry point
Function Open()

    Open = true

End Function


'Cluster resource Close entry point
Function Close()

    Close = true

End Function


'Cluster resource Terminate entry point
Function Terminate()

    Terminate = true

End Function
'<end script sample>
반응형