<p>I have this helm template for <code>secret</code> object:</p>

<pre><code>...
data:
{{- range $key, $val := fromYaml .Values.secretmap }}
  {{- $type := printf "%T" $val }}
  {{ $key }}: {{ if eq $type "float64"}}{{ printf "%.0f" $val | b64enc | quote }}{{ else }}{{ $val | b64enc | quote }}{{ end }}
{{- end }}
kind: Secret
...
</code></pre>

<p>And I load it as follows:</p>

<pre><code>helm template --set-file secretmap="secretmap.yaml"
</code></pre>

<p>I create the <code>secretmap.yaml</code> from env var like so:</p>

<pre><code>env | sed -n "s/^K8S_SECRET_\(.*\)$/\1/p" | sed s/=/': '/ \ &gt;secretmap.yaml
</code></pre>

<p>The problem is with multiline values.<br>
When I set a multi-line <code>pem</code> key as env var, only the first line inserted to the <code>secretmap.yaml</code>.</p>

<p>How can I load multi-line env var correctly to a <code>yaml</code> so helm could create a <code>secret</code> of it?</p>

natdev
<p>I'd reach for a more powerful tool than a shell script to write out the <code>secretmap.yaml</code> file.</p>

<p>The Helm template itself looks fine.  Assuming the content is valid YAML, it will echo it out, base64 encoding each value.  You'd be happier if every node in the YAML were a string so you didn't have to reinterpret it based on a dynamic type lookup.</p>

<p>So the actual problem is generating the YAML file.  You can take advantage of the fact that (a) YAML tries hard to make all valid JSON be valid YAML, and (b) almost every programming language includes JSON support in its standard library.  (Or you can use Helm's <code>fromJson</code> function too.)  Here's a minimal Python script that could write it out for you, in place of your <code>sed</code> command:</p>

<pre class="lang-py prettyprint-override"><code>#!/usr/bin/env python3
import json
import os

PREFIX = 'K8S_SECRET_'
result = {}
for k in os.environ.keys():
    if k.startswith(PREFIX):
        kk = k[len(PREFIX):]
        v = os.environ[k]
        result[kk] = v
print(json.dumps(result))
</code></pre>

<p>Or, a denser one-liner based on <a href="https://stedolan.github.io/jq/" rel="nofollow noreferrer">jq</a></p>

<pre class="lang-sh prettyprint-override"><code>jq -n 'env | with_entries(select(.key | startswith("K8S_SECRET_")) | .key |= ltrimstr("K8S_SECRET_"))'
</code></pre>

<p>If the environment variables have newlines embedded in them, it's almost impossible to process this reliably with basic shell tools.  As a minimal example try (bash/zsh specific syntax)</p>

<pre><code>K8S_SECRET_FOO=$'bar\nK8S_SECRET_BAZ=quux' env
</code></pre>

<p>You want just one variable, but with the embedded newline, <code>env</code> will print this in a way indistinguishable from two separate variables.</p>
