作者选择了 自由和开源基金作为 写给捐款计划的一部分接受捐款。
介绍
Terraform是由HashiCorp(https://www.hashicorp.com/)创建的基础设施代码工具,可帮助开发人员以更高效、更可扩展的方式部署、更新和删除基础设施中的不同资产。
开发人员可以使用Terraform来组织不同的环境,通过版本控制跟踪更改,并自动重复工作,以限制人为错误。
在本教程中,您将导入现有的DigitalOcean基础设施到Terraform. 在本教程结束时,您将能够使用Terraform用于所有现有的基础设施,除了创建新的资产。
前提条件
- 您可以通过DigitalOcean控制面板创建的DigitalOcean个人访问令牌,您可以在DigitalOcean产品文件中找到指示
【如何创建个人访问代码】(https://www.digitalocean.com/docs/api/create-personal-access-token/)
您可以使用以下指南: 如何从DigitalOcean控制面板创建一个Droplet)。在本教程中使用的标签是 terraform-testing
.
- 将DigitalOcean Cloud Firewall应用于您的Droplet。您可以使用指南: How To Create Firewalls。 防火墙名称
testing-terraform-firewall
用于本教程的目的 - 在本地机器上安装的DigitalOcean命令行客户端,您可以通过在
doctl
GitHub 页面上的安装说明来完成。 您可以阅读本教程: [How To Use Doctl, the Official DigitalOcean
本教程是使用Terraform 1.0.10测试的。
步骤一:本地安装地板
在此第一步中,您将在本地计算机上安装 Terraform. 此步骤详细介绍了在 Linux 发行版上安装 Terraform. 如果您使用的是 Windows 或 MacOS,您可以在 Terraform 网站上查看 下载 Terraform 页面。
安装步骤在 HashiCorp 网站上描述。
<$>[注] **注:通常在同一命令中直接从互联网下载的对象/可执行程序的管道运行通常是不好的做法,但由于HashiCorp是值得信赖的来源,我们将在这里做例外 如果你觉得不舒服这样做,先下载对象,检查它,然后继续前进,如果一切看起来很好 <$>
安装在 Ubuntu 20.04 上
HashiCorp 数字签名其存储库,因此您需要添加其 GNU 隐私保护程序 (GPG) 密钥,这提供了合理的保证,该存储库实际上由 HashiCorp 拥有和维护:
1curl -fsSL https://apt.releases.hashicorp.com/gpg | sudo apt-key add -
将官方 HashiCorp 存储库添加到系统:
1sudo apt-add-repository "deb [arch=$(dpkg --print-architecture)] https://apt.releases.hashicorp.com $(lsb_release -cs) main"
安装地形:
1sudo apt update; sudo apt install terraform=1.0.10
安装在 Fedora 34 上
为了添加 HashiCorp 存储库,您需要将其添加到您的存储库列表中。 DNF 核心插件 config-manager
用于此目的,并由 dnf-plugins-core
包提供。
1sudo dnf install -y dnf-plugins-core
将官方 HashiCorp 存储库添加到系统:
1sudo dnf config-manager --add-repo https://rpm.releases.hashicorp.com/fedora/hashicorp.repo
安装地形:
1sudo dnf install terraform-1.0.10-1
遵循您的操作系统的安装指示后,通过检查版本来检查Terraform是否正确安装:
1terraform version
结果将看起来像这样:
1[secondary_label Output]
2Terraform v1.0.10
3on linux_amd64
您已在本地机器上安装了 Terraform. 接下来,您将准备配置文件。
步骤 2 – 准备 Terraform 配置文件
在此步骤中,您将通过创建项目目录和编写配置文件来导入现有资产到Terraform。
运行以下命令来创建您的项目目录:
1mkdir -p do_terraform_import
然后进入该目录:
1cd do_terraform_import
启动一个新的 Terraform 工作空间:
1terraform workspace new do_terraform_import
查看您是否正在使用新创建的工作区:
1terraform workspace list
结果将类似于此:
1[secondary_label Output]
2 default
3* do_terraform_import
在此步骤中,您将创建三个附加文件,其中包含所需的配置. 此项目的目录结构将如下:
1├── digitalocean_droplet.tf
2├── digitalocean_firewall.tf
3├── provider.tf
4├── .terraform
5└── terraform.tfstate.d
首先,您将创建provider.tf
文件,将您的 DigitalOcean Access Token 定义为环境变量,而不是将其硬编码到您的配置中。
<$>[警告] 警告:您的访问令牌可以访问您的完整基础设施,无限制访问,因此,请确保您是唯一可以访问该令牌存储的机器的人。
在本教程中,它是digitalocean
。 对于有用的数据源和资源的完整列表,DigitalOcean with Terraform,请访问他们的网站上的提供者页面(https://www.terraform.io/docs/providers/do/index.html)。
使用以下命令创建和编辑 provider.tf:
1nano provider.tf
将以下内容添加到provider.tf
文件中:
1[label provider.tf]
2terraform {
3 required_providers {
4 digitalocean = {
5 source = "digitalocean/digitalocean"
6 version = "2.15.0"
7 }
8 }
9}
10
11variable "do_token" {}
12
13provider "digitalocean" {
14 token = var.do_token
15}
在此文件中,您将您的 DigitalOcean Access Token 添加为变量,而 Terraform 将其用作 DigitalOcean API 的标识。
保存并关闭文件。
现在你将创建的 digitalocean_droplet.tf
文件. 在这里,你将指定你要使用的资源,在这种情况下: droplet
。
此文件应复制现有资源,以便在以后的步骤中成功导入 Terraform 状态。
使用以下命令创建文件:
1nano digitalocean_droplet.tf
添加以下配置,在必要时更新以匹配您的现有资源:
1[label digitalocean_droplet.tf]
2resource "digitalocean_droplet" "do_droplet" {
3 name = "testing-terraform"
4 region = "fra1"
5 tags = ["terraform-testing"]
6 count = "1"
7}
在这里,您指定了四个参数,这些参数应匹配您的现有资源:
名称
: Droplet 名称区域
: Droplet 所在的区域标签
:将应用于此 Droplet 的标签列表- `数:此配置所需的资源数量
保存并关闭文件。
接下来,您将为您的防火墙创建一个配置文件. 使用以下命令创建文件 digitalocean_firewall.tf
:
1nano digitalocean_firewall.tf
将以下内容添加到文件中:
1[label digitalocean_firewall.tf]
2resource "digitalocean_firewall" "do_firewall" {
3 name = "testing-terraform-firewall"
4 tags = ["terraform-testing"]
5}
在这里,您指定您要导入的防火墙的名称以及适用于防火墙规则的 Droplets 标签。
保存并关闭文件。
<$>[注]
注:您也可以将防火墙资源包含在 digitalocean_droplet.tf
文件中;但是,如果您有多个环境,其中多个 Droplets 共享相同的防火墙,如果您只想删除单个 Droplet,则最好将它们分开。
现在是时候初始化这些更改,以便Terraform可以下载所需的依赖性,您将使用terraform init
命令,这将允许您初始化包含Terraform配置文件的工作目录。
从您的项目目录中运行此命令:
1terraform init
您将看到以下输出:
1[secondary_label Output]
2Terraform has been successfully initialized!
Terraform通过下载插件,搜索模块等成功准备了工作目录,接下来您将开始导入您的资产到Terraform。
步骤 3 – 将您的资产导入 Terraform
在此步骤中,您将将您的 DigitalOcean 资产导入 Terraform. 在导入资产之前,您将使用doctl
查找您的 Droplets 的 ID 号码。
首先,您将将您的 DigitalOcean Access Token 导出为环境变量,然后在运行时将其注入到 Terraform。
将其作为环境变量导出到当前壳会话中,使用以下命令:
1export DO_TOKEN="YOUR_TOKEN"
为了导入现有的 Droplet 和防火墙,您需要他们的 ID 号码,您可以使用doctl
,这是 DigitalOcean API 的命令行界面。
运行以下命令列出您的 Droplets 并访问他们的 ID:
1doctl compute droplet list
您将看到类似于以下的输出:
1[secondary_label Output]
2ID Name Public IPv4
3DROPLET-ID DROPLET-NAME DROPLET-IPv4
4DROPLET-ID DROPLET-NAME DROPLET-IPv4
5DROPLET-ID DROPLET-NAME DROPLET-IPv4
请注意您要导入的资源的 Droplet ID,因为您将在以后的命令中需要这样做。
接下来,运行以下命令列出您的防火墙并访问他们的ID:
1doctl compute firewall list
您将看到类似于以下的输出:
1[secondary_label Output]
2ID Name Status
3FIREWALL-ID FIREWALL-NAME succeeded
请注意您要导入的资源的防火墙 ID,因为您将在以后的命令中需要这样做。
将现有 Droplet 导入 Terraform,以您的 Droplet ID 代替 DROPLET-ID:
1terraform import -var "do_token=${DO_TOKEN}" digitalocean_droplet.do_droplet DROPLET-ID
您使用-var
旗帜来指定您之前向壳会话导出的DigitalOcean Access Token值,这需要DigitalOcean API来验证您是谁,并对您的基础设施进行更改。
现在为您的防火墙运行相同的命令,将FIREWALL ID替换为您的防火墙ID:
1terraform import -var "do_token=${DO_TOKEN}" digitalocean_firewall.do_firewall FIREWALL-ID
您可以通过使用terraform 显示
命令检查导入是否成功. 此命令可为基础设施状态提供可人读的输出。
在这种情况下, state 是指将您的 DigitalOcean 资产与您编写的 Terraform 配置进行映射,以及跟踪元数据,这使您能够确认您想要导入的现有 DigitalOcean 资产与 Terraform 正在跟踪的资产之间没有差异:
1terraform show
结果将看起来像这样:
1[secondary_label Output]
2. . .
3# digitalocean_droplet.do_droplet:
4resource "digitalocean_droplet" "do_droplet" {
5 backups = false
6 created_at = "2020-02-03T16:12:02Z"
7 disk = 25
8 id = "DROPLET-ID"
9 image = "DROPLET-IMAGE"
10 ipv4_address = "DROPLET-IP"
11 ipv6 = false
12 locked = false
13 memory = 1024
14 monitoring = false
15 name = "testing-terraform-0"
16 price_hourly = 0.00744
17 price_monthly = 5
18 private_networking = false
19 region = "fra1"
20 resize_disk = true
21 size = "s-1vcpu-1gb"
22 status = "active"
23 tags = [
24 "terraform-testing",
25 ]
26 urn = "DROPLET-URN"
27 vcpus = 1
28 volume_ids = []
29. . .
30}
您将在输出中看到两个资源及其属性。
将您的 Droplet 和防火墙导入 Terraform 状态后,您需要确保配置代表已导入资产的当前状态。 要做到这一点,您将指定您的 Droplet 的图像
和大小
。
打开digitalocean_droplet.tf
文件:
1nano digitalocean_droplet.tf
在本教程中:
- 现有 Droplet 所使用的操作系统图像为
ubuntu-20-04-x64
. - Droplet 所在的区域为
fra1
. *现有 Droplet 的 Droplet 标签为terraform-testing
.
<$>[注] 注:您的操作系统、区域、滴滴的大小和其他资源可能有所不同,请确保更新文件以反映您的值 <$> 为了确保 `digitalocean_droplet.tf 中的配置匹配进口滴滴的当前状态,它需要被更新以显示如下:
1[label digitalocean_droplet.tf]
2resource "digitalocean_droplet" "do_droplet" {
3 image = "ubuntu-20-04-x64"
4 name = "testing-terraform"
5 region = "fra1"
6 size = "s-1vcpu-1gb"
7 tags = ["terraform-testing"]
8}
如有必要,更新配置以匹配您导入的 Droplet。
接下来,您将添加防火墙规则。在我们的示例中,入口流量的开放端口为22
,80
和443
。
打开digitalocean_firewall.tf
:
1nano digitalocean_firewall.tf
添加以下配置:
1[label digitalocean_firewall.tf]
2resource "digitalocean_firewall" "do_firewall" {
3 name = "testing-terraform-firewall"
4 tags = ["terraform-testing"]
5
6 inbound_rule {
7 protocol = "tcp"
8 port_range = "22"
9 source_addresses = ["0.0.0.0/0", "::/0"]
10 }
11 inbound_rule {
12 protocol = "tcp"
13 port_range = "80"
14 source_addresses = ["0.0.0.0/0", "::/0"]
15 }
16 inbound_rule {
17 protocol = "tcp"
18 port_range = "443"
19 source_addresses = ["0.0.0.0/0", "::/0"]
20 }
21
22 outbound_rule {
23 protocol = "tcp"
24 port_range = "all"
25 destination_addresses = ["0.0.0.0/0", "::/0"]
26 }
27 outbound_rule {
28 protocol = "udp"
29 port_range = "all"
30 destination_addresses = ["0.0.0.0/0", "::/0"]
31 }
32 outbound_rule {
33 protocol = "icmp"
34 destination_addresses = ["0.0.0.0/0", "::/0"]
35 }
36}
这些规则复制现有示例防火墙的状态. 如果您想限制流量到不同的 IP 地址、不同的端口或不同的协议,您可以调整文件以复制现有防火墙。
保存并关闭文件。
更新 Terraform 文件后,您将使用计划
命令查看所做的更改是否复制了 DigitalOcean 上现有资产的状态。
使用此命令,您可以检查Terraform要做的更改是否是您想要做的更改。
运行terraform计划
以如下方式:
1terraform plan -var "do_token=$DO_TOKEN"
如果没有检测到任何变化,输出将看起来像这样:
1[secondary_label Output]
2No changes. Infrastructure is up-to-date.
如果检测到更改,Terraform输出将显示它们,以便您相应审查和调整。
您已成功将现有的 DigitalOcean 资产导入 Terraform,现在您可以通过 Terraform 对您的基础设施进行更改,而无需意外删除或修改现有资产的风险。
第4步:通过Terraform创建新资产
在此步骤中,您将添加两个额外的 Droplets 到您的现有基础设施. 以此方式添加资产到您的现有基础设施可以是有用的,例如,如果您有一个实时网站,而不想在工作时对该网站进行任何潜在的破坏性更改。
打开digitalocean_droplet.tf
以添加新 Droplets 的规则:
1nano digitalocean_droplet.tf
将突出的行添加到您的文件中:
1[label digitalocean_droplet.tf]
2resource "digitalocean_droplet" "do_droplet" {
3 image = "ubuntu-20-04-x64"
4 name = "testing-terraform"
5 region = "fra1"
6 size = "s-1vcpu-1gb"
7 tags = ["terraform-testing"]
8 count = "1"
9}
10
11resource "digitalocean_droplet" "do_droplet_new" {
12 image = "ubuntu-20-04-x64"
13 name = "testing-terraform-${count.index}"
14 region = "fra1"
15 size = "s-1vcpu-1gb"
16 tags = ["terraform-testing"]
17 count = "2"
18}
您可以使用计数
元参数告诉Terraform您想要的相同规格的 Droplets 数目。
应用这些规则来检查您在digitalocean_droplet.tf
中指定的更改:
1terraform plan -var "do_token=$DO_TOKEN"
检查您要做的更改是否在该命令的输出中复制。
您将看到类似于以下的输出:
1. . .
2[secondary_label Output]
3# digitalocean_droplet.do_droplet_new[1] will be created
4 + resource "digitalocean_droplet" "do_droplet_new" {
5 + backups = false
6 + created_at = (known after apply)
7 + disk = (known after apply)
8 + id = (known after apply)
9 + image = "ubuntu-20-04-x64"
10 + ipv4_address = (known after apply)
11 + ipv4_address_private = (known after apply)
12 + ipv6 = false
13 + ipv6_address = (known after apply)
14 + ipv6_address_private = (known after apply)
15 + locked = (known after apply)
16 + memory = (known after apply)
17 + monitoring = false
18 + name = "testing-terraform-1"
19 + price_hourly = (known after apply)
20 + price_monthly = (known after apply)
21 + private_networking = true
22 + region = "fra1"
23 + resize_disk = true
24 + size = "s-1vcpu-1gb"
25 + status = (known after apply)
26 + tags = [
27 + "terraform-testing",
28 ]
29 + urn = (known after apply)
30 + vcpus = (known after apply)
31 + volume_ids = (known after apply)
32 }
33
34Plan: 2 to add, 1 to change, 0 to destroy.
一旦您对输出满意,请使用terraform apply
命令将您指定的更改应用到配置状态:
1terraform apply -var "do_token=$DO_TOKEN"
通过在命令行中输入是
来确认更改,成功执行后,您将看到类似于以下的输出:
1[secondary_label Output]
2. . .
3digitalocean_droplet.do_droplet_new[1]: Creating...
4digitalocean_droplet.do_droplet_new[0]: Creating...
5digitalocean_firewall.do_firewall[0]: Modifying... [id=FIREWALL-ID]
6digitalocean_firewall.do_firewall[0]: Modifications complete after 1s [id=FIREWALL-ID]
7digitalocean_droplet.do_droplet_new[0]: Still creating... [10s elapsed]
8digitalocean_droplet.do_droplet_new[1]: Still creating... [10s elapsed]
9digitalocean_droplet.do_droplet_new[0]: Creation complete after 16s [id=DROPLET-ID]
10digitalocean_droplet.do_droplet_new[1]: Still creating... [20s elapsed]
11digitalocean_droplet.do_droplet_new[1]: Creation complete after 22s [id=DROPLET-ID]
12
13Apply complete! Resources: 2 added, 1 changed, 0 destroyed.
You'll see two new Droplets in your DigitalOcean web panel:
You'll also see them attached to your existing firewall:
您已使用 Terraform 创建新资产,使用现有资产. 要了解如何破坏这些资产,您可以选择完成下一步。
步骤 5 – 销毁已导入和创建的资产(可选)
在此步骤中,您将使用Terraform的摧毁
选项来摧毁您导入和创建的资产。
要摧毁由 Terraform 处理的资产,请执行以下命令:
1terraform destroy -var "do_token=${DO_TOKEN}"
Terraform 将要求您确认您是否想要摧毁 Droplets 和防火墙. 这将摧毁您通过 Terraform 导入和创建的所有资产,因此请确保在键入是
之前继续。
结果将看起来像这样:
1[secondary_label Output]
2. . .
3digitalocean_droplet.do_droplet[0]: Destroying... [id=YOUR-DROPLET-ID]]
4digitalocean_droplet.do_droplet_new[0]: Destroying... [id=YOUR-DROPLET-ID]
5digitalocean_droplet.do_droplet_new[1]: Destroying... [id=YOUR-DROPLET-ID]
6digitalocean_firewall.do_firewall[0]: Destroying... [id=YOUR-FIREWALL-ID]
7digitalocean_firewall.do_firewall[0]: Destruction complete after 1s
8digitalocean_droplet.do_droplet_new[1]: Still destroying... [id=YOUR-DROPLET-ID, 10s elapsed]
9digitalocean_droplet.do_droplet[0]: Still destroying... [id=YOUR-DROPLET-ID, 10s elapsed]
10digitalocean_droplet.do_droplet_new[0]: Still destroying... [id=YOUR-DROPLET-ID, 10s elapsed]
11digitalocean_droplet.do_droplet_new[1]: Still destroying... [id=YOUR-DROPLET-ID, 20s elapsed]
12digitalocean_droplet.do_droplet_new[0]: Still destroying... [id=YOUR-DROPLET-ID, 20s elapsed]
13digitalocean_droplet.do_droplet[0]: Still destroying... [id=YOUR-DROPLET-ID, 20s elapsed]
14digitalocean_droplet.do_droplet_new[1]: Destruction complete after 22s
15digitalocean_droplet.do_droplet[0]: Destruction complete after 22s
16digitalocean_droplet.do_droplet_new[0]: Destruction complete after 22s
17
18Apply complete! Resources: 0 added, 0 changed, 4 destroyed.
您已成功删除由 Terraform 管理的所有资产。
结论
在本教程中,您安装了Terraform,导入了现有资产,创建了新资产,并可选地摧毁了这些资产。您可以将此工作流程扩展到更大的项目,例如部署一个生产准备的Kubernetes集群。使用Terraform,您可以管理所有节点,DNS条目,防火墙,存储和其他资产,以及使用版本控制来跟踪变化并与团队合作。
要探索其他 Terraform 功能,请阅读他们的 文档。你也可以阅读 DigitalOcean 的 Terraform 内容 有关进一步的教程和问答。