Backport: Fix exec parameter parsing (#580) (#604)

* Fix exec parameter parsing (#580)

Exec seems to be broken by ad6fbba806
This change basically copies what's in remotecommand.NewOptions, just
without the logging.

(cherry picked from commit 449eb3bb7d)

* Don't set cancel function to nil on error

Backported from ceb9b16c5c
This commit is contained in:
Brian Goff
2019-05-06 11:32:34 -07:00
committed by GitHub
parent 686cdb8b36
commit 7b92d1eee2
3 changed files with 33 additions and 23 deletions

1
Gopkg.lock generated
View File

@@ -1905,6 +1905,7 @@
"k8s.io/client-go/tools/watch", "k8s.io/client-go/tools/watch",
"k8s.io/client-go/util/workqueue", "k8s.io/client-go/util/workqueue",
"k8s.io/kubernetes/pkg/api/v1/pod", "k8s.io/kubernetes/pkg/api/v1/pod",
"k8s.io/kubernetes/pkg/apis/core",
"k8s.io/kubernetes/pkg/apis/core/pods", "k8s.io/kubernetes/pkg/apis/core/pods",
"k8s.io/kubernetes/pkg/fieldpath", "k8s.io/kubernetes/pkg/fieldpath",
"k8s.io/kubernetes/pkg/kubelet/apis/cri/runtime/v1alpha2", "k8s.io/kubernetes/pkg/kubelet/apis/cri/runtime/v1alpha2",

View File

@@ -44,9 +44,9 @@ func loadTLSConfig(certPath, keyPath string) (*tls.Config, error) {
}, nil }, nil
} }
func setupHTTPServer(ctx context.Context, cfg *apiServerConfig) (cancel func(), retErr error) { func setupHTTPServer(ctx context.Context, cfg *apiServerConfig) (_ func(), retErr error) {
var closers []io.Closer var closers []io.Closer
cancel = func() { cancel := func() {
for _, c := range closers { for _, c := range closers {
c.Close() c.Close()
} }

View File

@@ -6,7 +6,10 @@ import (
"strings" "strings"
"time" "time"
"github.com/cpuguy83/strongerrors"
"github.com/gorilla/mux" "github.com/gorilla/mux"
"github.com/pkg/errors"
api "k8s.io/kubernetes/pkg/apis/core"
"k8s.io/kubernetes/pkg/kubelet/server/remotecommand" "k8s.io/kubernetes/pkg/kubelet/server/remotecommand"
) )
@@ -14,7 +17,7 @@ import (
// Note that this handler currently depends on gorrilla/mux to get url parts as variables. // Note that this handler currently depends on gorrilla/mux to get url parts as variables.
// TODO(@cpuguy83): don't force gorilla/mux on consumers of this function // TODO(@cpuguy83): don't force gorilla/mux on consumers of this function
func PodExecHandlerFunc(backend remotecommand.Executor) http.HandlerFunc { func PodExecHandlerFunc(backend remotecommand.Executor) http.HandlerFunc {
return func(w http.ResponseWriter, req *http.Request) { return handleError(func(w http.ResponseWriter, req *http.Request) error {
vars := mux.Vars(req) vars := mux.Vars(req)
namespace := vars["namespace"] namespace := vars["namespace"]
@@ -26,30 +29,36 @@ func PodExecHandlerFunc(backend remotecommand.Executor) http.HandlerFunc {
q := req.URL.Query() q := req.URL.Query()
command := q["command"] command := q["command"]
var stdin, stdout, stderr, tty bool streamOpts, err := getExecOptions(req)
if q.Get("stdin") == "true" { if err != nil {
stdin = true return strongerrors.InvalidArgument(err)
}
if q.Get("stdout") == "true" {
stdout = true
}
if q.Get("stderr") == "true" {
stderr = true
}
if q.Get("tty") == "true" {
tty = true
}
streamOpts := &remotecommand.Options{
Stdin: stdin,
Stdout: stdout,
Stderr: stderr,
TTY: tty,
} }
idleTimeout := time.Second * 30 idleTimeout := time.Second * 30
streamCreationTimeout := time.Second * 30 streamCreationTimeout := time.Second * 30
remotecommand.ServeExec(w, req, backend, fmt.Sprintf("%s-%s", namespace, pod), "", container, command, streamOpts, idleTimeout, streamCreationTimeout, supportedStreamProtocols) remotecommand.ServeExec(w, req, backend, fmt.Sprintf("%s-%s", namespace, pod), "", container, command, streamOpts, idleTimeout, streamCreationTimeout, supportedStreamProtocols)
} return nil
})
}
func getExecOptions(req *http.Request) (*remotecommand.Options, error) {
tty := req.FormValue(api.ExecTTYParam) == "1"
stdin := req.FormValue(api.ExecStdinParam) == "1"
stdout := req.FormValue(api.ExecStdoutParam) == "1"
stderr := req.FormValue(api.ExecStderrParam) == "1"
if tty && stderr {
return nil, errors.New("cannot exec with tty and stderr")
}
if !stdin && !stdout && !stderr {
return nil, errors.New("you must specify at least one of stdin, stdout, stderr")
}
return &remotecommand.Options{
Stdin: stdin,
Stdout: stdout,
Stderr: stderr,
TTY: tty,
}, nil
} }