Azure Compute Gallery (with Terraform)

bocopile·2025년 3월 28일

Azure

목록 보기
1/1
post-thumbnail

이번 포스팅에서는 Azure Compute Gallery란 무엇인지?? VM 이미지를 저장하는 법과, 저장된 이미지를 기반으로 VM 생성하는 방법을 진행하고자 한다.
VM 배포는 Terraform를 이용하여 배포를 진행한다.

Azure Compute Gallery??

Azure Compute Gallery는 Azure 내에서 사용자 지정 가상 머신 이미지와 애플리케이션 패키지를 중앙에서 관리하고 공유할 수 있도록 하는 서비스입니다.
이전에는 Shared Image Gallery로 불렸으며, 이미지 버전 관리, 글로벌 복제, RBAC를 통한 공유 등 다양한 기능을 제공하여 표준화된 이미지 배포와 빠른 VM 프로비저닝을 지원합니다.

장/단점

장점

  • 중앙 집중 관리 및 버전 관리 여러 이미지와 애플리케이션 패키지를 하나의 갤러리에서 관리하며, 버전별로 업데이트 이력을 관리할 수 있습니다. learn.microsoft.com
  • 글로벌 복제 및 고가용성 원하는 여러 지역으로 이미지를 복제할 수 있어, 배포 속도를 높이고 재해 복구 시에도 신속한 복원이 가능합니다. learn.microsoft.com
  • 공유 및 RBAC 지원 조직 내 사용자뿐만 아니라, 다른 구독이나 AD 테넌트와도 이미지와 애플리케이션을 안전하게 공유할 수 있습니다. learn.microsoft.com
  • 자동화 및 확장성 CI/CD 파이프라인이나 VM Scale Set과 연동하여 자동화된 대규모 배포가 용이합니다.

단점

  • 리소스 제한 구독 당 갤러리, 이미지 정의, 이미지 버전에 대한 제한이 있어 대규모 운영 환경에서는 주의가 필요합니다.
  • 복제 시간 지연 이미지 복제는 이미지 크기와 복제 대상 지역 수에 따라 시간이 소요될 수 있어, 긴 복제 대기 시간이 발생할 수 있습니다.
  • 리소스 이동의 제약 한 번 생성된 갤러리 리소스는 다른 구독이나 리전으로 이동하는 것이 지원되지 않아 초기 구성 시 신중해야 합니다.
  • 학습 곡선 다양한 기능(예: RBAC 설정, 직접 공유, 커뮤니티 공유 등)을 효과적으로 활용하기 위해서는 추가적인 학습이 필요합니다.

실습

1) 기본 설정

  • code
    # Azure Logion
    az login
    
    # Azure 구독 ID 확인
    az account list
    
    # 구독 활성화
    az account set --subscription "구독_ID"
    
    # 현재 구독 활성화
    az account show --output table
    
    # Azure Principal 생성
    ## 이미 생성이 되어 있다면 해당 단계는 스킵한다. 
    az ad sp create-for-rbac --name "terraform-sp" --role="Contributor" --scopes="/subscriptions/<SUBSCRIPTION_ID>"
     
    
    # 리소스 삭제시 해당 코드 삭제할것
    ## 이미 생성이 되어 있다면 해당 단계는 스킵한다. 
    
    cat << EOF >> ~/.zshrc
    
    export ARM_CLIENT_ID=$(az ad sp list --display-name "terraform-sp" --query "[].appId" -o tsv)"
    export ARM_CLIENT_SECRET=${password}"  # 해당 부분 수정 필요
    export ARM_TENANT_ID=$(az account show --query "tenantId" -o tsv)"
    export ARM_SUBSCRIPTION_ID=$(az account show --query id -o tsv)" 
    
    EOF
    
    source ~/.zshrc
    
    # 변수 확인
    echo $ARM_CLIENT_ID $ARM_CLIENT_SECRET $ARM_TENANT_ID $ARM_SUBSCRIPTION_ID
    tail -n 10 ~/.zshrc
  • 구독 ID 확인
  • 구독 활성화
  • Azure Principal 생성
    • 이미 생성이 되어 있다면 해당 단계를 스킵한다.
    • 여기서 password 는 아래 변수 선언시 필요하므로 복사할것
  • 변수 선언

    • 위에 나온 password를 기반으로 아래 코드를 수정한다.

      cat << EOF >> ~/.zshrc
      
      export ARM_CLIENT_ID=\$(az ad sp list --display-name "terraform-sp" --query "[].appId" -o tsv)
      export ARM_CLIENT_SECRET=${password}  # 실제 비밀번호로 대체 필요 (보안 주의)
      export ARM_TENANT_ID=$(az account show --query tenantId -o tsv)
      export ARM_SUBSCRIPTION_ID=$(az account show --query id -o tsv)
      
      EOF
      
      source ~/.zshrc
      
      # 변수 확인
      echo $ARM_CLIENT_ID $ARM_CLIENT_SECRET $ARM_TENANT_ID $ARM_SUBSCRIPTION_ID
      tail -n 10 ~/.zshrc
    • 결과

