67 lines
1.8 KiB
Terraform
67 lines
1.8 KiB
Terraform
|
|
variable "users" {
|
||
|
|
description = "List of userpass usernames to create."
|
||
|
|
type = list(string)
|
||
|
|
default = ["ms2k"]
|
||
|
|
}
|
||
|
|
|
||
|
|
variable "admin_user" {
|
||
|
|
description = "Username from var.users to grant the admin policy. Used to establish non-root administrative access before revoking the initial root token."
|
||
|
|
type = string
|
||
|
|
default = "ms2k"
|
||
|
|
|
||
|
|
validation {
|
||
|
|
condition = contains(var.users, var.admin_user)
|
||
|
|
error_message = "admin_user must be present in var.users."
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
# Auth method
|
||
|
|
resource "vault_auth_backend" "userpass" {
|
||
|
|
type = "userpass"
|
||
|
|
}
|
||
|
|
|
||
|
|
# Admin policy
|
||
|
|
resource "vault_policy" "admin" {
|
||
|
|
name = "admin"
|
||
|
|
|
||
|
|
policy = <<-EOT
|
||
|
|
path "*" {
|
||
|
|
capabilities = ["create", "read", "update", "delete", "list", "sudo", "patch", "subscribe"]
|
||
|
|
subscribe_event_types = ["*"]
|
||
|
|
}
|
||
|
|
EOT
|
||
|
|
}
|
||
|
|
|
||
|
|
# Users
|
||
|
|
resource "random_password" "user" {
|
||
|
|
for_each = toset(var.users)
|
||
|
|
length = 32
|
||
|
|
special = false # alphanumeric only — avoids quoting issues when pasting into CLI
|
||
|
|
}
|
||
|
|
|
||
|
|
resource "vault_generic_endpoint" "user" {
|
||
|
|
for_each = toset(var.users)
|
||
|
|
|
||
|
|
path = "auth/${vault_auth_backend.userpass.path}/users/${each.key}"
|
||
|
|
ignore_absent_fields = true
|
||
|
|
|
||
|
|
# Terraform sets the initial password and policies on creation only.
|
||
|
|
# Vault is the source of truth after that — re-runs won't reset passwords.
|
||
|
|
lifecycle {
|
||
|
|
ignore_changes = [data_json]
|
||
|
|
}
|
||
|
|
|
||
|
|
data_json = jsonencode({
|
||
|
|
password = random_password.user[each.key].result
|
||
|
|
policies = each.key == var.admin_user ? "admin" : ""
|
||
|
|
})
|
||
|
|
}
|
||
|
|
|
||
|
|
# Outputs
|
||
|
|
output "user_passwords" {
|
||
|
|
description = "Generated passwords keyed by username. Sensitive — retrieve with: tofu output -json user_passwords"
|
||
|
|
sensitive = true
|
||
|
|
value = {
|
||
|
|
for u in var.users : u => random_password.user[u].result
|
||
|
|
}
|
||
|
|
}
|