Migrate Init Containers to Concepts (#2438)
* Initial commit for Init Containers migration to Concepts section * Add 1.5 beta include file * Change include to renamed user-guide-content-moved.md file * Fix Concepts/KO/Pods ToC * reformat examples to bullet points * fix formatting * Add back Detailed Behavior, Support and compatibility * Adjust formatting issues * revised based on feedback from Steve * complete sentence rewrite
This commit is contained in:
parent
554d6b7e9f
commit
667c1818dc
|
|
@ -9,12 +9,14 @@ toc:
|
||||||
- docs/concepts/tools/kubectl/object-management-using-imperative-commands.md
|
- docs/concepts/tools/kubectl/object-management-using-imperative-commands.md
|
||||||
- docs/concepts/tools/kubectl/object-management-using-imperative-config.md
|
- docs/concepts/tools/kubectl/object-management-using-imperative-config.md
|
||||||
- docs/concepts/tools/kubectl/object-management-using-declarative-config.md
|
- docs/concepts/tools/kubectl/object-management-using-declarative-config.md
|
||||||
|
|
||||||
- title: Kubernetes Objects
|
- title: Kubernetes Objects
|
||||||
section:
|
section:
|
||||||
- docs/concepts/abstractions/overview.md
|
- docs/concepts/abstractions/overview.md
|
||||||
- docs/concepts/abstractions/pod.md
|
- title: Pods
|
||||||
|
section:
|
||||||
|
- docs/concepts/abstractions/pod.md
|
||||||
|
- docs/concepts/abstractions/init-containers.md
|
||||||
- title: Controllers
|
- title: Controllers
|
||||||
section:
|
section:
|
||||||
- docs/concepts/abstractions/controllers/statefulsets.md
|
- docs/concepts/abstractions/controllers/statefulsets.md
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1 @@
|
||||||
|
***NOTE: This feature is beta in Kubernetes 1.5.***
|
||||||
|
|
@ -0,0 +1,184 @@
|
||||||
|
---
|
||||||
|
assignees:
|
||||||
|
- erictune
|
||||||
|
title: Init Containers
|
||||||
|
---
|
||||||
|
|
||||||
|
{% capture overview %}
|
||||||
|
This page provides an overview of Init Containers, which are specialized
|
||||||
|
Containers that run before app Containers and can contain utilities or setup
|
||||||
|
scripts not present in an app image.
|
||||||
|
{% endcapture %}
|
||||||
|
|
||||||
|
{:toc}
|
||||||
|
|
||||||
|
{% include 1-5-beta.md %}
|
||||||
|
|
||||||
|
**Once the feature exits beta, Init Containers will be specified in the PodSpec
|
||||||
|
alongside the app `containers` array.**
|
||||||
|
|
||||||
|
{% capture body %}
|
||||||
|
## Understanding Init Containers
|
||||||
|
|
||||||
|
A [Pod](/docs/concepts/abstractions/pod/) can have multiple Containers running
|
||||||
|
apps within it, but it can also have one or more Init Containers, which are run
|
||||||
|
before the app Containers are started.
|
||||||
|
|
||||||
|
Init Containers are exactly like regular Containers, except:
|
||||||
|
|
||||||
|
* They always run to completion.
|
||||||
|
* Each one must complete successfully before the next one is started.
|
||||||
|
|
||||||
|
If an Init Container fails for a Pod, Kubernetes restarts the Pod repeatedly until the Init
|
||||||
|
Container succeeds. However, if the Pod has a `restartPolicy` of Never, it is not restarted.
|
||||||
|
|
||||||
|
To specify a Container as an Init Container, add the `annotations` key
|
||||||
|
`pod.beta.kubernetes.io/init-containers`. Its value should be a
|
||||||
|
JSON array of objects of type
|
||||||
|
[Container](http://kubernetes.io/docs/api-reference/v1/definitions/#_v1_container).
|
||||||
|
|
||||||
|
The status of an Init Container is returned as another annotation,
|
||||||
|
`pod.beta.kubernetes.io/init-container-statuses`, which is an array of
|
||||||
|
container statuses similar to the `status.containerStatuses` field.
|
||||||
|
|
||||||
|
### Differences from regular Containers
|
||||||
|
|
||||||
|
Init Containers support all the fields and features of app Containers,
|
||||||
|
including resource limits, volumes, and security settings. However, the
|
||||||
|
resource requests and limits for an Init Container are handled slightly
|
||||||
|
differently, which are documented in [Resources](#resources) below. Also, Init Containers do not
|
||||||
|
support readiness probes because they must run to completion before the Pod can
|
||||||
|
be ready.
|
||||||
|
|
||||||
|
If multiple Init Containers are specified for a Pod, those Containers are run
|
||||||
|
one at a time in sequential order. Each must succeed before the next can run.
|
||||||
|
When all of the Init Containers have run to completion, Kubernetes initializes
|
||||||
|
the Pod and runs the application Containers as usual.
|
||||||
|
|
||||||
|
## What can Init Containers be used for?
|
||||||
|
|
||||||
|
Because Init Containers have separate images from app Containers, they
|
||||||
|
have some advantages for start-up related code:
|
||||||
|
|
||||||
|
* They can contain and run utilities that are not desirable to include in the
|
||||||
|
app Container image for security reasons.
|
||||||
|
* They can contain utilities or custom code for setup that is not present in an app
|
||||||
|
image. For example, there is no need to make an image `FROM` another image just to use a tool like
|
||||||
|
`sed`, `awk`, `python`, or `dig` during setup.
|
||||||
|
* The application image builder and deployer roles can work independently without
|
||||||
|
the need to jointly build a single app image.
|
||||||
|
* They use Linux namespaces so they have a different filesystem view from app Containers.
|
||||||
|
Consequently, they can be given access to Secrets that app Containers are not able to
|
||||||
|
access.
|
||||||
|
* They run to completion before any app Containers start, whereas app
|
||||||
|
Containers run in parallel, so Init Containers provide an easy way to block or
|
||||||
|
delay the startup of app Containers until some set of preconditions are met.
|
||||||
|
|
||||||
|
### Examples
|
||||||
|
Here are some ideas for how to use Init Containers:
|
||||||
|
|
||||||
|
* Wait for a service to be created with a shell command like:
|
||||||
|
|
||||||
|
for i in {1..100}; do sleep 1; if dig myservice; then exit 0; fi; exit 1
|
||||||
|
|
||||||
|
* Register this Pod with a remote server from the downward API with a command like:
|
||||||
|
|
||||||
|
curl -X POST http://$MANAGEMENT_SERVICE_HOST:$MANAGEMENT_SERVICE_PORT/register -d 'instance=$(<POD_NAME>)&ip=$(<POD_IP>)'
|
||||||
|
|
||||||
|
* Wait for some time before starting the app Container with a command like `sleep 60`.
|
||||||
|
* Clone a git repository into a volume.
|
||||||
|
* Place values into a configuration file and run a template tool to dynamically
|
||||||
|
generate a configuration file for the the main app Container. For example,
|
||||||
|
place the POD_IP value in a configuration and generate the main app
|
||||||
|
configuration file using Jinja.
|
||||||
|
|
||||||
|
More detailed usage examples can be found in the [StatefulSets documentation](/docs/concepts/abstractions/controllers/statefulsets/)
|
||||||
|
and the [Production Pods guide](/docs/user-guide/production-pods.md#handling-initialization).
|
||||||
|
|
||||||
|
## Detailed behavior
|
||||||
|
|
||||||
|
During the startup of a Pod, the Init Containers are started in order, after the
|
||||||
|
network and volumes are initialized. Each Container must exit successfully before
|
||||||
|
the next is started. If a Container fails to start due to the runtime or
|
||||||
|
exits with failure, it is retried according to the Pod `restartPolicy`. However,
|
||||||
|
if the Pod `restartPolicy` is set to Always, the Init Containers use
|
||||||
|
`RestartPolicy` OnFailure.
|
||||||
|
|
||||||
|
A Pod cannot be `Ready` until all Init Containers have succeeded. The ports on an
|
||||||
|
Init Container are not aggregated under a service. A Pod that is initializing
|
||||||
|
is in the `Pending` state but should have a condition `Initializing` set to true.
|
||||||
|
|
||||||
|
If the Pod is [restarted](#pod-restart-reasons), all Init Containers must
|
||||||
|
execute again.
|
||||||
|
|
||||||
|
Changes to the Init Container spec are limited to the container image field.
|
||||||
|
Altering an Init Container image field is equivalent to restarting the Pod.
|
||||||
|
|
||||||
|
Because Init Containers can be restarted, retried, or re-executed, Init Container
|
||||||
|
code should be idempotent. In particular, code that writes to files on `EmptyDirs`
|
||||||
|
should be prepared for the possibility that an output file already exists.
|
||||||
|
|
||||||
|
Init Containers have all of the fields of an app Container. However, Kubernetes
|
||||||
|
prohibits `readinessProbe` from being used because Init Containers cannot
|
||||||
|
define readiness distinct from completion. This is enforced during validation.
|
||||||
|
|
||||||
|
Use `activeDeadlineSeconds` on the Pod and `livenessProbe` on the Container to
|
||||||
|
prevent Init Containers from failing forever. The active deadline includes Init
|
||||||
|
Containers.
|
||||||
|
|
||||||
|
The name of each app and Init Container in a Pod must be unique; a
|
||||||
|
validation error is thrown for any Container sharing a name with another.
|
||||||
|
|
||||||
|
### Resources
|
||||||
|
|
||||||
|
Given the ordering and execution for Init Containers, the following rules
|
||||||
|
for resource usage apply:
|
||||||
|
|
||||||
|
* The highest of any particular resource request or limit defined on all Init
|
||||||
|
Containers is the *effective init request/limit*
|
||||||
|
* The Pod's *effective request/limit* for a resource is the higher of:
|
||||||
|
* the sum of all app Containers request/limit for a resource
|
||||||
|
* the effective init request/limit for a resource
|
||||||
|
* Scheduling is done based on effective requests/limits, which means
|
||||||
|
Init Containers can reserve resources for initialization that are not used
|
||||||
|
during the life of the Pod.
|
||||||
|
* QoS tier of the Pod's *effective QoS tier* is the QoS tier for Init Containers
|
||||||
|
and app containers alike.
|
||||||
|
|
||||||
|
Quota and limits are applied based on the effective Pod request and
|
||||||
|
limit.
|
||||||
|
|
||||||
|
Pod level cgroups are based on the effective Pod request and limit, the
|
||||||
|
same as the scheduler.
|
||||||
|
|
||||||
|
|
||||||
|
### Pod restart reasons
|
||||||
|
|
||||||
|
A Pod can restart, causing re-execution of Init Containers, for the following
|
||||||
|
reasons:
|
||||||
|
|
||||||
|
* A user updates the PodSpec causing the Init Container image to change.
|
||||||
|
App Container image changes only restart the app Container.
|
||||||
|
* The Pod infrastructure container is restarted. This is uncommon and would
|
||||||
|
have to be done by someone with root access to nodes.
|
||||||
|
* All containers in a Pod are terminated while `restartPolicy` is set to Always,
|
||||||
|
forcing a restart, and the Init Container completion record has been lost due
|
||||||
|
to garbage collection.
|
||||||
|
|
||||||
|
## Support and compatibility
|
||||||
|
|
||||||
|
A cluster with Kubelet and Apiserver version 1.4.0 or greater supports Init
|
||||||
|
Containers with the beta annotations. Support varies for other combinations of
|
||||||
|
Kubelet and Apiserver versions; see the [release notes](https://github.com/kubernetes/kubernetes/blob/master/CHANGELOG.md) for details.
|
||||||
|
|
||||||
|
{% endcapture %}
|
||||||
|
|
||||||
|
|
||||||
|
{% capture whatsnext %}
|
||||||
|
|
||||||
|
* [Creating a Pod that has an Init Container](/docs/tasks/configure-pod-container/configure-pod-initialization/#creating-a-pod-that-has-an-init-container)
|
||||||
|
|
||||||
|
{% endcapture %}
|
||||||
|
|
||||||
|
|
||||||
|
{% include templates/concept.md %}
|
||||||
|
|
@ -1,168 +1,7 @@
|
||||||
---
|
---
|
||||||
assignees:
|
|
||||||
- erictune
|
|
||||||
title: Init Containers
|
title: Init Containers
|
||||||
---
|
---
|
||||||
|
|
||||||
* TOC
|
{% include user-guide-content-moved.md %}
|
||||||
{:toc}
|
|
||||||
|
|
||||||
In addition to having one or more main containers (or **app containers**), a
|
|
||||||
pod can also have one or more **init containers** which run before the app
|
|
||||||
containers. Init containers allow you to reduce and reorganize setup scripts
|
|
||||||
and "glue code".
|
|
||||||
|
|
||||||
## Overview
|
|
||||||
|
|
||||||
An init container is exactly like a regular container, except that it always
|
|
||||||
runs to completion and each init container must complete successfully before
|
|
||||||
the next one is started. If the init container fails, Kubernetes will restart
|
|
||||||
the pod until the init container succeeds. If a pod is marked as `RestartNever`,
|
|
||||||
the pod will fail if the init container fails.
|
|
||||||
|
|
||||||
You specify a container as an init container by adding an annotation.
|
|
||||||
The annotation key is `pod.beta.kubernetes.io/init-containers`. The annotation
|
|
||||||
value is a JSON array of [objects of type `v1.Container`
|
|
||||||
](http://kubernetes.io/docs/api-reference/v1/definitions/#_v1_container)
|
|
||||||
|
|
||||||
Once the feature exits beta, the init containers will be specified on the Pod
|
|
||||||
Spec alongside the app `containers` array.
|
|
||||||
The status of the init containers is returned as another annotation -
|
|
||||||
`pod.beta.kubernetes.io/init-container-statuses` -- as an array of the
|
|
||||||
container statuses (similar to the `status.containerStatuses` field).
|
|
||||||
|
|
||||||
Init containers support all of the same features as normal containers,
|
|
||||||
including resource limits, volumes, and security settings. The resource
|
|
||||||
requests and limits for an init container are [handled slightly differently](
|
|
||||||
#resources). Init containers do not support readiness probes since they will
|
|
||||||
run to completion before the pod can be ready.
|
|
||||||
An init container has all of the fields of an app container.
|
|
||||||
|
|
||||||
If you specify multiple init containers for a pod, those containers run one at
|
|
||||||
a time in sequential order. Each must succeed before the next can run. Once all
|
|
||||||
init containers have run to completion, Kubernetes initializes the pod and runs
|
|
||||||
the application containers as usual.
|
|
||||||
|
|
||||||
## What are Init Containers Good For?
|
|
||||||
|
|
||||||
Because init containers have separate images from application containers, they
|
|
||||||
have some advantages for start-up related code. These include:
|
|
||||||
|
|
||||||
* they can contain utilities that are not desirable to include in the app container
|
|
||||||
image for security reasons,
|
|
||||||
* they can contain utilities or custom code for setup that is not present in an app
|
|
||||||
image. (No need to make an image `FROM` another image just to use a tool like
|
|
||||||
`sed`, `awk`, `python`, `dig`, etc during setup).
|
|
||||||
* the application image builder and the deployer roles can work independently without
|
|
||||||
the need to jointly build a single app image.
|
|
||||||
|
|
||||||
Because init containers have different filesystem view (Linux namespaces) from
|
|
||||||
app containers, they can be given access to Secrets that the app containers are
|
|
||||||
not able to access.
|
|
||||||
|
|
||||||
Since init containers run to completion before any app containers start, and
|
|
||||||
since app containers run in parallel, they provide an easier way to block or
|
|
||||||
delay the startup of application containers until some precondition is met.
|
|
||||||
|
|
||||||
Because init containers run in sequence and there can be multiple init containers,
|
|
||||||
they can be composed easily.
|
|
||||||
|
|
||||||
Here are some ideas for how to use init containers:
|
|
||||||
- Wait for a service to be created with a shell command like:
|
|
||||||
`for i in {1..100}; do sleep 1; if dig myservice; then exit 0; fi; exit 1`
|
|
||||||
- Register this pod with a remote server with a command like:
|
|
||||||
`curl -X POST http://$MANAGEMENT_SERVICE_HOST:$MANAGEMENT_SERVICE_PORT/register -d 'instance=$(POD_NAME)&ip=$(POD_IP)'`
|
|
||||||
using `POD_NAME` and `POD_IP` from the downward API.
|
|
||||||
- Wait for some time before starting the app container with a command like `sleep 60`.
|
|
||||||
- Clone a git repository into a volume
|
|
||||||
- Place values like a POD_IP into a configuration file, and run a template tool (e.g. jinja)
|
|
||||||
to generate a configuration file to be consumed by the main app contianer.
|
|
||||||
|
|
||||||
Complete usage examples can be found in the [StatefulSets
|
|
||||||
documentation](/docs/concepts/abstractions/controllers/statefulsets/) and the [Production Pods
|
|
||||||
guide](/docs/user-guide/production-pods.md#handling-initialization).
|
|
||||||
|
|
||||||
|
|
||||||
## Detailed Behavior
|
|
||||||
|
|
||||||
Each pod may have 0..N init containers defined along with the existing
|
|
||||||
1..M app containers.
|
|
||||||
|
|
||||||
On startup of the pod, after the network and volumes are initialized, the init
|
|
||||||
containers are started in order. Each container must exit successfully before
|
|
||||||
the next is invoked. If a container fails to start (due to the runtime) or
|
|
||||||
exits with failure, it is retried according to the pod RestartPolicy, except
|
|
||||||
when the pod restart policy is RestartPolicyAlways, in which case just the init
|
|
||||||
containers use RestartPolicyOnFailure.
|
|
||||||
|
|
||||||
A pod cannot be ready until all init containers have succeeded. The ports on an
|
|
||||||
init container are not aggregated under a service. A pod that is being
|
|
||||||
initialized is in the `Pending` phase but should has a condition `Initializing`
|
|
||||||
set to `true`.
|
|
||||||
|
|
||||||
If the pod is [restarted](#pod-restart-reasons) all init containers must
|
|
||||||
execute again.
|
|
||||||
|
|
||||||
Changes to the init container spec are limited to the container image field.
|
|
||||||
Altering an init container image field is equivalent to restarting the pod.
|
|
||||||
|
|
||||||
Because init containers can be restarted, retried, or reexecuted, init container
|
|
||||||
code should be idempotent. In particular, code that writes to files on EmptyDirs
|
|
||||||
should be prepared for the possibility that an output file already exists.
|
|
||||||
|
|
||||||
An init container has all of the fields of an app container. The following
|
|
||||||
fields are prohibited from being used on init containers by validation:
|
|
||||||
|
|
||||||
* `readinessProbe` - init containers must exit for pod startup to continue,
|
|
||||||
are not included in rotation, and so cannot define readiness distinct from
|
|
||||||
completion.
|
|
||||||
|
|
||||||
Init container authors may use `activeDeadlineSeconds` on the pod and
|
|
||||||
`livenessProbe` on the container to prevent init containers from failing
|
|
||||||
forever. The active deadline includes init containers.
|
|
||||||
|
|
||||||
The name of each app and init container in a pod must be unique - it is a
|
|
||||||
validation error for any container to share a name.
|
|
||||||
|
|
||||||
### Resources
|
|
||||||
|
|
||||||
Given the ordering and execution for init containers, the following rules
|
|
||||||
for resource usage apply:
|
|
||||||
|
|
||||||
* The highest of any particular resource request or limit defined on all init
|
|
||||||
containers is the **effective init request/limit**
|
|
||||||
* The pod's **effective request/limit** for a resource is the higher of:
|
|
||||||
* sum of all app containers request/limit for a resource
|
|
||||||
* effective init request/limit for a resource
|
|
||||||
* Scheduling is done based on effective requests/limits, which means
|
|
||||||
init containers can reserve resources for initialization that are not used
|
|
||||||
during the life of the pod.
|
|
||||||
* QoS tier of the pod's **effective QoS tier** is the QoS tier for init containers
|
|
||||||
and app containers alike.
|
|
||||||
|
|
||||||
Quota and limits are applied based on the effective pod request and
|
|
||||||
limit.
|
|
||||||
|
|
||||||
Pod level cGroups are based on the effective pod request and limit, the
|
|
||||||
same as the scheduler.
|
|
||||||
|
|
||||||
|
|
||||||
## Pod Restart Reasons
|
|
||||||
|
|
||||||
A Pod may "restart", causing reexecution of init containers, for the following
|
|
||||||
reasons:
|
|
||||||
|
|
||||||
* An init container image is changed by a user updating the Pod Spec.
|
|
||||||
* App container image changes only restart the app container.
|
|
||||||
* The pod infrastructure container is restarted.
|
|
||||||
* This is uncommon and would have to be done by someone with root access to nodes.
|
|
||||||
* All containers in a pod are terminated, requiring a restart (RestartPolicyAlways) AND the record of init container completion has been lost due to garbage collection.
|
|
||||||
|
|
||||||
## Support and compatibility
|
|
||||||
|
|
||||||
A cluster with Kubelet and Apiserver version 1.4.0 or greater supports init
|
|
||||||
containers with the beta annotations. Support varies for other combinations of
|
|
||||||
Kubelet and Apiserver version; see the [release notes
|
|
||||||
](https://github.com/kubernetes/kubernetes/blob/master/CHANGELOG.md) for details.
|
|
||||||
|
|
||||||
|
|
||||||
|
* [Init Containers](/docs/concepts/abstractions/init-containers/)
|
||||||
Loading…
Reference in New Issue