How to save content of a configmap to a file with kubectl and jsonpath?

23,539

Solution 1

There’s an open issue at the Kubernetes GitHub repo with a list of things that needs to be fixed in regards to kubectl (and JSONpath), one of them are issue 16707 jsonpath template output should be json.

Edit:

How about this:

kubectl get cm my-configmap -o jsonpath='{.data.my\.file\.json}'

I just realized i had answered another question related (kind of) to this one. The above command should output what you had in mind!

Solution 2

If you have the ability to use jq, then you can use the following approach to e.g. "list" all config maps by selector, and extract the files:

readarray -d $'\0' -t a < <(kubectl get cm -l grafana=dashboards -o json | jq -cj '.items[] | . as $cm | .data | to_entries[] | [ ($cm.metadata.name + "-" + .key), .value ][]+"\u0000"') ; count=0; while [ $count -lt ${#a[@]} ]; do echo "${a[$((count + 1))]}" > ${a[$count]}; count=$(( $count + 2)); done

This uses kubectl (using -l for a label selector) to get all configmaps. Next it pipes them through jq, creating key value pairs with a null byte termination (the key also contains the name of the configmap, this way I ensured that duplicate file names are not an issue). Then it reads this into a bash array, iterating over the array in steps of 2. Creating files with the content.

This also works file config map values that contain newlines.

Share:
23,539

Related videos on Youtube

PeterH
Author by

PeterH

Software developer in the Netherlands, working mostly with .NET

Updated on July 09, 2022

Comments

  • PeterH
    PeterH almost 2 years

    I'm trying to save the contents of a configmap to a file on my local hard drive. Kubectl supports selecting with JSONPath but I can't find the expression I need to select just the file contents.

    The configmap was created using the command

    kubectl create configmap my-configmap --from-file=my.configmap.json=my.file.json
    

    When I run

    kubectl describe configmap my-configmap
    

    I see the following output:

    Name:         my-configmap 
    Namespace:    default 
    Labels:       <none> 
    Annotations:  <none>
    
    Data
    ==== 
    my.file.json:
    ---- 
    {
        "key": "value" 
    } 
    Events:  <none>
    

    The furthest I've gotten so selecting only the file contents is this:

     kubectl get configmap my-configmap -o jsonpath="{.data}"
    

    Which outputs

    map[my.file.json:{
        "key": "value"
    }]
    

    The output that I want is

    {
      "key": "value"
    }
    

    What is the last piece of the JSONPath puzzle?

  • stackoverflowed
    stackoverflowed about 4 years
    It works, but how would one do if the config map contains more than one key and one wishes to download all the files without knowing the keys in advance?