

기계 번역으로 제공되는 번역입니다. 제공된 번역과 원본 영어의 내용이 상충하는 경우에는 영어 버전이 우선합니다.

# ElastiCache 전송 중 데이터 암호화(TLS)
<a name="in-transit-encryption"></a>

데이터를 안전하게 유지하기 위해 Amazon ElastiCache 및 Amazon EC2는 서버의 데이터에 대한 무단 액세스를 방지하는 메커니즘을 제공합니다. ElastiCache에서는 전송 중 데이터 암호화 기능을 제공해 한 위치에서 다른 위치로 데이터 이동 시 데이터를 보호할 수 있는 수단을 제공합니다.

모든 Valkey 또는 Redis OSS 서버리스 캐시에는 전송 중 데이터 암호화가 활성화되어 있습니다. 노드 기반 클러스터의 경우 복제 그룹을 생성할 때 `TransitEncryptionEnabled` 파라미터를 `true`(CLI: `--transit-encryption-enabled`)로 설정해 복제 그룹에서 전송 중 암호화를 활성화합니다.AWS Management ConsoleAWS CLI, 또는 ElastiCache API를 사용하여 복제 그룹을 생성하든 관계없이이 작업을 수행할 수 있습니다.

모든 서버리스 캐시에는 전송 중 암호화가 활성화되어 있습니다. 노드 기반 클러스터의 경우 `CreateCacheCluster`(CLI: `create-cache-cluster`) 작업을 사용하여 클러스터를 생성할 때 `TransitEncryptionEnabled` 파라미터를 `true`(CLI: `--transit-encryption-enabled`)로 설정하여 클러스터에서 전송 중 암호화를 활성화할 수 있습니다.

**Topics**
+ [전송 중 데이터 암호화 개요](#in-transit-encryption-overview)
+ [전송 중 암호화 조건(Valkey 및 Redis OSS)](#in-transit-encryption-constraints)
+ [전송 중 데이터 암호화 조건(Memcached)](#in-transit-encryption-constraints)
+ [전송 중 데이터 암호화 모범 사례](#in-transit-encryption-best-practices)
+ [추가 Valkey 및 Redis OSS 옵션](#in-transit-encryption-see-also)
+ [Memcached에 대한 전송 중 데이터 암호화 활성화](#in-transit-encryption-enable-existing-mc)
+ [전송 중 데이터 암호화 사용 설정](in-transit-encryption-enable.md)
+ [valkey-cli를 사용하여 전송 중 암호화를 통해 ElastiCache(Valkey) 또는 Amazon ElastiCache for Redis OSS에 연결](connect-tls.md)
+ [Python을 사용하여 노드 기반 Redis OSS 클러스터에서 전송 중 데이터 암호화 활성화](in-transit-encryption-enable-python.md)
+ [전송 중 암호화 활성화 시 모범 사례](enable-python-best-practices.md)
+ [Openssl을 사용하여 전송 중 데이터 암호화가 사용 설정된 노드에 연결(Memcached)](#in-transit-encryption-connect-mc)
+ [Java를 사용하여 TLS Memcached 클라이언트 생성](#in-transit-encryption-connect-java)
+ [PHP를 사용하여 TLS Memcached 클라이언트 생성](#in-transit-encryption-connect-php-mc)

## 전송 중 데이터 암호화 개요
<a name="in-transit-encryption-overview"></a>

Amazon ElastiCache의 전송 중 암호화는 가장 취약한 지점 즉, 한 위치에서 다른 위치로 데이터를 전송할 때 데이터의 보안을 강화하는 기능입니다. 엔드포인트에서 데이터를 암호화 및 해독하기 위해 몇 가지 처리가 필요하기 때문에 전송 중 데이터 암호화를 활성화하면 성능에 어느 정도 영향이 있을 수 있습니다. 사용 사례에 대한 성능 영향을 파악하기 위해서는 전송 중 데이터 암호화를 사용한 상태와 사용하지 않은 상태에서 데이터를 벤치마크해야 합니다.

ElastiCache의 전송 중 데이터 암호화는 다음 기능을 구현합니다.
+ **암호화된 클라이언트 연결** - 캐시 노드에 대한 클라이언트 연결은 TLS로 암호화됩니다.
+ **암호화된 서버 연결 -** 클러스터의 노드 간에 이동하는 데이터는 암호화됩니다.
+ **서버 인증** - 클라이언트가 자신이 올바른 서버에 연결 중임을 인증할 수 있습니다.
+ **클라이언트 인증** - Valkey 또는 Redis OSS AUTH 기능을 사용하여 서버가 클라이언트를 인증할 수 있습니다.

## 전송 중 암호화 조건(Valkey 및 Redis OSS)
<a name="in-transit-encryption-constraints"></a>

노드 기반 클러스터를 구현하려는 경우 Amazon ElastiCache의 전송 중 암호화에 관한 다음 제한 사항을 고려해야 합니다.
+ 전송 중 데이터 암호화는 Valkey 7.2 이상 및 Redis OSS 3.2.6, 4.0.10 및 이후 버전을 실행 중인 복제 그룹에서만 지원됩니다.
+ 기존 클러스터의 전송 중 데이터 암호화 설정 수정은 Valkey 7.2 이상 및 Redis OSS 버전 7 이상을 실행하는 복제 그룹에서 지원됩니다.
+ 전송 중 데이터 암호화는 Amazon VPC에서 실행 중인 복제 그룹에 대해서만 지원됩니다.
+ 전송 중 데이터 암호화는 M1, M2 노드 유형을 실행하는 복제 그룹에 대해 지원되지 않습니다.

  자세한 내용은 [지원되는 노드 유형](CacheNodes.SupportedTypes.md) 단원을 참조하십시오.
+ 전송 중 데이터 암호화는 `TransitEncryptionEnabled` 파라미터를 명시적으로 `true`로 설정해 활성화합니다.
+ 캐시 클라이언트가 TLS 연결을 지원하고 클라이언트 구성에서 TLS 연결을 활성화합니다.
+ 2026년 1월 26일부터AWS는 Valkey용 ElastiCache 버전 7.2 이상 및 Redis용 ElastiCache OSS 버전 6 이상에서 지원되는 최소 TLS 버전을 1.2로 업데이트합니다. 고객은 해당 날짜 이전에 클라이언트 소프트웨어를 업데이트해야 합니다. 이 업데이트는 보안, 규정 준수 및 규제 요구 사항을 충족하는 데 도움이 됩니다.

## 전송 중 데이터 암호화 조건(Memcached)
<a name="in-transit-encryption-constraints"></a>

노드 기반 클러스터를 구현하려는 경우 Amazon ElastiCache의 전송 중 암호화에 관한 다음 제한 사항을 고려해야 합니다.
+ 전송 중 데이터 암호화는 Memcached 버전 1.6.12 이상 버전을 실행 중인 클러스터에서 지원됩니다.
+ 전송 중 암호화는 전송 계층 보안(TLS) 버전 1.2 및 1.3을 지원합니다.
+ 전송 중 데이터 암호화는 Amazon VPC에서 실행 중인 클러스터에 대해서만 지원됩니다.
+ 전송 중 데이터 암호화는 M1, M2, M3, R3, T2 노드 유형을 실행하는 복제 그룹에 대해 지원되지 않습니다.

  자세한 내용은 [지원되는 노드 유형](CacheNodes.SupportedTypes.md) 단원을 참조하십시오.
+ 전송 중 데이터 암호화는 `TransitEncryptionEnabled` 파라미터를 명시적으로 `true`로 설정해 활성화합니다.
+ 클러스터를 생성하는 경우에만 클러스터에서 전송 중 데이터 암호화를 사용 설정할 수 있습니다. 클러스터를 수정하여 전송 중 데이터 암호화 켜기 및 끄기를 전환할 수 없습니다.
+ 캐시 클라이언트가 TLS 연결을 지원하고 클라이언트 구성에서 TLS 연결을 활성화합니다.

## 전송 중 데이터 암호화 모범 사례
<a name="in-transit-encryption-best-practices"></a>
+ 엔드포인트에서 데이터를 암호화 및 해독하기 위해 처리가 필요하기 때문에 전송 중 데이터 암호화를 구현하면 성능이 저하될 수 있습니다. 이러한 암호화가 구현 성능에 미치는 영향을 확인하려면 전송 중 데이터 암호화와 데이터를 암호화하지 않은 경우를 비교해 벤치마크하세요.
+ 새로운 연결을 생성하면 비용이 높아질 수 있기 때문에 TLS 연결을 지속해 전송 중 데이터 암호화가 성능에 미치는 영향을 줄일 수 있습니다.

## 추가 Valkey 및 Redis OSS 옵션
<a name="in-transit-encryption-see-also"></a>

Valkey 및 Redis OSS에 사용할 수 있는 옵션에 대한 자세한 내용은 다음 링크를 참조하세요.
+ [ElastiCache에서 저장 시 암호화](at-rest-encryption.md)
+ [Valkey 및 Redis OSS AUTH 명령으로 인증](auth.md)
+ [역할 기반 액세스 제어(RBAC)](Clusters.RBAC.md)
+ [Amazon VPC 및 ElastiCache 보안](VPCs.md)
+ [Amazon ElastiCache의 Identity and Access Management](IAM.md)

## Memcached에 대한 전송 중 데이터 암호화 활성화
<a name="in-transit-encryption-enable-existing-mc"></a>

AWS관리 콘솔을 사용하여 Memcached 클러스터를 생성하는 경우 전송 중 데이터 암호화를 사용 설정하려면 다음을 선택합니다.
+ 엔진으로 Memcached를 선택합니다.
+ 엔진 버전 1.6.12 이상을 선택합니다.
+ **Encryption in transit**(전송 중 데이터 암호화)에서 **Enable**(사용 설정)을 선택합니다.

 단계별 절차는 [Valkey 또는 Redis OSS용 클러스터 생성](Clusters.Create.md) 섹션을 참조하세요.

# 전송 중 데이터 암호화 사용 설정
<a name="in-transit-encryption-enable"></a>

모든 서버리스 캐시에는 전송 중 암호화가 활성화되어 있습니다. 노드 기반 클러스터에서는AWS Management Console,AWS CLI 또는 ElastiCache API를 사용하여 전송 중 데이터 암호화를 활성화할 수 있습니다.

## 를 사용하여 전송 중 데이터 암호화 활성화AWS Management Console
<a name="in-transit-encryption-enable-console"></a>

### 를 사용하여 새 노드 기반 클러스터에 대한 전송 중 데이터 암호화 활성화AWS Management Console
<a name="in-transit-encryption-enable-con"></a>

자체 클러스터를 설계할 때 '간편한 생성' 메서드를 사용하는 '개발 및 테스트' 및 '프로덕션' 구성에서는 전송 중 암호화가 활성화됩니다. 구성을 직접 선택할 때 다음과 같이 진행합니다.
+ 다음 엔진 버전을 선택합니다. 3.2.6, 4.0.10 또는 이후 버전.
+ **전송 중 암호화**의 **활성화** 옵션 옆에서 확인란을 클릭합니다.

단계별 프로세스의 경우 다음을 참조하세요.
+ [Valkey(클러스터 모드 비활성화됨) 클러스터 생성(콘솔)](SubnetGroups.designing-cluster-pre.valkey.md#Clusters.Create.CON.valkey-gs)
+ [Valkey 또는 Redis OSS(클러스터 모드 활성화됨) 클러스터 생성(콘솔)](Clusters.Create.md#Clusters.Create.CON.RedisCluster)

### 를 사용하여 기존 노드 기반 클러스터에 대한 전송 중 암호화 활성화AWS Management Console
<a name="in-transit-encryption-enable-existing"></a>

전송 중 암호화 활성화는 두 단계 프로세스이므로, 먼저 전송 암호화 모드를 `preferred`(으)로 설정해야 합니다. 이 모드는 Valkey 또는 Redis OSS 클라이언트가 암호화된 연결과 암호화되지 않은 연결을 모두 사용하여 연결할 수 있도록 합니다. 암호화된 연결을 사용하도록 모든 Valkey 또는 Redis OSS 클라이언트를 마이그레이션한 후, 클러스터 구성을 수정하여 전송 암호화 모드를 `required`(으)로 설정할 수 있습니다. 전송 암호화 모드를 `required`(으)로 설정하면 암호화되지 않은 모든 연결이 끊어지고 암호화된 연결만 허용됩니다.

****전송 암호화 모드**를 **선호**로 설정**

1. 에 로그인AWS Management Console하고 [https://console.aws.amazon.com/elasticache/](https://console.aws.amazon.com/elasticache/) Amazon ElastiCache 콘솔을 엽니다.

1. 왼쪽에 표시되는 탐색 창에 나열된 ElastiCache **리소스**에서 **Valkey 캐시** 또는 **Redis OSS 캐시**를 선택합니다.

1. 업데이트할 캐시를 선택합니다.

1. **작업** 드롭다운을 선택한 다음, **수정**을 선택합니다.

1. **보안** 섹션, **전송 중 암호화**에서 **활성화**를 선택합니다.

1. **전송 암호화 모드**로 **선호**를 선택합니다.

1. **변경 사항 미리 보기**를 선택하여 변경 사항을 저장합니다.

암호화된 연결을 사용하도록 모든 Valkey 또는 Redis OSS 클라이언트를 마이그레이션한 후:

****전송 암호화 모드**를 **필수**로 설정**

1. 에 로그인AWS Management Console하고 [https://console.aws.amazon.com/elasticache/](https://console.aws.amazon.com/elasticache/) Amazon ElastiCache 콘솔을 엽니다.

1. 왼쪽에 표시되는 탐색 창에 나열된 ElastiCache **리소스**에서 **Valkey 캐시** 또는 **Redis OSS 캐시**를 선택합니다.

1. 업데이트할 캐시를 선택합니다.

1. **작업** 드롭다운을 선택한 다음, **수정**을 선택합니다.

1. **보안** 섹션에서 **전송 암호화 모드**로 **필수**를 선택합니다.

1. **변경 사항 미리 보기**를 선택하여 변경 사항을 저장합니다.

## 를 사용하여 전송 중 데이터 암호화 활성화AWS CLI
<a name="in-transit-encryption-enable-cli"></a>

AWS CLI를 사용하여 Valkey 또는 Redis OSS 복제 그룹을 생성할 때 전송 중 데이터 암호화를 활성화하려면 파라미터 `transit-encryption-enabled`를 설정합니다.

### Valkey 또는 Redis OSS용 새 노드 기반 클러스터에서 전송 중 암호화 활성화(클러스터 모드 비활성화)(CLI)
<a name="in-transit-encryption-enable-cli-redis-classic-rg"></a>

AWS CLI작업`create-replication-group`과 다음 파라미터를 사용하여 전송 중 데이터 암호화가 활성화된 복제본이 있는 Valkey 또는 Redis OSS 복제 그룹을 생성합니다.

**키 파라미터:**
+ **--engine** - `valkey` 또는 `redis`이어야 합니다.
+ **--engine-version** - 엔진이 Redis OSS인 경우 3.2.6, 4.0.10 또는 그 이상이어야 합니다.
+ **--transit-encryption-enabled** - 필수입니다. 전송 중 데이터 암호화를 활성화하면 `--cache-subnet-group` 파라미터의 값도 제공해야 합니다.
+ **--num-cache-clusters** - 1 이상이어야 합니다. 이 파라미터의 최대값은 6입니다.

자세한 내용은 다음을 참조하세요.
+ [Valkey 또는 Redis OSS(클러스터 모드 비활성화됨) 복제 그룹을 처음부터 새로 생성(AWS CLI)](Replication.CreatingReplGroup.NoExistingCluster.Classic.md#Replication.CreatingReplGroup.NoExistingCluster.Classic.CLI)
+ [create-replication-group](https://docs.aws.amazon.com/cli/latest/reference/elasticache/create-replication-group.html)

### Valkey 또는 Redis OSS용 새 노드 기반 클러스터에서 전송 중 암호화 활성화(클러스터 모드 활성화)(CLI)
<a name="in-transit-encryption-enable-cli-redis-cluster"></a>

AWS CLI작업`create-replication-group`과 다음 파라미터를 사용하여 전송 중 데이터 암호화가 활성화된 Valkey 또는 Redis OSS(클러스터 모드 활성화됨) 복제 그룹을 생성합니다.

**키 파라미터:**
+ **--engine** - `valkey` 또는 `redis`이어야 합니다.
+ **--engine-version** - 엔진이 Redis OSS인 경우 3.2.6, 4.0.10 또는 그 이상이어야 합니다.
+ **--transit-encryption-enabled** - 필수입니다. 전송 중 데이터 암호화를 활성화하면 `--cache-subnet-group` 파라미터의 값도 제공해야 합니다.
+ 다음 파라미터 세트 중 하나를 사용해 복제 그룹의 노드 그룹 구성을 지정합니다.
  + **--num-node-groups** - 이 복제 그룹의 샤드(노드 그룹) 수를 지정합니다. 이 파라미터의 최대값은 500입니다.

    **--replicas-per-node-group** - 각 노드 그룹의 복제 노드 수를 지정합니다. 여기서 지정된 값은 복제 그룹의 모든 샤드에 적용됩니다. 이 파라미터의 최대값은 5입니다.
  + **--node-group-configuration** - 각 샤드의 구성을 독립적으로 지정합니다.

자세한 내용은 다음을 참조하세요.
+ [처음부터 Valkey 또는 Redis OSS(클러스터 모드 활성화됨) 복제 그룹 만들기(AWS CLI)](Replication.CreatingReplGroup.NoExistingCluster.Cluster.md#Replication.CreatingReplGroup.NoExistingCluster.Cluster.CLI)
+ [create-replication-group](https://docs.aws.amazon.com/cli/latest/reference/elasticache/create-replication-group.html)

### AWS CLI을(를) 사용하여 기존 클러스터에 전송 중 암호화 활성화
<a name="in-transit-encryption-enable-cli-redis-cluster-existing-cli"></a>

전송 중 암호화 활성화는 두 단계 프로세스이므로, 먼저 전송 암호화 모드를 `preferred`(으)로 설정해야 합니다. 이 모드는 Valkey 또는 Redis OSS 클라이언트가 암호화된 연결과 암호화되지 않은 연결을 모두 사용하여 연결할 수 있도록 합니다. 암호화된 연결을 사용하도록 모든 Valkey 또는 Redis OSS 클라이언트를 마이그레이션한 후, 클러스터 구성을 수정하여 전송 암호화 모드를 `required`(으)로 설정할 수 있습니다. 전송 암호화 모드를 `required`(으)로 설정하면 암호화되지 않은 모든 연결이 끊어지고 암호화된 연결만 허용됩니다.

AWS CLI작업`modify-replication-group`과 다음 파라미터를 사용하여 전송 중 데이터 암호화가 비활성화된 Valkey 또는 Redis OSS(클러스터 모드 활성화됨) 복제 그룹을 업데이트합니다.

**전송 중 암호화를 활성화하려면**

1. 다음 파라미터를 사용하여 전송 암호화 모드를 `preferred`(으)로 설정
   + **--transit-encryption-enabled** - 필수입니다.
   + **--transit-encryption-mode** - `preferred`(으)로 설정해야 합니다.

1. 다음 파라미터를 사용하여 전송 암호화 모드를 `required`(으)로 설정합니다.
   + **--transit-encryption-enabled** - 필수입니다.
   + **--transit-encryption-mode** - `required`(으)로 설정해야 합니다.

# valkey-cli를 사용하여 전송 중 암호화를 통해 ElastiCache(Valkey) 또는 Amazon ElastiCache for Redis OSS에 연결
<a name="connect-tls"></a>

전송 중 암호화가 활성화된 ElastiCache for Redis OSS 캐시에서 데이터에 액세스하려면 Secure Sockets Layer(SSL)로 작업하는 클라이언트를 사용해야 합니다. 또한 Amazon Linux 및 Amazon Linux 2에서 TLS/SSL과 함께 valkey-cli를 사용할 수 있습니다. 클라이언트가 TLS를 지원하지 않는 경우 클라이언트 호스트에서 `stunnel` 명령을 사용하여 Redis OSS 노드에 SSL 터널을 생성할 수 있습니다.

## Linux를 사용한 암호화된 연결
<a name="connect-tls.linux"></a>

valkey-cli를 사용하여 Amazon Linux 2 또는 Amazon Linux에서 전송 중 암호화가 활성화된 Valkey 또는 Redis OSS 클러스터에 연결하려면 다음 단계를 따르세요.

1. valkey-cli 유틸리티를 다운로드하고 컴파일합니다. 이 유틸리티는 Valkey 소프트웨어 배포에 포함되어 있습니다.

1. EC2 인스턴스의 명령 프롬프트에 사용 중인 Linux 버전에 적합한 명령을 입력합니다.

   ** Amazon Linux 2**

   Amazon Linux 2를 사용하는 경우 다음을 입력합니다.

   ```
   sudo yum -y install openssl-devel gcc
   wget https://github.com/valkey-io/valkey/archive/refs/tags/7.2.6.tar.gz
   tar xvzf valkey-7.2.6.tar.gz
   cd valkey-7.2.6
   make distclean
   make valkey-cli BUILD_TLS=yes
   sudo install -m 755 src/valkey-cli /usr/local/bin/
   ```

   **Amazon Linux** – 

   Amazon Linux를 사용하는 경우 다음을 입력합니다.

   ```
   sudo yum install gcc jemalloc-devel openssl-devel tcl tcl-devel clang wget
   wget https://github.com/valkey-io/valkey/archive/refs/tags/8.0.0.tar.gz
   tar xvzf valkey-8.0.0.tar.gz
   cd valkey-8.0.0
   make valkey-cli CC=clang BUILD_TLS=yes
   sudo install -m 755 src/valkey-cli /usr/local/bin/
   ```

   Amazon Linux에서 다음 추가 단계를 실행해야 할 수도 있습니다.

   ```
   sudo yum install clang
   CC=clang make
   sudo make install
   ```

1. valkey-cli 유틸리티를 다운로드하고 설치한 후에는 선택적 `make-test` 명령을 실행하는 것이 좋습니다.

1. 암호화 및 인증이 활성화된 클러스터에 연결하려면 다음 명령을 입력합니다.

   ```
   valkey-cli -h Primary or Configuration Endpoint --tls -a 'your-password' -p 6379
   ```
**참고**  
Amazon Linux 2023에 redis6을 설치하는 경우 이제 `valkey-cli` 대신 `redis6-cli` 명령을 사용할 수 있습니다.  

   ```
   redis6-cli -h Primary or Configuration Endpoint --tls -p 6379
   ```

## stunnel을 사용한 암호화된 연결
<a name="connect-tls.stunnel"></a>

valkey-cli를 사용하여 stunnel을 통한 전송 중 데이터 암호화가 활성화된 Redis OSS 클러스터에 연결하려면 다음 단계를 따르세요.

1. SSH를 사용하여 클라이언트에 연결하고 `stunnel`을 설치합니다.

   ```
   sudo yum install stunnel
   ```

1. `'/etc/stunnel/valkey-cli.conf'` 파일을 생성하는 동시에 편집하기 위한 다음 명령을 실행하여 ElastiCache for Redis OSS 클러스터 엔드포인트를 아래 제공된 출력을 템플릿으로 사용하여 1개 이상의 연결 파라미터에 추가하세요.

   ```
   vi /etc/stunnel/valkey-cli.conf
   
   				
   fips = no
   setuid = root
   setgid = root
   pid = /var/run/stunnel.pid
   debug = 7 
   delay = yes
   options = NO_SSLv2
   options = NO_SSLv3
   [valkey-cli]
      client = yes
      accept = 127.0.0.1:6379
      connect = primary.ssltest.wif01h.use1.cache.amazonaws.com:6379
   [valkey-cli-replica]
      client = yes
      accept = 127.0.0.1:6380
      connect = ssltest-02.ssltest.wif01h.use1.cache.amazonaws.com:6379
   ```

   이 예에서는 구성 파일에 두 가지 연결, 즉 `valkey-cli`와 `valkey-cli-replica`가 있습니다. 파라미터는 다음과 같이 설정되어 있습니다.
   + **client**는 이 stunnel 인스턴스를 클라이언트로 지정하기 위해 yes로 설정되어 있습니다.
   + **accept**는 클라이언트 IP로 설정되어 있습니다. 이 예에서는 프라이머리 노드가 Redis OSS 기본인 포트 6379의 127.0.0.1로 설정되어 있습니다. 복제본은 다른 포트를 호출해야 하며 6380으로 설정되어야 합니다. 휘발성 포트 1024\$165535를 사용할 수 있습니다. 자세한 내용은 *Amazon VPC 사용 설명서*의 [휘발성 포트](https://docs.aws.amazon.com/AmazonVPC/latest/UserGuide/VPC_ACLs.html#VPC_ACLs_Ephemeral_Ports) 섹션을 참조하세요.
   + **연결**은 Redis 서버 엔드포인트로 설정되어 있습니다. 자세한 내용은 [ElastiCache에서 연결 엔드포인트 찾기](Endpoints.md) 섹션을 참조하세요.

1. Start `stunnel`.

   ```
   sudo stunnel /etc/stunnel/valkey-cli.conf
   ```

   `netstat` 명령을 사용하여 터널이 시작되었는지 확인합니다.

   ```
   sudo netstat -tulnp | grep -i stunnel
   				
   tcp        0      0 127.0.0.1:6379              0.0.0.0:*                   LISTEN      3189/stunnel        
   tcp        0      0 127.0.0.1:6380              0.0.0.0:*                   LISTEN      3189/stunnel
   ```

1. 터널의 로컬 엔드포인트를 사용하여 암호화된 Redis OSS 노드에 연결합니다.
   + ElastiCache for Redis OSS 클러스터 생성 중 AUTH 암호를 사용하지 않은 경우, 이 예에서는 Amazon Linux에서 valkey-cli에 대한 완전한 경로로 ElastiCache for Redis OSS 서버에 연결하기 위해 valkey-cli를 사용합니다.

     ```
     /home/ec2-user/redis-7.2.5/src/valkey-cli -h localhost -p 6379
     ```

     Redis OSS 클러스터 생성 중 AUTH 암호가 사용된 경우 이 예에서는 Amazon Linux에서 valkey-cli에 대한 완전한 경로로 Redis OSS 서버에 연결하기 위해 valkey-cli를 사용합니다.

     ```
      /home/ec2-user/redis-7.2.5/src/valkey-cli -h localhost -p 6379 -a my-secret-password
     ```

   OR
   + redis-7.2.5로 디렉토리를 변경하고 다음을 수행합니다.

     ElastiCache for Redis OSS 클러스터 생성 중 AUTH 암호를 사용하지 않은 경우, 이 예에서는 Amazon Linux에서 valkey-cli에 대한 완전한 경로로 ElastiCache for Redis OSS 서버에 연결하기 위해 valkey-cli를 사용합니다.

     ```
     src/valkey-cli -h localhost -p 6379
     ```

     Redis OSS 클러스터 생성 중 AUTH 암호가 사용된 경우 이 예에서는 Amazon Linux에서 valkey-cli에 대한 완전한 경로로 Valkey 또는 Redis OSS 서버에 연결하기 위해 valkey-cli를 사용합니다.

     ```
     src/valkey-cli -h localhost -p 6379 -a my-secret-password	
     ```

   이 예에서는 Telnet을 사용하여 Valkey Redis OSS 서버에 연결합니다.

   ```
   telnet localhost 6379
   			
   Trying 127.0.0.1...
   Connected to localhost.
   Escape character is '^]'.
   auth MySecretPassword
   +OK
   get foo
   $3
   bar
   ```

1. SSL 터널을 중단하고 닫으려면 stunnel 프로세스를 `pkill`합니다.

   ```
   sudo pkill stunnel
   ```

# Python을 사용하여 노드 기반 Redis OSS 클러스터에서 전송 중 데이터 암호화 활성화
<a name="in-transit-encryption-enable-python"></a>

다음 가이드에서는 원래 전송 중 데이터 암호화가 비활성화된 상태로 생성된 Redis OSS 7.0 클러스터에서 전송 중 데이터 암호화를 활성화하는 방법을 보여줍니다. TCP 및 TLS 클라이언트는 이 프로세스 동안 가동 중지 시간 없이 클러스터와 계속 통신합니다.

Boto3는 환경 변수에서 필요한 보안 인증 정보(`aws_access_key_id`, `aws_secret_access_key` 및 `aws_session_token`)를 가져옵니다. 이러한 보안 인증 정보는 이 가이드에 표시된 Python 코드를 처리하기 위해 `python3`를 실행할 동일한 bash 터미널에 미리 붙여넣어집니다. 아래 예제의 코드는 ElastiCache Redis OSS 클러스터를 생성하는 데 사용될 동일한 VPC에서 시작된 EC2 인스턴스에서 처리된 코드입니다.

**참고**  
다음 예에서는 boto3 SDK for ElastiCache 관리 작업(클러스터 또는 사용자 생성)과 데이터 처리를 위한 redis-py/redis-py-cluster를 사용합니다.
클러스터 수정 API와 함께 온라인 TLS 마이그레이션을 사용하려면 최소한 boto3 버전 (=\$1) 1.26.39를 사용해야 합니다.
ElastiCache는 Valkey 버전 7.2 이상 또는 Redis OSS 버전 7.0 이상의 클러스터에 대해서만 온라인 TLS 마이그레이션을 지원합니다. 따라서 7.0 이전의 Redis OSS 버전을 실행하는 클러스터가 있는 경우 클러스터의 Redis OSS 버전을 업그레이드해야 합니다. 버전 차이에 대한 자세한 내용은 [메이저 엔진 버전 동작 및 Redis OSS와의 호환성 차이](VersionManagementConsiderations.md) 섹션을 참조하세요.

**Topics**
+ [ElastiCache Valkey 또는 Redis OSS 클러스터를 시작할 문자열 상수를 정의합니다.](#enable-python-define-constants)
+ [클러스터 구성을 위한 클래스를 정의합니다.](#enable-python-define-classes)
+ [클러스터 자체를 나타내는 클래스를 정의합니다.](#enable-python-define-classes-cluster)
+ [(선택 사항) Valkey 또는 Redis OSS 클러스터에 대한 클라이언트 연결을 시연하는 래퍼 클래스 생성](#enable-python-create-wrapper)
+ [전송 중 데이터 암호화 구성 변경 프로세스를 시연하는 기본 함수 생성](#enable-python-main-function)

## ElastiCache Valkey 또는 Redis OSS 클러스터를 시작할 문자열 상수를 정의합니다.
<a name="enable-python-define-constants"></a>

먼저 , `security-group` `Cache Subnet group`및와 같이 ElastiCache 클러스터를 생성하는 데 필요한AWS엔터티의 이름을 포함하는 몇 가지 간단한 Python 문자열 상수를 정의해 보겠습니다`default parameter group`. 이러한 모든AWS엔터티는 사용하려는 리전의AWS계정에 미리 생성해야 합니다.

```
#Constants definitions 
SECURITY_GROUP = "sg-0492aa0a29c558427"
CLUSTER_DESCRIPTION = "This cluster has been launched as part of the online TLS migration user guide"
EC_SUBNET_GROUP = "client-testing"
DEFAULT_PARAMETER_GROUP_REDIS_7_CLUSTER_MODE_ENABLED = "default.redis7.cluster.on"
```

## 클러스터 구성을 위한 클래스를 정의합니다.
<a name="enable-python-define-classes"></a>

이제 클러스터의 구성을 나타내는 몇 가지 간단한 Python 클래스를 정의해 보겠습니다. 이 클래스에는 Valkey 또는 Redis OSS 버전, 인스턴스 유형, 전송 중 데이터 암호화(TLS) 활성화 또는 비활성화 여부와 같은 클러스터에 대한 메타데이터가 보관됩니다.

```
#Class definitions

class Config:
    def __init__(
        self,
        instance_type: str = "cache.t4g.small",
        version: str = "7.0",
        multi_az: bool = True,
        TLS: bool = True,
        name: str = None,
    ):
        self.instance_type = instance_type
        self.version = version
        self.multi_az = multi_az
        self.TLS = TLS
        self.name = name or f"tls-test"

    def create_base_launch_request(self):
        return {
            "ReplicationGroupId": self.name,
            "TransitEncryptionEnabled": self.TLS,
            "MultiAZEnabled": self.multi_az,
            "CacheNodeType": self.instance_type,
            "Engine": "redis",
            "EngineVersion": self.version,
            "CacheSubnetGroupName": EC_SUBNET_GROUP ,
            "CacheParameterGroupName": DEFAULT_PARAMETER_GROUP_REDIS_7_CLUSTER_MODE_ENABLED ,
            "ReplicationGroupDescription": CLUSTER_DESCRIPTION,
            "SecurityGroupIds": [SECURITY_GROUP],
        }
        
class ConfigCME(Config):
    def __init__(
        self,
        instance_type: str = "cache.t4g.small",
        version: str = "7.0",
        multi_az: bool = True,
        TLS: bool = True,
        name: str = None,
        num_shards: int = 2,
        num_replicas_per_shard: int = 1,
    ):
        super().__init__(instance_type, version, multi_az, TLS, name)
        self.num_shards = num_shards
        self.num_replicas_per_shard = num_replicas_per_shard

    def create_launch_request(self) -> dict:
        launch_request = self.create_base_launch_request()
        launch_request["NumNodeGroups"] = self.num_shards
        launch_request["ReplicasPerNodeGroup"] = self.num_replicas_per_shard
        return launch_request
```

## 클러스터 자체를 나타내는 클래스를 정의합니다.
<a name="enable-python-define-classes-cluster"></a>

이제 ElastiCache Valkey 또는 Redis OSS 클러스터 자체를 나타내는 몇 가지 간단한 Python 클래스를 정의해 보겠습니다. 이 클래스에는 클러스터 생성 및 ElastiCache API 쿼리와 같은 ElastiCache 관리 작업을 위한 boto3 클라이언트가 보관된 클라이언트 필드가 있습니다.

```
import botocore.config
import boto3

# Create boto3 client
def init_client(region: str = "us-east-1"):
    config = botocore.config.Config(retries={"max_attempts": 10, "mode": "standard"})
    init_request = dict()
    init_request["config"] = config
    init_request["service_name"] = "elasticache"
    init_request["region_name"] = region
    return boto3.client(**init_request) 
 
 
class ElastiCacheClusterBase:
    def __init__(self, name: str):
        self.name = name
        self.elasticache_client = init_client()

    def get_first_replication_group(self):
        return self.elasticache_client.describe_replication_groups(
        ReplicationGroupId=self.name
        )["ReplicationGroups"][0]
 
    def get_status(self) -> str:
        return self.get_first_replication_group()["Status"]
 
    def get_transit_encryption_enabled(self) -> bool:
        return self.get_first_replication_group()["TransitEncryptionEnabled"]
 
    def is_available(self) -> bool:
        return self.get_status() == "available"
        
    def is_modifying(self) -> bool:
        return self.get_status() == "modifying"
        
    def wait_for_available(self):
        while True:
            if self.is_available():
                break
            else:
                time.sleep(5)

    def wait_for_modifying(self):
        while True:
            if self.is_modifying():
                break
            else:
                time.sleep(5)
                
    def delete_cluster(self) -> bool:
        self.elasticache_client.delete_replication_group(
            ReplicationGroupId=self.name, RetainPrimaryCluster=False
        )
        
    def modify_transit_encryption_mode(self, new_transit_encryption_mode: str):
        # generate api call to migrate the cluster to TLS preffered or to TLS required
            self.elasticache_client.modify_replication_group(
                ReplicationGroupId=self.name,
                TransitEncryptionMode=new_transit_encryption_mode,
                TransitEncryptionEnabled=True,
                ApplyImmediately=True,
            )  
        self.wait_for_modifying()
              
 class ElastiCacheClusterCME(ElastiCacheClusterBase):
    def __init__(self, name: str):
        super().__init__(name)

    @classmethod
    def launch(cls, config: ConfigCME = None) -> ElastiCacheClusterCME:
        config = config or ConfigCME()
        print(config)
        new_cluster = ElastiCacheClusterCME(config.name)
        launch_request = config.create_launch_request()
        new_cluster.elasticache_client.create_replication_group(**launch_request)
        new_cluster.wait_for_available()
        return new_cluster

    def get_configuration_endpoint(self) -> str:
        return self.get_first_replication_group()["ConfigurationEndpoint"]["Address"]
     
#Since the code can throw exceptions, we define this class to make the code more readable and 
#so we won't forget to delete the cluster    
class ElastiCacheCMEManager:
    def __init__(self, config: ConfigCME = None):
        self.config = config or ConfigCME()

    def __enter__(self) -> ElastiCacheClusterCME:
        self.cluster = ElastiCacheClusterCME.launch(self.config)
        return self.cluster 
          
    def __exit__(self, exc_type, exc_val, exc_tb):
        self.cluster.delete_cluster()
```

## (선택 사항) Valkey 또는 Redis OSS 클러스터에 대한 클라이언트 연결을 시연하는 래퍼 클래스 생성
<a name="enable-python-create-wrapper"></a>

이제 `redis-py-cluster` 클라이언트를 위한 래퍼 클래스를 생성해 보겠습니다. 이 래퍼 클래스는 클러스터를 일부 키로 미리 채운 다음 무작위로 반복되는 `get` 명령을 수행하는 것을 지원합니다.

**참고**  
이 단계는 선택 사항이지만 이후 단계에 나오는 기본 함수의 코드를 단순화합니다.

```
import redis
improt random
from time import perf_counter_ns, time


class DowntimeTestClient:
    def __init__(self, client):
        self.client = client

        # num of keys prefilled
        self.prefilled = 0
        # percent of get above prefilled
        self.percent_get_above_prefilled = 10 # nil result expected when get hit above prefilled
        # total downtime in nano seconds 
        self.downtime_ns = 0
        # num of success and fail operations
        self.success_ops = 0
        self.fail_ops = 0
        self.connection_errors = 0
        self.timeout_errors = 0
        

    def replace_client(self, client):
        self.client = client

    def prefill_data(self, timelimit_sec=60):
        end_time = time() + timelimit_sec
        while time() < end_time:
            self.client.set(self.prefilled, self.prefilled)
            self.prefilled += 1

    # unsuccesful operations throw exceptions
    def _exec(self, func):
        try:
            start_ns = perf_counter_ns()
            func()
            self.success_ops += 1
            elapsed_ms = (perf_counter_ns() - start_ns) // 10 ** 6
            # upon succesful execution of func
            # reset random_key to None so that the next command
            # will use a new random key
            self.random_key = None

        except Exception as e:
            elapsed_ns = perf_counter_ns() - start_ns
            self.downtime_ns += elapsed_ns
            # in case of failure- increment the relevant counters so that we will keep track 
            # of how many connection issues we had while trying to communicate with
            # the cluster.
            self.fail_ops += 1
            if e.__class__ is redis.exceptions.ConnectionError:
                self.connection_errors += 1
            if e.__class__ is redis.exceptions.TimeoutError:
                self.timeout_errors += 1

    def _repeat_exec(self, func, seconds):
        end_time = time() + seconds
        while time() < end_time:
            self._exec(func)

    def _new_random_key_if_needed(self, percent_above_prefilled):
        if self.random_key is None:
            max = int((self.prefilled * (100 + percent_above_prefilled)) / 100)
            return random.randint(0, max)
        return self.random_key

    def _random_get(self):
        key = self._new_random_key_if_needed(self.percent_get_above_prefilled)
        result = self.client.get(key)
        # we know the key was set for sure only in the case key < self.prefilled
        if key < self.prefilled:
            assert result.decode("UTF-8") == str(key)


    def repeat_get(self, seconds=60):
        self._repeat_exec(self._random_get, seconds)

    def get_downtime_ms(self) -> int:
        return self.downtime_ns // 10 ** 6


    def do_get_until(self, cond_check):
        while not cond_check():
            self.repeat_get()
        # do one more get cycle once condition is met
        self.repeat_get()
```

## 전송 중 데이터 암호화 구성 변경 프로세스를 시연하는 기본 함수 생성
<a name="enable-python-main-function"></a>

이제 다음을 수행하는 기본 함수를 정의해 보겠습니다.

1. boto3 ElastiCache 클라이언트를 사용하여 클러스터를 생성합니다.

1. TLS 없이 명확한 TCP 연결로 클러스터에 연결할 `redis-py-cluster` 클라이언트를 초기화합니다.

1. `redis-py-cluster` 클라이언트는 클러스터를 일부 데이터로 미리 채웁니다.

1. boto3 클라이언트는 비 TLS에서 TLS 선호로의 TLS 마이그레이션을 트리거합니다.

1. 클러스터를 `Preferred` TLS로 마이그레이션하는 동안 `redis-py-cluster` TCP 클라이언트는 마이그레이션이 완료될 때까지 클러스터에 반복 `get` 작업을 전송합니다.

1. TLS `Preferred`로의 마이그레이션이 완료되면 클러스터가 전송 중 데이터 암호화를 지원하는지 확인합니다. 그런 다음 TLS를 사용하여 클러스터에 연결할 `redis-py-cluster` 클라이언트를 생성합니다.

1. 새 TLS 클라이언트와 이전 TCP 클라이언트를 사용하여 몇 가지 `get` 명령을 보내겠습니다.

1. boto3 클라이언트는 TLS `Preferred`에서 TLS 필수로의 TLS 마이그레이션을 트리거합니다.

1. 클러스터를 TLS로 마이그레이션하는 동안 redis-py-cluster TCP 클라이언트는 마이그레이션이 완료될 때까지 클러스터에 반복 `get` 작업을 전송합니다.

```
import redis

def init_cluster_client(
    cluster: ElastiCacheClusterCME, prefill_data: bool, TLS: bool = True) -> DowntimeTestClient:
    # we must use for the host name the cluster configuration endpoint. 
    redis_client = redis.RedisCluster(
        host=cluster.get_configuration_endpoint(), ssl=TLS, socket_timeout=0.25, socket_connect_timeout=0.1
    )
    test_client = DowntimeTestClient(redis_client)
    if prefill_data:
        test_client.prefill_data()
    return test_client

if __name__ == '__main__':
    config = ConfigCME(TLS=False, instance_type="cache.m5.large")

    with ElastiCacheCMEManager(config) as cluster:
        # create a client that will connect to the cluster with clear tcp connection
        test_client_tcp = init_cluster_client(cluster, prefill_data=True, TLS=False)
        
       # migrate the cluster to TLS Preferred
        cluster.modify_transit_encryption_mode(new_transit_encryption_mode="preferred")
        
        # do repeated get commands until the cluster finishes the migration to TLS Preferred
        test_client_tcp.do_get_until(cluster.is_available)
        
       # verify that in transit encryption is enabled so that clients will be able to connect to the cluster with TLS
        assert cluster.get_transit_encryption_enabled() == True
        
       # create a client that will connect to the cluster with TLS connection. 
        # we must first make sure that the cluster indeed supports TLS
        test_client_tls = init_cluster_client(cluster, prefill_data=True, TLS=True)
        
        # by doing get commands with the tcp client for 60 more seconds
       # we can verify that the existing tcp connection to the cluster still works 
        test_client_tcp.repeat_get(seconds=60)
        
        # do get commands with the new TLS client for 60 more seconds
        test_client_tcp.repeat_get(seconds=60)
        
       # migrate the cluster to TLS required
        cluster.modify_transit_encryption_mode(new_transit_encryption_mode="required")
        
       # from this point the tcp clients will be disconnected and we must not use them anymore.
       # do get commands with the TLS client until the cluster finishes migartion to TLS required mode.
        test_client_tls.do_get_until(cluster.is_available)
```

# 전송 중 암호화 활성화 시 모범 사례
<a name="enable-python-best-practices"></a>

## 전송 중 데이터 암호화를 활성화하기 전: DNS 레코드를 올바르게 처리했는지 확인하세요.
<a name="enable-python-best-practices-before"></a>

**참고**  
이 프로세스에서 기존 엔드포인트를 변경 및 삭제합니다. 엔드포인트를 잘못 사용하면 Valkey 또는 Redis OSS 클라이언트가 이전 엔드포인트 및 삭제된 엔드포인트를 사용하여 클러스터에 연결하지 못하게 될 수 있습니다.

클러스터가 TLS가 지원되지 않는 상태에서 TLS 선호로 마이그레이션되는 동안 이전 클러스터 구성 엔드포인트 DNS 레코드가 유지되고 새 클러스터 구성 엔드포인트 DNS 레코드가 다른 형식으로 생성됩니다. TLS 지원 클러스터는 TLS가 지원되지 않는 클러스터와 다른 형식의 DNS 레코드를 사용합니다. ElastiCache는 클러스터가 암호화 모드: `encryption mode: Preferred`로 구성될 때 애플리케이션 및 다른 Valkey 또는 Redis OSS 클라이언트가 둘 사이를 전환할 수 있도록 두 DNS 레코드를 모두 보관합니다. DNS 레코드의 다음 변경 사항은 TLS 마이그레이션 프로세스 중에 발생합니다.

### 전송 중 데이터 암호화를 활성화할 때 발생하는 DNS 레코드의 변경 사항에 대한 설명
<a name="enable-python-best-practices-before-desc"></a>

**CME 클러스터의 경우**

클러스터가 '전송 암호화 모드: 선호'로 설정된 경우:
+ TLS가 지원되지 않는 클러스터의 원래 클러스터 구성 엔드포인트는 활성 상태로 유지됩니다. 클러스터를 TLS 암호화 모드 '없음'에서 '선호'로 재구성해도 가동 중지가 발생하지 않습니다.
+ 클러스터를 TLS 선호 모드로 설정하면 새 TLS Valkey 또는 Redis OSS 엔드포인트가 생성됩니다. 이러한 새 엔드포인트는 이전 엔드포인트와 동일한 IP(비 TLS)로 변환됩니다.
+ 새로운 TLS Valkey 또는 Redis OSS 구성 엔드포인트는 ElastiCache 콘솔에서 및 `describe-replication-group` API에 대한 응답으로 노출됩니다.

클러스터가 '전송 암호화 모드: 필수'로 설정된 경우:
+ TLS가 지원되지 않는 이전 엔드포인트는 삭제됩니다. TLS 클러스터 엔드포인트의 가동 중지는 없습니다.
+ ElastiCache 콘솔 또는 `describe-replication-group` API에서 새 `cluster-configuration-endpoint`를 검색할 수 있습니다.

**자동 장애 조치가 활성화되었거나 자동 장애 조치가 비활성화된 CMD 클러스터의 경우**

복제 그룹이 '전송 암호화 모드: 선호'로 설정된 경우:
+ TLS가 지원되지 않는 클러스터의 원래 프라이머리 엔드포인트 및 리더 엔드포인트는 활성 상태로 유지됩니다.
+ 클러스터를 TLS `Preferred` 모드로 설정하면 새 TLS 프라이머리 및 리더 엔드포인트가 생성됩니다. 이 새 엔드포인트는 이전 엔드포인트와 동일한 IP(TLS 없음)로 변환됩니다.
+ 새로운 프라이머리 엔드포인트 및 리더 엔드포인트는 ElastiCache 콘솔에서 및 `describe-replication-group` API에 대한 응답으로 노출됩니다.

복제 그룹이 '전송 암호화 모드: 필수'로 설정된 경우:
+ 기존의 비 TLS 프라이머리 엔드포인트와 리더 엔드포인트는 삭제됩니다. TLS 클러스터 엔드포인트의 가동 중지는 없습니다.
+ ElastiCache 콘솔 또는 `describe-replication-group` API에서 새 프라이머리 엔드포인트 및 리더 엔드포인트를 검색할 수 있습니다.

### DNS 레코드의 권장 사용
<a name="enable-python-best-practices-before-usage"></a>

**CME 클러스터의 경우 **
+ 애플리케이션 코드에서 노드별 DNS 레코드 대신 클러스터 구성 엔드포인트를 사용하세요. 노드별 DNS 이름을 직접 사용하는 것은 권장되지 않습니다. 마이그레이션 중에 DNS 이름이 변경되고 애플리케이션 코드가 클러스터에 대한 연결을 끊기 때문입니다.
+ 클러스터 구성 엔드포인트는 이 프로세스 중에 변경되므로 애플리케이션에서 클러스터 구성 엔드포인트를 하드코딩하지 마세요.
+ 클러스터 구성 엔드포인트는 이 프로세스 중에 변경될 수 있으므로 애플리케이션에서 클러스터 구성 엔드포인트를 하드코딩하는 것은 좋지 않습니다. 전송 중 데이터 암호화가 완료된 후 `describe-replication-group` API로 클러스터 구성 엔드포인트를 쿼리하고(위에 굵게 표시) 이 시점부터 응답으로 받은 DNS를 사용하세요.

**자동 장애 조치가 활성화된 CMD 클러스터의 경우 **
+ 비 TLS에서 TLS 선호로 클러스터를 마이그레이션할 때 이전 노드별 DNS 이름이 삭제되고 새 이름이 생성되므로 애플리케이션 코드에서 노드별 DNS 이름 대신 프라이머리 엔드포인트와 리더 엔드포인트를 사용하세요. 향후 클러스터에 복제본을 추가할 수 있으므로 노드별 DNS 이름을 직접 사용하는 것은 권장되지 않습니다. 또한 자동 장애 조치가 활성화되면 프라이머리 클러스터 및 복제본의 역할이 ElastiCache 서비스에 의해 자동으로 변경됩니다. 이러한 변경 사항을 추적하는 데 도움이 되도록 프라이머리 엔드포인트와 리더 엔드포인트를 사용하는 것이 좋습니다. 마지막으로 리더 엔드포인트를 사용하면 복제본의 읽기를 클러스터의 복제본 간에 균등하게 분산하는 데 도움이 됩니다.
+ TLS 마이그레이션 프로세스 중에 변경될 수 있으므로 애플리케이션에서 프라이머리 엔드포인트와 리더 엔드포인트를 하드코딩하는 것은 좋지 않습니다. TLS 선호로의 마이그레이션 변경이 완료되면 describe-replication-group API를 사용하여 프라이머리 엔드포인트 및 리더 엔드포인트를 쿼리하고 이 시점부터 응답으로 받은 DNS를 사용하세요. 이렇게 하면 엔드포인트의 변경 사항을 동적으로 추적할 수 있습니다.

**자동 장애 조치가 비활성화된 CMD 클러스터의 경우 **
+ 애플리케이션 코드에서 노드별 DNS 이름 대신 프라이머리 엔드포인트와 리더 엔드포인트를 사용하세요. 자동 장애 조치가 비활성화되면 자동 장애 조치가 활성화되었을 때 ElastiCache 서비스에서 자동으로 관리되는 크기 조정, 패치, 장애 조치 및 기타 절차를 사용자가 대신 수행합니다. 이렇게 하면 여러 엔드포인트를 쉽게 수동으로 추적할 수 있습니다. 비 TLS에서 TLS 선호로 클러스터를 마이그레이션할 때 이전 노드별 DNS 이름이 삭제되고 새 이름이 생성되므로 노드별 DNS 이름을 직접 사용하지 마세요. 이는 TLS 마이그레이션 중에 클라이언트가 클러스터에 연결할 수 있도록 하기 위한 필수 사항입니다. 또한 리더 엔드포인트를 사용할 때 복제본 간에 읽기를 균등하게 분산하고 클러스터에서 복제본을 추가하거나 삭제할 때 DNS 레코드를 추적할 수 있다는 이점이 있습니다.
+ 클러스터 구성 엔드포인트는 TLS 마이그레이션 프로세스 중에 변경될 수 있으므로 애플리케이션에서 클러스터 구성 엔드포인트를 하드코딩하는 것은 좋지 않습니다.

## 전송 중 데이터 암호화 중: 마이그레이션 프로세스가 언제 완료되는지에 주의 기울이기
<a name="enable-python-best-practices-during"></a>

전송 중 데이터 암호화 모드 변경은 즉시 이루어지지 않으며 시간이 좀 걸릴 수 있습니다. 대규모 클러스터의 경우 특히 그렇습니다. 클러스터가 TLS 선호로 마이그레이션을 완료한 후에만 TCP 연결과 TLS 연결을 모두 수락하고 제공할 수 있습니다. 따라서 전송 중 데이터 암호화가 완료될 때까지 클러스터에 TLS 연결을 설정하려고 시도하는 클라이언트를 생성해서는 안 됩니다.

전송 중 데이터 암호화가 성공적으로 완료되거나 실패했을 때 알림을 받는 방법에는 다음과 같은 여러 가지가 있습니다(위 코드 예에는 표시되지 않음).
+ SNS 서비스를 사용하여 암호화 완료 시 알림 받기
+ 암호화가 완료될 때 이벤트를 발생시키는 `describe-events` API 사용
+ ElastiCache 콘솔에서 암호화가 완료되었다는 메시지 확인

또한 애플리케이션에 로직을 구현하여 암호화가 완료되었는지 확인할 수 있습니다. 위의 예에서는 클러스터가 마이그레이션을 완료하도록 하는 몇 가지 방법을 살펴보았습니다.
+ 마이그레이션 프로세스가 시작될 때까지 대기(클러스터 상태가 ‘수정 중’으로 변경됨) 및 수정이 완료될 때까지 대기(클러스터 상태가 다시 ‘사용 가능’으로 변경됨)
+ `describe-replication-group` API를 쿼리하여 클러스터의 `transit_encryption_enabled`가 True로 설정되었는지 확인.

### 전송 중 데이터 암호화를 활성화한 후: 사용하는 클라이언트가 올바르게 구성되었는지 확인
<a name="enable-python-best-practices-after"></a>

클러스터가 TLS 선호 모드에 있는 동안 애플리케이션은 클러스터에 대한 TLS 연결을 열고 해당 연결만 사용해야 합니다. 이렇게 하면 전송 중 데이터 암호화를 활성화할 때 애플리케이션이 가동 중지를 겪지 않습니다. SSL 섹션 아래의 info 명령을 사용하여 Valkey 또는 Redis OSS 엔진에 대한 보다 명확한 TCP 연결이 없는지 확인할 수 있습니다.

```
# SSL
ssl_enabled:yes
ssl_current_certificate_not_before_date:Mar 20 23:27:07 2017 GMT
ssl_current_certificate_not_after_date:Feb 24 23:27:07 2117 GMT
ssl_current_certificate_serial:D8C7DEA91E684163
tls_mode_connected_tcp_clients:0   (should be zero)
tls_mode_connected_tls_clients:100
```

## Openssl을 사용하여 전송 중 데이터 암호화가 사용 설정된 노드에 연결(Memcached)
<a name="in-transit-encryption-connect-mc"></a>

전송 중 데이터 암호화가 사용 설정된 ElastiCache for Memcached 노드에서 데이터에 액세스하려면 Secure Sockets Layer(SSL)에서 작업하는 클라이언트를 사용해야 합니다. 또한 Amazon Linux 및 Amazon Linux 2에서 Openssl s\$1client를 사용할 수 있습니다.

Openssl s\$1client를 사용하여 Amazon Linux 2 또는 Amazon Linux에서 전송 중 데이터 암호화가 사용 설정된 Memcached 클러스터에 연결하려면 다음을 수행합니다.

```
/usr/bin/openssl s_client -connect memcached-node-endpoint:memcached-port
```

## Java를 사용하여 TLS Memcached 클라이언트 생성
<a name="in-transit-encryption-connect-java"></a>

TLS 모드로 클라이언트를 생성하려면 다음을 수행하여 적절한 SSLContext를 통해 클라이언트를 초기화합니다.

```
import java.security.KeyStore;
import javax.net.ssl.SSLContext;
import javax.net.ssl.TrustManagerFactory;
import net.spy.memcached.AddrUtil;
import net.spy.memcached.ConnectionFactoryBuilder;
import net.spy.memcached.MemcachedClient;
public class TLSDemo {
    public static void main(String[] args) throws Exception {
        ConnectionFactoryBuilder connectionFactoryBuilder = new ConnectionFactoryBuilder();
        // Build SSLContext
        TrustManagerFactory tmf = TrustManagerFactory.getInstance(TrustManagerFactory.getDefaultAlgorithm());
        tmf.init((KeyStore) null);
        SSLContext sslContext = SSLContext.getInstance("TLS");
        sslContext.init(null, tmf.getTrustManagers(), null);
        // Create the client in TLS mode
        connectionFactoryBuilder.setSSLContext(sslContext);
        MemcachedClient client = new MemcachedClient(connectionFactoryBuilder.build(), AddrUtil.getAddresses("mycluster.fnjyzo.cfg.use1.cache.amazonaws.com:11211"));

        // Store a data item for an hour.
        client.set("theKey", 3600, "This is the data value");
    }
}
```

## PHP를 사용하여 TLS Memcached 클라이언트 생성
<a name="in-transit-encryption-connect-php-mc"></a>

TLS 모드로 클라이언트를 생성하려면 다음을 수행하여 적절한 SSLContext를 통해 클라이언트를 초기화합니다.

```
<?php

/**
 * Sample PHP code to show how to create a TLS Memcached client. In this example we
 * will use the Amazon ElastiCache Auto Descovery feature, but TLS can also be
 * used with a Static mode client. 
 * See Using the ElastiCache Cluster Client for PHP (https://docs.aws.amazon.com/AmazonElastiCache/latest/dg/AutoDiscovery.Using.ModifyApp.PHP.html) for more information 
 * about Auto Discovery and persistent-id.
 */

/* Configuration endpoint to use to initialize memcached client.
 * this is only an example */
$server_endpoint = "mycluster.fnjyzo.cfg.use1.cache.amazonaws.com";

/* Port for connecting to the cluster. 
 * This is only an example     */
$server_port = 11211;

/* Initialize a persistent Memcached client and configure it with the Dynamic client mode  */
$tls_client =  new Memcached('persistent-id');
$tls_client->setOption(Memcached::OPT_CLIENT_MODE, Memcached::DYNAMIC_CLIENT_MODE);

/* Add the memcached's cluster server/s */
$tls_client->addServer($server_endpoint, $server_port);

/* Configure the client to use TLS */
if(!$tls_client->setOption(Memcached::OPT_USE_TLS, 1)) {
    echo $tls_client->getLastErrorMessage(), "\n";
    exit(1);
}

/* Set your TLS context configurations values.
 * See MemcachedTLSContextConfig in memcached-api.php for all configurations */
$tls_config = new MemcachedTLSContextConfig();
$tls_config->hostname = '*.mycluster.fnjyzo.use1.cache.amazonaws.com';
$tls_config->skip_cert_verify = false;
$tls_config->skip_hostname_verify = false;

/* Use the created TLS context configuration object to create OpenSSL's SSL_CTX and set it to your client.
 * Note:  These TLS context configurations will be applied to all the servers connected to this client. */
$tls_client->createAndSetTLSContext((array)$tls_config);

/* test the TLS connection with set-get scenario: */

 /* store the data for 60 seconds in the cluster.
 * The client will decide which cache host will store this item.
 */
if($tls_client->set('key', 'value', 60)) {
    print "Successfully stored key\n";
} else {
    echo "Failed to set key: ", $tls_client->getLastErrorMessage(), "\n";
    exit(1);
}

/* retrieve the key */
if ($tls_client->get('key') === 'value') {
    print "Successfully retrieved key\n";
} else {
    echo "Failed to get key: ", $tls_client->getLastErrorMessage(), "\n";
    exit(1);
}
```

PHP 클라이언트 사용 방법에 관한 자세한 정보는 [PHP용 ElastiCache 클러스터 클라이언트 설치](Appendix.PHPAutoDiscoverySetup.md) 섹션을 참조하세요.