如何使用 Terraform 和 Git 分支有效管理多环境?

如何,使用,terraform,git,分支,有效,管理,环境 · 浏览次数 : 206

小编点评

## Terraform 工作空间概述 **工作空间插值序列**是一个用于管理多个环境的强大工具,它可以帮助我们创建不同的环境,并对这些环境进行安全管理。 **使用 Git 分支管理多个环境** **主要优势:** * 减少冲突 * 提高效率 * 改善安全 * 方便管理 **注意:** * 确保工作空间插值序列的顺序正确 * 避免使用与开发环境相同的后端 * 对生产环境进行安全管理

正文

作者|Sumeet Ninawe
翻译|Seal软件
链接|https://spacelift.io/blog/terraform-environments

 

通常我们使用 Terraform 将我们的基础设施定义为代码,然后用 Terraform CLI 在我们选择的云平台中创建制定的基础设施组件。从表面上看,整个过程看起来似乎不需要花费太多精力。然而当我们深入研究将其用于真实场景时,很快就会遇到有关管理子生产和生产环境的问题。
 

在这篇文章中,我们将重点关注如何使用 Terraform Workspace 和 Git 分支来有效管理多个环境。
 

多环境基础设施

下面列出了使用 IaC 管理多个环境的基础设施的期望和要求:

  • 可以使用相同的 IaC 配置来管理生产和非生产环境。

  • 某些非生产环境,如开发、QA、测试版或 UAT 应该与生产的相同和缩小版本并永久存在。

  • 团队成员能够创建、管理和销毁与生产相同的临时环境。

  • 所有环境并不是在同一个云帐户或订阅中创建的。
     

这里的关键点在于对所有环境中的基础设施使用相同的 Terraform 配置模板。
 

Terraform Workspace

Terraform 提供了一个工作区功能,使用该功能可以使用相同的配置创建和管理多个相同的、按比例缩小的环境。以这种方式创建的多个环境是完全隔离的,不会以任何方式相互干扰。这是我们需要的关键功能。一起看看如何利用这个功能来满足我们的要求。
 

Terraform Workspace 不同于 Terraform Cloud Workspace。在 Terraform Cloud 中,工作空间类似于一个“项目”,对应于 Terraform 配置存储库。除了存储和管理状态信息外,还管理变量、凭证、历史跟踪等,以支持端到端的 Terraform Cloud CI/CD 工作流。
 

用于处理工作区的 Terraform CLI 命令

下表表示 Terraform 工作区命令的基本用法。每个命令都遵循如下简单格式:
terraform workspace <command>
 

 

下面的 CLI 输出显示了管理工作区的示例。简而言之,我们检查当前选择的工作空间——默认,然后创建一个名为 beta 的新工作空间,列出所有工作空间,并删除 beta 工作空间。
 

% terraform workspace show
default
% terraform workspace new beta
Created and switched to workspace "beta"!

You're now on a new, empty workspace. Workspaces isolate their state,
so if you run "terraform plan" Terraform will not see any existing state
for this configuration.
% terraform workspace list
  default
* beta

% terraform workspace select default
Switched to workspace "default".
% terraform workspace delete beta
Releasing state lock. This may take a few moments...
Deleted workspace "beta"!
% terraform workspace list
* default

 

工作区插值

要使用相同的配置管理多个按比例缩小的环境,需要有一种方法让 Terraform 知道我们正在使用哪个工作区,这有助于正确设置配置。例如,我们可能希望为特定工作区管理的环境提供更多的 EC2 实例,为其他环境提供更少的实例。
 

Terraform 工作空间插值序列为我们提供了一种实现这种动态变化的方法。通过访问所选工作区的值,我们可以使用多个构造和运算符来创建具有所需规模和其他自定义属性的环境。
 

考虑下面的例子。在这里,Terraform 配置旨在在 AWS 中创建 EC2 实例。但是,基于所选工作区的计数属性定义了要创建的实例数。这里,“terraform.workspace”插值序列用于访问它。
 

resource "aws_instance" "my_vm" {
 count = terraform.workspace == "default" ? 3 : 1
 ami = var.ami //Ubuntu AMI
 instance_type = var.instance_type

 tags = {
   Name = format("%s_%s_%s", var.name_tag, terraform.workspace, count.index)
 }
}

 

如果选择“默认”工作区,则将创建三个 EC2 实例,否则只创建一个。当然,这只是一个例子。我们可以使用更复杂的变量和运算符来管理更多的环境。
 

基础设施和应用程序开发

端到端产品开发涉及几个方面——基础设施和要部署在基础设施上的应用程序。通常,会有对应的个人团队来负责相应的任务。在微服务中,由于依赖性和资源限制,在本地机器上测试和开发应用程序可能并不总是可行的。应用程序团队成员可能需要调整临时环境来运行他们的测试用例,甚至在将更改部署到“永久”开发环境之前。
 

在这种情况下,无需担心 Terraform 源代码,因为他们可以简单地克隆存储库,然后使用工作区功能创建自己的临时环境。这种能力对于应用程序开发团队来说非常有用,可以在将更改合并到 dev 并将它们向前推进之前单独运行他们的测试用例。
 

帐户和凭据

多个环境通常使用多个云帐户或订阅进行管理。云平台还实施了“组织”概念,以从单个根帐户管理多个帐户。此根帐户负责所有管理活动,如计费、访问配置等。当 Terraform 配置被“应用”时,更改将根据其提供者配置为目标帐户进行验证和执行。
 

provider "aws" {
  shared_config_files = ["/path/to/.aws/conf"]
  shared_credentials_files = ["/path/to/.aws/creds"]
  profile = "profile_name"
}

 

在这里,我们对配置文件名称进行了硬编码,以便 Terraform 为目标帐户使用适当的凭据。在这里,我们还可以利用工作区插值序列从共享凭证文件中动态选择配置文件名称。
 

Terraform Workspace 小结

在使用 Terraform 管理多个环境时,Terraform 中的状态管理可能是一个敏感话题。不过 Terraform 提供的工作区管理可以通过在当前设置的后端中创建子目录来在后台处理此问题。状态管理也可能是一个限制因素,因为所有状态文件都存储在同一个后端目录中。这意味着所有用于 terraform 配置的插件也会在每个工作区中被复制。
 

Terraform 工作区提供了一种创建瞬态环境的好方法,只需学习一些命令即可测试基础设施的变化。依靠内部布线——使用插值序列。如果代码已经构建,引入工作空间插值依赖性可能需要一些努力。
 

Git 分支

在本节中,我们将探索使用 Git 分支管理多个环境的可能性,并了解为什么它可能不是最佳策略。下图旨在满足本博文介绍中所述的要求。
 


 

开发的两个方面——基础设施和应用程序,分别以绿色和蓝色显示。此处表示的分支策略是将 Terraform 配置用于各种目的的应用。我们将深入探讨 Git 分支的各个部分。
 

Git 的目的

简而言之,Git 旨在协调整个团队的开发工作。它为部署维护各种版本的源代码和包版本。主分支通常包含经过充分测试的功能,适用于任何给定软件的一般用途。
 

执行开发活动或以错误修复、功能或增强的形式引入任何更改——创建主分支的副本,在其上执行修改、重建、部署到子生产环境,并在合并之前进行彻底测试对主要分支的更改。
 

环境的 Git 分支

考虑到这一点,使用 Git 分支来管理多个环境也是可以的,每个环境一个分支是非常理想的。在给定的图表中,infra-dev 团队在三个分支上工作:

  • Main – 用于管理生产基础设施设置。

  • QA – 用于管理 QA 基础设施设置,合格用户在其中执行 UAT 测试。

  • Dev – 用于管理开发基础架构设置,其中首先发布功能并进行单元测试。
     

在高层次上,从主分支分出并创建相同配置的副本以创建 QA 和开发环境是有意义的。
 

存在的问题

然而,当我们将 Terraform 的更深层次视为 IaC 时,我们需要关注一些点:

  • 状态文件管理和关联的远程后端。

  • 缩放转化为环境特定属性方面。

  • 多个帐户的凭据。
     

这里考虑的环境是单独的基础设施部署。这些环境都有自有的状态信息,需要对其进行远程安全管理。远程后端在 terraform 资源块中定义。
 

下面的示例使用 AWS S3 后端。
 

terraform {
  required_providers {
    aws = {
      source = "hashicorp/aws"
      version = "~> 4.18.0"
    }
  }

  backend "s3" {
    bucket = "tf-state-bucket"
    key = "terraform.tfstate"
    region = "eu-central-1"
    dynamodb_table = "tf_state_lock"
  }
}

 

假设这是生产环境使用的配置,即主分支。当我们从主分支分出来时,后端配置也会被复制。所有 Terraform CLI 命令都假定此后端对于所有其他副本(分支)都相同,但这是不可取的,而且可能是非常危险的。事实上,运行任何 Terraform 命令(如 plan、apply、destroy)将引用生产状态文件,甚至对生产执行操作。
 

如果我们手动修改后端配置,为 QA 和开发环境使用不同的后端,那么它就违背了 Git 的初衷。Git 合并会产生冲突,并要求开发人员通过选择后端来解决这些冲突。
 

这个情况也适用于.tfvars 文件中定义的特定于环境的属性值。各种环境的扩展方面是通过变量管理的——更具体地说,是 .tfvars 文件。现代 Git 工作流通常需要在任何分支上进行推送和拉取。在这种方法中可能是不可行的。
 

提供商配置可能包含多个别名以表示多个云提供商帐户和区域中的部署。这也被 Git 的优点所覆盖。
 

CI/CD 流水线

大多数远程 Git 存储库都提供了以 CI/CD 流水线的形式引入自动化的能力。值得注意的是 GitHub Actions 和 Gitlab CI/CD。就源代码版本控制而言,使用远程 Git 存储库并定义处理凭据的自动化流水线是有意义的。在我们的示例中,如果我们在特定分支上进行提交或批准拉取请求,则可以运行特定于分支的管道,该管道使用特定于环境的凭证将更改应用到正确的目标环境。
 

然而,即使这解决了凭据问题,特定于环境的提供程序配置和属性仍然是 Git 工作流程的一部分。这与 Terraform 期望这些配置用于我们想要的更改方式不一致。此外,CI/CD 流水线功能是任何其他 Terraform 工作流都可以利用的功能。所以这不会增加依赖 Git 分支的任何特定优势。
 

应用开发

现代应用程序开发基于微服务、容器和函数。通常,本地开发环境是开发团队遇到的一个问题,具体取决于各种因素。一个简单的例子——当运行一组相互依赖和其他因素的容器时,可能会发现开发机器上可用的资源不够用。
 

使用 Terraform 作为 IaC 确实有助于旋转临时和隔离的环境来为开发人员执行单元测试。还可以从所需的源分支(主分支、QA 分支或开发分支)创建一个临时 Git 分支,并创建一个隔离的缩小环境——如上图中的“Temp2”部署所示。
 

此外,假设任何应用程序功能都依赖于仍在开发中的特定基础结构组件。在这种情况下,应用程序团队可以选择从基础架构开发的“dev”分支分支出来,其中包含预期的更改。它由图中的“Temp1”部署表示。
 

应该注意的是,使用 Git 分支策略管理环境使用了一个总体上的假设,即拥有正确的分支策略。例如,应用程序开发团队创建的分支不能合并到任何基础设施开发团队的分支中。如果 Terraform 有办法知道当前检出哪个分支,那么采用 Git 分支策略会更有意义。在使用 Terraform 工作空间时,工作空间插值序列提供了这个确切的功能。

