Skip to content

[v17] fix: prevent panic in httputils.Forwarder on client cancellation#55767

Merged
tigrato merged 1 commit intobranch/v17from
bot/backport-55764-branch/v17
Jun 16, 2025
Merged

[v17] fix: prevent panic in httputils.Forwarder on client cancellation#55767
tigrato merged 1 commit intobranch/v17from
bot/backport-55764-branch/v17

Conversation

@tigrato
Copy link
Copy Markdown
Contributor

@tigrato tigrato commented Jun 16, 2025

Backport #55764 to branch/v17

changelog: Fixes a memory leak in Kubernetes Access caused by resources not being cleaned up when clients terminate watch streams.

@github-actions github-actions Bot requested review from espadolini and mjsmithnh June 16, 2025 15:18
@github-actions github-actions Bot requested a review from rosstimothy June 16, 2025 15:18
@tigrato tigrato force-pushed the bot/backport-55764-branch/v17 branch 2 times, most recently from 6efd3c9 to 582a025 Compare June 16, 2025 15:35
@public-teleport-github-review-bot public-teleport-github-review-bot Bot removed the request for review from mjsmithnh June 16, 2025 15:43
…55764)

* fix: prevent panic in `httputils.Forwarder` on client cancellation

Kubernetes Watchers are usually a long-lived HTTP request where the
server pushes new updates to clients. When clients are no longer
interested in the stream because they already received the information
they were looking for, the client cancels the request. The request
cancellation is propagated via context cancelation.

Go's `httputils.ReverseProxy` has a special handling for cases where the
read or write body operations fail. This happens when the client
initially started the request, receive the contents and then cancelled
it. The reverse proxy sees the error as `context.Canceled` error - i.e.
the client canceled it - but
[`copyBuffer`](https://cs.opensource.google/go/go/+/refs/tags/go1.24.4:src/net/http/httputil/reverseproxy.go;l=664-669;drc=e64f7ef03fdfa1c0d847c21b16c9302cc824e79b)
only has a special case for `io.EOF`. This means that `context.Canceled`
error is propagated to [`ServeHTTP`](https://cs.opensource.google/go/go/+/refs/tags/go1.24.4:src/net/http/httputil/reverseproxy.go;l=520-530;drc=e64f7ef03fdfa1c0d847c21b16c9302cc824e79b)
and hits the `shouldPanicOnCopyError` function. This function checks if
the function should panic or not. Since we are running inside
`http.Server`, the decision is always to panic which caused all
watcher resources to never cleanup and accumulate.

This PR changes the logic of our `httputils.Forwarder` to remove the
`http.ServerContextKey` to avoid any panic. It also fixes a possible
deadlock caused by incorrect condition.

Changes:
- Remove http.ServerContextKey from httputils.Forwarder to prevent panic
- Fix potential deadlock caused by incorrect condition

This ensures graceful handling of client cancellations and proper
resource cleanup for Kubernetes Watchers.

Signed-off-by: Tiago Silva <tiago.silva@goteleport.com>

* Update lib/httplib/reverseproxy/reverse_proxy.go

Co-authored-by: rosstimothy <39066650+rosstimothy@users.noreply.github.com>

---------

Signed-off-by: Tiago Silva <tiago.silva@goteleport.com>
Co-authored-by: rosstimothy <39066650+rosstimothy@users.noreply.github.com>
@tigrato tigrato force-pushed the bot/backport-55764-branch/v17 branch from 582a025 to 0475d36 Compare June 16, 2025 15:44
@tigrato tigrato added this pull request to the merge queue Jun 16, 2025
Merged via the queue into branch/v17 with commit a88dea7 Jun 16, 2025
38 checks passed
@tigrato tigrato deleted the bot/backport-55764-branch/v17 branch June 16, 2025 16:53
@fheinecke fheinecke mentioned this pull request Jul 1, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants