cd ..
Kubernetes

Limiting CPU and Memory Consumption of Pods in Kubernetes

This article is a continuation of the Kubernetes Fundamentals series. In previous posts, we learned what Pods are, how to create them using kubectl, and how to generate YAML manifests. Now, we will see how to control container resource consumption.

Note: This content was produced from my studies in PICK – Intensive Container and Kubernetes Program by LINUXtips, complemented by the official Kubernetes documentation.

Limiting CPU and Memory Consumption of Pods in Kubernetes

When running applications in a Kubernetes cluster, it’s important to prevent a single container from consuming all available Node resources.

To achieve this, Kubernetes allows you to define how much CPU and memory a container requests and how much it can use at most.

These configurations are made through the resources block.

Creating a Manifest

Building on the manifest created in the previous article, we can create a new version to add resource limits.

cp pod.yaml pod-limitado.yaml

Then, simply edit the new file.

Manifest Structure

Our Pod will look similar to the example below:

apiVersion: v1
kind: Pod

metadata:
  name: timao

spec:
  containers:
    - name: ubuntu
      image: ubuntu

      args:
        - sleep
        - "1800"

      resources:
        requests:
          cpu: "300m"
          memory: "64Mi"

        limits:
          cpu: "500m"
          memory: "128Mi"

After saving the file, we can apply it to the cluster.

kubectl apply -f pod-limitado.yaml

The resources block

All configuration related to resource consumption is located within:

resources:

This block has two main sections:

Although they seem similar, they have different functions.

Requests

Requests represent the minimum amount of resources that the container asks the cluster for.

resources:
  requests:
    cpu: "300m"
    memory: "64Mi"

These values are used by the Scheduler during Pod scheduling.

Before choosing a Node, the Scheduler checks if there is enough capacity to meet the requested resources.

We can think of requests as a minimum guarantee.

If we specify:

cpu: "300m"

we are requesting approximately 300 millicores, or about 30% of a CPU core.

Whereas:

memory: "64Mi"

requests 64 MiB (Mebibytes) of RAM for the container.

Limits

While requests represent the guaranteed minimum amount, limits define the maximum allowed consumption.

resources:
  limits:
    cpu: "500m"
    memory: "128Mi"

When the container reaches these values, the behavior depends on the resource.

CPU Limit

When the CPU limit is exceeded, the container is not terminated.

The Kernel reduces the processing time available to it, a process known as CPU Throttling.

In practice, the application continues to function, but with reduced performance.

Memory Limit

With memory, the behavior is different.

If the container exceeds the defined limit, the Kernel terminates the process to protect the rest of the system.

In Kubernetes, we will usually see the status:

OOMKilled

This is one of the most common problems found in applications that do not have limits configured correctly.

Verifying the Pod

After creating the resource, we can view its configurations using:

kubectl describe pod timao

If it’s necessary to access the container:

kubectl exec -it timao -- sh

Inside it, we can use some commands to inspect the environment.

View processes:

ps -ef

View memory usage:

free -m

These commands help understand the container’s behavior during testing.

Conclusion

Configuring requests and limits is one of the most important practices in Kubernetes.

While requests guarantee the minimum necessary resources for the Scheduler to correctly place the Pod on a Node, limits prevent a container from using resources beyond what is allowed.

This configuration makes the cluster more predictable, improves resource sharing among applications, and reduces problems caused by excessive CPU and memory consumption.

References

Official Documentation

Complementary Material

What did you think?