@@ -228,6 +228,12 @@ func (k *Bootstrapper) createCompatSymlinks() error {
228
228
229
229
// StartCluster starts the cluster
230
230
func (k * Bootstrapper ) StartCluster (k8s config.KubernetesConfig ) error {
231
+ start := time .Now ()
232
+ glog .Infof ("StartCluster: %+v" , k8s )
233
+ defer func () {
234
+ glog .Infof ("StartCluster complete in %s" , time .Since (start ))
235
+ }()
236
+
231
237
version , err := parseKubernetesVersion (k8s .KubernetesVersion )
232
238
if err != nil {
233
239
return errors .Wrap (err , "parsing kubernetes version" )
@@ -266,7 +272,15 @@ func (k *Bootstrapper) StartCluster(k8s config.KubernetesConfig) error {
266
272
267
273
glog .Infof ("Configuring cluster permissions ..." )
268
274
269
- if err := retry .Expo (elevateKubeSystemPrivileges , time .Millisecond * 500 , 60 * time .Second ); err != nil {
275
+ elevate := func () error {
276
+ client , err := k .client (k8s )
277
+ if err != nil {
278
+ return err
279
+ }
280
+ return elevateKubeSystemPrivileges (client )
281
+ }
282
+
283
+ if err := retry .Expo (elevate , time .Millisecond * 500 , 120 * time .Second ); err != nil {
270
284
return errors .Wrap (err , "timed out waiting to elevate kube-system RBAC privileges" )
271
285
}
272
286
@@ -326,6 +340,23 @@ func addAddons(files *[]assets.CopyableFile, data interface{}) error {
326
340
return nil
327
341
}
328
342
343
+ // client returns a Kubernetes client to use to speak to a kubeadm launched apiserver
344
+ func (k * Bootstrapper ) client (k8s config.KubernetesConfig ) (* kubernetes.Clientset , error ) {
345
+ // Catch case if WaitCluster was called with a stale ~/.kube/config
346
+ config , err := kapi .ClientConfig (k .contextName )
347
+ if err != nil {
348
+ return nil , errors .Wrap (err , "client config" )
349
+ }
350
+
351
+ endpoint := fmt .Sprintf ("https://%s:%d" , k8s .NodeIP , k8s .NodePort )
352
+ if config .Host != endpoint {
353
+ glog .Errorf ("Overriding stale ClientConfig host %s with %s" , config .Host , endpoint )
354
+ config .Host = endpoint
355
+ }
356
+
357
+ return kubernetes .NewForConfig (config )
358
+ }
359
+
329
360
// WaitCluster blocks until Kubernetes appears to be healthy.
330
361
func (k * Bootstrapper ) WaitCluster (k8s config.KubernetesConfig , timeout time.Duration ) error {
331
362
// Do not wait for "k8s-app" pods in the case of CNI, as they are managed
@@ -341,22 +372,11 @@ func (k *Bootstrapper) WaitCluster(k8s config.KubernetesConfig, timeout time.Dur
341
372
return errors .Wrap (err , "waiting for apiserver" )
342
373
}
343
374
344
- // Catch case if WaitCluster was called with a stale ~/.kube/config
345
- config , err := kapi .ClientConfig (k .contextName )
375
+ client , err := k .client (k8s )
346
376
if err != nil {
347
- return errors .Wrap (err , "client config" )
348
- }
349
-
350
- endpoint := fmt .Sprintf ("https://%s:%d" , k8s .NodeIP , k8s .NodePort )
351
- if config .Host != endpoint {
352
- glog .Errorf ("Overriding stale ClientConfig host %s with %s" , config .Host , endpoint )
353
- config .Host = endpoint
377
+ return errors .Wrap (err , "client" )
354
378
}
355
379
356
- client , err := kubernetes .NewForConfig (config )
357
- if err != nil {
358
- return errors .Wrap (err , "k8s client" )
359
- }
360
380
for _ , p := range PodsByLayer {
361
381
if componentsOnly && p .key != "component" { // skip component check if network plugin is cni
362
382
continue
@@ -458,8 +478,12 @@ func (k *Bootstrapper) waitForAPIServer(k8s config.KubernetesConfig) error {
458
478
return false , nil
459
479
}
460
480
return true , nil
481
+
482
+ // TODO: Check apiserver/kubelet logs for fatal errors so that users don't
483
+ // need to wait minutes to find out their flag didn't work.
484
+
461
485
}
462
- err = wait .PollImmediate (kconst .APICallRetryInterval , kconst .DefaultControlPlaneTimeout , f )
486
+ err = wait .PollImmediate (kconst .APICallRetryInterval , 2 * kconst .DefaultControlPlaneTimeout , f )
463
487
return err
464
488
}
465
489
0 commit comments