Revise downward API documentation

- add a glossary entry
- add a concept page
- revise other documentation in light of above changes
pull/32400/head
Tim Bannister 2022-03-21 22:29:53 +00:00
parent 6a89b98cc0
commit 7f3604a949
No known key found for this signature in database
GPG Key ID: 1E76582C4F66FA48
5 changed files with 255 additions and 150 deletions
content/en/docs

View File

@ -295,15 +295,17 @@ keyed with `log_level`.
### downwardAPI {#downwardapi}
A `downwardAPI` volume makes downward API data available to applications.
It mounts a directory and writes the requested data in plain text files.
A `downwardAPI` volume makes {{< glossary_tooltip term_id="downward-api" text="downward API" >}}
data available to applications. Within the volume, you can find the exposed
data as read-only files in plain text format.
{{< note >}}
A container using the downward API as a [`subPath`](#using-subpath) volume mount will not
receive downward API updates.
A container using the downward API as a [`subPath`](#using-subpath) volume mount does not
receive updates when field values change.
{{< /note >}}
See the [downward API example](/docs/tasks/inject-data-application/downward-api-volume-expose-pod-information/) for more details.
See [Expose Pod Information to Containers Through Files](/docs/tasks/inject-data-application/downward-api-volume-expose-pod-information/)
to learn more.
### emptyDir {#emptydir}

View File

@ -0,0 +1,131 @@
---
title: Downward API
content_type: concept
description: >
There are two ways to expose Pod and container fields to a running container:
environment variables, and as files that are populated by a special volume type.
Together, these two ways of exposing Pod and container fields are called the downward API.
---
<!-- overview -->
It is sometimes useful for a container to have information about itself, without
being overly coupled to Kubernetes. The _downward API_ allows containers to consume
information about themselves or the cluster without using the Kubernetes client
or API server.
An example is an existing application that assumes a particular well-known
environment variable holds a unique identifier. One possibility is to wrap the
application, but that is tedious and error prone, and it violates the goal of low
coupling. A better option would be to use the Pod's name as an identifier, and
inject the Pod's name into the well-known environment variable.
In Kubernetes, there are two ways to expose Pod and container fields to a running container:
* as [environment variables](/docs/tasks/inject-data-application/environment-variable-expose-pod-information/#the-downward-api)
* as [files in a `downwardAPI` volume](/docs/tasks/inject-data-application/downward-api-volume-expose-pod-information/)
Together, these two ways of exposing Pod and container fields are called the
_downward API_.
<!-- body -->
## Available fields
Only some Kubernetes API fields are available through the downward API. This
section lists which fields you can make available.
You can pass information from available Pod-level fields using `fieldRef`.
At the API level, the `spec` for a Pod always defines at least one
[Container](/docs/reference/kubernetes-api/workload-resources/pod-v1/#Container).
You can pass information from available Container-level fields using
`resourceFieldRef`.
### Information available via `fieldRef` {#downwardapi-fieldRef}
For most Pod-level fields, you can provide them to a container either as
an environment variable or using a `downwardAPI` volume. The fields available
via either mechanism are:
`metadata.name`
: the pod's name
`metadata.namespace`
: the pod's {{< glossary_tooltip text="namespace" term_id="namespace" >}}
`metadata.uid`
: the pod's unique ID
`metadata.annotations['<KEY>']`
: the value of the pod's {{< glossary_tooltip text="annotation" term_id="annotation" >}} named `<KEY>` (for example, `metadata.annotations['myannotation']`)
`metadata.labels['<KEY>']`
: the text value of the pod's {{< glossary_tooltip text="label" term_id="label" >}} named `<KEY>` (for example, `metadata.labels['mylabel']`)
`spec.serviceAccountName`
: the name of the pod's {{< glossary_tooltip text="service account" term_id="service-account" >}}
`spec.nodeName`
: the name of the {{< glossary_tooltip term_id="node" text="node">}} where the Pod is executing
`status.hostIP`
: the primary IP address of the node to which the Pod is assigned
`status.podIP`
: the pod's primary IP address (usually, its IPv4 address)
In addition, the following information is available through
a `downwardAPI` volume `fieldRef`, but **not as environment variables**:
`metadata.labels`
: all of the pod's labels, formatted as `label-key="escaped-label-value"` with one label per line
`metadata.annotations`
: all of the pod's annotations, formatted as `annotation-key="escaped-annotation-value"` with one annotation per line
### Information available via `resourceFieldRef` {#downwardapi-resourceFieldRef}
These container-level fields allow you to provide information about
[requests and limits](/docs/concepts/configuration/manage-resources-containers/#requests-and-limits)
for resources such as CPU and memory.
`resource: limits.cpu`
: A container's CPU limit
`resource: requests.cpu`
: A container's CPU request
`resource: limits.memory`
: A container's memory limit
`resource: requests.memory`
: A container's memory request
`resource: limits.hugepages-*`
: A container's hugepages limit (provided that the `DownwardAPIHugePages` [feature gate](/docs/reference/command-line-tools-reference/feature-gates/) is enabled)
`resource: requests.hugepages-*`
: A container's hugepages request (provided that the `DownwardAPIHugePages` [feature gate](/docs/reference/command-line-tools-reference/feature-gates/) is enabled)
`resource: limits.ephemeral-storage`
: A container's ephemeral-storage limit
`resource: requests.ephemeral-storage`
: A container's ephemeral-storage request
#### Fallback information for resource limits
If CPU and memory limits are not specified for a container, and you use the
downward API to try to expose that information, then the
kubelet defaults to exposing the maximum allocatable value for CPU and memory
(based on the [node allocatable](/docs/tasks/administer-cluster/reserve-compute-resources/#node-allocatable)
calculation).
## {{% heading "whatsnext" %}}
You can read about [`downwardAPI` volumes](/docs/concepts/storage/volumes/#downwardapi).
You can try using the downward API to expose container- or Pod-level information:
* as [environment variables](/docs/tasks/inject-data-application/environment-variable-expose-pod-information/#the-downward-api)
* as [files in `downwardAPI` volume](/docs/tasks/inject-data-application/downward-api-volume-expose-pod-information/)

View File

@ -0,0 +1,28 @@
---
title: Downward API
id: downward-api
date: 2022-03-21
short_description: >
A mechanism to expose Pod and container field values to code running in a container.
aka:
full_link: /docs/concepts/workloads/pods/downward-api/
tags:
- architecture
---
Kubernetes' mechanism to expose Pod and container field values to code running in a container.
<!--more-->
It is sometimes useful for a container to have information about itself, without
needing to make changes to the container code that directly couple it to Kubernetes.
The Kubernetes downward API allows containers to consume information about themselves
or their context in a Kubernetes cluster. Applications in containers can have
access to that information, without the application needing to act as a client of
the Kubernetes API.
There are two ways to expose Pod and container fields to a running container:
- using [environment variables](/docs/tasks/inject-data-application/environment-variable-expose-pod-information/)
- using [a `downwardAPI` volume](/docs/tasks/inject-data-application/downward-api-volume-expose-pod-information/)
Together, these two ways of exposing Pod and container fields are called the _downward API_.

View File

@ -7,38 +7,38 @@ weight: 40
<!-- overview -->
This page shows how a Pod can use a
[`DownwardAPIVolumeFile`](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#downwardapivolumefile-v1-core)
to expose information about itself to Containers running in the Pod.
A `DownwardAPIVolumeFile` can expose Pod fields and Container fields.
[`downwardAPI` volume](/docs/concepts/storage/volumes/#downwardapi),
to expose information about itself to containers running in the Pod.
A `downwardAPI` volume can expose Pod fields and container fields.
In Kubernetes, there are two ways to expose Pod and container fields to a running container:
* [Environment variables](/docs/tasks/inject-data-application/environment-variable-expose-pod-information/#the-downward-api)
* Volume files, as explained in this task
Together, these two ways of exposing Pod and container fields are called the
_downward API_.
## {{% heading "prerequisites" %}}
{{< include "task-tutorial-prereqs.md" >}} {{< version-check >}}
{{< include "task-tutorial-prereqs.md" >}}
<!-- steps -->
## The Downward API
There are two ways to expose Pod and Container fields to a running Container:
* [Environment variables](/docs/tasks/inject-data-application/environment-variable-expose-pod-information/#the-downward-api)
* Volume files
Together, these two ways of exposing Pod and Container fields are called the
"Downward API".
## Store Pod fields
In this exercise, you create a Pod that has one Container.
Here is the configuration file for the Pod:
In this part of exercise, you create a Pod that has one container, and you
project Pod-level fields into the running container as files.
Here is the manifest for the Pod:
{{< codenew file="pods/inject/dapi-volume.yaml" >}}
In the configuration file, you can see that the Pod has a `downwardAPI` Volume,
and the Container mounts the Volume at `/etc/podinfo`.
In the manifest, you can see that the Pod has a `downwardAPI` Volume,
and the container mounts the volume at `/etc/podinfo`.
Look at the `items` array under `downwardAPI`. Each element of the array is a
[DownwardAPIVolumeFile](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#downwardapivolumefile-v1-core).
Look at the `items` array under `downwardAPI`. Each element of the array
defines a `downwardAPI` volume.
The first element specifies that the value of the Pod's
`metadata.labels` field should be stored in a file named `labels`.
The second element specifies that the value of the Pod's `annotations`
@ -46,7 +46,7 @@ field should be stored in a file named `annotations`.
{{< note >}}
The fields in this example are Pod fields. They are not
fields of the Container in the Pod.
fields of the container in the Pod.
{{< /note >}}
Create the Pod:
@ -145,26 +145,30 @@ Exit the shell:
/# exit
```
## Store Container fields
## Store container fields
The preceding exercise, you stored Pod fields in a
[`DownwardAPIVolumeFile`](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#downwardapivolumefile-v1-core)..
In this next exercise, you store Container fields. Here is the configuration
file for a Pod that has one Container:
The preceding exercise, you made Pod-level fields accessible using the
downward API.
In this next exercise, you are going to pass fields that are part of the Pod
definition, but taken from the specific
[container](/docs/reference/kubernetes-api/workload-resources/pod-v1/#Container)
rather than from the Pod overall. Here is a manifest for a Pod that again has
just one container:
{{< codenew file="pods/inject/dapi-volume-resources.yaml" >}}
In the configuration file, you can see that the Pod has a
In the manifest, you can see that the Pod has a
[`downwardAPI` volume](/docs/concepts/storage/volumes/#downwardapi),
and the Container mounts the volume at `/etc/podinfo`.
and that the single container in that Pod mounts the volume at `/etc/podinfo`.
Look at the `items` array under `downwardAPI`. Each element of the array is a
[`DownwardAPIVolumeFile`](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#downwardapivolumefile-v1-core).
Look at the `items` array under `downwardAPI`. Each element of the array
defines a file in the downward API volume.
The first element specifies that in the Container named `client-container`,
The first element specifies that in the container named `client-container`,
the value of the `limits.cpu` field in the format specified by `1m` should be
stored in a file named `cpu_limit`. The `divisor` field is optional and has the
default value of `1` which means cores for cpu and bytes for memory.
published as a file named `cpu_limit`. The `divisor` field is optional and has the
default value of `1`. A divisor of 1 means cores for `cpu` resources, or
bytes for `memory` resources.
Create the Pod:
@ -181,7 +185,8 @@ kubectl exec -it kubernetes-downwardapi-volume-example-2 -- sh
In your shell, view the `cpu_limit` file:
```shell
/# cat /etc/podinfo/cpu_limit
# Run this in a shell inside the container
cat /etc/podinfo/cpu_limit
```
You can use similar commands to view the `cpu_request`, `mem_limit` and
@ -189,79 +194,20 @@ You can use similar commands to view the `cpu_request`, `mem_limit` and
<!-- discussion -->
<!-- TODO: This section should be extracted out of the task page. -->
## Capabilities of the Downward API
The following information is available to containers through environment
variables and `downwardAPI` volumes:
* Information available via `fieldRef`:
* `metadata.name` - the pod's name
* `metadata.namespace` - the pod's namespace
* `metadata.uid` - the pod's UID
* `metadata.labels['<KEY>']` - the value of the pod's label `<KEY>`
(for example, `metadata.labels['mylabel']`)
* `metadata.annotations['<KEY>']` - the value of the pod's annotation `<KEY>`
(for example, `metadata.annotations['myannotation']`)
* Information available via `resourceFieldRef`:
* A Container's CPU limit
* A Container's CPU request
* A Container's memory limit
* A Container's memory request
* A Container's hugepages limit (provided that the `DownwardAPIHugePages`
[feature gate](/docs/reference/command-line-tools-reference/feature-gates/) is enabled)
* A Container's hugepages request (provided that the `DownwardAPIHugePages`
[feature gate](/docs/reference/command-line-tools-reference/feature-gates/) is enabled)
* A Container's ephemeral-storage limit
* A Container's ephemeral-storage request
In addition, the following information is available through
`downwardAPI` volume `fieldRef`:
* `metadata.labels` - all of the pod's labels, formatted as `label-key="escaped-label-value"`
with one label per line
* `metadata.annotations` - all of the pod's annotations, formatted as
`annotation-key="escaped-annotation-value"` with one annotation per line
The following information is available through environment variables:
* `status.podIP` - the pod's IP address
* `spec.serviceAccountName` - the pod's service account name
* `spec.nodeName` - the name of the node to which the scheduler always attempts to
schedule the pod
* `status.hostIP` - the IP of the node to which the Pod is assigned
{{< note >}}
If CPU and memory limits are not specified for a Container, the
Downward API defaults to the node allocatable value for CPU and memory.
{{< /note >}}
## Project keys to specific paths and file permissions
You can project keys to specific paths and specific permissions on a per-file
basis. For more information, see
[Secrets](/docs/concepts/configuration/secret/).
## Motivation for the Downward API
It is sometimes useful for a container to have information about itself, without
being overly coupled to Kubernetes. The Downward API allows containers to consume
information about themselves or the cluster without using the Kubernetes client
or API server.
An example is an existing application that assumes a particular well-known
environment variable holds a unique identifier. One possibility is to wrap the
application, but that is tedious and error prone, and it violates the goal of low
coupling. A better option would be to use the Pod's name as an identifier, and
inject the Pod's name into the well-known environment variable.
## {{% heading "whatsnext" %}}
* Check the [`PodSpec`](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#podspec-v1-core)
API definition which defines the desired state of a Pod.
* Read the [`spec`](/docs/reference/kubernetes-api/workload-resources/pod-v1/#PodSpec)
API definition for Pod. This includes the definition of Container (part of Pod).
* Read the list of [available fields](/docs/concepts/workloads/pods/downward-api/#available-fields) that you
can expose using the downward API.
Read about volumes in the legacy API reference:
* Check the [`Volume`](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#volume-v1-core)
API definition which defines a generic volume in a Pod for containers to access.
* Check the [`DownwardAPIVolumeSource`](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#downwardapivolumesource-v1-core)
@ -271,4 +217,3 @@ inject the Pod's name into the well-known environment variable.
populating a file in the Downward API volume.
* Check the [`ResourceFieldSelector`](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#resourcefieldselector-v1-core)
API definition which specifies the container resources and their output format.

View File

@ -7,50 +7,40 @@ weight: 30
<!-- overview -->
This page shows how a Pod can use environment variables to expose information
about itself to Containers running in the Pod. Environment variables can expose
Pod fields and Container fields.
about itself to containers running in the Pod, using the _downward API_.
You can use environment variables to expose Pod fields, container fields, or both.
In Kubernetes, there are two ways to expose Pod and container fields to a running container:
* _Environment variables_, as explained in this task
* [Volume files](/docs/tasks/inject-data-application/downward-api-volume-expose-pod-information/)
Together, these two ways of exposing Pod and container fields are called the
downward API.
## {{% heading "prerequisites" %}}
{{< include "task-tutorial-prereqs.md" >}} {{< version-check >}}
{{< include "task-tutorial-prereqs.md" >}}
<!-- steps -->
## The Downward API
There are two ways to expose Pod and Container fields to a running Container:
* Environment variables
* [Volume Files](/docs/tasks/inject-data-application/downward-api-volume-expose-pod-information/#the-downward-api)
Together, these two ways of exposing Pod and Container fields are called the
*Downward API*.
## Use Pod fields as values for environment variables
In this exercise, you create a Pod that has one Container. Here is the
configuration file for the Pod:
In this part of exercise, you create a Pod that has one container, and you
project Pod-level fields into the running container as environment variables.
{{< codenew file="pods/inject/dapi-envars-pod.yaml" >}}
In the configuration file, you can see five environment variables. The `env`
In that manifest, you can see five environment variables. The `env`
field is an array of
[EnvVars](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#envvar-v1-core).
environment variable definitions.
The first element in the array specifies that the `MY_NODE_NAME` environment
variable gets its value from the Pod's `spec.nodeName` field. Similarly, the
other environment variables get their names from Pod fields.
{{< note >}}
The fields in this example are Pod fields. They are not fields of the
Container in the Pod.
container in the Pod.
{{< /note >}}
Create the Pod:
@ -59,13 +49,14 @@ Create the Pod:
kubectl apply -f https://k8s.io/examples/pods/inject/dapi-envars-pod.yaml
```
Verify that the Container in the Pod is running:
Verify that the container in the Pod is running:
```shell
# If the new Pod isn't yet healthy, rerun this command a few times.
kubectl get pods
```
View the Container's logs:
View the container's logs:
```shell
kubectl logs dapi-envars-fieldref
@ -82,10 +73,10 @@ default
```
To see why these values are in the log, look at the `command` and `args` fields
in the configuration file. When the Container starts, it writes the values of
in the configuration file. When the container starts, it writes the values of
five environment variables to stdout. It repeats this every ten seconds.
Next, get a shell into the Container that is running in your Pod:
Next, get a shell into the container that is running in your Pod:
```shell
kubectl exec -it dapi-envars-fieldref -- sh
@ -94,7 +85,8 @@ kubectl exec -it dapi-envars-fieldref -- sh
In your shell, view the environment variables:
```shell
/# printenv
# Run this in a shell inside the container
printenv
```
The output shows that certain environment variables have been assigned the
@ -111,22 +103,26 @@ MY_NODE_NAME=minikube
MY_POD_NAME=dapi-envars-fieldref
```
## Use Container fields as values for environment variables
## Use container fields as values for environment variables
In the preceding exercise, you used Pod fields as the values for environment
variables. In this next exercise, you use Container fields as the values for
environment variables. Here is the configuration file for a Pod that has one
container:
In the preceding exercise, you used information from Pod-level fields as the values
for environment variables.
In this next exercise, you are going to pass fields that are part of the Pod
definition, but taken from the specific
[container](/docs/reference/kubernetes-api/workload-resources/pod-v1/#Container)
rather than from the Pod overall.
Here is a manifest for another Pod that again has just one container:
{{< codenew file="pods/inject/dapi-envars-container.yaml" >}}
In the configuration file, you can see four environment variables. The `env`
In this manifest, you can see four environment variables. The `env`
field is an array of
[EnvVars](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#envvar-v1-core).
environment variable definitions.
The first element in the array specifies that the `MY_CPU_REQUEST` environment
variable gets its value from the `requests.cpu` field of a Container named
variable gets its value from the `requests.cpu` field of a container named
`test-container`. Similarly, the other environment variables get their values
from Container fields.
from fields that are specific to this container.
Create the Pod:
@ -134,13 +130,14 @@ Create the Pod:
kubectl apply -f https://k8s.io/examples/pods/inject/dapi-envars-container.yaml
```
Verify that the Container in the Pod is running:
Verify that the container in the Pod is running:
```shell
# If the new Pod isn't yet healthy, rerun this command a few times.
kubectl get pods
```
View the Container's logs:
View the container's logs:
```shell
kubectl logs dapi-envars-resourcefieldref
@ -155,18 +152,20 @@ The output shows the values of selected environment variables:
67108864
```
## {{% heading "whatsnext" %}}
* [Defining Environment Variables for a Container](/docs/tasks/inject-data-application/define-environment-variable-container/)
* Read [Defining Environment Variables for a Container](/docs/tasks/inject-data-application/define-environment-variable-container/)
* Read the [`spec`](/docs/reference/kubernetes-api/workload-resources/pod-v1/#PodSpec)
API definition for Pod. This includes the definition of Container (part of Pod).
* Read the list of [available fields](/docs/concepts/workloads/pods/downward-api/#available-fields) that you
can expose using the downward API.
Read about Pods, containers and environment variables in the legacy API reference:
* [PodSpec](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#podspec-v1-core)
* [Container](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#container-v1-core)
* [EnvVar](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#envvar-v1-core)
* [EnvVarSource](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#envvarsource-v1-core)
* [ObjectFieldSelector](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#objectfieldselector-v1-core)
* [ResourceFieldSelector](/docs/reference/generated/kubernetes-api/{{< param "version" >}}/#resourcefieldselector-v1-core)