Skip to content

fix(trainer): resolve E2E log streaming incompatibility with kubernetes client v35+#504

Open
HKanoje wants to merge 1 commit into
kubeflow:mainfrom
HKanoje:fix/kubernetes-log-streaming-compatibility
Open

fix(trainer): resolve E2E log streaming incompatibility with kubernetes client v35+#504
HKanoje wants to merge 1 commit into
kubeflow:mainfrom
HKanoje:fix/kubernetes-log-streaming-compatibility

Conversation

@HKanoje
Copy link
Copy Markdown
Contributor

@HKanoje HKanoje commented May 26, 2026

Fix log streaming to properly yield line-terminated chunks instead of raw 64KB byte buffers, maintaining Iterator[str] contract for caller code.

Changes

  • Replace watch.Watch().stream() with response.stream() for pod log streaming
  • Pass _preload_content=False to read_namespaced_pod_log when following logs
  • Remove unused watch import that caused ApiTypeError in newer kubernetes versions
  • Update mock_read_namespaced_pod_log to support streaming responses
  • Add parameterized test case for get_job_logs with follow=True

Issue

Fixes the RuntimeError in E2E tests: 'Got an unexpected keyword argument watch to method read_namespaced_pod_log' which occurs with kubernetes client >= 35.0.0

…ubernetes client v35+

- Replace watch.Watch().stream() with response.stream() for pod log streaming
- Pass _preload_content=False to read_namespaced_pod_log when following logs
- Remove unused watch import that caused ApiTypeError in newer kubernetes versions
- Update mock_read_namespaced_pod_log to support streaming responses
- Add parameterized test case for get_job_logs with follow=True

Fixes the RuntimeError in E2E tests: 'Got an unexpected keyword argument watch
to method read_namespaced_pod_log' which occurs with kubernetes client >= 35.0.0

Signed-off-by: HKanoje <hrithik.kanoje@gmail.com>
Copilot AI review requested due to automatic review settings May 26, 2026 01:10
@google-oss-prow
Copy link
Copy Markdown
Contributor

[APPROVALNOTIFIER] This PR is NOT APPROVED

This pull-request has been approved by:
Once this PR has been reviewed and has the lgtm label, please assign electronic-waste for approval. For more information see the Kubernetes Code Review Process.

The full list of commands accepted by this bot can be found here.

Details Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

Note

Copilot was unable to run its full agentic suite in this review.

This PR updates Kubernetes pod log streaming to use a streaming HTTP response (_preload_content=False) instead of watch.Watch().stream, and extends unit tests to cover follow=True behavior.

Changes:

  • Switch _read_pod_logs(..., follow=True) to stream via read_namespaced_pod_log(..., _preload_content=False) and response.stream()
  • Add a streaming-capable mock for read_namespaced_pod_log in tests
  • Add a new test case validating get_job_logs(..., follow=True) behavior

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 4 comments.

File Description
kubeflow/trainer/backends/kubernetes/backend.py Replaces Watch-based streaming with HTTPResponse streaming for follow=True pod logs.
kubeflow/trainer/backends/kubernetes/backend_test.py Extends mocking/test cases to validate streaming logs via follow=True.

Comment on lines +619 to +623
# Stream logs incrementally using response.stream().
for line in response.stream():
if line:
# Decode bytes to string and yield each line.
yield line.decode("utf-8").rstrip("\n")
Comment on lines +619 to +623
# Stream logs incrementally using response.stream().
for line in response.stream():
if line:
# Decode bytes to string and yield each line.
yield line.decode("utf-8").rstrip("\n")
Comment on lines +456 to +466
# Handle streaming case: when _preload_content=False and follow=True
if kwargs.get("_preload_content") is False and kwargs.get("follow") is True:
# Return a mock response object with a stream() method
mock_response = Mock()

def mock_stream():
"""Mock stream generator that yields log lines as bytes."""
yield b"test log content"

mock_response.stream = mock_stream
return mock_response
Comment on lines +1435 to +1440
TestCase(
name="valid flow with follow=True for streaming logs",
expected_status=SUCCESS,
config={"name": BASIC_TRAIN_JOB_NAME, "follow": True},
expected_output=["test log content"],
),
@HKanoje HKanoje changed the title fix(trainer/kubernetes): fix E2E log streaming incompatibility with kubernetes client v35+ fix(trainer): resolve E2E log streaming incompatibility with kubernetes client v35+ May 26, 2026
@Fiona-Waters
Copy link
Copy Markdown
Contributor

Fiona-Waters commented May 27, 2026

This issue is being tracked upstream in kubernetes python client - kubernetes-client/python#2596 (comment)
We should wait for this fix, or we could pin kubernetes<36 until it's fixed
wdyt @andreyvelich @tariq-hasan ?

@tariq-hasan
Copy link
Copy Markdown
Member

There's no definite timeline yet for a patch release for the bug.

There has been a recent 36.0.1 which has been breaking the tests again because it does not address the logging error.

I suppose best to pin <36.0.0.

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

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants