I'm trying to use a ytt overlay to replace the objectName in my secret class following this gist example replacing only part of a multi-line string, but it ends up appending a new item instead of replacing the existing one. How can I get it to work for this case?
Input Files
db_secret.yaml
kind: SecretProviderClass
metadata:
namespace: default
name: db_credentials
spec:
provider: aws
parameters:
objects: |
- objectName: TO_BE_REPLACED_BY_YTT
objectType: "secretsmanager"
jmesPath:
- path: username
objectAlias: dbusername
- path: password
objectAlias: dbpassword
overlay.yaml
#@ load("@ytt:overlay", "overlay")
#@ load("@ytt:yaml", "yaml")
#@ load("@ytt:data", "data")
#@ def updates():
- objectName: #@ data.values.db_secret_name
#@ end
#@overlay/match by=overlay.subset({"kind": "SecretProviderClass", "metadata": {"name": "db_credentials"}})
---
spec:
provider: aws
parameters:
#@overlay/replace via=lambda a,_: yaml.encode(overlay.apply(yaml.decode(a), updates()))
objects:
values-staging.yaml
db_secret_name: db-secret-staging
ytt output:
apiVersion: secrets-store.csi.x-k8s.io/v1alpha1
kind: SecretProviderClass
metadata:
namespace: default
name: db_credentials
spec:
provider: aws
parameters:
objects: |
- objectName: TO_BE_REPLACED_BY_YTT
objectType: secretsmanager
jmesPath:
- path: username
objectAlias: dbusername
- path: password
objectAlias: dbpassword
- objectName: db-secret-staging
It's key to notice that the YAML value being overlayed is itself an array. It's an array of one item, but an array nonetheless.
In order to reach the map that has the
objectNamemap item, you need to first match its parent: that containing array item.The most durable way to do that is by selecting for the array item that has a map that contains the
objectNamekey. You can say that like this:can be read: "in the array value being overlay'ed (aka 'left'), find the array item whose value has a map whose keys include the string "objectName"... merge the value of this array item (i.e. the map in the array item within this overlay) into that matched map."
(Playground: https://carvel.dev/ytt/#gist:https://gist.github.com/pivotaljohn/9593f971ac5962055ff38c5eeaf1df11)
When working with overlays, it can be helpful to visualize the tree of values. There are some nice examples in the docs: https://carvel.dev/ytt/docs/v0.40.0/yaml-primer/
Also, there was a recent-ish vlog post that has been reported to help folks level up using
yttoverlays: https://carvel.dev/blog/primer-on-ytt-overlays/