DZone
Thanks for visiting DZone today,
Edit Profile
  • Manage Email Subscriptions
  • How to Post to DZone
  • Article Submission Guidelines
Sign Out View Profile
  • Post an Article
  • Manage My Drafts
Over 2 million developers have joined DZone.
Log In / Join
Refcards Trend Reports
Events Video Library
Refcards
Trend Reports

Events

View Events Video Library

Related

  • Stop Debugging Code That Works: Identifying False Failures in Kubernetes
  • Monitoring Kubernetes Service Topology Changes in Real Time
  • Zero-Downtime Deployments for Java Apps on Kubernetes
  • Kubernetes Scheduler Plugins: Optimizing AI/ML Workloads

Trending

  • Edge Computing in Utility IoT: Two Architecture Patterns That Actually Work
  • Building a DevOps-Ready Internal Developer Platform: A Hands-On Guide to Golden Paths, Self-Service, and Automated Delivery Pipelines
  • Designing API-First EMR Architectures in .NET: Enabling Modular Growth in Compliance-Driven Systems
  • From Indicators to Insights: Automating IOC Enrichment Using Python and Threat Feeds
  1. DZone
  2. Software Design and Architecture
  3. Cloud Architecture
  4. Kubernetes Container Lifecycle Events and Hooks

Kubernetes Container Lifecycle Events and Hooks

Learn about container lifecycle events and hooks with a deployment example comprising a main Kubernetes container running NGINX and a sidecar container running busybox.

By 
Rahul Rai user avatar
Rahul Rai
·
Oct. 28, 21 · Tutorial
Likes (2)
Comment
Save
Tweet
Share
14.0K Views

Join the DZone community and get the full member experience.

Join For Free

You might encounter cases where you need to instruct Kubernetes to start a pod only when a condition is met, such as dependencies are running, or sidecar containers are ready. Likewise, you might want to execute a command before Kubernetes terminates a pod to release the resources in use and gracefully terminate the application.

You can do so easily with two container lifecycle hooks:

  1. PostStart: This hook is executed right after a container is created. However, the hook might be invoked after the container's ENTRYPOINT is executed. The hook handler must not accept any parameters.
  2. PreStop: This hook is executed immediately before a container is terminated due to any reason, such as resource contention, liveness probe failure, etc. You cannot pass any parameters to the handler, and the container will be terminated irrespective of the outcome of the handler.

Here's an illustration of the lifecycle events of a pod comprising two containers starting from the point when you instruct Kubernetes to create it to the point when both of them are running:

Pod State Transitions
Pod state transitions

There are two types of handlers that you can attach to a lifecycle hook:

  1. exec: It executes the specified command in the container's main process. The command is executed in parallel with the container's ENTRYPOINT instruction. If the hook takes too long or fails, the kubelet process will restart the container.
  2. httpGet or tcpSocket: It sends an HTTP request or establishes a TCP socket connection against a specific endpoint on the container. Unlike the exec, which is executed by the container, this handler is executed by the kubelet process.

The hooks are executed at least once, and for HTTP handlers, the kubelet makes only one request delivery unless the kubelet restarts in the middle of sending the request.

Deployment Example

Here's an example of a deployment comprising a main container running NGINX and a sidecar container running busybox. The main container serves the file index.html from the mounted volume on port 80. The sidecar container writes scheduled logs to the same file, index.html, served by the main container. The sidecar container will start only when the main container is ready.

YAML
 
apiVersion: v1
kind: Pod
metadata:
  name: sidecar-container-demo
spec:
  containers:
    - image: busybox
      command: ["/bin/sh"]
      args:
        [
          "-c",
          "while true; do echo echo $(date -u) 'Written by busybox sidecar container' >> /var/log/index.html; sleep 5;done",
        ]
      name: sidecar-container
      resources: {}
      volumeMounts:
        - name: var-logs
          mountPath: /var/log
      lifecycle:
        postStart:
          httpGet:
            path: /index.html
            port: 80
            host: localhost
            scheme: HTTP
    - image: nginx
      name: main-container
      resources: {}
      ports:
        - containerPort: 80
      volumeMounts:
        - name: var-logs
          mountPath: /usr/share/nginx/html
  dnsPolicy: Default
  volumes:
    - name: var-logs
      emptyDir: {}


Till the hook postStart fails, the sidecar container will keep restarting. You can force the sidecar container to fail by changing the lifecycle check to the following:

YAML
 
lifecycle:
  postStart:
    httpGet:
      path: /index.html
      port: 5000
      host: localhost
      scheme: HTTP


You can view the events generated by the kubelet by running the following command:

Shell
 
kubectl describe pod/sidecar-container-demo


Here is the output of the command:

Failed Post Start Hook Event
Failed post start hook event

Let's implement the next hook, preStop. The following command will print a log message and ensure that pod shuts down gracefully:

Tip: You can direct preStop output to the PID 1 stdout, which ends up in the application logs. We'll use this trick to track the execution of a pre-stop hook next.

YAML
 
apiVersion: v1
kind: Pod
metadata:
  name: prestop-demo
spec:
  containers:
    - image: nginx
      name: nginx-container
      resources: {}
      ports:
        - containerPort: 80
      lifecycle:
        preStop:
          exec:
            command:
              - sh
              - -c
              - echo "Stopping container now...">/proc/1/fd/1 && nginx -s stop
  dnsPolicy: Default


When the container using the pre-stop hook is terminated, the command nginx -s quit is executed in the container before kubelet sends the SIGTERM signal to the main process.

If you delete the pod while keeping a watch on the logs of the NGINX container, you will see the following output:

Pre-Stop Hook Event
Pre-stop hook event

Finally, let's discuss some important details about the lifecycle hooks:

  • When you delete a pod object, the pre-stop hook is executed first, followed by the TERM signal to the main process. Next, the kubelet waits for the process to stop within seconds specified in the terminationGracePeriodSeconds property, after which it is killed.
  • When you delete a pod object, all its containers are terminated in parallel. You can grant each container a custom grace period in seconds by setting the deletionGracePeriodSeconds property in the container's specification.
  • Handling the TERM signal using a handler is better than shortening the termination or deletion grace period.
Kubernetes Hook Event pods

Published at DZone with permission of Rahul Rai. See the original article here.

Opinions expressed by DZone contributors are their own.

Related

  • Stop Debugging Code That Works: Identifying False Failures in Kubernetes
  • Monitoring Kubernetes Service Topology Changes in Real Time
  • Zero-Downtime Deployments for Java Apps on Kubernetes
  • Kubernetes Scheduler Plugins: Optimizing AI/ML Workloads

Partner Resources

×

Comments

The likes didn't load as expected. Please refresh the page and try again.

  • RSS
  • X
  • Facebook

ABOUT US

  • About DZone
  • Support and feedback
  • Community research

ADVERTISE

  • Advertise with DZone

CONTRIBUTE ON DZONE

  • Article Submission Guidelines
  • Become a Contributor
  • Core Program
  • Visit the Writers' Zone

LEGAL

  • Terms of Service
  • Privacy Policy

CONTACT US

  • 3343 Perimeter Hill Drive
  • Suite 215
  • Nashville, TN 37211
  • [email protected]

Let's be friends:

  • RSS
  • X
  • Facebook