Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Kubernetes label validation is invalid #206

Closed
alkar opened this issue Nov 1, 2018 · 11 comments
Closed

Kubernetes label validation is invalid #206

alkar opened this issue Nov 1, 2018 · 11 comments

Comments

@alkar
Copy link

alkar commented Nov 1, 2018

Terraform Version

terraform -v
Terraform v0.11.8
+ provider.kubernetes v1.3.0

Your version of Terraform is out of date! The latest version
is 0.11.10. You can update by downloading from www.terraform.io/downloads.html

Affected Resource(s)

I noticed this with kubernetes_namespace but it might affect others too?

Terraform Configuration Files

resource "kubernetes_namespace" "foobar" {
  metadata {
    labels {
      name  = "foo/bar"
      value = ""
    }

    name = "foobar"
  }
}

Actual Behavior

In the above example terraform does not accept the label:

$ terraform init

Initializing provider plugins...
- Checking for available provider plugins on https://releases.hashicorp.com...
- Downloading plugin for provider "kubernetes" (1.3.0)...

The following providers do not have any version constraints in configuration,
so the latest version was installed.

To prevent automatic upgrades to new major versions that may contain breaking
changes, it is recommended to add version = "..." constraints to the
corresponding provider blocks in configuration, with the constraint strings
suggested below.

* provider.kubernetes: version = "~> 1.3"

Terraform has been successfully initialized!

You may now begin working with Terraform. Try running "terraform plan" to see
any changes that are required for your infrastructure. All Terraform commands
should now work.

If you ever set or change modules or backend configuration for Terraform,
rerun this command to reinitialize your working directory. If you forget, other
commands will detect it and remind you to do so if necessary.
$ terraform plan

Error: kubernetes_namespace.foobar: metadata.0.labels ("foo/bar") a valid label must be an empty string or consist of alphanumeric characters, '-', '_' or '.', and must start and end with an alphanumeric character (e.g. 'MyValue',  or 'my_value',  or '12345', regex used for validation is '(([A-Za-z0-9][-A-Za-z0-9_.]*)?[A-Za-z0-9])?')

Expected Behavior

It should apply cleanly.

The documentation states:

Valid label keys have two segments: an optional prefix and name, separated by a slash [...]

$ cat foo.yaml
apiVersion: v1
kind: Namespace
metadata:
  name: foobar
  labels:
    foo/bar: ""
$ kubectl apply -f foo.yaml
namespace/foobar created
$ kubectl describe ns foobar
Name:         foobar
Labels:       foo/bar=
Annotations:  kubectl.kubernetes.io/last-applied-configuration={"apiVersion":"v1","kind":"Namespace","metadata":{"annotations":{},"labels":{"foo/bar":""},"name":"foobar","namespace":""}}

Status:  Active

No resource quota.

No resource limits.

Steps to Reproduce

See above.

@ctranstrum
Copy link

ctranstrum commented Dec 27, 2018

Try this:

resource "kubernetes_namespace" "foobar" {
  metadata {
    labels {
      "foo/bar" = ""
    }

    name = "foobar"
  }
}

@rmacian
Copy link
Contributor

rmacian commented Mar 19, 2019

@ctranstrum at first I thought your solution worked , because indeed works for the first time , but in the next apply is not able to process the '/' from the state and does not read the label correctly and at the end you have a perpetual diff.

'terraform show' does not display the label but I can see it with the kubetcl

@primeroz
Copy link

I am having the same issue . Terraform is applying the labels but at every run it sets them again

for example:

  ~ kubernetes_cluster_role.argocd-application-controller                                                                                      
      metadata.0.labels.%:                                        "0" => "3"                                                                
      metadata.0.labels.app.kubernetes.io/component:              "" => "application-controller"      
      metadata.0.labels.app.kubernetes.io/name:                   "" => "argocd-application-controller"                                   
      metadata.0.labels.app.kubernetes.io/part-of:                "" => "argocd"  

I can see that those labels where indeed set on the resource.

