Skip to main content
This document explains how to configure Hashicorp Vault as the external secrets store for Astro Private Cloud (APC) data plane failover, which is supported starting in Astro Private Cloud 2.1. Use it after you’ve read Data plane failover and before you complete Enable data plane failover. APC authenticates to Vault with Vault’s Kubernetes auth method: ESO presents its Kubernetes service account token, and Vault validates it and issues a Vault token. AppRole and token auth aren’t supported in Astro Private Cloud 2.1.
This document covers Vault as the ClusterSecretStore or SecretStore backend that the External Secrets Operator (ESO) uses to replicate Airflow secrets between data planes during failover. It’s a different integration from using Vault as an Airflow secrets backend for Airflow variables and connections within a single Deployment. You can use either integration independently, or both together.

Prerequisites

  • A Vault server reachable from every data plane cluster that will use it.
  • Permission to create policies, auth mounts, and roles in Vault.
  • The Vault CLI, or equivalent API access, authenticated with an admin or operator token.
  • kubectl access to each data plane cluster. Depending on your ESO mode, you need permission to create either a cluster-scoped ClusterSecretStore or a namespaced SecretStore. See Which secret store to create.
The manifests and commands here assume the platform is installed in the astronomer namespace. If you installed it into a different namespace, replace astronomer throughout, including bound_service_account_namespaces and the serviceAccountRef.namespace.

Which secret store to create

Vault works behind either an external-secrets.io ClusterSecretStore or a namespaced SecretStore. Which kind you create — a single shared store, a platform-synced store, or one per pool namespace — is determined by your External Secrets Operator mode, not by Vault. See External Secrets Operator security to choose a mode, and the manifests reference for the store manifests. This page covers only the Vault-specific configuration you add to that store.

Grant Vault access for data plane failover

APC currently offers ESO integration with Vault only for data plane failover, not as a standalone mechanism for syncing other secrets. The policy in this document grants read and write access unconditionally:
  • ESO creates ExternalSecret resources on every failover-enabled cluster, which read the replicated secrets from Vault.
  • The deployment orchestrator on the source cluster also creates PushSecret resources, which write the fernet key, environment variables, and database credentials to Vault so the destination cluster can pull them.
Enabling data plane failover (global.dataPlaneFailover.enabled: true) doesn’t enable ESO by itself. ESO installs from its own Helm subchart, gated separately by external-secrets.enabled. See Enable data plane failover.

Step 1: Create a Vault policy

Create a Vault policy that grants read and write access:
This requires capabilities on both the secret/data/* and secret/metadata/* paths. PushSecret uses the metadata path to manage secret versions, so a policy that grants access only to secret/data/* still causes PushSecret writes to fail. Write the policy to Vault:

Step 2: Enable a Kubernetes auth mount for each data plane cluster

Vault’s auth.kubernetes method validates a service account token against one specific Kubernetes API server per auth mount. If more than one data plane cluster authenticates to the same Vault instance, each cluster needs its own auth mount — a single mount can’t validate tokens from more than one cluster.
  1. Enable a dedicated mount for the cluster:
  2. Configure the mount with that cluster’s API server details:
    Retrieve kubernetes_host from the cluster’s API server endpoint, and retrieve kubernetes_ca_cert and token_reviewer_jwt from a service account token that Vault uses to validate other tokens. See Vault’s Kubernetes auth method documentation for how to generate the reviewer JWT for your Kubernetes version.
Repeat this step for every data plane cluster that authenticates to this Vault instance, substituting a unique -path value each time.

Step 3: Create a Vault role

Create a role that binds the policy from Step 1 to the auth mount from Step 2, scoped to the service account ESO runs as:
<eso-service-account> is the Kubernetes service account that the ESO Pod runs as on this data plane cluster. If you installed ESO through the APC Helm chart’s bundled subchart (external-secrets.enabled: true), this is the release’s ESO service account in the astronomer namespace.
If the cluster uses External Secrets Operator security Mode 3 (customer-managed isolated identity), map the per-namespace service account here instead of the shared ESO service account, so each Deployment authenticates to Vault as its own identity.

Step 4: Add the Vault provider to your secret store

Reference the auth mount and role you created from the spec.provider.vault block of your ESO secret store. The example below is a ClusterSecretStore (the shared-identity form). For a namespaced SecretStore — the platform-synced store in Mode 2 or a per-pool-namespace store in Mode 3 — use the identical spec.provider.vault block in the SecretStore shape shown in the manifests reference.
Use the same value for metadata.name on every data plane cluster that shares this Vault instance — this is the value you provide for global.dataPlaneFailover.externalSecretManagerName in your Helm values. Use the same path on every cluster as well, since it identifies the Vault secrets engine that holds the replicated secrets, and the destination cluster reads from the same location the source cluster writes to. The auth.kubernetes.mountPath and auth.kubernetes.role values differ per cluster.

Network requirements

If your data plane clusters run in separate networks, Vault must be reachable from each of them over the network, not just from its own cluster’s in-cluster DNS.
  • Expose Vault through a network load balancer reachable from every data plane cluster that needs it.
  • Open firewall or security group rules that allow traffic from each data plane cluster’s CIDR range to the Vault endpoint.
  • Confirm connectivity from each cluster before you rely on the configuration — see the verification steps in the following section.

Verify the configuration

Before applying Helm values that depend on this ClusterSecretStore or SecretStore, confirm the setup works end to end.
  1. Write a test secret to Vault:
  2. Create a test ExternalSecret in the data plane cluster’s astronomer namespace that references the store and reads the test secret. This example uses a ClusterSecretStore; on a namespace-pools cluster, set secretStoreRef.kind to SecretStore instead.
  3. Confirm it syncs:
    The STATUS column should show SecretSynced. If it doesn’t, check the ESO Pod logs for authentication or permission errors before continuing.
Repeat this test from each data plane cluster that shares the Vault instance, since each cluster authenticates through its own auth mount. After you enable data plane failover (dataPlaneFailover.enabled: true), also complete the PushSecret and connection-secret checks in Verify secret replication before a failover. Those checks confirm write access, which the preceding ExternalSecret test doesn’t cover.

Troubleshooting

  • PushSecret reports a failure, or Airflow secrets don’t appear on the destination cluster after a failover: The Vault policy likely grants read-only access on a cluster where dataPlaneFailover.enabled is true. Update the policy to include create and update on both secret/data/* and secret/metadata/*, then retry.
  • ExternalSecret or PushSecret fails to authenticate from one data plane cluster but succeeds from another: Confirm the failing cluster has its own Kubernetes auth mount and that the mount’s kubernetes_host and reviewer JWT match that cluster, not another cluster’s.
  • A cluster in a different network can’t reach Vault: Confirm Vault is exposed beyond in-cluster DNS for that network, and that firewall or security group rules allow traffic from the cluster’s CIDR range. See Network requirements.