2) pem 파일 생성

vm 접속을 위하여 pem 파일 생성이 필요하다.

Azure portal에 접속하여 key 파일을 생성한다. - Link

pem key를 생성하였다면 pem → pub으로 변경하는 작업이 필요하다.

  • code
chmod 600 my_key.pem
ssh-keygen -y -f my_key.pem > my_key.pub

# 예시
ssh-keygen -y -f /Users/bokhoshin/azure/bocopile-azure-key.pem > /Users/bokhoshin/azure/bocopile-azure-key.pub
  • 생성 결과

3) Resouce Group 생성

  • code
    az group create --name ${resource-group-name} --location ${location-path}
    az group create --name sample-group --location koreasouth
  • 생성 결과
  • code
    az sig create --resource-group ${resouce-group-name} --gallery-name ${compute-gallery-name} --location ${location-path}
    az sig create --resource-group sample-group --gallery-name sample --location koreasouth
  • 생성 결과

Azure Compute gallery 생성 결과는 Azure Portal에서도 확인할수 있습니다.

5) VM Image 생성

해당 단계를 진행하기 위해선 VM 생성이 되어야 한다.

우선 Terraform를 이용하여 VM 생성하도록 하자

git clone

git clone https://github.com/bocopile/terraform-azure.git
cd vm/vm-create

variables 수정

해당 코드를 보면 변수 선언이 되어 있다.

variable "resource_group_name" {
  description = "Azure Resource Group Name"
  type        = string
  default     = "sample-resouce"
}

variable "location" {
  description = "Azure Region"
  type        = string
  default     = "Korea South"
}

# 해당 부분 수정 필요
variable "ssh_public_key_path" {
  description = "Path to SSH Public Key"
  type        = string
  default     = "/Users/bokhoshin/azure/bocopile-azure-key.pub"
}

# 해당 부분
variable "admin_username" {
  description = "Admin username for the VM"
  type        = string
  default     = "bocopile"
}

해당 코드 중에서 ssh_public_key_path 및, admin_username 자신의 환경에 맞춰서 변경한다.

해당 작업을 진행한 후에 아래 코드를 순차적으로 실행한다.

VM 생성

# 테라폼 작업 디렉터리 초기화
terraform init

# 현재 구성 파일과 실제 인프라 상태를 비교하여, 적용될 인프라를 보여준다.
terraform plan

# 인프라 구성
terraform apply -auto-approve
  • terraform init
  • terraform plan
  • terraform apply -auto-approve

VM 이미지 추출

VM 할당 해제 / 운영 상태 변경

가장 먼저 VM 할당 해제 및 일반화를 진행한다.

단 VM 이미지는 운영체제 상태에 따라서 일반화 / 특수화로 나눌수 있다.

