Skip to content

Add cancellation handling to prevent UnobservedTaskException in Watcher#1827

Open
tg123 wants to merge 1 commit into
kubernetes-client:masterfrom
tg123:pr-1814
Open

Add cancellation handling to prevent UnobservedTaskException in Watcher#1827
tg123 wants to merge 1 commit into
kubernetes-client:masterfrom
tg123:pr-1814

Conversation

@tg123

@tg123 tg123 commented Jul 1, 2026

Copy link
Copy Markdown
Member

follow up copilot ver #1814
fix #1813

Cancelling a watch's CancellationToken while ReadLineAsync() is in flight left the original read task orphaned. When the transport tore the connection down, that task faulted with an unobserved IOException, surfacing as a TaskScheduler.UnobservedTaskException at finalization (e.g. during app shutdown).

Root cause: AttachCancellationToken in CreateWatchEventEnumerator wraps the read via task.ContinueWith(..., cancellationToken). On cancellation the continuation is cancelled immediately while the original ReadLineAsync() keeps running and later faults — with no one observing it.

Copilot AI review requested due to automatic review settings July 1, 2026 21:39
@kubernetes-prow

Copy link
Copy Markdown

[APPROVALNOTIFIER] This PR is APPROVED

This pull-request has been approved by: tg123

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

The pull request process is described 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

@kubernetes-prow kubernetes-prow Bot requested a review from brendandburns July 1, 2026 21:39
@kubernetes-prow kubernetes-prow Bot added approved Indicates a PR has been approved by an approver from all required OWNERS files. size/M Denotes a PR that changes 30-99 lines, ignoring generated files. cncf-cla: yes Indicates the PR's author has signed the CNCF CLA. labels Jul 1, 2026

Copilot AI 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.

Pull request overview

This PR fixes a watch-cancellation edge case where cancelling while an async read is in-flight can orphan the original task and later surface as TaskScheduler.UnobservedTaskException during finalization/shutdown.

Changes:

  • Update Watcher<T>.CreateWatchEventEnumerator to ensure faulted orphan tasks are observed, preventing UnobservedTaskException.
  • On newer TFMs, pass the CancellationToken directly into ReadLineAsync(...) to cancel the read itself.
  • Add a regression test that reproduces the orphaned-task scenario and asserts no UnobservedTaskException is raised.

Reviewed changes

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

File Description
src/KubernetesClient/Watcher.cs Ensures faulted orphan tasks are observed; uses cancellation-aware read on newer TFMs.
tests/KubernetesClient.Tests/WatchTests.cs Adds regression coverage to detect UnobservedTaskException during watch cancellation/fault scenarios.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +1040 to +1044
var unobservedExceptions = new List<Exception>();
void Handler(object sender, UnobservedTaskExceptionEventArgs e)
{
unobservedExceptions.Add(e.Exception);
}
await Task.Delay(50).ConfigureAwait(true);
}

Assert.Empty(unobservedExceptions);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

approved Indicates a PR has been approved by an approver from all required OWNERS files. cncf-cla: yes Indicates the PR's author has signed the CNCF CLA. size/M Denotes a PR that changes 30-99 lines, ignoring generated files.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

UnobservedTaskException from orphaned ReadLineAsync task in Watcher<T>.CreateWatchEventEnumerator during cancellation

2 participants