Is there a correct way to apply this kind of "complex" labels through the terraform kubernetes provider ?

@mascah
Copy link

mascah commented Apr 26, 2019

I'm also having this issue. I'm stuck with a perpetual diff when trying to use labels that have keys that are quoted and have a / in them. The labels are definitely applied, but they're not detected on subsequent apply operations.

@jwm
Copy link

jwm commented Apr 27, 2019

Looks like this is caused by this fix for this previous bug, from when Terraform didn't allow label names to contain /. The solution was to filter out "internal" k8s labels that were being automatically applied.

Now that we're using the upstream k8s libraries to validate label names and can set labels with names containing /, we should revert the previous bugfix/workaround.

@seboudry
Copy link

So is there a workaround?

@playermanny2
Copy link

playermanny2 commented May 30, 2019

bump having the same issues with kubernetes_service_account

@sepulworld
Copy link

Having same issue with kubernetes_config_map

@pdecat
Copy link
Contributor

pdecat commented Jun 19, 2019

The issue reported by the OP does not happen with recent versions.

For example, this works fine:

provider kubernetes {
  version = "1.7.0"
}

terraform {
  required_version = "0.12.2"
}

resource "kubernetes_namespace" "foobar" {
  metadata {
    labels = {
      "foo/bar" = ""
    }

    name = "foobar"
  }
}
# terraform init && terraform apply -auto-approve

Initializing the backend...

Initializing provider plugins...

Terraform has been successfully initialized!

You may now begin working with Terraform. Try running "terraform plan" to see
any changes that are required for your infrastructure. All Terraform commands
should now work.

If you ever set or change modules or backend configuration for Terraform,
rerun this command to reinitialize your working directory. If you forget, other
commands will detect it and remind you to do so if necessary.
kubernetes_namespace.foobar: Creating...
kubernetes_namespace.foobar: Creation complete after 0s [id=foobar]

Apply complete! Resources: 1 added, 0 changed, 0 destroyed.
# terraform plan
Refreshing Terraform state in-memory prior to plan...
The refreshed state will be used to calculate this plan, but will not be
persisted to local or remote state storage.

kubernetes_namespace.foobar: Refreshing state... [id=foobar]

------------------------------------------------------------------------

No changes. Infrastructure is up-to-date.

This means that Terraform did not detect any differences between your
configuration and real physical resources that exist. As a result, no
actions need to be performed.
# kubectl get namespaces foobar -o yaml
apiVersion: v1
kind: Namespace
metadata:
  creationTimestamp: "2019-06-19T11:16:55Z"
  labels:
    foo/bar: ""
  name: foobar
  resourceVersion: "39691"
  selfLink: /api/v1/namespaces/foobar
  uid: beff1b0f-9283-11e9-9dcb-e851f8def6f3
spec:
  finalizers:
  - kubernetes
status:
  phase: Active
# terraform state show kubernetes_namespace.foobar
# kubernetes_namespace.foobar: 
resource "kubernetes_namespace" "foobar" {
    id = "foobar"

    metadata {
        generation       = 0
        labels           = {
            "foo/bar" = ""
        }
        name             = "foobar"
        resource_version = "39691"
        self_link        = "/api/v1/namespaces/foobar"
        uid              = "beff1b0f-9283-11e9-9dcb-e851f8def6f3"
    }
}

@alexsomesan
Copy link
Member

I can confirm what @pdecat has demonstrated above. I am also not able to reproduce this issue anymore. It works correctly using these versions:

Terraform v0.12.2
+ provider.kubernetes v1.7.0

Here's the configuration I used:

terraform {
  required_version = "0.12.2"
}

resource "kubernetes_config_map" "foobar" {
  metadata {
    labels = {
      "foo/bar" = "some-data"
    }
    name = "foobar"
  }
}

@alexsomesan
Copy link
Member

I'm going to close this issue.
If anyone has configurations that can still reproduce the error, please reopen this and post your configuration.

@ghost ghost locked and limited conversation to collaborators Apr 21, 2020
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests