본문 바로가기
클라우드

🚀 Azure VM 복제, 더 이상 로컬 다운로드는 그만! (feat. Azure CLI)

by gasbugs 2025. 10. 12.

안녕하세요! 클라우드 환경을 다루다 보면 가상 머신(VM)을 백업하거나, 특정 시점의 VM을 그대로 복제해서 테스트 환경을 만들어야 할 때가 정말 많죠.

 

많은 분들이 사용하는 일반적인 방법은 아마 이럴 거예요.

  1. VM 디스크의 스냅샷을 만든다. 📸
  2. 스냅샷을 VHD 파일로 로컬 컴퓨터에 다운로드한다. (⏳ 한세월...)
  3. 다운로드한 VHD 파일을 다시 Blob 스토리지에 업로드한다. (😩 또 한세월...)
  4. 업로드한 VHD로 새 디스크를 만들고, 그 디스크로 새 VM을 생성한다.

이 과정, 뭔가 이상하지 않나요? 분명 Azure에 있는 데이터를 Azure 다른 곳으로 옮기는 것뿐인데, 왜 굳이 제 컴퓨터를 거쳐가야 할까요? 이 방식은 시간도 오래 걸리고, 제 컴퓨터의 네트워크 대역폭과 저장 공간을 낭비하며, 중간에 오류가 발생할 확률도 높습니다.

 

그래서 오늘은! 이 비효율적인 과정을 완전히 건너뛰고 Azure 내부에서 직접 스냅샷을 Blob으로 복사하여 VM을 복제하는 아주 스마트한 방법을 Azure CLI 스크립트와 함께 상세히 알려드리겠습니다.

 

 

🤔 핵심 원리: 로컬 경유 vs Azure 직통

기존 방식이 서울에서 부산을 가는데 굳이 제주도(내 컴퓨터)를 경유하는 비행기라면, 오늘 소개할 방법은 KTX를 타고 한 번에 가는 것과 같습니다. 🚅

핵심은 바로 az storage blob copy start라는 Azure CLI 명령어입니다. 이 명령어는 "Azure야, A 위치(스냅샷)에 있는 데이터를 B 위치(Blob 스토리지)로 네가 직접 복사해줘!" 라고 지시하는 역할을 합니다. 데이터는 우리 컴퓨터를 전혀 거치지 않고, 빠르고 안정적인 Azure의 내부 네트워크를 통해 직접 이동하게 되죠.

이것을 서버 측 복사(Server-Side Copy)라고 부르며, 다음과 같은 엄청난 장점이 있습니다.

  • ⚡️ 속도: 로컬 네트워크 속도와는 비교할 수 없을 정도로 빠릅니다.
  • 👍 효율성: 내 컴퓨터의 리소스(CPU, 네트워크, 디스크)를 전혀 사용하지 않습니다.
  • 🔒 안정성: 중간에 인터넷이 끊길 걱정 없이 안정적으로 대용량 파일을 복사할 수 있습니다.

 

📜 전체 스크립트 대공개!

백문이 불여일견이죠? 아래는 이 모든 과정을 자동화하는 전체 Bash 스크립트입니다. 그대로 복사해서 사용하셔도 좋습니다.

#!/bin/bash

# --- 사용자 설정 변수 ---
# 이미 생성된 리소스의 이름을 정확하게 입력해주세요.
resourceGroup="gasbugs_group"      # 리소스 그룹
vmName="gasbugs"                   # 원본 가상머신
storageAccount="storageaccountgasbugs0" # VHD를 저장할 스토리지 계정
containerName="blob-test"          # VHD를 저장할 컨테이너

# 새로 생성할 리소스의 이름을 원하는 대로 설정하세요.
snapshotName="new-snapshot-$(date +%s)" # 스냅샷 이름 (중복 방지를 위해 타임스탬프 추가)
newDiskName="new-disk-$(date +%s)"      # 새 디스크 이름
newVmName="new-vm-$(date +%s)"          # 새 가상 머신 이름

# --- 스크립트 실행 ---
echo ">> 1. 원본 VM의 OS 디스크 ID를 가져옵니다..."
osDiskId=$(az vm show --resource-group $resourceGroup --name $vmName --query "storageProfile.osDisk.managedDisk.id" -o tsv)
if [ -z "$osDiskId" ]; then echo "오류: OS 디스크 ID를 찾을 수 없습니다."; exit 1; fi
echo "   - OS Disk ID: $osDiskId"

echo -e "\n>> 2. OS 디스크의 스냅샷을 생성합니다..."
az snapshot create --resource-group $resourceGroup --name $snapshotName --source $osDiskId
echo "   - 생성된 스냅샷: $snapshotName"

echo -e "\n>> 3. 스냅샷에 접근할 수 있는 임시 SAS URL을 생성합니다..."
snapshotUrl=$(az snapshot grant-access --duration-in-seconds 3600 --name $snapshotName --resource-group $resourceGroup --query "accessSas" -o tsv)
echo "   - SAS URL이 성공적으로 생성되었습니다."

