From e78a548da2fb95d4417eafe91edde522e3cacaf8 Mon Sep 17 00:00:00 2001 From: iwilltry42 Date: Mon, 6 May 2019 08:13:11 +0200 Subject: [PATCH 1/7] [Feature] add --image/-i flag to specify custom k3s image --- cli/commands.go | 4 ++-- main.go | 7 ++++++- 2 files changed, 8 insertions(+), 3 deletions(-) diff --git a/cli/commands.go b/cli/commands.go index 8735fcb3..1993584a 100644 --- a/cli/commands.go +++ b/cli/commands.go @@ -75,7 +75,7 @@ func CreateCluster(c *cli.Context) error { log.Printf("Creating cluster [%s]", c.String("name")) dockerID, err := createServer( c.GlobalBool("verbose"), - fmt.Sprintf("docker.io/rancher/k3s:%s", c.String("version")), + fmt.Sprintf("%s:%s", c.String("image"), c.String("version")), c.String("port"), k3sServerArgs, env, @@ -137,7 +137,7 @@ func CreateCluster(c *cli.Context) error { for i := 0; i < c.Int("workers"); i++ { workerID, err := createWorker( c.GlobalBool("verbose"), - fmt.Sprintf("docker.io/rancher/k3s:%s", c.String("version")), + fmt.Sprintf("%s:%s", c.String("image"), c.String("version")), k3sWorkerArgs, env, c.String("name"), diff --git a/main.go b/main.go index ec8b28de..5621d814 100644 --- a/main.go +++ b/main.go @@ -56,7 +56,7 @@ func main() { Usage: "Mount one or more volumes into every node of the cluster (Docker notation: `source:destination[,source:destination]`)", }, cli.StringFlag{ - Name: "version", + Name: "version, tag", Value: version.GetK3sVersion(), Usage: "Choose the k3s image version", }, @@ -74,6 +74,11 @@ func main() { Name: "wait, w", Usage: "Wait for the cluster to come up before returning", }, + cli.StringFlag{ + Name: "image, i", + Usage: "Specify a k3s image (repo only)", + Value: "docker.io/rancher/k3s", + }, cli.StringSliceFlag{ Name: "server-arg, x", Usage: "Pass an additional argument to k3s server (new flag per argument)", From 40fb583160dedfb05a00bd4f9b266216d40435b8 Mon Sep 17 00:00:00 2001 From: iwilltry42 Date: Tue, 7 May 2019 09:09:05 +0200 Subject: [PATCH 2/7] better image and version flags --- cli/commands.go | 24 ++++++++++++++++++++++-- cli/container.go | 2 -- main.go | 12 ++++++++---- 3 files changed, 30 insertions(+), 8 deletions(-) diff --git a/cli/commands.go b/cli/commands.go index 1993584a..c342a601 100644 --- a/cli/commands.go +++ b/cli/commands.go @@ -23,6 +23,8 @@ import ( "github.com/urfave/cli" ) +const defaultRegistry = "docker.io" + // CheckTools checks if the docker API server is responding func CheckTools(c *cli.Context) error { log.Print("Checking docker...") @@ -43,6 +45,24 @@ func CheckTools(c *cli.Context) error { // CreateCluster creates a new single-node cluster container and initializes the cluster directory func CreateCluster(c *cli.Context) error { + // define image + image := c.String("image") + if c.IsSet("version") { + // TODO: --version to be deprecated + log.Println("[WARNING] The `--version` flag will be deprecated soon, please use `--image rancher/k3s:` instead") + if c.IsSet("image") { + // version specified, custom image = error (to push deprecation of version flag) + log.Fatalln("[ERROR] Please use `--image :` instead of --image and --version") + } else { + // version specified, default image = ok (until deprecation of version flag) + image = fmt.Sprintf("%s:%s", strings.Split(image, ":")[0], c.String("version")) + } + } + if len(strings.Split(image, "/")) <= 2 { + // fallback to default registry + image = fmt.Sprintf("%s/%s", defaultRegistry, image) + } + // create cluster network networkID, err := createClusterNetwork(c.String("name")) if err != nil { @@ -75,7 +95,7 @@ func CreateCluster(c *cli.Context) error { log.Printf("Creating cluster [%s]", c.String("name")) dockerID, err := createServer( c.GlobalBool("verbose"), - fmt.Sprintf("%s:%s", c.String("image"), c.String("version")), + image, c.String("port"), k3sServerArgs, env, @@ -137,7 +157,7 @@ func CreateCluster(c *cli.Context) error { for i := 0; i < c.Int("workers"); i++ { workerID, err := createWorker( c.GlobalBool("verbose"), - fmt.Sprintf("%s:%s", c.String("image"), c.String("version")), + image, k3sWorkerArgs, env, c.String("name"), diff --git a/cli/container.go b/cli/container.go index a1714816..962c1346 100644 --- a/cli/container.go +++ b/cli/container.go @@ -165,8 +165,6 @@ func createWorker(verbose bool, image string, args []string, env []string, name // removeContainer tries to rm a container, selected by Docker ID, and does a rm -f if it fails (e.g. if container is still running) func removeContainer(ID string) error { - // TODO: first check if container is running, then try to stop it with a timeout before trying to remove it - // if it does not terminate gracefully, try a force remove ctx := context.Background() docker, err := client.NewEnvClient() if err != nil { diff --git a/main.go b/main.go index 5621d814..a9ef14fe 100644 --- a/main.go +++ b/main.go @@ -1,6 +1,7 @@ package main import ( + "fmt" "log" "os" @@ -9,6 +10,9 @@ import ( "github.com/urfave/cli" ) +// defaultK3sImage specifies the default image being used for server and workers +const defaultK3sImage = "docker.io/rancher/k3s" + // main represents the CLI application func main() { @@ -56,8 +60,8 @@ func main() { Usage: "Mount one or more volumes into every node of the cluster (Docker notation: `source:destination[,source:destination]`)", }, cli.StringFlag{ - Name: "version, tag", - Value: version.GetK3sVersion(), + // TODO: to be deprecated + Name: "version", Usage: "Choose the k3s image version", }, cli.IntFlag{ @@ -76,8 +80,8 @@ func main() { }, cli.StringFlag{ Name: "image, i", - Usage: "Specify a k3s image (repo only)", - Value: "docker.io/rancher/k3s", + Usage: "Specify a k3s image (Format: /:)", + Value: fmt.Sprintf("%s:%s", defaultK3sImage, version.GetK3sVersion()), }, cli.StringSliceFlag{ Name: "server-arg, x", From 15b1326456c94074fc33f3a8b49bbf89699baeb8 Mon Sep 17 00:00:00 2001 From: iwilltry42 Date: Wed, 8 May 2019 18:28:38 +0200 Subject: [PATCH 3/7] [bugfix] default name without underscore --- main.go | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/main.go b/main.go index a9ef14fe..b6d3b5eb 100644 --- a/main.go +++ b/main.go @@ -52,7 +52,7 @@ func main() { Flags: []cli.Flag{ cli.StringFlag{ Name: "name, n", - Value: "k3s_default", + Value: "k3s-default", Usage: "Set a name for the cluster", }, cli.StringFlag{ @@ -107,7 +107,7 @@ func main() { Flags: []cli.Flag{ cli.StringFlag{ Name: "name, n", - Value: "k3s_default", + Value: "k3s-default", Usage: "name of the cluster", }, cli.BoolFlag{ @@ -124,7 +124,7 @@ func main() { Flags: []cli.Flag{ cli.StringFlag{ Name: "name, n", - Value: "k3s_default", + Value: "k3s-default", Usage: "Name of the cluster", }, cli.BoolFlag{ @@ -141,7 +141,7 @@ func main() { Flags: []cli.Flag{ cli.StringFlag{ Name: "name, n", - Value: "k3s_default", + Value: "k3s-default", Usage: "Name of the cluster", }, cli.BoolFlag{ @@ -171,7 +171,7 @@ func main() { Flags: []cli.Flag{ cli.StringFlag{ Name: "name, n", - Value: "k3s_default", + Value: "k3s-default", Usage: "Name of the cluster", }, cli.BoolFlag{ From 4ebf34218b282ba5279011eaa0242f6eb57ec80e Mon Sep 17 00:00:00 2001 From: Andy Zhou Date: Wed, 8 May 2019 09:19:38 -0700 Subject: [PATCH 4/7] Consolidate the default cluster name into as single definition To ensure all reference of the default cluster name are the same. Not having to check for typos will make it easier to maintain. --- main.go | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/main.go b/main.go index b6d3b5eb..c6e12460 100644 --- a/main.go +++ b/main.go @@ -12,6 +12,7 @@ import ( // defaultK3sImage specifies the default image being used for server and workers const defaultK3sImage = "docker.io/rancher/k3s" +const defaultK3sClusterName string = "k3s-default" // main represents the CLI application func main() { @@ -52,7 +53,7 @@ func main() { Flags: []cli.Flag{ cli.StringFlag{ Name: "name, n", - Value: "k3s-default", + Value: defaultK3sClusterName, Usage: "Set a name for the cluster", }, cli.StringFlag{ @@ -107,7 +108,7 @@ func main() { Flags: []cli.Flag{ cli.StringFlag{ Name: "name, n", - Value: "k3s-default", + Value: defaultK3sClusterName, Usage: "name of the cluster", }, cli.BoolFlag{ @@ -124,7 +125,7 @@ func main() { Flags: []cli.Flag{ cli.StringFlag{ Name: "name, n", - Value: "k3s-default", + Value: defaultK3sClusterName, Usage: "Name of the cluster", }, cli.BoolFlag{ @@ -141,7 +142,7 @@ func main() { Flags: []cli.Flag{ cli.StringFlag{ Name: "name, n", - Value: "k3s-default", + Value: defaultK3sClusterName, Usage: "Name of the cluster", }, cli.BoolFlag{ @@ -171,7 +172,7 @@ func main() { Flags: []cli.Flag{ cli.StringFlag{ Name: "name, n", - Value: "k3s-default", + Value: defaultK3sClusterName, Usage: "Name of the cluster", }, cli.BoolFlag{ From 93f72e672a60eddb8a5e9e09c05e68643b2deebd Mon Sep 17 00:00:00 2001 From: Andy Zhou Date: Wed, 8 May 2019 11:17:17 -0700 Subject: [PATCH 5/7] Make sure the culster name is valid before creating it. MAke sure the cluster name is a RFC 1123 compliant host name, since the cluster name is used as base for expanding into a auto generated host names for k3s nodes. --- cli/commands.go | 35 +++++++++++++++++++++++++++++++++++ 1 file changed, 35 insertions(+) diff --git a/cli/commands.go b/cli/commands.go index c342a601..5e8c7602 100644 --- a/cli/commands.go +++ b/cli/commands.go @@ -24,6 +24,37 @@ import ( ) const defaultRegistry = "docker.io" +const clusterNameMaxSize int = 35 + +// Make sure a cluster name is also a valid host name according to RFC 1123. +// We further restrict the length of the cluster name to shorter than 'clusterNameMaxSize' +// so that we can construct the host names based on the cluster name, and still stay +// within the 64 characters limit. +func checkClusterName(name string) error { + if len(name) > clusterNameMaxSize { + return fmt.Errorf("cluster name is too long") + } + + if name[0] == '-' || name[len(name) - 1] == '-' { + return fmt.Errorf("cluster name can not start or end with - (dash)") + } + + + for _ , c := range name { + switch { + case '0' <= c && c <= '9': + case 'a' <= c && c <= 'z': + case 'A' <= c && c <= 'Z': + case c == '-': + break; + default: + return fmt.Errorf("cluster name contains charaters other than 'Aa-Zz', '0-9' or '-'") + + } + } + + return nil +} // CheckTools checks if the docker API server is responding func CheckTools(c *cli.Context) error { @@ -45,6 +76,10 @@ func CheckTools(c *cli.Context) error { // CreateCluster creates a new single-node cluster container and initializes the cluster directory func CreateCluster(c *cli.Context) error { + if err := checkClusterName(c.String("name")); err != nil { + return err; + } + // define image image := c.String("image") if c.IsSet("version") { From fd720b08872399c669dedeb882ac63964f48f4db Mon Sep 17 00:00:00 2001 From: iwilltry42 Date: Thu, 9 May 2019 08:05:39 +0200 Subject: [PATCH 6/7] move hostname check to util --- cli/commands.go | 35 ++--------------------------------- cli/util.go | 33 +++++++++++++++++++++++++++++++++ 2 files changed, 35 insertions(+), 33 deletions(-) diff --git a/cli/commands.go b/cli/commands.go index 5e8c7602..2552a3d5 100644 --- a/cli/commands.go +++ b/cli/commands.go @@ -24,37 +24,6 @@ import ( ) const defaultRegistry = "docker.io" -const clusterNameMaxSize int = 35 - -// Make sure a cluster name is also a valid host name according to RFC 1123. -// We further restrict the length of the cluster name to shorter than 'clusterNameMaxSize' -// so that we can construct the host names based on the cluster name, and still stay -// within the 64 characters limit. -func checkClusterName(name string) error { - if len(name) > clusterNameMaxSize { - return fmt.Errorf("cluster name is too long") - } - - if name[0] == '-' || name[len(name) - 1] == '-' { - return fmt.Errorf("cluster name can not start or end with - (dash)") - } - - - for _ , c := range name { - switch { - case '0' <= c && c <= '9': - case 'a' <= c && c <= 'z': - case 'A' <= c && c <= 'Z': - case c == '-': - break; - default: - return fmt.Errorf("cluster name contains charaters other than 'Aa-Zz', '0-9' or '-'") - - } - } - - return nil -} // CheckTools checks if the docker API server is responding func CheckTools(c *cli.Context) error { @@ -76,8 +45,8 @@ func CheckTools(c *cli.Context) error { // CreateCluster creates a new single-node cluster container and initializes the cluster directory func CreateCluster(c *cli.Context) error { - if err := checkClusterName(c.String("name")); err != nil { - return err; + if err := CheckClusterName(c.String("name")); err != nil { + return err } // define image diff --git a/cli/util.go b/cli/util.go index 66d0ba2b..1688c57b 100644 --- a/cli/util.go +++ b/cli/util.go @@ -1,6 +1,7 @@ package run import ( + "fmt" "math/rand" "strings" "time" @@ -36,3 +37,35 @@ func GenerateRandomString(n int) string { return sb.String() } + +/*** Cluster Name Validation ***/ +const clusterNameMaxSize int = 35 + +// CheckClusterName ensures that a cluster name is also a valid host name according to RFC 1123. +// We further restrict the length of the cluster name to maximum 'clusterNameMaxSize' +// so that we can construct the host names based on the cluster name, and still stay +// within the 64 characters limit. +func CheckClusterName(name string) error { + if len(name) > clusterNameMaxSize { + return fmt.Errorf("[ERROR] Cluster name is too long") + } + + if name[0] == '-' || name[len(name)-1] == '-' { + return fmt.Errorf("[ERROR] Cluster name can not start or end with - (dash)") + } + + for _, c := range name { + switch { + case '0' <= c && c <= '9': + case 'a' <= c && c <= 'z': + case 'A' <= c && c <= 'Z': + case c == '-': + break + default: + return fmt.Errorf("[ERROR] Cluster name contains characters other than 'Aa-Zz', '0-9' or '-'") + + } + } + + return nil +} From d0f905d2fa60b8b1cd829d24a5fd82bdd4cf6c56 Mon Sep 17 00:00:00 2001 From: iwilltry42 Date: Thu, 9 May 2019 09:52:51 +0200 Subject: [PATCH 7/7] readme on go install --- README.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index b027ae47..4bd81595 100644 --- a/README.md +++ b/README.md @@ -13,7 +13,7 @@ This repository is based on [@zeerorg](https://github.com/zeerorg/)'s [zeerorg/k - [docker](https://docs.docker.com/install/) -## Install +## Get You have several options there: @@ -21,7 +21,7 @@ You have several options there: - wget: `wget -q -O - https://raw.githubusercontent.com/rancher/k3d/master/install.sh | bash` - curl: `curl -s https://raw.githubusercontent.com/rancher/k3d/master/install.sh | bash` - Grab a release from the [release tab](https://github.com/rancher/k3d/releases) and install it yourself. -- Via go: `go install github.com/rancher/k3d` +- Via go: `go install github.com/rancher/k3d` (**Note**: this will give you unreleased/bleeding-edge changes) or... @@ -32,7 +32,7 @@ or... - 'make install-tools' to make sure required go packages are installed 3. Inside the repo run - `make build` to build for your current system - - `go install` to install it to your `GOPATH` + - `go install` to install it to your `GOPATH` (**Note**: this will give you unreleased/bleeding-edge changes) - `make build-cross` to build for all systems ## Usage