Set up Data Connectivity Proxy
Set up Data Connectivity Proxy (데이터 연결 프록시 설정)
이 단계들을 완료해 DCP(Data Connectivity Proxy) 객체를 만들고, 네트워크에 에이전트를 배포하며, Openflow 커넥터 트래픽을 사설 데이터 소스로 라우팅할 수 있어요. 에이전트 호스트는 최소 1 vCPU와 512MB 메모리가 필요해요.
본문
전체 전제 조건 목록은 전제 조건을 참고해요.
Step 1: Snowflake에서 DCP 객체 생성
ACCOUNTADMIN 역할(또는 CREATE DATA CONNECTIVITY PROXY 권한이 있는 역할)로 Data Connectivity Proxy 객체를 만들어요.
DCP 객체를 만들 때 외부 접근 통합(EAI)을 연결할 수 있어요. 먼저 네트워크 규칙과 EAI를 만든 뒤(Step 6, Step 7):
CREATE DATA CONNECTIVITY PROXY my_dcp_client
EXTERNAL_ACCESS_INTEGRATIONS = (my_private_source_eai)
ENABLED = TRUE;
지금 DCP 객체만 만들고 Step 7에서 EAI를 연결할 수도 있어요:
CREATE DATA CONNECTIVITY PROXY my_dcp_client;
네트워크 정책 연결은 선택 사항이에요. DCP 컨트롤 플레인에 연결할 수 있는 소스 IP를 제한하는 DCP 전용 네트워크 정책을 원할 때만 사용해요:
CREATE DATA CONNECTIVITY PROXY my_dcp_client
NETWORK_POLICY = my_network_policy;
나중에 ALTER DATA CONNECTIVITY PROXY ... SET NETWORK_POLICY로 정책을 연결하거나 변경할 수도 있어요. 자세한 내용은 네트워크 정책으로 네트워크 트래픽 제어를 참고해요.
Note
DCP 객체를 만든 후 계정 수준 TLS 인증서를 발급해요:
SELECT SYSTEM$ISSUE_PER_ACCOUNT_CERTIFICATES();
성공적인 호출은 Certificates will be issued.를 반환해요. 발급은 비동기예요. 계정의 첫 호출 후 최소 30분을 기다린 뒤 에이전트를 시작해요. 함수를 다시 호출해도 추가 효과는 없어요.
자세한 내용은 SYSTEM$ISSUE_PER_ACCOUNT_CERTIFICATES를 참고해요.
Step 2: Bootstrap 토큰 생성
에이전트가 Snowflake로 인증하고 mTLS 인증서를 받는 데 사용할 일회용 bootstrap JWT를 생성해요. 두 번째 인자는 토큰 유효 기간(일)이에요:
SELECT SYSTEM$GENERATE_DATA_CONNECTIVITY_PROXY_BOOTSTRAP_TOKEN('my_dcp_client', 7);
출력 토큰을 저장해요. 에이전트 호스트의 자격 증명 파일에 작성할 거예요.
Important
토큰 형식은 Snowflake Access JWT여야 해요. PAT_로 시작하는 토큰은 허용되지 않으며 에이전트가 시작하지 못하게 해요.
Step 3: 자격 증명 파일 작성
에이전트 호스트에서 토큰을 파일에 작성해요. 에이전트는 시작 시와 인증서 교체 중에 이 파일을 읽어요:
echo '<token from Step 2>' > /etc/dcp-agent/secrets/dcp-bootstrap-token
chmod 600 /etc/dcp-agent/secrets/dcp-bootstrap-token
에이전트는 매 인증서 교체 주기마다 이 파일을 다시 읽어요. 에이전트를 재시작하지 않고 토큰을 업데이트할 수 있어요. 무중단 bootstrap 토큰 교체를 참고해요.
시크릿 매니저에 토큰 저장
bootstrap JWT를 전 세계에서 읽을 수 있는 파일이나 오케스트레이션 매니페스트에 남겨 두지 마세요. AWS Secrets Manager, Microsoft Azure Key Vault, Google Cloud Secret Manager, HashiCorp Vault 같은 시크릿 매니저에 저장한 뒤 에이전트가 마운트하는 자격 증명 경로에 작성해요.
에이전트는 로컬 파일만 읽어요(--sf-bootstrap-credentials, 기본 /etc/dcp-agent/secrets/dcp-bootstrap-token). 자체적으로 시크릿 매니저 API를 호출하지 않아요. 배포 시점이나 사이드카에서 시크릿을 가져와 그 경로에 배치해요. 파일 권한을 제한(chmod 600)하고 시크릿을 읽을 수 있는 IAM 또는 RBAC 신원을 한정해요.
다음 예시들은 시크릿을 /etc/dcp-agent/secrets/dcp-bootstrap-token에 작성해요. 시크릿 이름을 바꾸고 Step 4처럼 에이전트를 시작해요.
AWS Secrets Manager:
aws secretsmanager get-secret-value \
--secret-id dcp/my_dcp_client/bootstrap-token \
--query SecretString \
--output text > /etc/dcp-agent/secrets/dcp-bootstrap-token
chmod 600 /etc/dcp-agent/secrets/dcp-bootstrap-token
Microsoft Azure Key Vault:
az keyvault secret show \
--vault-name <your-key-vault> \
--name dcp-my-dcp-client-bootstrap-token \
--query value \
--output tsv > /etc/dcp-agent/secrets/dcp-bootstrap-token
chmod 600 /etc/dcp-agent/secrets/dcp-bootstrap-token
Google Cloud Secret Manager:
gcloud secrets versions access latest \
--secret=dcp-my-dcp-client-bootstrap-token > /etc/dcp-agent/secrets/dcp-bootstrap-token
chmod 600 /etc/dcp-agent/secrets/dcp-bootstrap-token
bootstrap 토큰을 교체할 때 매니저의 시크릿을 업데이트하고, 자격 증명 파일을 다시 작성하며(무중단 bootstrap 토큰 교체 참고), 에이전트를 실행 중으로 유지해요. 에이전트가 시작되기 전에 파일이 --sf-bootstrap-credentials(또는 기본 마운트 경로)에 나타나기만 하면 CSI 드라이버나 init 컨테이너로 시크릿을 마운트할 수도 있어요.
Step 4: 에이전트 배포
자격 증명 파일을 마운트하며 에이전트 컨테이너를 풀(pull)하고 시작해요:
docker run -d \
--name dcp-agent \
--restart unless-stopped \
-v /etc/dcp-agent/secrets/dcp-bootstrap-token:/etc/dcp-agent/secrets/dcp-bootstrap-token:ro \
-e DCP_METRICS_PORT=9092 \
-p 9092:9092 \
snowflakedb/dcp-client:latest
컨트롤 플레인 URL과 계정 신원은 bootstrap JWT에서 나와요.
토큰을 /etc/dcp-agent/secrets/dcp-bootstrap-token에 마운트하는 것이 기본 경로이므로 --sf-bootstrap-credentials를 전달할 필요가 없어요. 다른 곳에 마운트할 때만 전달해요.
DCP_METRICS_PORT 설정과 포트 게시를 권장해요. 기본적으로 메트릭과 /ready 엔드포인트는 컨테이너 내부의 루프백에 바인딩되어 호스트의 모니터링 스택에서 도달할 수 없어요. Prometheus 메트릭(에이전트 측)을 참고해요.
에이전트 호스트가 Docker Hub에서 이미지를 풀한다면 *.docker.io로 아웃바운드 HTTPS를 허용해요. 이미지를 사설 레지스트리에 복사해 그쪽에서 풀면 이 단계를 건너뛸 수 있어요.
에이전트는 시작해 bootstrap JWT로 컨트롤 플레인에 인증하고, mTLS 인증서 쌍을 받아 릴레이에 연결해요. 이후 JWT는 다음 인증서 교체까지 다시 사용되지 않아요.
Step 5: 에이전트 연결 확인
Snowflake에서 DCP 클라이언트를 설명해 연결 상태를 보이는지 확인해요:
DESCRIBE DATA CONNECTIVITY PROXY my_dcp_client;
AGENT_HEALTH가 HEALTHY이고 AGENT_STATUS가 DCP_AGENT_LIFECYCLE_CONNECTED인지 확인해요. 컬럼 상세는 데이터 연결 프록시 모니터링을 참고해요.
Step 6: 사설 목적지용 네트워크 규칙 생성
에이전트가 도달해야 하는 호스트와 포트를 명명하는 네트워크 규칙을 만들어요. 원시 IP 주소가 아닌 DNS 호스트 이름을 사용해요. MODE = DATA_CONNECTIVITY_PROXY_EGRESS와 TYPE = HOST_PORT를 사용해요. 일반 MODE = EGRESS 규칙은 DCP에 적용되지 않아요.
CREATE NETWORK RULE my_private_network_rule
MODE = DATA_CONNECTIVITY_PROXY_EGRESS
TYPE = HOST_PORT
VALUE_LIST = ('my-private-db.internal:5432');
목적지에 DNS 이름이 없으면 에이전트 호스트에 hosts 항목을 추가해(/etc/hosts, 또는 Docker의 --add-host) VALUE_LIST의 호스트 이름이 거기서 해석되게 해요.
자세한 내용은 CREATE NETWORK RULE을 참고해요.
Step 7: 외부 접근 통합 생성 및 DCP 객체와 연결
DCP 네트워크 규칙을 참조하는 외부 접근 통합(EAI)을 만들어요:
CREATE EXTERNAL ACCESS INTEGRATION my_private_source_eai
ALLOWED_NETWORK_RULES = (my_private_network_rule)
ENABLED = TRUE;
규칙이 MODE = DATA_CONNECTIVITY_PROXY_EGRESS를 사용하므로 해당 규칙의 목적지로 가는 트래픽은 DCP 대상이에요.
EAI를 DCP 객체와 연결해요. 객체를 만들 때 이미 EXTERNAL_ACCESS_INTEGRATIONS를 설정했다면 이 ALTER는 건너뛰어요:
ALTER DATA CONNECTIVITY PROXY my_dcp_client
SET EXTERNAL_ACCESS_INTEGRATIONS = (my_private_source_eai);
자세한 내용은 외부 접근 통합 생성 및 사용을 참고해요.
Step 8: 커넥터 구성
Openflow UI에서 같은 EAI를 Openflow 런타임에 연결해 커넥터가 목적지로 연결을 열 수 있게 하고, 평소처럼 커넥터가 소스 FQDN과 포트를 사용하도록 구성해요. 커넥터에 명시적 터널 참조는 필요 없어요. UI 단계는 러타임에 외부 접근 통합 연결을 참고해요.
네트워킹 요구 사항
아웃바운드 포트
에이전트는 포트 443의 아웃바운드 접근만 필요해요. 인바운드 포트를 열 필요가 없어요.
다음 표의 모든 호스트 이름을 허용해요. 에이전트는 네트워크가 허용하는 것에 따라 두 릴레이 호스트 이름 중 하나로 자동 연결해요. 둘 다 완전히 지원되므로 하나를 선호할 필요가 없어요. 폴백 호스트 이름만 허용 목록에 추가해도 에이전트는 여전히 동작하며 모든 릴레이 트래픽이 그 호스트 이름을 사용해요.
Important
에이전트는 이 호스트 이름들에 종단 간 TLS 연결이 필요해요. TLS 검사·복호화, 인증서 대체, TLS 종료 없이 이 트래픽이 지나가도록 방화벽, 프록시 및 기타 네트워크 보안 장치를 구성해요. 보안 장치가 여전히 TLS 연결을 가로채거나 수정하면 아웃바운드 허용 규칙만으로는 충분하지 않아요.
네트워크가 기본적으로 TLS 검사를 적용한다면 에이전트 호스트에서 이 호스트 이름들로 가는 포트 443 트래픽에 대해 좁게 스코프된 no-decrypt 예외를 만들어요.
이 패턴에서 <cloud>는 Snowflake 계정을 호스팅하는 클라우드 공급자(aws, azure, gcp)예요. 세그먼트는 호스트 이름 형식만 반영해요. 에이전트의 트래픽이 해당 공급자의 네트워크를 경유한다는 뜻은 아니에요.
| 목적지 | 포트 | 프로토콜 | 용도 |
|---|---|---|---|
| dcp. |
443 | TLS | DCP 컨트롤 플레인 |
| dcp-proxy. |
443 | TLS | 릴레이(데이터 경로) |
| dcp-proxy-fallback. |
443 | TLS | 릴레이(데이터 경로), 에이전트가 dcp-proxy 호스트 이름으로 연결하지 않을 때 사용 |
필요한 호스트 이름은 클라우드와 리전에 따라 달라져요. 계정의 확정 목록을 얻으려면 SYSTEM$ALLOWLIST를 쿼리해요:
SELECT f.VALUE:host::STRING AS host,
f.VALUE:port::INT AS port,
f.VALUE:type::STRING AS type
FROM TABLE(FLATTEN(input => PARSE_JSON(SYSTEM$ALLOWLIST()))) f
WHERE f.VALUE:type::STRING LIKE 'DCP%';
전달 프록시와 TLS 검사 제한에 대한 자세한 내용은 기업 프록시 지원을 참고해요.
DNS
에이전트는 표준 공용 DNS로 Snowflake 엔드포인트 호스트 이름을 해석해요. 그 이름을 PrivateLink 호스트 이름이나 PrivateLink IP 주소로 오버라이드하지 마세요. PrivateLink 엔드포인트를 통해 DCP 에이전트를 연결하는 것은 지원되지 않아요.
텔레메트리 엔드포인트
Snowflake는 bootstrap 시 텔레메트리 호스트 이름을 에이전트에 전달해요. 포트 443 아웃바운드 TLS를 허용해요:
<org>-<account>.telemetry.<locator>.snowflakecomputing.com
이 엔드포인트에 도달할 수 있을 때까지 연결 기록과 일부 경로 확인 단계는 비어 있어요.
고가용성
장애 도메인을 달리하는 두 인스턴스 이상을 실행해(예: 서로 다른 VM이나 가용 영역) 장애 조치 커버리지를 제공해요.
각 인스턴스는 라이브이며 동시에 자체 연결 집합을 처리해요. 컨트롤 플레인은 각 워크로드-목적지 쌍을 특정 에이전트에 매핑하는 라우팅 테이블을 유지해요. 에이전트를 사용할 수 없게 되면 컨트롤 플레인이 라우팅 테이블을 업데이트해 영향을 받는 연결을 정상 인스턴스로 리디렉션해요.
Important
에이전트가 실패하면 처리하던 터널이 끊기고 워크로드의 TCP 연결이 해제돼요. 애플리케이션이 다시 연결해야 해요. DCP는 연결 재설정으로부터 애플리케이션을 보호하지 않아요. 커넥터에 재연결 로직이 구성되어 있는지 확인해요.
같은 목적지에 대한 에이전트 간 액티브-액티브 부하 분산은 향후 릴리스에서 계획돼요.
처리량 확장
에이전트는 CPU 중심이 아닌 I/O 중심이에요. 데이터 프레임은 AES-256-GCM으로 암호화되며, AES-NI가 있는 하드웨어에서는 암호화가 처리량 병목이 아니에요. 릴레이는 제로 카피 커널 I/O를 사용해 바이트당 CPU 비용을 최소화해요. 실질적 한계는 에이전트 호스트의 가용 네트워크 대역폭이에요.
처리량을 높이려면 에이전트 인스턴스를 추가로 실행하고(컨테이너나 VM 추가) 별도 EAI로 목적지를 분할해요. DCP는 같은 목적지에 대한 개별 연결을 에이전트 간에 부하 분산하지 않아요.
에이전트 업그레이드
Snowflake 관리형 릴레이 업그레이드
Snowflake가 릴레이를 업그레이드할 때 조치가 필요 없어요. 활성 데이터베이스 연결은 유지돼요.
에이전트 프로세스 업그레이드
에이전트 바이너리를 업그레이드하면(컨테이너 이미지 교체) 데이터 소스로의 활성 TCP 연결이 해제돼요. 에이전트는 정상 드레인(graceful drain)을 지원해요. SIGTERM을 받으면 새 연결 수락을 중단하고 활성 터널이 끝날 때까지 기다린 뒤 종료해요.
정상 드레인으로 중단을 최소화해 업그레이드하려면:
# Start a new agent instance first (when running multiple agents for HA)
docker run -d --name dcp-agent-new ... snowflakedb/dcp-client:<new-version> ...
# Wait for routing table to shift traffic to the new instance, then drain the old one
docker stop --time 300 dcp-agent # allows up to 300s for active connections to finish
무중단 bootstrap 토큰 교체
에이전트는 매 인증서 교체 주기마다 자격 증명 파일을 다시 읽어요. 활성 연결을 중단하지 않고 토큰을 교체하려면 새 토큰을 파일에 작성해요(보관 위치가 시크릿 매니저라면 그쪽에서):
# Write the new token to a temporary file
echo '<new-token>' > /etc/dcp-agent/secrets/dcp-bootstrap-token.new
chmod 600 /etc/dcp-agent/secrets/dcp-bootstrap-token.new
# Atomically replace the credentials file
mv /etc/dcp-agent/secrets/dcp-bootstrap-token.new /etc/dcp-agent/secrets/dcp-bootstrap-token
에이전트는 다음 교체 주기에 새 토큰을 읽어요. 재시작이 필요 없고 연결도 중단되지 않아요.
Note
토큰이 만료되기 전에 사전 경고를 받으려면 dcp_agent_bootstrap_jwt_expires_at_seconds Prometheus 메트릭에 알림을 설정해요. 토큰이 교체 전에 만료되면 에이전트는 현재 인증서로 계속 실행되지만 다음 교체 시 갱신된 자격 증명을 얻을 수 없어요. 활성 연결이 즉시 끊기지는 않지만 유효한 토큰이 놓일 때까지 교체가 실패해요.
더 알아보기 (Learn more)
- Data Connectivity Proxy 개요 — 개념·아키텍처
- Monitor Data Connectivity Proxy — 모니터링
- Data Connectivity Proxy security — 보안·인증
- Troubleshoot Data Connectivity Proxy — 문제 해결