kubernetesmatomokubernetes-secrets

Keep formating of data in kubernetes secret


I am deploying Matomo to Kubernetes. I have a config file that contains database credentials. I would like to create a secret from the config file and mount it to the pod.

I can´t figure out a way to define the secret manifest and keep the formatting of the config.

If I don´t keep the formatting the Matomo server complains that it has a syntax error in the config file.

Example of the secret manifest I am working with:

apiVersion: v1
kind: Secret
metadata:
  name: matomo-config
  labels:
    app: matomo
type: Opaque
data:
  config:
    [database]
    host = "matomodb.com"
    username = "${supersecret_secret}"
    password = "${supersecret_secret}"

    [Plugins]
    Plugins[] = "CorePluginsAdmin"
    Plugins[] = "CoreAdminHome"
    Plugins[] = "CoreHome"
    Plugins[] = "WebsiteMeasurable"
    Plugins[] = "Diagnostics"
    Plugins[] = "CoreVisualizations"
    Plugins[] = "Proxy"
    Plugins[] = "API"
    Plugins[] = "Widgetize"
    Plugins[] = "Transitions"
    Plugins[] = "LanguagesManager"
    Plugins[] = "Actions"
    Plugins[] = "Dashboard"
    Plugins[] = "MultiSites"
    Plugins[] = "Referrers"

What I tried

I tried to use quotes (single and double), I tried with data or stringData but I always get just long string after mounting.

The only way to keep the formating I found so far was to use:

kubectl create secret generic matomo-config --from-file=config=config.ini.php

but that doesn´t play that well in my pipeline.


Solution

  • YAML has a specific format for a multi-line string, a block scalar. On the line that declares the key, end the line with a pipe |. The following indented lines will be read as a single multi-line string, keeping newlines, and stripping a consistent amount of leading space.

    stringData:
      #       v  add this pipe
      config: |
        [database]
        host = "matomodb.com"
        ...
    

    For a Secret in particular, data: is required to be base64 encoded. That allows arbitrary binary data, which means you could include newlines inside the data as well. For the volume of data you have, you'll still probably want to break the base64 block across multiple lines, which will work the same way.

    data:
      config: |
        W2RhdGFiYXNlXQpob3N0ID0gIm1hdG9tb2RiLmNvbSIK
        ...
    

    In my first example I used plain text in combination with stringData:. Kubernetes will do the base64 encoding for you here, but it won't match what you get back from kubectl get secret -o yaml.