1. 程式人生 > >Code as IaaS for Azure : Terraform 初步

Code as IaaS for Azure : Terraform 初步

生產環境 bili client 獨立 結果 network forms ply wid

  節前有用戶提了兩個需求,PostgreSQL和Terraform,趁著過節有大塊的時間,把這兩個都粗略的過了下。之前已經把PostgreSQL相關測試結果寫了篇文檔,正好把Terraform的學習經歷也記錄下來,寫個文檔。

Terraform的網站上是這麽介紹的“Terraform is a tool for building, changing, and versioning infrastructure safely and efficiently. Terraform can manage existing and popular service providers as well as custom in-house solutions.”。在我看來它是一個可以實現跨雲的代碼即基礎架構工具。目前Terraform支持的公有/私有雲平臺包括: AWS,Azure(ARM和ASM),阿裏雲,Google Cloud,Oracle Cloud,OpenStack,CloudStack,VMware等等等等等。嗯,要是還能支持AzureStack就完美了。

Terraform具體的功能可以在www.terraform.io上學習,它的文檔和示例都寫得很不錯,我在這就簡單介紹下怎麽用Terraform來管理Azure上的基礎架構。

  目前Terraform支持Azure ARM的功能如下

Base Resource

azurerm_resource_group

Creates a new resource group on Azure.

Template

azurerm_template_deployment

Create a template deployment of resources

Web App

azurerm_app_service_plan

Create an App Service Plan component

azurerm_app_service

Manages an App Service (within an App Service Plan)

Virtual Machine

azurerm_virtual_machine

Create a virtual machine.

azurerm_availability_set

Create an availability set for virtual machines.

azurerm_virtual_machine_extension

Creates a new Virtual Machine Extension to provide post deployment configuration and run automated tasks.

azurerm_virtual_machine_scale_set

Create a virtual machine scale set.

Storage

azurerm_storage_account

Create an Azure Storage Account.

azurerm_storage_container

Create an Azure Storage Container.

azurerm_storage_blob

Create an Azure Storage Blob.

azurerm_storage_queue

Create an Azure Storage Queue.

azurerm_storage_share

Create an Azure Storage File Share.

azurerm_storage_table

Create an Azure Storage Table.

Managed Disk

azurerm_managed_disk

Create a managed disk.

azurerm_image

Create a custom virtual machine image that can be used to create virtual machines.

Network

azurerm_express_route_circuit

Creates an ExpressRoute circuit.

azurerm_local_network_gateway

Creates a new local network gateway connection over which specific connections can be configured.

azurerm_network_interface

Manages a Network Interface located in a Virtual Network, usually attached to a Virtual Machine.

azurerm_network_security_group

Create a network security group that contains a list of network security rules.

azurerm_network_security_rule

Create a Network Security Rule.

azurerm_public_ip

Create a Public IP Address.

azurerm_route

Creates a new Route Resource

azurerm_route_table

Creates a new Route Table Resource

azurerm_subnet

Creates a new subnet. Subnets represent network segments within the IP space defined by the virtual network.

azurerm_traffic_manager_endpoint

Creates a Traffic Manager Endpoint.

azurerm_traffic_manager_profile

Creates a Traffic Manager Profile to which multiple endpoints can be attached.

azurerm_virtual_network

Creates a new virtual network including any configured subnets. Each subnet can optionally be configured with a security group to be associated with the subnet.

azurerm_virtual_network_peering

Creates a new virtual network peering which allows resources to access other resources in the linked virtual network.

Load Balance

azurerm_lb

Create a LoadBalancer Resource.

azurerm_lb_backend_address_pool

Create a LoadBalancer Backend Address Pool.

azurerm_lb_rule

Create a LoadBalancer Rule.

azurerm_lb_nat_rule

Create a LoadBalancer NAT Rule.

azurerm_lb_nat_pool

Create a LoadBalancer NAT pool.

azurerm_lb_probe

Create a LoadBalancer Probe Resource.

