How it Works
Learn about the inner workings of akv2k8s.
Akv2k8s consist of three main components:
- a Custom Resource Definition called 
AzureKeyVaultSecret - Controller
 - Env Injector
 
The AzureKeyVaultSecret CRD
The AzureKeyVaultSecret Custom Resource Definition (CRD) contains metadata used by the Controller and Env Injector to access objects in Azure Key Vault. For each secret, certificate or key in AzureKeyVault that you want available in Kubernetes, you create a AzureKeyVaultSecret and provide:
- The Kubernetes namespace where the Azure Key Vault secret should be available
 - The name of the Azure Key Vault
 - The name, type and version (optional) of the Azure Key Vault object
 - Optionally a Kubernetes 
SecretorConfigMapand data-key to sync to 
An example AzureKeyVaultSecret looks like this:
# secret-sync.yaml
apiVersion: spv.no/v2beta1
kind: AzureKeyVaultSecret
metadata:
  name: secret-sync 
  namespace: akv-test
spec:
  vault:
    name: akv2k8s-test # name of key vault
    object:
      name: my-secret # name of the akv object
      type: secret # akv object type
  output: # optional - only used to sync to a kubernetes secret
    secret: 
      name: my-secret-from-akv # kubernetes secret name
      dataKey: secret-value # key to store object value in kubernetes secretThe Controller
The Controller is responsible for:
- syncing Azure Key Vault objects into Kubernetes 
Secret's orConfigMaps, where theAzureKeyVaultSecrethasspec.output.secretorspec.output.configMapdefined (like in the example above) - periodically poll Azure Key Vault for changes and apply to the Kubernetes 
SecretorConfigMap 
The Env Injector
The Env Injector is a bit more complicated than the Controller and consists of:
- a Mutating Admission Webhook (see Kubernetes docs)
 - a Docker image (spvest/azure-keyvault-env) containing the 
azure-keyvault-envexecutable 
Below are the steps that gets executed for a Pod using env-injection.
- 1
The Mutating Admission Webhook triggers
The Env Injector webhook gets triggered just before every Pod gets created and inspects the Pod definition for environment variables containing
@azurekeyvault(see example below). If it does not find any, the Pod start as normal. If it does, it mutates (changes) the Pod with:- A init-container (image: spvest/azure-keyvault-env) with a in-memory volume at 
/azure-keyvault/ - Akv2k8s own executable instead of the original executable in the Pod (more on that later)
 - Multiple environment variables with akv2k8s specific information
 - A client certificate is generated for the Pod to use when requesting Azure Key Vault credentials
 
Example where environment variable has value containing
@azurekeyvault:env: - name: MY_AKV_SECRET value: some-secret@azurekeyvaultAs mentioned, the Pod container gets mutated to use a different executable. It does this by changing either the CMD or the ENTRYPOINT, depending on which was used by the original container, to use the
azure-keyvault-envexecutable instead. The "old" command gets passed in as parameter to this new executable. - A init-container (image: spvest/azure-keyvault-env) with a in-memory volume at 
 - 2
The Pod starts the init-container
When the Env Injector webhook is finished, Kubernetes will start the Pod with the mutated changes. This will trigger the following sequence:
- The init-container will start
 - The init-container copies the 
azure-keyvault-envexecutable into/azure-keyvault/ 
The volume
/azure-keyvault/in the Pod is shared between its containers (the init-container and the original container) and is how the init-container can "give" the original container its executable. - 3
The Pod starts the original container
When the original container starts, it will execute the
azure-keyvault-envcommand, which will:- Get Azure Key Vault credentials from the Env-Injector auth service (using client certificate from earlier) or from local environment (depending how auth is configured - see Authentication for details)
 - Connect to Azure Key Vault, using credentials from previous step
 - Download all Azure Key Vault objects, identified by the environment placeholders
 - Execute the original command and params, pass on the updated environment variables with real secret values
 
 ✨The end result is secrets injected transparently in-memory during container startup. It will not reveal any of the actual secrets in the container spec, disk or logs. The only component containing the actual secrets is the application process.✨