echo -e "\n>> 4. 스냅샷을 Blob Storage로 서버 측 복사를 시작합니다 (로컬 다운로드 없음)..."
# 복사할 Blob의 전체 URL
sharedVhdUrl="https://$storageAccount.blob.core.windows.net/$containerName/$snapshotName.vhd"

az storage blob copy start \
    --account-name $storageAccount \
    --destination-blob "$snapshotName.vhd" \
    --destination-container $containerName \
    --source-uri $snapshotUrl

# 복사가 완료될 때까지 상태를 확인합니다.
while true; do
    copy_status=$(az storage blob show --account-name $storageAccount --container-name $containerName --name "$snapshotName.vhd" --query "properties.copy.status" -o tsv)
    echo "   - 복사 상태: $copy_status"
    if [ "$copy_status" == "success" ]; then
        echo "   - Blob 복사가 완료되었습니다."
        break
    elif [ "$copy_status" == "failed" ]; then
        echo "오류: Blob 복사에 실패했습니다."
        exit 1
    fi
    sleep 15
done

echo -e "\n>> 5. 스냅샷의 SAS URL 접근 권한을 해제합니다..."
az snapshot revoke-access --name $snapshotName --resource-group $resourceGroup

echo -e "\n>> 6. 복사된 VHD Blob을 소스로 하여 새 관리 디스크를 생성합니다..."
az disk create --resource-group $resourceGroup --name $newDiskName --source $sharedVhdUrl
echo "   - 생성된 디스크: $newDiskName"

echo -e "\n>> 7. 생성된 디스크를 사용하여 새 가상 머신을 생성합니다..."
az vm create --resource-group $resourceGroup --name $newVmName --attach-os-disk $newDiskName --os-type Linux --public-ip-address "" # Public IP 없이 생성
echo "   - 생성된 VM: $newVmName"

echo -e "\n✅ 모든 작업이 성공적으로 완료되었습니다."

 

🔬 스크립트 상세 분석

스크립트가 어떻게 동작하는지 단계별로 자세히 알아볼까요?

1단계: 변수 설정 ⚙️

스크립트 상단에서 복제할 대상 VM, 리소스 그룹, VHD를 저장할 스토리지 계정 등 기본 정보를 설정합니다. 스크립트를 여러 번 실행해도 이름이 겹치지 않도록, 새로 만들 리소스 이름에는 $(date +%s)를 붙여 현재 시간을 기준으로 고유한 이름을 만들어주었습니다.

2단계: 스냅샷 생성 📸

az vm show로 원본 VM의 OS 디스크 ID를 가져온 뒤, az snapshot create 명령으로 디스크의 특정 시점 복사본, 즉 스냅샷을 만듭니다.

3단계: SAS URL 생성 🔑

az snapshot grant-access는 정말 중요한 역할을 합니다. 생성된 스냅샷 데이터에 딱 1시간(3600초) 동안만 접근할 수 있는 임시 비밀키가 포함된 URL, 즉 SAS(공유 액세스 서명) URL을 만들어줍니다. 이 URL이 바로 우리 데이터의 '직통 티켓'이 됩니다.

4단계: 서버 측 복사 및 상태 확인 ☁️➡️☁️

이 스크립트의 하이라이트입니다! az storage blob copy start 명령에 방금 만든 SAS URL을 --source-uri로, 목표 지점인 Blob 정보를 --destination-blob 등으로 알려줍니다.

명령이 실행되는 즉시 Azure는 백그라운드에서 복사를 시작합니다. 하지만 복사가 끝날 때까지 기다려야 다음 작업을 할 수 있겠죠? 그래서 while 루프를 사용해 az storage blob show 명령으로 15초마다 복사 상태를 확인합니다. 상태가 success로 바뀌면 루프를 탈출하고 다음 단계로 넘어갑니다. 정말 스마트하죠?

5~7단계: 권한 해제 및 리소스 생성 🏗️

복사가 끝났으니 보안을 위해 az snapshot revoke-access로 SAS URL을 즉시 만료시킵니다. 이제 Blob 스토리지에 안전하게 저장된 VHD 파일의 URL을 소스로 az disk create를 실행해 새로운 관리 디스크를 만듭니다. 마지막으로, 이 디스크를 OS 디스크로 사용하여 az vm create로 최종 복제 VM을 생성하면 모든 과정이 끝납니다!

 

✨ 마무리하며

이제 더 이상 VM을 복제하거나 백업할 때마다 VHD 파일을 로컬로 다운로드하고 업로드하며 시간을 낭비하지 마세요. 오늘 배운 서버 측 복사 방법을 활용하면 Azure CLI 스크립트 한 번 실행하는 것만으로 모든 과정을 빠르고 안정적으로 자동화할 수 있습니다.

이 스크립트를 활용하여 여러분만의 VM 백업 시스템을 만들거나, 개발/테스트 환경을 신속하게 구축하는 데 응용해 보시는 건 어떨까요?


태그: Azure, VM, Virtual Machine, Snapshot, Blob, Storage, Azure CLI, Bash, Script, DevOps, IaC, Cloud, IT