Automation

azurerm_automation_account

Creates a new Automation Account.

azurerm_automation_credential

Creates a new Automation Credential.

azurerm_automation_runbook

Creates a new Automation Runbook.

azurerm_automation_schedule

Creates a new Automation Schedule.

除了這些基礎服務,Terraform還支持更多服務,包括Database:MySQL,SQL Server,還有Azure.com支持的PostgreSQL和CosmosDB。DNS 服務,KeyVault服務,消息隊列:Event Hub,Service Bus。Redis服務,CDN服務,容器服務(Azure.com支持)。

要使用Terraform來部署Azure資源,官方建議是通過Service Principal 來通過Azure認證。我們會在每個部署腳本最前面看到這樣一段內容:

provider "azurerm" {

subscription_id = "..."

client_id = "..."

client_secret = "..."

tenant_id = "..."

}

在這段腳本裏指定了登錄到哪個Azure環境,使用哪個訂閱,以及用戶認證。所以接下來我們首先要獲得這幾個參數。

  首先,我們通過Azure Cli登錄Azure。如果要登錄Azure.cn,記得先用“az cloud set -n AzureChinaCloud” 設置登錄環境。

用 az login 命令登錄,按照提示進行網頁驗證。登錄成功後會看到類似以下的返回:

[

{

"cloudName": "AzureChinaCloud",

"id": "XXXXXXXXXXXXXXXXXXXXXXXXXX",

"isDefault": true,

"name": "Microsoft Azure Enterprise \u8bd5\u7528\u7248",

"state": "Enabled",

"tenantId": "XXXXXXXXXXXXXXXXXXXXXXXXX",

"user": {

"name": "[email protected]",

"type": "user"

}

}

]

註意,這其中的id和tenantid就對應了我們需要的subscription_id和tenant_id這兩個參數。

接下來用az ad sp create-for-rbac --role="Contributor" --scopes="/subscriptions/<subscription_id>" 這個命令來創建 Service Principal . 順利的話可以看到以下返回:

Retrying role assignment creation: 1/36

Retrying role assignment creation: 2/36

Retrying role assignment creation: 3/36

{

"appId": "XXXXXXXXXXXXXXXXXXXXXXXXX",

"displayName": "azure-cli-2017-09-28-08-01-33",

"name": "http://azure-cli-2017-09-28-08-01-33",

"password": "XXXXXXXXXXXXXXXXXXXXXXXXXXX",

"tenant": "XXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

}

其中appId和password分別對應了我們需要的參數client_id和client_secret

其實也可以在GUI界面裏進行相同的工作,結果大致如下圖所示

技術分享

順便說一下,按照這個思路,我最後寫了4個腳本,可以分別在Azure CLI和Powershell環境下登錄Azure.com和Azure.cn。不需要在本機或Azure上保存任何證書都可以使用。還是很方便的。大家如果有興趣以後再寫一個文檔說明是怎麽做的。

獲得所需要的Azure登錄參數,我們就可以正式來寫一個Terraform腳本來部署一個虛機了。

這次我們用到的腳本如下:

variable "resourcesname" {

default = "helloterraform"

}

# 這段是配置Azure的使用環境

# 註意,因為使用的是Azure.cn,所以要加上參數environment = "china",默認是azure.com,參數使用上面所講的步驟裏獲得的那幾個參數

provider "azurerm" {

subscription_id = "XXXXXXXXXXXXXXXXXXXXXXXXXXXX"

client_id = "XXXXXXXXXXXXXXXXXXXXXXXXXXX"

client_secret = "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

tenant_id = "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

environment = "china"

}

# 創建一個Resource Group,名字是lyq-testterraform-rg,位置是北京

resource "azurerm_resource_group" "helloterraform" {

name = "lyq-testterraform-rg"

location = "China North"

}

# 創建一個虛擬網絡,給定name,IP,位置和所屬資源組

