Skip to content

Commit

Permalink
Merge pull request #7984 from medyagh/detect_windows_container
Browse files Browse the repository at this point in the history
Detect windows container and exit with instructions
  • Loading branch information
medyagh committed May 4, 2020
2 parents 9c77eda + 85aa970 commit e0685c8
Show file tree
Hide file tree
Showing 7 changed files with 72 additions and 6 deletions.
9 changes: 9 additions & 0 deletions cmd/minikube/cmd/start.go
Original file line number Diff line number Diff line change
Expand Up @@ -156,6 +156,15 @@ func runStart(cmd *cobra.Command, args []string) {
ds, alts, specified := selectDriver(existing)
starter, err := provisionWithDriver(cmd, ds, existing)
if err != nil {
if errors.Is(err, oci.ErrWindowsContainers) {
out.ErrLn("")
out.ErrT(out.Conflict, "Your Docker Desktop container os type is Windows but Linux is required.")
out.T(out.Warning, "Please change Docker settings to use Linux containers instead of Windows containers.")
out.T(out.Documentation, "https://minikube.sigs.k8s.io/docs/drivers/docker/#verify-docker-container-type-is-linux")
exit.UsageT(`You can verify your Docker container type by running:
{{.command}}
`, out.V{"command": "docker info --format '{{.OSType}}'"})
}
if specified {
// If the user specified a driver, don't fallback to anything else
exit.WithError("error provisioning host", err)
Expand Down
22 changes: 22 additions & 0 deletions pkg/drivers/kic/oci/errors.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
/*
Copyright 2020 The Kubernetes Authors All rights reserved.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/

package oci

import "errors"

// ErrWindowsContainers is thrown when docker been configured to run windows containers instead of Linux
var ErrWindowsContainers = errors.New("docker container type is windows")
7 changes: 5 additions & 2 deletions pkg/drivers/kic/oci/info.go
Original file line number Diff line number Diff line change
Expand Up @@ -27,8 +27,9 @@ import (

// SysInfo Info represents common system Information between docker and podman that minikube cares
type SysInfo struct {
CPUs int // CPUs is Number of CPUs
TotalMemory int64 // TotalMemory Total available ram
CPUs int // CPUs is Number of CPUs
TotalMemory int64 // TotalMemory Total available ram
OSType string // container's OsType (windows or linux)
}

// DaemonInfo returns common docker/podman daemon system info that minikube cares about
Expand All @@ -38,11 +39,13 @@ func DaemonInfo(ociBin string) (SysInfo, error) {
p, err := podmanSystemInfo()
info.CPUs = p.Host.Cpus
info.TotalMemory = p.Host.MemTotal
info.OSType = p.Host.Os
return info, err
}
d, err := dockerSystemInfo()
info.CPUs = d.NCPU
info.TotalMemory = d.MemTotal
info.OSType = d.OSType
return info, err
}

Expand Down
12 changes: 12 additions & 0 deletions pkg/drivers/kic/oci/oci.go
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,18 @@ func PrepareContainerNode(p CreateParams) error {

// CreateContainerNode creates a new container node
func CreateContainerNode(p CreateParams) error {
// on windows os, if docker desktop is using Windows Containers. Exit early with error
if p.OCIBinary == Docker && runtime.GOOS == "windows" {
info, err := DaemonInfo(p.OCIBinary)
if info.OSType == "windows" {
return ErrWindowsContainers
}
if err != nil {
glog.Warningf("error getting dameon info: %v", err)
return errors.Wrap(err, "daemon info")
}
}

runArgs := []string{
"-d", // run the container detached
"-t", // allocate a tty for entrypoint logs
Expand Down
9 changes: 8 additions & 1 deletion pkg/minikube/node/start.go
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ import (
"golang.org/x/sync/errgroup"
cmdcfg "k8s.io/minikube/cmd/minikube/cmd/config"
"k8s.io/minikube/pkg/addons"
"k8s.io/minikube/pkg/drivers/kic/oci"
"k8s.io/minikube/pkg/minikube/bootstrapper"
"k8s.io/minikube/pkg/minikube/bootstrapper/images"
"k8s.io/minikube/pkg/minikube/cluster"
Expand Down Expand Up @@ -356,7 +357,6 @@ func startHost(api libmachine.API, cc config.ClusterConfig, n config.Node) (*hos
if err == nil {
return host, exists, nil
}
out.ErrT(out.Embarrassed, "StartHost failed, but will try again: {{.error}}", out.V{"error": err})

// NOTE: People get very cranky if you delete their prexisting VM. Only delete new ones.
if !exists {
Expand All @@ -366,6 +366,13 @@ func startHost(api libmachine.API, cc config.ClusterConfig, n config.Node) (*hos
}
}

// don't try to re-create if container type is windows.
if errors.Is(err, oci.ErrWindowsContainers) {
glog.Infof("will skip retrying to create machine because error is not retriable: %v", err)
return host, exists, err
}

out.ErrT(out.Embarrassed, "StartHost failed, but will try again: {{.error}}", out.V{"error": err})
// Try again, but just once to avoid making the logs overly confusing
time.Sleep(5 * time.Second)

Expand Down
6 changes: 5 additions & 1 deletion pkg/minikube/registry/drvs/docker/docker.go
Original file line number Diff line number Diff line change
Expand Up @@ -80,9 +80,13 @@ func status() registry.State {
defer cancel()

// Quickly returns an error code if server is not running
cmd := exec.CommandContext(ctx, oci.Docker, "version", "--format", "{{.Server.Version}}")
cmd := exec.CommandContext(ctx, oci.Docker, "version", "--format", "{{.Server.Os}}-{{.Server.Version}}")
o, err := cmd.Output()
output := string(o)
if strings.Contains(output, "windows-") {
return registry.State{Error: oci.ErrWindowsContainers, Installed: true, Healthy: false, Fix: "Change container type to \"linux\" in Docker Desktop settings", Doc: docURL + "#verify-docker-container-type-is-linux"}

}
if err == nil {
glog.Infof("docker version: %s", output)
return registry.State{Installed: true, Healthy: true}
Expand Down
13 changes: 11 additions & 2 deletions site/content/en/docs/drivers/docker.md
Original file line number Diff line number Diff line change
Expand Up @@ -30,11 +30,20 @@ The Docker driver allows you to install Kubernetes into an existing Docker insta

## Troubleshooting

- On macOS or Windows, you may need to restart Docker for Desktop if a command gets hung

[comment]: <> (this title is used in the docs links, don't change)
### Verify Docker container type is Linux
- On Windows, make sure Docker Desktop's container type setting is Linux and not windows. see docker docs on [switching container type](https://docs.docker.com/docker-for-windows/#switch-between-windows-and-linux-containers).
You can verify your Docker container type by running:
```shell
docker info --format '{{.OSType}}'
```

### Run with logs
- Run `--alsologtostderr -v=1` for extra debugging information

### Deploying MySql on a linux with AppArmor
- On Linux, if you want to run MySQL pod, you need to disable AppArmor for mysql profile

If your docker has [AppArmor](https://wiki.ubuntu.com/AppArmor) enabled, running mysql in privileged mode with docker driver will have the issue [#7401](https://github.com/kubernetes/minikube/issues/7401).
There is a workaround - see [moby/moby#7512](https://github.com/moby/moby/issues/7512#issuecomment-61787845).

0 comments on commit e0685c8

Please sign in to comment.