henry3260 opened a new pull request, #76393:
URL: https://github.com/apache/airflow/pull/76393
`KubernetesPodOperator` waited out the full `startup_timeout` when an init
container's image could not be pulled.
`detect_pod_terminate_early_issues` scanned only
`status.container_statuses`. While init containers run, the main container
reports `PodInitializing`, which matches neither `FATAL_STATES` nor
`TRANSIENT_STATES`, so the detector returned `None` and the caller kept
polling. A typo in an init container image therefore cost the default 120s
instead of failing immediately.
The detector now scans `init_container_statuses` too, init containers first,
so a fatal init container image is reported ahead of the main container's
`PodInitializing`. This reaches all three callers: `await_pod_start`,
`await_pod_completion`, and the re-defer guard in `trigger_reentry`.
The error also names the stuck container now:
```
Image for container 'init' cannot be pulled, unable to start:
ImagePullBackOff
Back-off pulling image "nonexistent:latest"
```
Previously neither the raised error nor `_read_pod_container_states`
identified the container, and that log omits init containers entirely and runs
behind the non-default `log_events_on_failure`.
Builds on #65490, which introduced the transient-pattern allowlist this
reuses.
### Notes for reviewers
Two things the Gen-AI review checklist flags, both deliberate:
- **Two existing tests were modified.**
`test_start_pod_raises_fast_error_on_image_error` and its synchronous
counterpart changed because the error text now names the container. That is the
behaviour change itself, not an accommodation of a regression.
- **One added case passes without this branch.** The `main_container` half
of the `("InvalidImageName", '... "timeout-worker:Bad Tag"')` row is a
deliberate behaviour test. It pins the refactor to a single fatal/transient
condition, which is otherwise unguarded: mutating that condition so the fatal
branch also consults the message fails exactly those two cases and nothing
else. The `init_container` half does fail without the branch.
### Known related gap, not addressed here
The transient check matches the whole kubelet message, so a genuinely
missing image whose name happens to contain a transient pattern (for example
`timeout-worker`, which contains `timeout`) is still treated as transient and
waits out `startup_timeout`. That predates this change and has the same
user-visible symptom through a different trigger.
---
##### Was generative AI tooling used to co-author this PR?
- [X] Yes — Claude Code (Opus 5, 1M context)
Generated-by: Claude Code (Opus 5, 1M context) following [the
guidelines](https://github.com/apache/airflow/blob/main/contributing-docs/05_pull_requests.rst#gen-ai-assisted-contributions)
🤖 Generated with [Claude Code](https://claude.com/claude-code)
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: [email protected]
For queries about this service, please contact Infrastructure at:
[email protected]