resource "azurerm_virtual_network" "helloterraformnetwork" {

name = "tfvn"

address_space = ["10.0.0.0/16"]

location = "China North"

resource_group_name = "${azurerm_resource_group.helloterraform.name}"

}

# 創建一個虛擬子網

resource "azurerm_subnet" "helloterraformsubnet" {

name = "tfsub"

resource_group_name = "${azurerm_resource_group.helloterraform.name}"

virtual_network_name = "${azurerm_virtual_network.helloterraformnetwork.name}"

address_prefix = "10.0.2.0/24"

}

# 創建一個公網地址

resource "azurerm_public_ip" "helloterraformips" {

name = "terraformtestip"

location = "China North"

resource_group_name = "${azurerm_resource_group.helloterraform.name}"

public_ip_address_allocation = "dynamic"

tags {

environment = "TerraformDemo"

}

}

# 創建一塊虛擬網卡

resource "azurerm_network_interface" "helloterraformnic" {

name = "tfni"

location = "China North"

resource_group_name = "${azurerm_resource_group.helloterraform.name}"

ip_configuration {

name = "testconfiguration1"

subnet_id = "${azurerm_subnet.helloterraformsubnet.id}"

private_ip_address_allocation = "static"

private_ip_address = "10.0.2.5"

public_ip_address_id = "${azurerm_public_ip.helloterraformips.id}"

}

}

# 創建一個隨機數,我們知道存儲賬戶是要求一個不沖突的獨立命名,這個隨機數就是用在存儲賬戶裏的

resource "random_id" "randomId" {

byte_length = 4

}

# 創建一個存儲賬戶,也可以創建一個managed disk

resource "azurerm_storage_account" "helloterraformstorage" {

name = "tfstorage${random_id.randomId.hex}"

resource_group_name = "${azurerm_resource_group.helloterraform.name}"

location = "China North"

account_type = "Standard_LRS"

tags {

environment = "staging"

}

}

# 創建一個存儲容器

resource "azurerm_storage_container" "helloterraformstoragestoragecontainer" {

name = "vhd"

resource_group_name = "${azurerm_resource_group.helloterraform.name}"

storage_account_name = "${azurerm_storage_account.helloterraformstorage.name}"

container_access_type = "private"

depends_on = ["azurerm_storage_account.helloterraformstorage"]

}

# 創建虛擬機,用Ubuntu系統,將之前創建的虛擬網卡,存儲都掛載好,設定用戶名和密碼,在生產環境裏建議disable_password_authentication = true,這樣需要指定證書登錄。

resource "azurerm_virtual_machine" "helloterraformvm" {

name = "terraformvm"

location = "China North"

resource_group_name = "${azurerm_resource_group.helloterraform.name}"

network_interface_ids = ["${azurerm_network_interface.helloterraformnic.id}"]

vm_size = "Standard_A0"

storage_image_reference {

publisher = "Canonical"

offer = "UbuntuServer"

sku = "14.04.2-LTS"

version = "latest"

}

storage_os_disk {

name = "myosdisk"

vhd_uri = "${azurerm_storage_account.helloterraformstorage.primary_blob_endpoint}${azurerm_storage_container.helloterraformstoragestoragecontainer.name}/myosdisk.vhd"

caching = "ReadWrite"

create_option = "FromImage"

}

os_profile {

computer_name = "hostname"

admin_username = "testadmin"

admin_password = "Password1234!"

}

os_profile_linux_config {

disable_password_authentication = false

}

tags {

environment = "staging"

}

}

這樣就可以創建一個虛擬機了。可以先用terraform plan命令來驗證腳本是否正確,還可以用-out參數來輸出一個執行腳本,例如:terraform plan -out lyqdemo .

驗證沒有問題後,用 terraform apply lyqdemo 命令來執行變更。等執行完成後,我們可以在Azure.cn界面裏查看下創建的是否正確

技術分享

創建虛擬機可以說是最簡單的一個動作了,接下來我們會做一些更復雜的事情。

Code as IaaS for Azure : Terraform 初步