Skip to content

Secrets Manager

aws sm

Secrets Manager

A SecretStore points to AWS Secrets Manager in a certain account within a defined region. You should define Roles that define fine-grained access to individual secrets and pass them to ESO using spec.provider.aws.role. This way users of the SecretStore can only access the secrets necessary.

apiVersion: external-secrets.io/v1alpha1
kind: SecretStore
metadata:
  name: secretstore-sample
spec:
  provider:
    aws:
      service: SecretsManager
      # define a specific role to limit access
      # to certain secrets.
      # role is a optional field that 
      # can be omitted for test purposes
      role: iam-role
      region: eu-central-1
      auth:
        secretRef:
          accessKeyIDSecretRef:
            name: awssm-secret
            key: access-key
          secretAccessKeySecretRef:
            name: awssm-secret
            key: secret-access-key
NOTE: In case of a ClusterSecretStore, Be sure to provide namespace in accessKeyIDSecretRef and secretAccessKeySecretRef with the namespaces where the secrets reside.

IAM Policy

Create a IAM Policy to pin down access to secrets matching dev-*.

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Action": [
        "secretsmanager:GetResourcePolicy",
        "secretsmanager:GetSecretValue",
        "secretsmanager:DescribeSecret",
        "secretsmanager:ListSecretVersionIds"
      ],
      "Resource": [
        "arn:aws:secretsmanager:us-west-2:111122223333:secret:dev-*",
      ]
    }
  ]
}

JSON Secret Values

SecretsManager supports simple key/value pairs that are stored as json. If you use the API you can store more complex JSON objects. You can access nested values or arrays using gjson syntax:

Consider the following JSON object that is stored in the SecretsManager key my-json-secret:

{
  "name": {"first": "Tom", "last": "Anderson"},
  "friends": [
    {"first": "Dale", "last": "Murphy"},
    {"first": "Roger", "last": "Craig"},
    {"first": "Jane", "last": "Murphy"}
  ]
}

This is an example on how you would look up nested keys in the above json object:

apiVersion: external-secrets.io/v1alpha1
kind: ExternalSecret
metadata:
  name: example
spec:
  refreshInterval: 1m
  secretStoreRef:
    name: secretstore-sample
    kind: SecretStore
  target:
    name: secret-to-be-created
    creationPolicy: Owner
  data:
  - secretKey: firstname
    remoteRef:
      key: my-json-secret
      property: name.first # Tom
  - secretKey: first_friend
    remoteRef:
      key: my-json-secret
      property: friends.1.first # Roger

AWS Authentication

Controller's Pod Identity

Pod Identity Authentication

This is basicially a zero-configuration authentication method that inherits the credentials from the runtime environment using the aws sdk default credential chain.

You can attach a role to the pod using IRSA, kiam or kube2iam. When no other authentication method is configured in the Kind=Secretstore this role is used to make all API calls against AWS Secrets Manager or SSM Parameter Store.

Based on the Pod's identity you can do a sts:assumeRole before fetching the secrets to limit access to certain keys in your provider. This is optional.

apiVersion: external-secrets.io/v1alpha1
kind: SecretStore
metadata:
  name: team-b-store
spec:
  provider:
    aws:
      service: SecretsManager
      region: eu-central-1
      # optional: do a sts:assumeRole before fetching secrets
      role: team-b

Access Key ID & Secret Access Key

SecretRef

You can store Access Key ID & Secret Access Key in a Kind=Secret and reference it from a SecretStore.

apiVersion: external-secrets.io/v1alpha1
kind: SecretStore
metadata:
  name: team-b-store
spec:
  provider:
    aws:
      service: SecretsManager
      region: eu-central-1
      # optional: assume role before fetching secrets
      role: team-b
      auth:
        secretRef:
          accessKeyIDSecretRef:
            name: awssm-secret
            key: access-key
          secretAccessKeySecretRef:
            name: awssm-secret
            key: secret-access-key
NOTE: In case of a ClusterSecretStore, Be sure to provide namespace in accessKeyIDSecretRef, secretAccessKeySecretRef with the namespaces where the secrets reside.

EKS Service Account credentials

Service Account

This feature lets you use short-lived service account tokens to authenticate with AWS. You must have Service Account Volume Projection enabled - it is by default on EKS. See EKS guide on how to set up IAM roles for service accounts.

The big advantage of this approach is that ESO runs without any credentials.

apiVersion: v1
kind: ServiceAccount
metadata:
  annotations:
    eks.amazonaws.com/role-arn: arn:aws:iam::123456789012:role/team-a
  name: my-serviceaccount
  namespace: default

Reference the service account from above in the Secret Store:

apiVersion: external-secrets.io/v1alpha1
kind: SecretStore
metadata:
  name: secretstore-sample
spec:
  provider:
    aws:
      service: SecretsManager
      region: eu-central-1
      auth:
        jwt:
          serviceAccountRef:
            name: my-serviceaccount
NOTE: In case of a ClusterSecretStore, Be sure to provide namespace for serviceAccountRef with the namespace where the service account resides.