Skip to content

Projected volume gets replaced on every apply #1358

@rymnc

Description

@rymnc

Terraform Version, Provider Version and Kubernetes Version

Terraform version: v1.0.0
Kubernetes provider version: v2.3.2
Kubernetes version: 1.20.8-gke.900

Affected Resource(s)

  • kubernetes_deployment

Terraform Configuration Files

# If the deployment does require zzz and has secrets of its own
dynamic "volume" {
  for_each = local.secret_length_gt_0 && var.inject_db_url ? [1] : []
  content {
    name = "${var.service_name}-secrets"
    projected {
      sources {
        secret {
          name     = "${var.service_name}-secrets"
          optional = false
        }
        secret {
          name     = "zzz-secrets"
          optional = false
        }
     }
    }
  }
}
# If the deployment does not require zzz and has secrets of its own
dynamic "volume" {
  for_each = local.secret_length_gt_0 && !var.inject_db_url ? [1] : []
  content {
    name = "${var.service_name}-secrets"
    secret {
      secret_name = "${var.service_name}-secrets"
    }
  }
}
# If the deployment requires zzz but doesn't have any secrets of its own
dynamic "volume" {
  for_each = !local.secret_length_gt_0 && var.inject_db_url ? [1] : []
  content {
    name = "${var.service_name}-secrets"
    secret {
      secret_name = "zzz-secrets"
    }
  }
}

Assume the following inputs -

var.inject_db_url = true
local.secret_length_gt_0 = true
var.service_name = foobar

Steps to Reproduce

  1. terraform apply --> creates the deployment with the volume
  2. terraform apply --> the volume must be replaced

Expected Behavior

It should apply the second time without any changes

Actual Behavior

The second secret in volume.projected.sources is always replaced. Example -

volume {
                        name = "service-secrets"

                      ~ projected {
                            # (1 unchanged attribute hidden)

                          ~ sources {

                              + secret {
                                  + name     = "zzz-secrets"
                                  + optional = false
                                }
                                # (1 unchanged block hidden)
                            }
                          - sources {

                              - secret {
                                  - name     = "zzz-secrets" -> null
                                  - optional = false -> null
                                }
                            }
                        }
                    }

The state for the service above ->

volume {
                    name = "service-secrets"

                    projected {
                        default_mode = "0644"

                        sources {

                            secret {
                                name     = "service-secrets"
                                optional = false
                            }
                        }
                        sources {

                            secret {
                                name     = "zzz-secrets"
                                optional = false
                            }
                        }
                    }
                }

Is it intended to store them in different sources?

Important Factoids

The volume setup is made so that only if the service requires the zzz secret, it is mounted as a projected volume with the existing secrets (if any). Only one of these volumes must be mounted.

The issue only arises with the projected volume

Community Note

  • Please vote on this issue by adding a 👍 reaction to the original issue to help the community and maintainers prioritize this request
  • If you are interested in working on this issue or have submitted a pull request, please leave a comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    acknowledgedIssue has undergone initial review and is in our work queue.bug

    Type

    No type

    Projects

    No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions