Skip to content

Commit ea19649

Browse files
committed
add validate to not allow mix --config with other arguments
1 parent da5edc1 commit ea19649

File tree

7 files changed

+132
-18
lines changed

7 files changed

+132
-18
lines changed

Diff for: cmd/kubeadm/app/apis/kubeadm/validation/BUILD

+2
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ go_test(
1515
tags = ["automanaged"],
1616
deps = [
1717
"//cmd/kubeadm/app/apis/kubeadm:go_default_library",
18+
"//vendor/github.com/spf13/pflag:go_default_library",
1819
"//vendor/k8s.io/apimachinery/pkg/util/validation/field:go_default_library",
1920
],
2021
)
@@ -30,6 +31,7 @@ go_library(
3031
"//pkg/api/validation:go_default_library",
3132
"//pkg/kubeapiserver/authorizer/modes:go_default_library",
3233
"//pkg/registry/core/service/ipallocator:go_default_library",
34+
"//vendor/github.com/spf13/pflag:go_default_library",
3335
"//vendor/k8s.io/apimachinery/pkg/util/validation:go_default_library",
3436
"//vendor/k8s.io/apimachinery/pkg/util/validation/field:go_default_library",
3537
],

Diff for: cmd/kubeadm/app/apis/kubeadm/validation/validation.go

+9
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,8 @@ import (
2424
"path/filepath"
2525
"strings"
2626

27+
"github.com/spf13/pflag"
28+
2729
"k8s.io/apimachinery/pkg/util/validation"
2830
"k8s.io/apimachinery/pkg/util/validation/field"
2931
"k8s.io/kubernetes/cmd/kubeadm/app/apis/kubeadm"
@@ -239,3 +241,10 @@ func ValidateCloudProvider(provider string, fldPath *field.Path) field.ErrorList
239241
allErrs = append(allErrs, field.Invalid(fldPath, provider, "cloudprovider not supported"))
240242
return allErrs
241243
}
244+
245+
func ValidateMixedArguments(flag *pflag.FlagSet) error {
246+
if flag.Changed("config") && flag.NFlag() != 1 {
247+
return fmt.Errorf("can not mix '--config' with other arguments")
248+
}
249+
return nil
250+
}

Diff for: cmd/kubeadm/app/apis/kubeadm/validation/validation_test.go

+41
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,8 @@ package validation
1919
import (
2020
"testing"
2121

22+
"github.com/spf13/pflag"
23+
2224
"k8s.io/apimachinery/pkg/util/validation/field"
2325
"k8s.io/kubernetes/cmd/kubeadm/app/apis/kubeadm"
2426
)
@@ -227,3 +229,42 @@ func TestValidateNodeConfiguration(t *testing.T) {
227229
}
228230
}
229231
}
232+
233+
func TestValidateMixedArguments(t *testing.T) {
234+
var tests = []struct {
235+
args []string
236+
expected bool
237+
}{
238+
{[]string{"--foo=bar"}, true},
239+
{[]string{"--config=hello"}, true},
240+
{[]string{"--foo=bar", "--config=hello"}, false},
241+
}
242+
243+
var cfgPath string
244+
var skipPreFlight bool
245+
246+
for _, rt := range tests {
247+
f := pflag.NewFlagSet("test", pflag.ContinueOnError)
248+
if f.Parsed() {
249+
t.Error("f.Parse() = true before Parse")
250+
}
251+
f.String("foo", "", "string value")
252+
f.StringVar(&cfgPath, "config", cfgPath, "Path to kubeadm config file")
253+
f.BoolVar(
254+
&skipPreFlight, "skip-preflight-checks", skipPreFlight,
255+
"Skip preflight checks normally run before modifying the system",
256+
)
257+
if err := f.Parse(rt.args); err != nil {
258+
t.Fatal(err)
259+
}
260+
261+
actual := ValidateMixedArguments(f)
262+
if (actual == nil) != rt.expected {
263+
t.Errorf(
264+
"failed ValidateMixedArguments:\n\texpected: %t\n\t actual: %t",
265+
rt.expected,
266+
(actual == nil),
267+
)
268+
}
269+
}
270+
}

Diff for: cmd/kubeadm/app/cmd/init.go

+5-2
Original file line numberDiff line numberDiff line change
@@ -83,7 +83,7 @@ func NewCmdInit(out io.Writer) *cobra.Command {
8383

8484
i, err := NewInit(cfgPath, internalcfg, skipPreFlight, skipTokenPrint)
8585
kubeadmutil.CheckErr(err)
86-
kubeadmutil.CheckErr(i.Validate())
86+
kubeadmutil.CheckErr(i.Validate(cmd))
8787
kubeadmutil.CheckErr(i.Run(out))
8888
},
8989
}
@@ -191,7 +191,10 @@ type Init struct {
191191
}
192192

193193
// Validate validates configuration passed to "kubeadm init"
194-
func (i *Init) Validate() error {
194+
func (i *Init) Validate(cmd *cobra.Command) error {
195+
if err := validation.ValidateMixedArguments(cmd.PersistentFlags()); err != nil {
196+
return err
197+
}
195198
return validation.ValidateMasterConfiguration(i.cfg).ToAggregate()
196199
}
197200

Diff for: cmd/kubeadm/app/cmd/join.go

+19-16
Original file line numberDiff line numberDiff line change
@@ -63,26 +63,26 @@ func NewCmdJoin(out io.Writer) *cobra.Command {
6363
Use: "join <flags> [DiscoveryTokenAPIServers]",
6464
Short: "Run this on any machine you wish to join an existing cluster",
6565
Long: dedent.Dedent(`
66-
When joining a kubeadm initialized cluster, we need to establish
67-
bidirectional trust. This is split into discovery (having the Node
68-
trust the Kubernetes Master) and TLS bootstrap (having the Kubernetes
66+
When joining a kubeadm initialized cluster, we need to establish
67+
bidirectional trust. This is split into discovery (having the Node
68+
trust the Kubernetes Master) and TLS bootstrap (having the Kubernetes
6969
Master trust the Node).
7070
71-
There are 2 main schemes for discovery. The first is to use a shared
72-
token along with the IP address of the API server. The second is to
73-
provide a file (a subset of the standard kubeconfig file). This file
74-
can be a local file or downloaded via an HTTPS URL. The forms are
75-
kubeadm join --discovery-token abcdef.1234567890abcdef 1.2.3.4:6443,
71+
There are 2 main schemes for discovery. The first is to use a shared
72+
token along with the IP address of the API server. The second is to
73+
provide a file (a subset of the standard kubeconfig file). This file
74+
can be a local file or downloaded via an HTTPS URL. The forms are
75+
kubeadm join --discovery-token abcdef.1234567890abcdef 1.2.3.4:6443,
7676
kubeadm join --discovery-file path/to/file.conf, or kubeadm join
77-
--discovery-file https://url/file.conf. Only one form can be used. If
78-
the discovery information is loaded from a URL, HTTPS must be used and
77+
--discovery-file https://url/file.conf. Only one form can be used. If
78+
the discovery information is loaded from a URL, HTTPS must be used and
7979
the host installed CA bundle is used to verify the connection.
8080
81-
The TLS bootstrap mechanism is also driven via a shared token. This is
81+
The TLS bootstrap mechanism is also driven via a shared token. This is
8282
used to temporarily authenticate with the Kubernetes Master to submit a
83-
certificate signing request (CSR) for a locally created key pair. By
84-
default kubeadm will set up the Kubernetes Master to automatically
85-
approve these signing requests. This token is passed in with the
83+
certificate signing request (CSR) for a locally created key pair. By
84+
default kubeadm will set up the Kubernetes Master to automatically
85+
approve these signing requests. This token is passed in with the
8686
--tls-bootstrap-token abcdef.1234567890abcdef flag.
8787
8888
Often times the same token is used for both parts. In this case, the
@@ -97,7 +97,7 @@ func NewCmdJoin(out io.Writer) *cobra.Command {
9797

9898
j, err := NewJoin(cfgPath, args, internalcfg, skipPreFlight)
9999
kubeadmutil.CheckErr(err)
100-
kubeadmutil.CheckErr(j.Validate())
100+
kubeadmutil.CheckErr(j.Validate(cmd))
101101
kubeadmutil.CheckErr(j.Run(out))
102102
},
103103
}
@@ -166,7 +166,10 @@ func NewJoin(cfgPath string, args []string, cfg *kubeadmapi.NodeConfiguration, s
166166
return &Join{cfg: cfg}, nil
167167
}
168168

169-
func (j *Join) Validate() error {
169+
func (j *Join) Validate(cmd *cobra.Command) error {
170+
if err := validation.ValidateMixedArguments(cmd.PersistentFlags()); err != nil {
171+
return err
172+
}
170173
return validation.ValidateNodeConfiguration(j.cfg).ToAggregate()
171174
}
172175

Diff for: cmd/kubeadm/test/cmd/init_test.go

+28
Original file line numberDiff line numberDiff line change
@@ -137,3 +137,31 @@ func TestCmdInitAPIPort(t *testing.T) {
137137
kubeadmReset()
138138
}
139139
}
140+
141+
func TestCmdInitArgsMixed(t *testing.T) {
142+
if *kubeadmCmdSkip {
143+
t.Log("kubeadm cmd tests being skipped")
144+
t.Skip()
145+
}
146+
147+
var initTest = []struct {
148+
args string
149+
expected bool
150+
}{
151+
{"--api-port=1000 --config=/etc/kubernets/kubeadm.config", false},
152+
}
153+
154+
for _, rt := range initTest {
155+
_, _, actual := RunCmd(*kubeadmPath, "init", rt.args, "--skip-preflight-checks")
156+
if (actual == nil) != rt.expected {
157+
t.Errorf(
158+
"failed CmdInitArgsMixed running 'kubeadm init %s' with an error: %v\n\texpected: %t\n\t actual: %t",
159+
rt.args,
160+
actual,
161+
rt.expected,
162+
(actual == nil),
163+
)
164+
}
165+
kubeadmReset()
166+
}
167+
}

Diff for: cmd/kubeadm/test/cmd/join_test.go

+28
Original file line numberDiff line numberDiff line change
@@ -191,3 +191,31 @@ func TestCmdJoinBadArgs(t *testing.T) {
191191
kubeadmReset()
192192
}
193193
}
194+
195+
func TestCmdJoinArgsMixed(t *testing.T) {
196+
if *kubeadmCmdSkip {
197+
t.Log("kubeadm cmd tests being skipped")
198+
t.Skip()
199+
}
200+
201+
var initTest = []struct {
202+
args string
203+
expected bool
204+
}{
205+
{"--discovery-token=abcdef.1234567890abcdef --config=/etc/kubernets/kubeadm.config", false},
206+
}
207+
208+
for _, rt := range initTest {
209+
_, _, actual := RunCmd(*kubeadmPath, "join", rt.args, "--skip-preflight-checks")
210+
if (actual == nil) != rt.expected {
211+
t.Errorf(
212+
"failed CmdJoinArgsMixed running 'kubeadm join %s' with an error: %v\n\texpected: %t\n\t actual: %t",
213+
rt.args,
214+
actual,
215+
rt.expected,
216+
(actual == nil),
217+
)
218+
}
219+
kubeadmReset()
220+
}
221+
}

0 commit comments

Comments
 (0)