Skip to content

Commit cefc0bc

Browse files
authored
Merge pull request #224 from covexo/issue-218
resolve #218
2 parents f97a288 + ea3cbd6 commit cefc0bc

3 files changed

Lines changed: 118 additions & 28 deletions

File tree

cmd/init.go

Lines changed: 90 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,10 @@ import (
77
"strconv"
88
"strings"
99

10+
"github.com/covexo/devspace/pkg/devspace/clients/kubectl"
11+
12+
"github.com/covexo/devspace/pkg/devspace/builder/docker"
13+
1014
"github.com/covexo/devspace/pkg/devspace/config/configutil"
1115
"github.com/covexo/devspace/pkg/devspace/generator"
1216
"github.com/covexo/devspace/pkg/util/log"
@@ -421,10 +425,31 @@ func (cmd *InitCmd) configureKubernetes() {
421425
}
422426

423427
func (cmd *InitCmd) configureRegistry() {
428+
dockerUsername := ""
429+
createInternalRegistryDefaultAnswer := "yes"
430+
431+
var imageBuilder *docker.Builder
432+
var dockerBuilderErr error
433+
434+
imageBuilder, dockerBuilderErr = docker.NewBuilder("", "", "", false)
435+
436+
if dockerBuilderErr == nil {
437+
log.StartWait("Checking Docker credentials")
438+
dockerAuthConfig, dockerAuthErr := imageBuilder.Authenticate("", "", true)
439+
log.StopWait()
440+
441+
if dockerAuthErr == nil {
442+
dockerUsername = dockerAuthConfig.Username
443+
444+
if dockerUsername != "" {
445+
createInternalRegistryDefaultAnswer = "no"
446+
}
447+
}
448+
}
424449
internalRegistryConfig := cmd.config.Services.InternalRegistry
425450
createInternalRegistry := stdinutil.GetFromStdin(&stdinutil.GetFromStdinParams{
426451
Question: "Should we create a private registry within your Kubernetes cluster for you? (yes | no)",
427-
DefaultValue: "yes",
452+
DefaultValue: createInternalRegistryDefaultAnswer,
428453
ValidationRegexPattern: "^(yes)|(no)$",
429454
})
430455

@@ -437,22 +462,77 @@ func (cmd *InitCmd) configureRegistry() {
437462

438463
cmd.defaultRegistry.URL = registryURL
439464
internalRegistryConfig = nil
465+
loginWarningServer := ""
466+
467+
if dockerUsername == "" {
468+
if *registryURL != "hub.docker.com" {
469+
loginWarningServer = " " + *registryURL
470+
imageBuilder, dockerBuilderErr = docker.NewBuilder(*registryURL, "", "", false)
471+
}
472+
473+
if dockerBuilderErr == nil {
474+
log.StartWait("Checking Docker credentials")
475+
dockerAuthConfig, dockerAuthErr := imageBuilder.Authenticate("", "", true)
476+
log.StopWait()
477+
478+
if dockerAuthErr == nil {
479+
dockerUsername = dockerAuthConfig.Username
480+
}
481+
}
482+
}
483+
484+
if dockerUsername == "" {
485+
if cmd.defaultImage.Build.Engine.Docker != nil {
486+
log.Fatal("Make sure you login to the registry with: docker login" + loginWarningServer)
487+
} else {
488+
registryMapOverwrite := *cmd.overwriteConfig.Registries
489+
defaultRegistryOverwrite, defaultRegistryOverwriteDefined := registryMapOverwrite["default"]
490+
491+
if !defaultRegistryOverwriteDefined {
492+
defaultRegistryOverwrite = &v1.RegistryConfig{}
493+
registryMapOverwrite["default"] = defaultRegistryOverwrite
494+
}
495+
496+
if defaultRegistryOverwrite.Auth == nil {
497+
defaultRegistryOverwrite.Auth = &v1.RegistryAuth{}
498+
}
499+
500+
if defaultRegistryOverwrite.Auth.Username == nil {
501+
defaultRegistryOverwrite.Auth.Username = configutil.String("")
502+
}
503+
504+
defaultRegistryOverwrite.Auth.Username = stdinutil.GetFromStdin(&stdinutil.GetFromStdinParams{
505+
Question: "Which username do you want to use to push images to " + *registryURL + "?",
506+
DefaultValue: *defaultRegistryOverwrite.Auth.Username,
507+
ValidationRegexPattern: "^[a-zA-Z0-9]{4,30}$",
508+
})
509+
dockerUsername = *defaultRegistryOverwrite.Auth.Username
510+
511+
if defaultRegistryOverwrite.Auth.Password == nil {
512+
defaultRegistryOverwrite.Auth.Password = configutil.String("")
513+
}
514+
515+
defaultRegistryOverwrite.Auth.Username = stdinutil.GetFromStdin(&stdinutil.GetFromStdinParams{
516+
Question: "Which password do you want to use to push images to " + *registryURL + "?",
517+
DefaultValue: *defaultRegistryOverwrite.Auth.Password,
518+
ValidationRegexPattern: "^.*$",
519+
})
520+
}
521+
}
440522

441523
if *registryURL == "hub.docker.com" {
442524
defaultImageName := *cmd.defaultImage.Name
443525
defaultImageNameParts := strings.Split(defaultImageName, "/")
444-
existingDockerUsername := ""
445526

446-
if len(defaultImageNameParts) > 1 {
447-
existingDockerUsername = defaultImageNameParts[0]
527+
if len(defaultImageNameParts) < 2 {
528+
defaultImageName = dockerUsername + "/" + strings.TrimPrefix(defaultImageName, dockerUsername)
448529
}
449530

450-
dockerUsername := stdinutil.GetFromStdin(&stdinutil.GetFromStdinParams{
451-
Question: "What is your Docker username?",
452-
DefaultValue: existingDockerUsername,
531+
cmd.defaultImage.Name = stdinutil.GetFromStdin(&stdinutil.GetFromStdinParams{
532+
Question: "Which image name do you want to use on Docker Hub?",
533+
DefaultValue: defaultImageName,
453534
ValidationRegexPattern: "^[a-zA-Z0-9]{4,30}$",
454535
})
455-
cmd.defaultImage.Name = configutil.String(*dockerUsername + "/" + strings.TrimPrefix(defaultImageName, *dockerUsername))
456536
}
457537
} else {
458538
imageMap := *cmd.config.Images
@@ -537,6 +617,8 @@ func (cmd *InitCmd) configureRegistry() {
537617
},
538618
},
539619
}
620+
} else if kubectl.IsMinikube() == false {
621+
log.Warn("Your Kubernetes cluster will not be able to pull images from a registry without a registry domain!\n")
540622
}
541623
}
542624
secrets, registryHasSecrets := registryReleaseValues["secrets"]

pkg/devspace/builder/docker/client.go

Lines changed: 7 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -2,20 +2,20 @@ package docker
22

33
import (
44
"context"
5+
"errors"
56
"fmt"
67
"net/http"
78
"os/exec"
89
"path/filepath"
910
"strings"
1011

12+
"github.com/covexo/devspace/pkg/devspace/clients/kubectl"
13+
1114
"github.com/docker/docker/api"
1215
"github.com/docker/docker/client"
1316
"github.com/docker/go-connections/tlsconfig"
14-
"k8s.io/client-go/tools/clientcmd"
1517
)
1618

17-
var isMinikubeVar *bool
18-
1919
func newDockerClientFromEnvironment() (client.CommonAPIClient, error) {
2020
cli, err := client.NewClientWithOpts(client.FromEnv)
2121
if err != nil {
@@ -27,6 +27,10 @@ func newDockerClientFromEnvironment() (client.CommonAPIClient, error) {
2727
}
2828

2929
func newDockerClientFromMinikube() (client.CommonAPIClient, error) {
30+
if kubectl.IsMinikube() == false {
31+
return nil, errors.New("Cluster is not a minikube cluster")
32+
}
33+
3034
env, err := getMinikubeEnvironment()
3135
if err != nil {
3236
return nil, err
@@ -65,23 +69,6 @@ func newDockerClientFromMinikube() (client.CommonAPIClient, error) {
6569
return client.NewClient(host, version, httpclient, nil)
6670
}
6771

68-
func isMinikube() bool {
69-
if isMinikubeVar == nil {
70-
loadingRules := clientcmd.NewDefaultClientConfigLoadingRules()
71-
kubeConfig := clientcmd.NewNonInteractiveDeferredLoadingClientConfig(loadingRules, &clientcmd.ConfigOverrides{})
72-
cfg, err := kubeConfig.RawConfig()
73-
74-
if err != nil {
75-
return false
76-
}
77-
78-
isMinikube := cfg.CurrentContext == "minikube"
79-
isMinikubeVar = &isMinikube
80-
}
81-
82-
return *isMinikubeVar
83-
}
84-
8572
func getMinikubeEnvironment() (map[string]string, error) {
8673
cmd := exec.Command("minikube", "docker-env", "--shell", "none")
8774
out, err := cmd.Output()

pkg/devspace/clients/kubectl/client.go

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ import (
1616
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
1717
"k8s.io/client-go/kubernetes"
1818
"k8s.io/client-go/rest"
19+
"k8s.io/client-go/tools/clientcmd"
1920
"k8s.io/client-go/tools/portforward"
2021
"k8s.io/client-go/tools/remotecommand"
2122
"k8s.io/client-go/transport/spdy"
@@ -28,6 +29,8 @@ import (
2829
"k8s.io/kubernetes/pkg/util/node"
2930
)
3031

32+
var isMinikubeVar *bool
33+
3134
//NewClient creates a new kubernetes client
3235
func NewClient() (*kubernetes.Clientset, error) {
3336
config, err := GetClientConfig()
@@ -39,6 +42,24 @@ func NewClient() (*kubernetes.Clientset, error) {
3942
return kubernetes.NewForConfig(config)
4043
}
4144

45+
// IsMinikube returns true if the Kubernetes cluster is a minikube
46+
func IsMinikube() bool {
47+
if isMinikubeVar == nil {
48+
loadingRules := clientcmd.NewDefaultClientConfigLoadingRules()
49+
kubeConfig := clientcmd.NewNonInteractiveDeferredLoadingClientConfig(loadingRules, &clientcmd.ConfigOverrides{})
50+
cfg, err := kubeConfig.RawConfig()
51+
52+
if err != nil {
53+
return false
54+
}
55+
56+
isMinikube := cfg.CurrentContext == "minikube"
57+
isMinikubeVar = &isMinikube
58+
}
59+
60+
return *isMinikubeVar
61+
}
62+
4263
// GetFirstRunningPod retrieves the first pod that is found that has the status "Running" using the label selector string
4364
func GetFirstRunningPod(kubectl *kubernetes.Clientset, labelSelector, namespace string) (*k8sv1.Pod, error) {
4465
podList, err := kubectl.Core().Pods(namespace).List(metav1.ListOptions{

0 commit comments

Comments
 (0)