일반화 / 특수화는 다음과 같이 구분이 된다.

  • 일반화됨: 이 이미지에서 만든 VM의 경우 처음 부팅할 때 호스트 이름, 관리 사용자 및 기타 VM 관련 설정이 완료
  • 특수화됨: 이 이미지에서 만든 VM의 경우 구성이 완료되었으며 호스트 이름 및 관리 사용자/암호와 같은 매개 변수가 필요하지 않다.

해당 블로그 글에선 일반화로 진행한다.

  • code
# VM 할당 해제 (중지)
az vm deallocate --resource-group sample-resouce --name sample-vm

# VM 일반화 (Sysprep) - skip
az vm generalize --resource-group sample-resouce --name sample-vm
  • 결과
    • Azure portal에서 확인하면 해당 VM이 중지되어 있음을 확인 할수 있다.

Managed Image 생성

  • code

az image create \
  --resource-group ${resource-group-name} \
  --name ${image-name} \
  --source ${vm-name} \
  --hyper-v-generation V2

# 예시
az image create \
  --resource-group sample-resouce \
  --name sample-vm-image \
  --source sample-vm \
  --hyper-v-generation V2
  • 결과

    • 해당 명령어가 실행 되면 아래 결과가 나온다.
    • 해당 결과는 해당 링크에서도 확인이 가능하다. - Link

Azure Compute Gallery에 이미지 정의 생성

이미 해당 Gallery에 정의가 되어 있는 경우 해당 단계는 스킵한다.

확인 방법 - Link


# --gallery-name : 이미지 정의를 생성할 Azure Compute Gallery 명칭
# --gallery-image-definition : 생성할 이미지 이름을 정의
# --publisher : 이미지 게시자
# --offer : 이미지 오퍼 이름을 지정
# --sku : 이미지의 SKU(Stock Keeping Unit)를 지정합니다
# --os-type : 이미지 운영체제 유형을 지정 (Linux, Windows)
# --hyper-v-generation : 이미지가 지원하는 Hyper-V 세대 버전을 지정 (일반적으로 v2)
az sig image-definition create \
  --resource-group sample-group \
  --gallery-name sample \
  --gallery-image-definition "${gallay-image}" \
  --publisher "${publisher}" \
  --offer "${offer}" \
  --sku "${sku}" \
  --os-type Linux \
  --hyper-v-generation V2

# 예시
az sig image-definition create \
  --resource-group sample-group \
  --gallery-name sample \
  --gallery-image-definition "sample-vm-ubuntu-24" \
  --publisher "MyPublisher" \
  --offer "MyOffer" \
  --sku "MySKU" \
  --os-type Linux \
  --hyper-v-generation V2

해당 명령어를 실행하면 Azure Compute Gallery에 다음과 같은 이미지가 정의 된다.

갤러리에 이미지 업로드

이미지가 정의가 됬다면 VM 이미지를 Azure Compute Gallery에 저장 하는 것이 필요하다.

여기서 몇가지 주의할 내용이 있다.

(주의사항)

  • ${managed-resource-group-name} : Managed Image 가 속한 리소스 그룹명 → sample-resouce

  • ${managed-resource-image-name} : Managed Image 생성시 지정했던 이미지명 → sample-vm-image

  • ${compute-gallery-resource-name} : Azure Compute Gallery가 속한 리소스 그룹명 → sample-group

  • ${compute-gallery-name} : Azure Compute Gallery 명 → sample

  • ${compute-gallery-image-name} : Azure Compute Gallery 이미지 정의 명칭 : sample-vm-ubuntu-24

  • code

# Managed Image의 ID 조회
image_id=$(az image show \
  --resource-group ${managed-resource-group-name}\
  --name ${managed-resource-image-name} \
  --query id --output tsv)
  
az image list \
  --resource-group ${managed-resource-group-name} \
  --query "[?name=='${managed-resource-image-name}].id" -o tsv
  
# 해당 갤러리에 Image 등록  
az sig image-version create \
  --resource-group ${compute-gallery-resource-name} \
  --gallery-name ${compute-gallery-name} \
  --gallery-image-definition " ${compute-gallery-image-name}" \
  --gallery-image-version 1.0.0 \
  --target-regions "koreasouth" \
  --replica-count 1 \
  --managed-image $(az image list --resource-group ${managed-resource-group-name} --query "[?name=='${managed-resource-image-name}'].id" -o tsv)    

