mirror of
https://github.com/k3s-io/kubernetes.git
synced 2025-08-20 01:01:22 +00:00
apiserver: cancel context on timeout in WithTimeoutForNonLongRunningRequests
This commit is contained in:
parent
44ffcdd9c5
commit
f3ba7f9558
@ -18,6 +18,7 @@ package filters
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"bufio"
|
"bufio"
|
||||||
|
"context"
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
"fmt"
|
"fmt"
|
||||||
"net"
|
"net"
|
||||||
@ -54,14 +55,23 @@ func WithTimeoutForNonLongRunningRequests(handler http.Handler, requestContextMa
|
|||||||
if longRunning(req, requestInfo) {
|
if longRunning(req, requestInfo) {
|
||||||
return nil, nil, nil
|
return nil, nil, nil
|
||||||
}
|
}
|
||||||
metricFn := func() {
|
|
||||||
|
ctx, cancel := context.WithCancel(ctx)
|
||||||
|
if err := requestContextMapper.Update(req, ctx); err != nil {
|
||||||
|
return time.After(timeout), func() {}, apierrors.NewInternalError(fmt.Errorf("failed to update context during timeout"))
|
||||||
|
}
|
||||||
|
|
||||||
|
postTimeoutFn := func() {
|
||||||
|
cancel()
|
||||||
metrics.Record(req, requestInfo, "", http.StatusGatewayTimeout, 0, 0)
|
metrics.Record(req, requestInfo, "", http.StatusGatewayTimeout, 0, 0)
|
||||||
}
|
}
|
||||||
return time.After(timeout), metricFn, apierrors.NewTimeoutError(fmt.Sprintf("request did not complete within %s", timeout), 0)
|
return time.After(timeout), postTimeoutFn, apierrors.NewTimeoutError(fmt.Sprintf("request did not complete within %s", timeout), 0)
|
||||||
}
|
}
|
||||||
return WithTimeout(handler, timeoutFunc)
|
return WithTimeout(handler, timeoutFunc)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type timeoutFunc = func(*http.Request) (timeout <-chan time.Time, postTimeoutFunc func(), err *apierrors.StatusError)
|
||||||
|
|
||||||
// WithTimeout returns an http.Handler that runs h with a timeout
|
// WithTimeout returns an http.Handler that runs h with a timeout
|
||||||
// determined by timeoutFunc. The new http.Handler calls h.ServeHTTP to handle
|
// determined by timeoutFunc. The new http.Handler calls h.ServeHTTP to handle
|
||||||
// each request, but if a call runs for longer than its time limit, the
|
// each request, but if a call runs for longer than its time limit, the
|
||||||
@ -71,17 +81,17 @@ func WithTimeoutForNonLongRunningRequests(handler http.Handler, requestContextMa
|
|||||||
// http.ErrHandlerTimeout. If timeoutFunc returns a nil timeout channel, no
|
// http.ErrHandlerTimeout. If timeoutFunc returns a nil timeout channel, no
|
||||||
// timeout will be enforced. recordFn is a function that will be invoked whenever
|
// timeout will be enforced. recordFn is a function that will be invoked whenever
|
||||||
// a timeout happens.
|
// a timeout happens.
|
||||||
func WithTimeout(h http.Handler, timeoutFunc func(*http.Request) (timeout <-chan time.Time, recordFn func(), err *apierrors.StatusError)) http.Handler {
|
func WithTimeout(h http.Handler, timeoutFunc timeoutFunc) http.Handler {
|
||||||
return &timeoutHandler{h, timeoutFunc}
|
return &timeoutHandler{h, timeoutFunc}
|
||||||
}
|
}
|
||||||
|
|
||||||
type timeoutHandler struct {
|
type timeoutHandler struct {
|
||||||
handler http.Handler
|
handler http.Handler
|
||||||
timeout func(*http.Request) (<-chan time.Time, func(), *apierrors.StatusError)
|
timeout timeoutFunc
|
||||||
}
|
}
|
||||||
|
|
||||||
func (t *timeoutHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
func (t *timeoutHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
||||||
after, recordFn, err := t.timeout(r)
|
after, postTimeoutFn, err := t.timeout(r)
|
||||||
if after == nil {
|
if after == nil {
|
||||||
t.handler.ServeHTTP(w, r)
|
t.handler.ServeHTTP(w, r)
|
||||||
return
|
return
|
||||||
@ -97,7 +107,7 @@ func (t *timeoutHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
|||||||
case <-done:
|
case <-done:
|
||||||
return
|
return
|
||||||
case <-after:
|
case <-after:
|
||||||
recordFn()
|
postTimeoutFn()
|
||||||
tw.timeout(err)
|
tw.timeout(err)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user