与如何使用 Terraform 和 Git 分支有效管理多环境?相似的内容:

如何使用 Terraform 和 Git 分支有效管理多环境?

> 作者|Sumeet Ninawe > 翻译|Seal软件 > 链接|https://spacelift.io/blog/terraform-environments 通常我们使用 Terraform 将我们的基础设施定义为代码,然后用 Terraform CLI 在我们选择的云平台中创建制定的基

Terraform 改善基础架构的十个最佳实践

Terraform 是一种非常流行的开源 IaC(基础设施即代码)工具,用于定义和提供完整的基础设施。Terraform 于 2014 年推出,其采用率已在全球范围内快速增长,越来越多的开发人员正在学习 Terraform 并尝试在其组织中部署基础设施。 如果您已经开始使用 Terraform,则必

Azure Terraform(十四)Azure Key Vault 的机密管理

一,引言 最近有网友私信我,将 Terraform 部署到 Azure 是一种将基础结构作为代码进行管理的好方法,但是如何使用 Azure Key Vault 来存储我们的 Secret ?在这篇博文中,我将给大家展示一下展示如何使用 Terraform 引用 Azure Key Vault Sec

Terraform 系列-批量创建资源时如何根据某个字段判断是否创建

这几天碰到一个情况, 使用 Terraform 批量创建日志数据源时, 有的数据源类型是 ElasticSearch, 有些是 Opensearch. 那么, 如何根据某个字段(如:`es_type`)判断是否创建?

终极指南!Terraform的进阶技巧

如果您已经对 Terraform 了如指掌,并期望自己的 IaC 技能有进一步提升的话,这篇文章很适合您!在本文中,我们将分享一些 Terraform 的高级使用技巧。从使用模块(module)、工作区(workspace)到管理远程状态存储、自定义 provider等技巧,帮助您轻松、高效地管理基

如何使用csproj构建C#源代码组件NuGet包?

一般我们构建传统的NuGet包,都是打包和分发dll程序集文件。 至于打包和分发C#源代码文件的做法,比较少见。 那么这种打包源代码文件的做法,有什么优点和缺点呢? 优点: 方便阅读源代码。 方便断点调试。 减少 Assembly 程序集模块加载个数。 更利于发布期间的剪裁(PublishTrimm

如何使用JavaScript实现在线Excel附件的上传与下载?

前言 在本地使用Excel时,经常会有需要在Excel中添加一些附件文件的需求,例如在Excel中附带一些Word,CAD图等等。同样的,类比到Web端,现在很多人用的在线Excel是否也可以像本地一样实现附件文件的操作呢?答案是肯定的,不过和本地不同的是,Web端不会直接打开附件,而是使用超链接单

如何使用前端表格控件实现数据更新?

前言 小编之前分享过一篇文章叫《如何使用前端表格控件实现多数据源整合?》。今天,继续为大家介绍如何使用前端表格控件来更新已连接的数据源信息。 环境准备 SpreadJS在线表格编辑器: SpreadJS 前端表格控件新版本新增了一款报表插件,该插件基于 SpreadJS 本身强大的表格能力,在 Da

如何使用Node.js、TypeScript和Express实现RESTful API服务

Node.js是一个基于 Chrome V8 引擎的 JavaScript 运行环境。Node.js 使用了一个事件驱动、非阻塞式 I/O 的模型,使其轻量又高效。Express是一个保持最小规模的灵活的 Node.js Web应用程序开发框架,为Web和移动应用程序提供一组强大的功能。使用Node

如何使用前端表格控件实现多数据源整合?

前言 作为表格产品的典型应用场景之一,几乎所有的行业都会存在类 Excel 报表开发这样的应用场景,而在这些应用场景中,经常会遇见下面的这些痛点: 报表数据往往来自多个不同的数据源,需要报表系统能够同时连接多个数据源,并融合不同的数据格式 实际的报表中需要对数据结果进行逻辑计算,例如销售的环比和同比