feat: support portforwarding over websocket (#2894)
* feat: support portforwarding over websocket * replicating kubectl implementation * update readmemine
parent
6b5d24f574
commit
c2f0962cfc
|
|
@ -563,6 +563,13 @@ In order to surface hotkeys globally please follow these steps:
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
|
## Port Forwarding over websockets
|
||||||
|
|
||||||
|
K9s follows `kubectl` feature flag environment variables to enable/disable port-forwarding over websockets. (default enabled in >1.30)
|
||||||
|
To disable Websocket support, set `KUBECTL_PORT_FORWARD_WEBSOCKETS=false`
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
## FastForwards
|
## FastForwards
|
||||||
|
|
||||||
As of v0.25.0, you can leverage the `FastForwards` feature to tell K9s how to default port-forwards. In situations where you are dealing with multiple containers or containers exposing multiple ports, it can be cumbersome to specify the desired port-forward from the dialog as in most cases, you already know which container/port tuple you desire. For these use cases, you can now annotate your manifests with the following annotations:
|
As of v0.25.0, you can leverage the `FastForwards` feature to tell K9s how to default port-forwards. In situations where you are dealing with multiple containers or containers exposing multiple ports, it can be cumbersome to specify the desired port-forward from the dialog as in most cases, you already know which container/port tuple you desire. For these use cases, you can now annotate your manifests with the following annotations:
|
||||||
|
|
|
||||||
|
|
@ -18,10 +18,12 @@ import (
|
||||||
"k8s.io/apimachinery/pkg/runtime"
|
"k8s.io/apimachinery/pkg/runtime"
|
||||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||||
"k8s.io/apimachinery/pkg/runtime/serializer"
|
"k8s.io/apimachinery/pkg/runtime/serializer"
|
||||||
|
"k8s.io/apimachinery/pkg/util/httpstream"
|
||||||
"k8s.io/cli-runtime/pkg/genericclioptions"
|
"k8s.io/cli-runtime/pkg/genericclioptions"
|
||||||
"k8s.io/client-go/rest"
|
"k8s.io/client-go/rest"
|
||||||
"k8s.io/client-go/tools/portforward"
|
"k8s.io/client-go/tools/portforward"
|
||||||
"k8s.io/client-go/transport/spdy"
|
"k8s.io/client-go/transport/spdy"
|
||||||
|
cmdutil "k8s.io/kubectl/pkg/cmd/util"
|
||||||
)
|
)
|
||||||
|
|
||||||
const defaultTimeout = 30 * time.Second
|
const defaultTimeout = 30 * time.Second
|
||||||
|
|
@ -181,6 +183,18 @@ func (p *PortForwarder) forwardPorts(method string, url *url.URL, addr, portMap
|
||||||
}
|
}
|
||||||
dialer := spdy.NewDialer(upgrader, &http.Client{Transport: transport, Timeout: defaultTimeout}, method, url)
|
dialer := spdy.NewDialer(upgrader, &http.Client{Transport: transport, Timeout: defaultTimeout}, method, url)
|
||||||
|
|
||||||
|
if !cmdutil.PortForwardWebsockets.IsDisabled() {
|
||||||
|
tunnelingDialer, err := portforward.NewSPDYOverWebsocketDialer(url, cfg)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
// First attempt tunneling (websocket) dialer, then fallback to spdy dialer.
|
||||||
|
dialer = portforward.NewFallbackDialer(tunnelingDialer, dialer, func(err error) bool {
|
||||||
|
return httpstream.IsUpgradeFailure(err) || httpstream.IsHTTPSProxyError(err)
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
return portforward.NewOnAddresses(dialer, []string{addr}, []string{portMap}, p.stopChan, p.readyChan, p.Out, p.ErrOut)
|
return portforward.NewOnAddresses(dialer, []string{addr}, []string{portMap}, p.stopChan, p.readyChan, p.Out, p.ErrOut)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue