Terraform破坏GitHub团队,而不是为新成员更新



我有一个地形脚本来管理我的GitHub团队成员。如果:

  1. 现有团队成员角色变更
  2. 创建团队时正在添加新用户

脚本让我困惑的地方是当一个团队退出时,它包含用户,并且正在添加一个新用户。而不是将新用户添加到团队中,从而实现我所期望的就地更新操作,而是执行destroy + replace操作。Terraform将删除原来的团队[由我和我在脚本第一次运行时添加的用户组成,当这个团队也是第一次创建时]创建一个新的团队,并用这个新的第三个用户替换第二个用户[第一个用户是我,默认情况下我添加的我的凭据是用来创建团队的]。

具体示例:目前我没有团队,但我想将用户A添加到test_team_1。我填写这些需求并运行地形计划。Terraform让我知道将创建一个名为test_team_1的团队,并将用户a添加到其中。在Terraform应用程序上,我在GitHub上看到一个名为test_team_1的新团队,该团队有2名成员,我和用户a。

现在我被要求将用户B添加到同一个团队。当我运行terraform plan时,我被告知不是更新团队以包含更多的用户,而是删除test_team_1。Terraform进一步告诉我,发生这种情况是因为用户B与用户a拥有不同的用户名,这将强制执行替换操作。如果我现在运行terraform apply,原始的test_team_1将被删除,创建一个新的test_team_1,现在它有两个成员me和新用户b。

我需要确保terraform可以添加更多的用户,而不必删除团队,只有我,创建者和新用户作为成员。

代码示例:

子模块:

module Test_Child_Module {
source = "./modules/GitHubAccessRequest"
owner = var.owner
team_name = ["test_team_1", "test_team_2"]
username = "user-a"
role = "member"
}

父模块代码

resource "github_team" "team" {
for_each = toset(var.team_name)
name = each.key
}
resource "github_team_membership" "some_team_membership" {
for_each = toset(var.team_name)
team_id  = github_team.team[each.key].id
username = var.username
role     = var.role
}

对于给定的用户和团队列表,该用户将被添加到特定角色的团队中,如果团队不存在,则将创建团队。

我不确定我完全理解这段代码是如何应用的,但如果是这种情况,当你来添加user-b时,你只需修改模块定义中的username参数,那么行为确实是有意义的。

Terraform的工作原理是,它将在其生命周期内管理每个资源。因此,您不能编写仅描述增量更改的代码,它必须描述基础结构的整个状态。每次运行Terraform时,它都会将代码所描述的整个状态与实际的整个状态进行比较,然后应用任何差异。

当我正在阅读你的代码时,你每个团队只有一个github_team_membership资源,你有时将username设置为user-a,有时设置为user-b。Terraform会解释这是一个单独的github_team_membership。我认为实际上每个用户,每个团队都需要一个。更具体地说,如果你有两个团队,每个团队有两名成员,那么你的代码需要描述4个github_team_membership资源。如果你有10个,那么你需要20个github_team_membership资源。每个github_team_membership资源描述了特定用户的单个成员资格。

如果您正在使用Terraform的最新版本(因此可以循环模块),这可能是一个更好的方法,其中代码遍历每个团队,调用一个模块,然后遍历应该是该团队成员的每个团队成员:

(免责声明:未经测试,但希望能给你一个想法)

main.tf

variable "owner" {}
variable "default_users" {
type = list(map(string))
default = [ 
{ name = "user-a", role = "member" },
{ name = "user-b", role = "member" }
]
}
variable "teams" {
type = map()
default = {
test_team_1 = {},
test_team_2 = {
users = [ { name = "user-a", role = "member" },
{ name = "user-c", role = "some_other_role" } 
]
}
}
}
module "github_team" {
source = "./modules/GitHubTeam"  
for_each = var.teams

owner = var.owner
team_name = each.key
users = lookup(each.value, "users", var.default_users)
}

注意:lookup()函数将检查映射中指定的键,如果它不存在,则返回第三个参数。因此,在test_team_1的情况下使用这种技术,将返回var.default_users,而在test_team_2的情况下,将使用自定义提供的用户列表。

。/模块/GitHubTeam main.tf

variable "owner" {}
variable "team_name" {}
variable "users" {
type = list(map(string))
}

resource "github_team" "team" {
name = var.team_name
}
# Create one team membership per user passed in the users list
resource "github_team_membership" "team_membership" {
for_each = toset(var.users)
team_id  = github_team.team.id
username = each.value["name"]
role     = each.value["role"]
}

如果我完全误解了,我道歉,这是没有用的。

最新更新