자습서: Ansible을 사용하여 Azure 가상 머신 확장 집합의 사용자 지정 이미지 업데이트
Important
이 문서의 샘플 플레이북을 실행하려면 Ansible 2.8 이상이 필요합니다.
Azure 가상 머신 확장 집합 은 부하가 분산된 동일한 VM 그룹을 구성할 수 있는 Azure 기능입니다. 확장 집합에 대한 추가 비용은 없으며 가상 머신에서 작성됩니다. VM 인스턴스, 부하 분산 장치 또는 Managed Disk Storage와 같은 기본 컴퓨팅 리소스에 대해서만 비용을 지불합니다. 확장 집합을 사용하면 애플리케이션을 실행하고 크기를 조정할 수 있는 관리 및 자동화 계층이 제공됩니다. 개별 VM을 수동으로 만들고 관리할 수도 있습니다. 단, 확장 집합을 사용하면 두 가지 주요 이점이 있습니다. Azure에 기본 제공되며 애플리케이션 요구 사항에 맞게 가상 머신의 크기를 자동으로 조정합니다.
VM을 배포한 후 앱에 필요한 소프트웨어로 VM을 구성합니다. 각 VM에 대해 이 구성 작업을 수행하는 대신 사용자 지정 이미지를 만들 수 있습니다. 사용자 지정 이미지는 설치된 모든 소프트웨어를 포함하는 기존 VM의 스냅샷입니다. 확장 집합을 구성할 때 해당 확장 집합의 VM에 사용할 이미지를 지정합니다. 사용자 지정 이미지를 사용하면 각 VM 인스턴스가 앱에 대해 동일하게 구성됩니다. 경우에 따라 확장 집합의 사용자 지정 이미지를 업데이트해야 할 수 있습니다. 이 작업은 이 자습서의 핵심입니다.
이 문서에서는 다음 방법을 설명합니다.
- HTTPD를 사용하여 두 VM 구성
- 기존 VM에서 사용자 지정 이미지 만들기
- 이미지에서 확장 집합 만들기
- 사용자 지정 이미지 업데이트
필수 조건
- Azure 구독: Azure 구독이 아직 없는 경우 시작하기 전에 체험 계정을 만듭니다.
Ansible 설치: 다음 옵션 중 하나를 수행합니다.
- Linux 가상 머신에서 Ansible 설치 및 구성
- Azure Cloud Shell 구성 - Linux 가상 머신에 액세스할 수 없는 경우 Ansible을 사용하여 가상 머신 만들기
두 개의 VM 구성
이 섹션의 플레이북 코드는 둘 다에 HTTPD가 설치된 두 개의 가상 머신을 만듭니다.
index.html
각 VM의 페이지에는 테스트 문자열이 표시됩니다.
- 첫 번째 VM은 값을 표시합니다.
Image A
- 두 번째 VM은 값
Image B
를 표시합니다.
이 문자열은 서로 다른 소프트웨어로 각 VM을 구성하는 것을 모방하기 위한 것입니다.
다음과 같은 두 가지 방법으로 샘플 플레이북을 가져올 수 있습니다.
플레이북 을 다운로드하고 저장합니다
create_vms.yml
.이름이
create_vms.yml
인 새 파일을 만듭니다. 새 파일에 다음 코드를 삽입합니다.
- name: Create two VMs (A and B) with HTTPS
hosts: localhost
connection: local
vars:
vm_name: vmforimage
admin_username: testuser
admin_password: Pass123$$$abx!
location: eastus
tasks:
- name: Create a resource group
azure_rm_resourcegroup:
name: "{{ resource_group }}"
location: "{{ location }}"
- name: Create virtual network
azure_rm_virtualnetwork:
resource_group: "{{ resource_group }}"
name: "{{ vm_name }}"
address_prefixes: "10.0.0.0/16"
- name: Create subnets for VM A and B
azure_rm_subnet:
resource_group: "{{ resource_group }}"
virtual_network: "{{ vm_name }}"
name: "{{ vm_name }}"
address_prefix: "10.0.1.0/24"
- name: Create Network Security Group that allows HTTP
azure_rm_securitygroup:
resource_group: "{{ resource_group }}"
name: "{{ vm_name }}"
rules:
- name: HTTP
protocol: Tcp
destination_port_range: 80
access: Allow
priority: 1002
direction: Inbound
- name: Create public IP addresses for VM A and B
azure_rm_publicipaddress:
resource_group: "{{ resource_group }}"
allocation_method: Static
name: "{{ vm_name }}_{{ item }}"
loop:
- A
- B
register: pip_output
- name: Create virtual network interface cards for VM A and B
azure_rm_networkinterface:
resource_group: "{{ resource_group }}"
name: "{{ vm_name }}_{{ item }}"
virtual_network: "{{ vm_name }}"
subnet: "{{ vm_name }}"
public_ip_name: "{{ vm_name }}_{{ item }}"
security_group: "{{ vm_name }}"
loop:
- A
- B
- name: Create VM A and B
azure_rm_virtualmachine:
resource_group: "{{ resource_group }}"
name: "{{ vm_name }}{{ item }}"
admin_username: "{{ admin_username }}"
admin_password: "{{ admin_password }}"
vm_size: Standard_B1ms
network_interfaces: "{{ vm_name }}_{{ item }}"
image:
offer: UbuntuServer
publisher: Canonical
sku: 16.04-LTS
version: latest
loop:
- A
- B
- name: Create VM Extension
azure_rm_virtualmachineextension:
resource_group: "{{ resource_group }}"
name: testVMExtension
virtual_machine_name: "{{ vm_name }}{{ item }}"
publisher: Microsoft.Azure.Extensions
virtual_machine_extension_type: CustomScript
type_handler_version: 2.0
auto_upgrade_minor_version: true
settings: {"commandToExecute": "sudo apt-get -y install apache2"}
loop:
- A
- B
- name: Create VM Extension
azure_rm_virtualmachineextension:
resource_group: "{{ resource_group }}"
name: testVMExtension
virtual_machine_name: "{{ vm_name }}{{ item }}"
publisher: Microsoft.Azure.Extensions
virtual_machine_extension_type: CustomScript
type_handler_version: 2.0
auto_upgrade_minor_version: true
settings: {"commandToExecute": "printf '<html><body><h1>Image {{ item }}</h1></body></html>' >> index.html; sudo cp index.html /var/www/html/"}
loop:
- A
- B
- debug:
msg: "Public IP Address A: {{ pip_output.results[0].state.ip_address }}"
- debug:
msg: "Public IP Address B: {{ pip_output.results[1].state.ip_address }}"
명령을 사용하여 플레이북을 ansible-playbook
실행하고 리소스 그룹 이름으로 바꿉 myrg
니다.
ansible-playbook create-vms.yml --extra-vars "resource_group=myrg"
플레이북 ansible-playbook
의 debug
섹션으로 인해 명령은 각 VM의 IP 주소를 출력합니다. 나중에 사용하기 위해 이러한 IP 주소를 복사합니다.
두 VM에 연결
이 섹션에서는 각 VM에 연결합니다. 이전 섹션에서 설명한 것처럼 문자열 Image A
및 Image B
는 구성이 각기 다른 두 개의 고유한 VM을 모방합니다.
이전 섹션의 IP 주소를 사용하여 브라우저를 열고 각 VM에 연결합니다.
각 VM에서 이미지 만들기
이 시점에서 약간 다른 구성(해당 파일)을 사용하는 두 개의 VM이 index.html
있습니다.
이 섹션의 플레이북 코드는 각 VM에 대한 사용자 지정 이미지를 만듭니다.
image_vmforimageA
- 홈페이지에 표시되는Image A
VM에 대해 만들어진 사용자 지정 이미지입니다.image_vmforimageB
- 홈페이지에 표시되는Image B
VM에 대해 만들어진 사용자 지정 이미지입니다.
다음과 같은 두 가지 방법으로 샘플 플레이북을 가져올 수 있습니다.
플레이북 을 다운로드하고 저장합니다
capture-images.yml
.이름이
capture-images.yml
인 새 파일을 만듭니다. 새 파일에 다음 코드를 삽입합니다.
- name: Capture VM Images
hosts: localhost
connection: local
vars:
vm_name: vmforimage
tasks:
- name: Stop and generalize VMs
azure_rm_virtualmachine:
resource_group: "{{ resource_group }}"
name: "{{ vm_name }}{{ item }}"
generalized: yes
loop:
- A
- B
- name: Create an images from a VMs
azure_rm_image:
resource_group: "{{ resource_group }}"
name: "image_{{ vm_name }}{{ item }}"
source: "{{ vm_name }}{{ item }}"
loop:
- A
- B
명령을 사용하여 플레이북을 ansible-playbook
실행하고 리소스 그룹 이름으로 바꿉 myrg
니다.
ansible-playbook capture-images.yml --extra-vars "resource_group=myrg"
이미지 A를 사용하여 확장 집합 만들기
이 섹션에서는 플레이북을 사용하여 다음 Azure 리소스를 구성합니다.
- 공용 IP 주소
- 부하 분산 장치
- 참조하는 확장 집합
image_vmforimageA
다음과 같은 두 가지 방법으로 샘플 플레이북을 가져올 수 있습니다.
플레이북 을 다운로드하고 저장합니다
create-vmss.yml
.이름이
create-vmss.yml
인 새 파일을 만듭니다. 새 파일에 다음 코드를 삽입합니다.
---
- hosts: localhost
vars:
vmss_name: vmsstest
location: eastus
admin_username: vmssadmin
admin_password: User123!!!abc
vm_name: vmforimage
image_name: "image_vmforimageA"
tasks:
- name: Create public IP address
azure_rm_publicipaddress:
resource_group: "{{ resource_group }}"
allocation_method: Static
name: "{{ vmss_name }}"
register: pip_output
- name: Create a load balancer
azure_rm_loadbalancer:
name: "{{ vmss_name }}lb"
location: "{{ location }}"
resource_group: "{{ resource_group }}"
public_ip: "{{ vmss_name }}"
probe_protocol: Tcp
probe_port: 80
probe_interval: 10
probe_fail_count: 3
protocol: Tcp
load_distribution: Default
frontend_port: 80
backend_port: 80
idle_timeout: 4
natpool_frontend_port_start: 50000
natpool_frontend_port_end: 50040
natpool_backend_port: 22
natpool_protocol: Tcp
- name: Create a scale set
azure_rm_virtualmachinescaleset:
resource_group: "{{ resource_group }}"
name: "{{ vmss_name }}"
vm_size: Standard_DS1_v2
admin_username: "{{ admin_username }}"
admin_password: "{{ admin_password }}"
ssh_password_enabled: true
capacity: 2
virtual_network_name: "{{ vm_name }}"
subnet_name: "{{ vm_name }}"
upgrade_policy: Manual
tier: Standard
managed_disk_type: Standard_LRS
os_disk_caching: ReadWrite
image:
name: "{{ image_name }}"
resource_group: "{{ resource_group }}"
load_balancer: "{{ vmss_name }}lb"
- debug:
msg: "Scale set public IP address: {{ pip_output.state.ip_address }}"
명령을 사용하여 플레이북을 ansible-playbook
실행하고 리소스 그룹 이름으로 바꿉 myrg
니다.
ansible-playbook create-vmss.yml --extra-vars "resource_group=myrg"
플레이북 ansible-playbook
섹션 debug
으로 인해 이 명령은 확장 집합의 IP 주소를 인쇄합니다. 나중에 사용할 수 있는 이 IP 주소를 복사합니다.
확장 집합에 연결
이전 섹션의 IP 주소를 사용하여 확장 집합에 연결합니다.
이전 섹션에서 설명한 것처럼 문자열 Image A
및 Image B
는 구성이 각기 다른 두 개의 고유한 VM을 모방합니다.
확장 집합은 명명 image_vmforimageA
된 사용자 지정 이미지를 참조합니다. 홈페이지가 표시되는 Image A
VM에서 사용자 지정 이미지를 image_vmforimageA
만들었습니다.
결과적으로 표시되는 홈 페이지가 표시됩니다 Image A
.
다음 섹션을 계속 진행하면서 브라우저 창을 열어 둡니다.
확장 집합의 사용자 지정 이미지 변경 및 인스턴스 업그레이드
이 섹션의 플레이북 코드는 확장 집합의 이미지를 image_vmforimageA
에서 image_vmforimageB
로 변경합니다. 또한 확장 집합에서 배포한 모든 현재 가상 머신이 업데이트됩니다.
다음과 같은 두 가지 방법으로 샘플 플레이북을 가져올 수 있습니다.
플레이북 을 다운로드하고 저장합니다
update-vmss-image.yml
.이름이
update-vmss-image.yml
인 새 파일을 만듭니다. 새 파일에 다음 코드를 삽입합니다.
- name: Update scale set image reference
hosts: localhost
connection: local
vars:
vmss_name: vmsstest
image_name: image_vmforimageB
admin_username: vmssadmin
admin_password: User123!!!abc
tasks:
- name: Update scale set - second image
azure_rm_virtualmachinescaleset:
resource_group: "{{ resource_group }}"
name: "{{ vmss_name }}"
vm_size: Standard_DS1_v2
admin_username: "{{ admin_username }}"
admin_password: "{{ admin_password }}"
ssh_password_enabled: true
capacity: 3
virtual_network_name: "{{ vmss_name }}"
subnet_name: "{{ vmss_name }}"
upgrade_policy: Manual
tier: Standard
managed_disk_type: Standard_LRS
os_disk_caching: ReadWrite
image:
name: "{{ image_name }}"
resource_group: "{{ resource_group }}"
load_balancer: "{{ vmss_name }}lb"
- name: List all of the instances
azure_rm_virtualmachinescalesetinstance_facts:
resource_group: "{{ resource_group }}"
vmss_name: "{{ vmss_name }}"
register: instances
- debug:
var: instances
- name: manually upgrade all the instances
azure_rm_virtualmachinescalesetinstance:
resource_group: "{{ resource_group }}"
vmss_name: "{{ vmss_name }}"
instance_id: "{{ item.instance_id }}"
latest_model: yes
with_items: "{{ instances.instances }}"
명령을 사용하여 플레이북을 ansible-playbook
실행하고 리소스 그룹 이름으로 바꿉 myrg
니다.
ansible-playbook update-vmss-image.yml --extra-vars "resource_group=myrg"
브라우저로 돌아가서 페이지를 새로 고쳐 가상 머신의 기본 사용자 지정 이미지가 업데이트되는지 확인합니다.
리소스 정리
다음 코드를 .로
delete_rg.yml
저장합니다.--- - hosts: localhost tasks: - name: Deleting resource group - "{{ name }}" azure_rm_resourcegroup: name: "{{ name }}" state: absent register: rg - debug: var: rg
ansible-playbook 명령을 사용하여 플레이북을 실행합니다. 자리 표시자를 삭제할 리소스 그룹의 이름으로 바꿉니다. 리소스 그룹 내의 모든 리소스가 삭제됩니다.
ansible-playbook delete_rg.yml --extra-vars "name=<resource_group>"
주요 정보:
- 플레이북의
register
변수 및debug
섹션으로 인해 명령이 완료되면 결과가 표시됩니다.
- 플레이북의