# Managed Image의 ID 조회 - 예시
image_id=$(az image show \
  --resource-group sample-resouce \
  --name sample-vm-image \
  --query id --output tsv)

az image list \
  --resource-group sample-resouce \
  --query "[?name=='sample-vm-image'].id" -o tsv

# 조회된 ID를 명령어에 직접 입력
az sig image-version create \
  --resource-group sample-group \
  --gallery-name sample \
  --gallery-image-definition "sample-vm-ubuntu-24" \
  --gallery-image-version 1.0.0 \
  --target-regions "koreasouth" \
  --replica-count 1 \
  --managed-image $(az image list --resource-group sample-resouce --query "[?name=='sample-vm-image'].id" -o tsv)  
  • Managed image ID 조회
  • 이미지 업로드 결과
  • 해당 결과는 Azure Portal에서도 확인이 가능하다.


)

기존 VM 삭제

이미지 생성이 완료되었다면 VM을 재실행 및 VM 생성했던 폴더로 돌아가 VM 및 리소스를 삭제한다.

단 일반화/특수화 설정에 따라서 VM 삭제 하는 방법이 다르다.

일반화를 설정한 경우 VM은 더 이상 부팅할 수 없는 상태가 됩니다.

VM 삭제 - 특수화

# Azure VM 실행
az vm start --resource-group sample-group --name sample-vm

cd vm/vm-create

# terraform를 이용하여 리소스 삭제 명령어
terraform destroy -auto-approve

VM 삭제 - 일반화

해당 경우에는 Azure portal를 이용하여 삭제가 필요하다.

6) VM Image 기반으로 VM 생성

VM 생성시 Clone 하였던 프로젝트에 vm/vm-create-compute-gallery 해당 코드를 이용하여 배포를 진행한다.

우선 Variables.tf 파일에서 아래 변수들을 자신의 환경에 맞게 수정 한다.

variable "vm_version" {
  description = "Azure VM version"
  type        = string
  default     = "1.0.0"
}

variable "vm_image_name" {
  description = "Azure VM image name"
  type        = string
  default     = "sample-vm-ubuntu-24"
}

variable "vm_gallery_name" {
  description = "Azure Gallery Name"
  type        = string
  default     = "sample"
}

variable "vm_resource_group_name" {
  description = "Azure Gallery resource group"
  type        = string
  default     = "sample-group"
}

해당 코드를 수정하였다면 terraform을 이용하여 배포 해보자

  • code
    # 테라폼 작업 디렉터리 초기화
    terraform init
    
    # 현재 구성 파일과 실제 인프라 상태를 비교하여, 적용될 인프라를 보여준다.
    terraform plan
    
    # 인프라 구성
    terraform apply -auto-approve
  • terraform init
  • terraform plan
  • terraform apply -auto-approve
  • ssh 접속
    ssh -i ${pem-path} ${id}@${VM-ip}
    
    #예시
    ssh -i /Users/bokhoshin/azure/bocopile-azure-key.pem bocopile@52.231.185.204
  • ssh 접속 확인

삭제

실습이 완료되었다면 다음 순서 대로 삭제를 진행한다.

# image 삭제
az sig image-version delete \
  --resource-group sample-group \
  --gallery-name sample \
  --gallery-image-definition sample-vm-ubuntu-24 \
  --gallery-image-version 1.0.0

# image 정의 삭제
 az sig image-definition delete \
  --resource-group sample-group \
  --gallery-name sample \
  --gallery-image-definition sample-vm-ubuntu-24

# Azure Compute Gallery 삭제
 az sig delete \
  --resource-group sample-group \
  --gallery-name sample-group
  
# Resource Group 삭제
az group delete --name sample-group --yes --no-wait
profile
DevOps Engineer

0개의 댓글