

# Windows 기반 CloudFormation 스택 부트스트래핑
<a name="cfn-windows-stacks-bootstrapping"></a>

이 주제에서는 Windows 스택을 부트스트랩하고 스택 생성 문제를 해결하는 방법을 설명합니다.

**Topics**
+ [EC2 인스턴스의 사용자 데이터](#cfn-windows-bootstrapping-user-data)
+ [CloudFormation 헬퍼 스크립트](#cfn-windows-bootstrapping-helper-scripts)
+ [Windows 스택 부트스트래핑 예](#cfn-windows-bootstrapping-example)
+ [Windows 파일 경로의 백슬래시 이스케이프 처리](#cfn-windows-stacks-escape-backslashes)
+ [Windows 서비스 관리](#cfn-windows-stacks-manage-windows-services)
+ [스택 생성 문제 해결](#cfn-windows-stacks-troubleshooting)

## EC2 인스턴스의 사용자 데이터
<a name="cfn-windows-bootstrapping-user-data"></a>

사용자 데이터는 Amazon EC2 실행 시에 스크립트 또는 구성 정보를 EC2 인스턴스에 전달할 수 있는 Amazon EC2 기능입니다.

Windows EC2 인스턴스의 경우:
+ 배치 스크립트(`<script>` 태그 사용) 또는 PowerShell 스크립트(`<powershell>` 태그 사용)를 사용할 수 있습니다.
+ 스크립트 실행은 EC2Launch에 의해 처리됩니다.

**중요**  
CloudFormation에서 사용할 자체 Windows AMI를 생성하는 경우 EC2Launch v2가 올바르게 구성되었는지 확인합니다. 스택 생성 중에 CloudFormation 부트스트래핑 도구가 Windows 인스턴스를 올바르게 초기화하고 구성하려면 EC2Launch v2가 필요합니다. 자세한 내용은 *Amazon EC2 사용 설명서*의 [EC2Launch v2 에이전트를 사용하여 EC2 Windows 인스턴스 시작 중 태스크 수행](https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/ec2launch-v2.html)을 참조하세요.  
AWS Windows AMI에 대한 자세한 내용은 [AWSWindows AMI 참조](https://docs.aws.amazon.com/ec2/latest/windows-ami-reference/windows-amis.html)를 참조하세요.

## CloudFormation 헬퍼 스크립트
<a name="cfn-windows-bootstrapping-helper-scripts"></a>

헬퍼 스크립트는 부트스트래핑 프로세스 중에 인스턴스를 구성하기 위한 유틸리티로, Amazon EC2 사용자 데이터와 함께 사용되며 강력한 구성 옵션을 제공합니다.

CloudFormation에서는 스택의 일부로 생성한 Amazon EC2 인스턴스에서 소프트웨어를 설치하고 서비스를 시작하는 데 사용할 수 있도록 다음과 같은 Python 헬퍼 스크립트 세트를 제공합니다.
+  `cfn-init` - 리소스 메타데이터를 검색 및 해석하고, 패키지를 설치하고, 파일을 생성하고, 서비스를 시작하는 데 사용됩니다.
+  `cfn-signal` - 필수 리소스나 애플리케이션이 준비될 때 스택에서 다른 리소스를 동기화할 수 있도록 `CreationPolicy`에서 신호를 전송하는 데 사용됩니다.
+  `cfn-get-metadata` - 특정 키에 대한 리소스나 경로의 메타데이터를 검색하는 데 사용됩니다.
+  `cfn-hup` - 메타데이터에 대한 업데이트가 있는지 확인하고 변경 사항이 감지된 경우 사용자 지정 후크를 실행하는 데 사용됩니다.

템플릿에서 직접 헬퍼 스크립트를 호출할 수 있습니다. 헬퍼 스크립트는 동일한 템플릿에서 정의한 리소스 메타데이터와 함께 작동합니다. 헬퍼 스크립트는 스택 생성 과정에서 Amazon EC2 인스턴스에서 실행됩니다.

자세한 내용은 *CloudFormation 템플릿 참조 가이드*의 [CloudFormation 헬퍼 스크립트 참조](https://docs.aws.amazon.com/AWSCloudFormation/latest/TemplateReference/cfn-helper-scripts-reference.html)를 참조하세요.

## Windows 스택 부트스트래핑 예
<a name="cfn-windows-bootstrapping-example"></a>

다음 작업을 수행하는 Windows Server 서버 템플릿의 예제 코드 조각을 살펴보겠습니다.
+ Windows Server 2022 AMI에서 `TestInstance`라는 EC2 인스턴스를 시작합니다.
+ 간단한 테스트 파일을 생성하여 `cfn-init`가 작동하는지 확인합니다.
+ 지속적인 구성 관리를 위해 `cfn-hup`를 구성합니다.
+ `CreationPolicy`를 사용하여 인스턴스가 성공적인 완료를 알리는지 확인합니다.

`cfn-init` 헬퍼 스크립트는 템플릿에 있는 `AWS::CloudFormation::Init` 리소스의 정보를 기반으로 이러한 각 작업을 수행하는 데 사용됩니다.

`AWS::CloudFormation::Init` 섹션 이름은 `TestInstance`이고 이 섹션은 표준 선언으로 시작합니다.

```
TestInstance:
  Type: AWS::EC2::Instance
  Metadata:
    AWS::CloudFormation::Init:
      configSets:
        default:
          - create_files
          - start_services
```

이후에 `AWS::CloudFormation::Init`의 `files` 섹션이 선언됩니다.

```
      create_files:
        files:
          c:\cfn\test.txt:
            content: !Sub |
              Hello from ${AWS::StackName}
          c:\cfn\cfn-hup.conf:
            content: !Sub |
              [main]
              stack=${AWS::StackName}
              region=${AWS::Region}
              interval=2
          c:\cfn\hooks.d\cfn-auto-reloader.conf:
            content: !Sub |
              [cfn-auto-reloader-hook]
              triggers=post.update
              path=Resources.TestInstance.Metadata.AWS::CloudFormation::Init
              action=cfn-init.exe -v -s ${AWS::StackName} -r TestInstance -c default --region ${AWS::Region}
```

여기서 3개 파일이 생성되어 서버 인스턴스의 `C:\cfn` 디렉터리에 배치됩니다.
+ `test.txt`: `cfn-init`가 올바르게 작동하는지 확인하고 동적 콘텐츠로 파일을 생성할 수 있는 간단한 테스트 파일.
+ `cfn-hup.conf`: 검사 간격이 2분인 `cfn-hup`에 대한 구성 파일.
+ `cfn-auto-reloader.conf` - `AWS::CloudFormation::Init`의 메타데이터가 변경될 때 `cfn-hup`가 업데이트를 시작(`cfn-init` 직접 호출)하는 데 사용되는 후크에 대한 구성 파일입니다.

다음은 Windows 서비스를 구성하는 `start_services` 섹션입니다.

```
      start_services:
        services:
          windows:
            cfn-hup:
              enabled: true
              ensureRunning: true
              files:
                - c:\cfn\cfn-hup.conf
                - c:\cfn\hooks.d\cfn-auto-reloader.conf
```

이 섹션에서는 `cfn-hup` 서비스가 시작되고 구성 파일이 수정되면 자동으로 다시 시작되도록 보장합니다. 서비스는 CloudFormation 메타데이터의 변경 사항을 모니터링하고 업데이트가 감지되면 `cfn-init`를 다시 실행합니다.

다음은 `Properties` 섹션입니다.

```
TestInstance:
  Type: AWS::EC2::Instance
  CreationPolicy:
    ResourceSignal:
      Timeout: PT20M
  Metadata:
    AWS::CloudFormation::Init:
      # ... metadata configuration ...
  Properties:
    InstanceType: t2.large
    ImageId: '{{resolve:ssm:/aws/service/ami-windows-latest/Windows_Server-2022-English-Full-Base}}'
    SecurityGroupIds:
      - !Ref InstanceSecurityGroup
    KeyName: !Ref KeyPairName
    UserData:
      Fn::Base64: !Sub |
        <powershell>
        cfn-init.exe -v -s ${AWS::StackName} -r TestInstance -c default --region ${AWS::Region}
        cfn-signal.exe -e $lastexitcode --stack ${AWS::StackName} --resource TestInstance --region ${AWS::Region}
        </powershell>
```

이 섹션에서 `UserData` 속성에는 EC2Launch에 의해 실행될 PowerShell 스크립트가 `<powershell>` 태그로 둘러싸여 있습니다. 스크립트는 `default` configSet와 함께 `cfn-init`를 실행한 다음 `cfn-signal`을 사용하여 종료 코드를 CloudFormation에 다시 보고합니다. `CreationPolicy`는 스택 생성이 완료된 것으로 간주되기 전에 인스턴스가 올바르게 구성되었는지 확인하는 데 사용됩니다.

`ImageId` 속성은 Systems Manager Parameter Store 퍼블릭 파라미터를 사용하여 최신 Windows Server 2022 AMI ID를 자동으로 검색합니다. 이 접근 방식을 사용하면 리전별 AMI 매핑이 필요하지 않으며 항상 최신 AMI를 얻을 수 있습니다. AMI ID에 대한 Systems Manager 파라미터를 사용하는 것이 최신 AMI 참조를 유지하는 모범 사례입니다. 인스턴스에 연결하려는 경우 `SecurityGroupIds` 속성이 RDP 액세스를 허용하는 보안 그룹을 참조하는지 확인합니다.

`CreationPolicy`는 리소스 속성의 일부로 선언되며 제한 시간을 지정합니다. 인스턴스 구성이 완료되면 사용자 데이터에서 `cfn-signal` 명령이 신호를 보냅니다.

```
TestInstance:
  Type: AWS::EC2::Instance
  CreationPolicy:
    ResourceSignal:
      Timeout: PT20M
  Properties:
    # ... other properties ...
```

부트스트래핑 프로세스는 최소이며 파일을 생성하고 서비스만 시작하기 때문에 `CreationPolicy`는 제한 시간이 초과되기 전에 20분(PT20M)을 기다립니다. 제한 시간은 ISO 8601 지속 시간 형식을 사용하여 지정됩니다. Windows 인스턴스는 Linux 인스턴스보다 일반적으로 시작하는 데 시간이 오래 걸리므로 철저하게 테스트하여 요구 사항에 가장 적합한 제한 시간 값을 결정합니다.

모두 잘 진행되면 `CreationPolicy`가 성공적으로 완료되며 해당 퍼블릭 IP 주소를 사용하여 Windows Server 인스턴스에 액세스할 수 있습니다. 스택 생성이 완료되면 인스턴스 ID 및 퍼블릭 IP 주소가 CloudFormation 콘솔의 **출력** 탭에 표시됩니다.

```
Outputs:
  InstanceId:
    Value: !Ref TestInstance
    Description: Instance ID of the Windows Server
  PublicIP:
    Value: !GetAtt TestInstance.PublicIp
    Description: Public IP address of the Windows Server
```

또한 RDP를 통해 인스턴스에 연결하고 `C:\cfn\test.txt` 파일이 존재하고 예상 콘텐츠를 포함하는지 확인하여 부트스트래핑이 올바르게 작동하는지 수동으로 확인할 수 있습니다. Windows 인스턴스에 연결에 대한 자세한 내용은 *Amazon EC2 사용자 설명서*의 [RDP를 사용하여 Windows 인스턴스에 연결](https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/connecting_to_windows_instance.html)을 참조하세요.

## Windows 파일 경로의 백슬래시 이스케이프 처리
<a name="cfn-windows-stacks-escape-backslashes"></a>

CloudFormation 템플릿에서 Windows 경로를 참조하는 경우 항상 사용 중인 템플릿 형식에 따라 백슬래시(`\`)를 올바르게 이스케이프해야 합니다.
+ JSON 템플릿의 경우 JSON은 백슬래시를 이스케이프 문자로 취급하므로 Windows 파일 경로에서 이중 백슬래시를 사용해야 합니다. 첫 번째 백슬래시는 두 번째 백슬래시를 이스케이프 처리하므로 단일 리터럴 백슬래시로 해석됩니다.

  ```
  "commands" : {
    "1-extract" : {
      "command" : "C:\\SharePoint\\SharePointFoundation2010.exe /extract:C:\\SharePoint\\SPF2010 /quiet /log:C:\\SharePoint\\SharePointFoundation2010-extract.log"
    }
  }
  ```
+ YAML 템플릿의 경우 일반적으로 단일 백슬래시로 충분합니다.

  ```
  commands:
    1-extract:
      command: C:\SharePoint\SharePointFoundation2010.exe /extract:C:\SharePoint\SPF2010 /quiet /log:C:\SharePoint\SharePointFoundation2010-extract.log
  ```

## Windows 서비스 관리
<a name="cfn-windows-stacks-manage-windows-services"></a>

`sysvinit` 대신 `windows` 키를 사용한다는 점을 제외하면 Linux 서비스와 동일한 방법으로 Windows 서비스를 관리합니다. 다음 예제에서는 `cfn-hup` 서비스를 시작하고 Automatic으로 설정한 다음 `cfn-init`가 `c:\cfn\cfn-hup.conf` 또는 `c:\cfn\hooks.d\cfn-auto-reloader.conf` 구성 파일을 수정하면 서비스를 다시 시작합니다.

```
        services:
          windows:
            cfn-hup:
              enabled: true
              ensureRunning: true
              files:
                - c:\cfn\cfn-hup.conf
                - c:\cfn\hooks.d\cfn-auto-reloader.conf
```

이름(표시 이름 아님)으로 서비스를 참조하여 동일한 방식으로 다른 Windows 서비스를 관리할 수 있습니다.

## 스택 생성 문제 해결
<a name="cfn-windows-stacks-troubleshooting"></a>

생성 중에 스택이 실패할 경우 기본 동작은 실패 시 롤백입니다. 일반적으로 기본 동작은 불필요한 과금을 피할 수 있다는 점은 좋지만 스택 생성이 실패한 원인을 디버깅하기 어렵습니다.

CloudFormation 콘솔을 사용하여 스택을 생성하거나 업데이트할 때 이 동작을 끄려면 **스택 실패 옵션**에서 **성공적으로 프로비저닝된 리소스 보존** 옵션을 선택합니다. 자세한 내용은 [리소스 프로비저닝 시 실패 처리 방법 선택](stack-failure-options.md) 섹션을 참조하세요. 그러면 인스턴스에 로그인한 후 로그 파일을 보고 시작 스크립트를 실행할 때 발생한 문제를 정확히 파악할 수 있습니다.

검토할 중요 로그는 다음과 같습니다.
+ `%ProgramData%\Amazon\EC2Launch\log\agent.log`의 EC2 구성 로그
+ `C:\cfn\log\cfn-init.log`의 **cfn-init** 로그(특정 장애 지점에 대한 종료 코드 및 오류 메시지 확인)

자세한 로그는 *Amazon EC2 사용 설명서*에서 다음 주제를 참조하세요.
+ [EC2Launch 디렉터리 구조](https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/ec2config-service.html#UsingConfigXML_WinAMI)
+ [EC2Launch v2 디렉터리 구조](https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/ec2launch-v2.html#ec2launch-v2-directory)

부트스트래핑 문제 해결에 대한 자세한 내용은 [Windows 인스턴스의 CloudFormation 스택에서 부트스트랩되지 않는 도우미 스크립트 문제를 해결하려면 어떻게 해야 합니까?](https://repost.aws/knowledge-center/cloudformation-helper-scripts-windows)를 참조하세요.