我正在AWS上开发无服务器数据管道。与Serverless framework相比,Terraform对诸如Glue之类的服务有更好的支持。
Serverless的好处是,您可以在部署时定义--stage
参数。这允许在AWS上创建隔离的堆栈。在数据管道上开发新功能时,我可以部署代码状态,例如
serverless deploy --stage my-new-feature
这使我可以对与同事共享的AWS账户进行隔离集成测试。使用Terraform是否可以?
答案 0 :(得分:2)
答案 1 :(得分:1)
Terraform通过状态管理资源。
如果状态文件中已经存在资源,并且Terraform没有检测到配置,状态和提供程序之间的任何差异(例如,在AWS控制台或其他工具中进行了更改),则它将显示没有变化。如果它确实检测到某种形式的漂移,那么plan
将向您显示需要进行哪些更改才能将提供程序中的现有状态推到Terraform代码中定义的状态。
如果您想要拥有多个环境或什至其他资源,这些资源彼此分开且不由同一Terraform操作管理(例如plan
,apply
或destroy
)那么您要将它们分成不同的状态文件。
执行此操作的一种方法是按环境分隔Terraform代码,并使用与代码库的目录结构匹配的状态文件。一个简单的示例可能看起来像这样:
terraform/
├── production
│ ├── main.tf -> ../stacks/main.tf
│ └── terraform.tfvars
├── stacks
│ └── main.tf
└── staging
├── main.tf -> ../stacks/main.tf
└── terraform.tfvars
variable "environment" {}
resource "aws_lambda_function" "foo" {
function_name = "foo-${var.environment}"
# ...
}
environment = "production"
environment = "staging"
这使用符号链接,以便在terraform.tfvars
文件中引入唯一更改的情况下,使登台和生产保持一致。在这种情况下,它将更改Lambda函数的名称以包括环境。
这通常是我建议在静态环境中使用的内容,因为从查看存在哪些环境的代码/目录结构中可以更清楚地了解到。
但是,如果您具有更多的动态环境(例如每个功能分支),则无法直接在terraform.tfvars
文件中对环境名称进行硬编码。
在这种情况下,我会推荐这样的东西:
terraform/
├── production
│ ├── main.tf -> ../stacks/main.tf
│ └── terraform.tfvars
├── review
│ ├── main.tf -> ../stacks/main.tf
│ └── terraform.tfvars
├── stacks
│ └── main.tf
└── staging
├── main.tf -> ../stacks/main.tf
└── terraform.tfvars
这种方法的工作方式相同,但是我将从environment
结构中省略了review
变量,以便以交互方式或通过CI环境变量(例如,在Travis CI中运行export TF_VAR_environment=${TRAVIS_BRANCH}
进行设置),进行调整以支持您使用的任何CI系统。
这只会使您半途而废,因为当另一个人尝试将其与另一个分支一起使用时,他们将看到Terraform想要销毁/更新通过运行Terraform已经创建的任何资源(如果您只是使用默认的{{ 3}}。
工作区提供了一种以更动态的方式分离状态的选项,并且还允许您workspace:
resource "aws_instance" "example" {
tags {
Name = "web - ${terraform.workspace}"
}
# ... other arguments
}
相反,审阅环境将需要创建或使用仅适用于该分支的动态工作空间。您可以通过运行以下interpolate the workspace name into Terraform code来做到这一点:
terraform workspace new [NAME]
如果工作空间已经存在,则应改用以下command:
terraform workspace select [NAME]
在CI中,您可以使用与以前相同的环境变量来自动将分支名称用作您的工作空间名称。