dev-v2.0.0: refactor cmd package

Signed-off-by: 24sama <leo@kubesphere.io>
This commit is contained in:
24sama 2021-11-12 18:03:03 +08:00
parent 8958b215bf
commit f8462eb110
38 changed files with 1043 additions and 645 deletions

View File

@ -3,7 +3,7 @@ project_name: kubekey
builds:
- env:
- CGO_ENABLED=0
main: ./cmd/kk/main.go
main: ./cmd/main.go
binary: kk
goarch:
- amd64

View File

@ -14,7 +14,7 @@ RUN git clone https://github.com/kubesphere/helm-charts.git
ADD ./ /workspace
# Build
RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 GO111MODULE=on go build -a -o manager main.go
RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 GO111MODULE=on go build -a -o kk cmd/kk/main.go
RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 GO111MODULE=on go build -a -o kk cmd/main.go
# Build the manager image
FROM debian:stable

View File

@ -232,7 +232,7 @@ binary:
-e CGO_ENABLED=0 \
-e GO111MODULE=on \
-w /usr/src/myapp golang:1.16 \
go build -ldflags '$(LDFLAGS)' -v -o output/linux/amd64/kk ./cmd/kk/main.go # linux
go build -ldflags '$(LDFLAGS)' -v -o output/linux/amd64/kk ./cmd/main.go # linux
sha256sum output/linux/amd64/kk || shasum -a 256 output/linux/amd64/kk
docker run --rm \
@ -242,13 +242,13 @@ binary:
-e CGO_ENABLED=0 \
-e GO111MODULE=on \
-w /usr/src/myapp golang:1.16 \
go build -ldflags '$(LDFLAGS)' -v -o output/linux/arm64/kk ./cmd/kk/main.go # linux
go build -ldflags '$(LDFLAGS)' -v -o output/linux/arm64/kk ./cmd/main.go # linux
sha256sum output/linux/arm64/kk || shasum -a 256 output/linux/arm64/kk
# build the binary file of kk
kk-linux:
GOOS=linux GOARCH=amd64 CGO_ENABLED=0 GO111MODULE=on go build -ldflags '$(LDFLAGS)' -o bin/linux/amd64/kk ./cmd/kk/main.go
GOOS=linux GOARCH=amd64 CGO_ENABLED=0 GO111MODULE=on go build -ldflags '$(LDFLAGS)' -o bin/linux/amd64/kk ./cmd/main.go
kk-darwin:
GOOS=darwin GOARCH=amd64 CGO_ENABLED=0 GO111MODULE=on go build -ldflags '$(LDFLAGS)' -o bin/darwin/amd64/kk ./cmd/kk/main.go
GOOS=darwin GOARCH=amd64 CGO_ENABLED=0 GO111MODULE=on go build -ldflags '$(LDFLAGS)' -o bin/darwin/amd64/kk ./cmd/main.go
go-releaser-test:
goreleaser release --rm-dist --skip-publish --snapshot

View File

@ -24,10 +24,10 @@ LDFLAGS="-X github.com/kubesphere/kubekey/version.version=${VERSION}
if [ -n "$1" ]; then
if [ "$1" == "-p" ] || [ "$1" == "--proxy" ]; then
# Using the most trusted Go module proxy in China
docker run --rm -e GO111MODULE=on -e GOPROXY=https://goproxy.cn -v "$PWD":/usr/src/myapp -w /usr/src/myapp golang:1.16 go build -ldflags "$LDFLAGS" -v -o output/kk ./cmd/kk/main.go
docker run --rm -e GO111MODULE=on -e GOPROXY=https://goproxy.cn -v "$PWD":/usr/src/myapp -w /usr/src/myapp golang:1.16 go build -ldflags "$LDFLAGS" -v -o output/kk ./cmd/main.go
else
echo "The option should be '-p' or '--proxy'"
fi
else
docker run --rm -v "$PWD":/usr/src/myapp -w /usr/src/myapp golang:1.16 go build -ldflags "$LDFLAGS" -v -o output/kk ./cmd/kk/main.go
docker run --rm -v "$PWD":/usr/src/myapp -w /usr/src/myapp golang:1.16 go build -ldflags "$LDFLAGS" -v -o output/kk ./cmd/main.go
fi

View File

@ -1,13 +0,0 @@
package cmd
import "github.com/spf13/cobra"
// addCmd represents the add command
var addCmd = &cobra.Command{
Use: "add",
Short: "Add nodes to kubernetes cluster",
}
func init() {
rootCmd.AddCommand(addCmd)
}

View File

@ -1,50 +0,0 @@
/*
Copyright 2020 The KubeSphere Authors.
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 cmd
import (
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/spf13/cobra"
)
// addNodesCmd represents the nodes command
var addNodesCmd = &cobra.Command{
Use: "nodes",
Short: "Add nodes to the cluster according to the new nodes information from the specified configuration file",
RunE: func(cmd *cobra.Command, args []string) error {
arg := common.Argument{
FilePath: opt.ClusterCfgFile,
KsEnable: false,
Debug: opt.Verbose,
IgnoreErr: opt.IgnoreErr,
SkipConfirmCheck: opt.SkipConfirmCheck,
SkipPullImages: opt.SkipPullImages,
InCluster: opt.InCluster,
ContainerManager: opt.ContainerManager,
}
return pipelines.AddNodes(arg, opt.DownloadCmd)
},
}
func init() {
addCmd.AddCommand(addNodesCmd)
addNodesCmd.Flags().StringVarP(&opt.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
addNodesCmd.Flags().BoolVarP(&opt.SkipPullImages, "skip-pull-images", "", false, "Skip pre pull images")
addNodesCmd.Flags().StringVarP(&opt.ContainerManager, "container-manager", "", "docker", "Container manager: docker, crio, containerd and isula.")
addNodesCmd.Flags().StringVarP(&opt.DownloadCmd, "download-cmd", "", "curl -L -o %s %s",
`The user defined command to download the necessary binary files. The first param '%s' is output path, the second param '%s', is the URL`)
}

View File

@ -1,12 +0,0 @@
package cmd
import "github.com/spf13/cobra"
var certsCmd = &cobra.Command{
Use: "certs",
Short: "cluster certs",
}
func init() {
rootCmd.AddCommand(certsCmd)
}

View File

@ -1,87 +0,0 @@
/*
Copyright 2020 The KubeSphere Authors.
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 cmd
import (
"fmt"
"github.com/kubesphere/kubekey/apis/kubekey/v1alpha2"
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/kubesphere/kubekey/version"
"github.com/spf13/cobra"
"time"
)
// clusterCmd represents the cluster command
var clusterCmd = &cobra.Command{
Use: "cluster",
Short: "Create a Kubernetes or KubeSphere cluster",
RunE: func(cmd *cobra.Command, args []string) error {
var ksVersion string
if opt.Kubesphere && len(args) > 0 {
ksVersion = args[0]
} else {
ksVersion = ""
}
arg := common.Argument{
FilePath: opt.ClusterCfgFile,
KubernetesVersion: opt.Kubernetes,
KsEnable: opt.Kubesphere,
KsVersion: ksVersion,
SkipPullImages: opt.SkipPullImages,
InCluster: opt.InCluster,
DeployLocalStorage: opt.LocalStorage,
Debug: opt.Verbose,
IgnoreErr: opt.IgnoreErr,
SkipConfirmCheck: opt.SkipConfirmCheck,
ContainerManager: opt.ContainerManager,
}
return pipelines.CreateCluster(arg, opt.DownloadCmd)
},
}
func init() {
createCmd.AddCommand(clusterCmd)
clusterCmd.Flags().StringVarP(&opt.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
clusterCmd.Flags().StringVarP(&opt.Kubernetes, "with-kubernetes", "", v1alpha2.DefaultKubeVersion, "Specify a supported version of kubernetes")
clusterCmd.Flags().BoolVarP(&opt.LocalStorage, "with-local-storage", "", false, "Deploy a local PV provisioner")
clusterCmd.Flags().BoolVarP(&opt.Kubesphere, "with-kubesphere", "", false, "Deploy a specific version of kubesphere (default v3.2.0)")
clusterCmd.Flags().BoolVarP(&opt.SkipPullImages, "skip-pull-images", "", false, "Skip pre pull images")
clusterCmd.Flags().StringVarP(&opt.ContainerManager, "container-manager", "", "docker", "Container runtime: docker, crio, containerd and isula.")
clusterCmd.Flags().StringVarP(&opt.DownloadCmd, "download-cmd", "", "curl -L -o %s %s",
`The user defined command to download the necessary binary files. The first param '%s' is output path, the second param '%s', is the URL`)
if err := setValidArgs(clusterCmd); err != nil {
panic(fmt.Sprintf("Got error with the completion setting"))
}
}
func setValidArgs(cmd *cobra.Command) (err error) {
cmd.ValidArgsFunction = func(cmd *cobra.Command, args []string, toComplete string) (
strings []string, directive cobra.ShellCompDirective) {
versionArray := []string{"v2.1.1", "v3.0.0", "v3.1.0", "v3.1.1", time.Now().Add(-time.Hour * 24).Format("nightly-20060102")}
return versionArray, cobra.ShellCompDirectiveNoFileComp
}
err = cmd.RegisterFlagCompletionFunc("with-kubernetes", func(cmd *cobra.Command, args []string, toComplete string) (
strings []string, directive cobra.ShellCompDirective) {
return version.SupportedK8sVersionList(), cobra.ShellCompDirectiveNoFileComp
})
return
}

View File

@ -1,62 +0,0 @@
/*
Copyright 2020 The KubeSphere Authors.
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 cmd
import (
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/config"
"github.com/spf13/cobra"
)
// configCmd represents the config command
var configCmd = &cobra.Command{
Use: "config",
Short: "Create cluster configuration file",
RunE: func(cmd *cobra.Command, args []string) error {
var ksVersion string
if opt.Kubesphere && len(args) > 0 {
ksVersion = args[0]
} else {
ksVersion = ""
}
arg := common.Argument{
FilePath: opt.ClusterCfgFile,
KubernetesVersion: opt.Kubernetes,
KsEnable: opt.Kubesphere,
KsVersion: ksVersion,
FromCluster: opt.FromCluster,
KubeConfig: opt.Kubeconfig,
}
err := config.GenerateKubeKeyConfig(arg, opt.Name)
if err != nil {
return err
}
return err
},
}
func init() {
createCmd.AddCommand(configCmd)
configCmd.Flags().StringVarP(&opt.Name, "name", "", "sample", "Specify a name of cluster object")
configCmd.Flags().StringVarP(&opt.ClusterCfgFile, "filename", "f", "", "Specify a configuration file path")
configCmd.Flags().StringVarP(&opt.Kubernetes, "with-kubernetes", "", "", "Specify a supported version of kubernetes")
configCmd.Flags().BoolVarP(&opt.Kubesphere, "with-kubesphere", "", false, "Deploy a specific version of kubesphere (default v3.1.0)")
configCmd.Flags().BoolVarP(&opt.FromCluster, "from-cluster", "", false, "Create a configuration based on existing cluster")
configCmd.Flags().StringVarP(&opt.Kubeconfig, "kubeconfig", "", "", "Specify a kubeconfig file")
}

30
cmd/ctl/add/add.go Normal file
View File

@ -0,0 +1,30 @@
package add
import (
"github.com/kubesphere/kubekey/cmd/ctl/options"
"github.com/spf13/cobra"
)
type AddOptions struct {
CommonOptions *options.CommonOptions
}
func NewAddOptions() *AddOptions {
return &AddOptions{
CommonOptions: options.NewCommonOptions(),
}
}
// NewCmdAdd creates a new add command
func NewCmdAdd() *cobra.Command {
o := NewAddOptions()
cmd := &cobra.Command{
Use: "add",
Short: "Add nodes to kubernetes cluster",
}
o.CommonOptions.AddCommonFlag(cmd)
cmd.AddCommand(NewCmdAddNodes())
return cmd
}

76
cmd/ctl/add/add_nodes.go Normal file
View File

@ -0,0 +1,76 @@
/*
Copyright 2020 The KubeSphere Authors.
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 add
import (
"github.com/kubesphere/kubekey/cmd/ctl/options"
"github.com/kubesphere/kubekey/cmd/ctl/util"
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/spf13/cobra"
)
type AddNodesOptions struct {
CommonOptions *options.CommonOptions
ClusterCfgFile string
SkipPullImages bool
ContainerManager string
DownloadCmd string
}
func NewAddNodesOptions() *AddNodesOptions {
return &AddNodesOptions{
CommonOptions: options.NewCommonOptions(),
}
}
// NewCmdAddNodes creates a new add nodes command
func NewCmdAddNodes() *cobra.Command {
o := NewAddNodesOptions()
cmd := &cobra.Command{
Use: "nodes",
Short: "Add nodes to the cluster according to the new nodes information from the specified configuration file",
Run: func(cmd *cobra.Command, args []string) {
util.CheckErr(o.Run())
},
}
o.CommonOptions.AddCommonFlag(cmd)
o.AddFlags(cmd)
return cmd
}
func (o *AddNodesOptions) Run() error {
arg := common.Argument{
FilePath: o.ClusterCfgFile,
KsEnable: false,
Debug: o.CommonOptions.Verbose,
IgnoreErr: o.CommonOptions.IgnoreErr,
SkipConfirmCheck: o.CommonOptions.SkipConfirmCheck,
SkipPullImages: o.SkipPullImages,
InCluster: o.CommonOptions.InCluster,
ContainerManager: o.ContainerManager,
}
return pipelines.AddNodes(arg, o.DownloadCmd)
}
func (o *AddNodesOptions) AddFlags(cmd *cobra.Command) {
cmd.Flags().StringVarP(&o.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
cmd.Flags().BoolVarP(&o.SkipPullImages, "skip-pull-images", "", false, "Skip pre pull images")
cmd.Flags().StringVarP(&o.ContainerManager, "container-manager", "", "docker", "Container manager: docker, crio, containerd and isula.")
cmd.Flags().StringVarP(&o.DownloadCmd, "download-cmd", "", "curl -L -o %s %s",
`The user defined command to download the necessary binary files. The first param '%s' is output path, the second param '%s', is the URL`)
}

31
cmd/ctl/cert/cert.go Normal file
View File

@ -0,0 +1,31 @@
package cert
import (
"github.com/kubesphere/kubekey/cmd/ctl/options"
"github.com/spf13/cobra"
)
type CertOptions struct {
CommonOptions *options.CommonOptions
}
func NewCertsOptions() *CertOptions {
return &CertOptions{
CommonOptions: options.NewCommonOptions(),
}
}
// NewCmdCerts creates a new cert command
func NewCmdCerts() *cobra.Command {
o := NewCertsOptions()
cmd := &cobra.Command{
Use: "certs",
Short: "cluster certs",
}
o.CommonOptions.AddCommonFlag(cmd)
cmd.AddCommand(NewCmdCertList())
cmd.AddCommand(NewCmdCertRenew())
return cmd
}

48
cmd/ctl/cert/list_cert.go Normal file
View File

@ -0,0 +1,48 @@
package cert
import (
"github.com/kubesphere/kubekey/cmd/ctl/options"
"github.com/kubesphere/kubekey/cmd/ctl/util"
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/spf13/cobra"
)
type CertListOptions struct {
CommonOptions *options.CommonOptions
ClusterCfgFile string
}
func NewCertListOptions() *CertListOptions {
return &CertListOptions{
CommonOptions: options.NewCommonOptions(),
}
}
// NewCmdCertList creates a new cert list command
func NewCmdCertList() *cobra.Command {
o := NewCertListOptions()
cmd := &cobra.Command{
Use: "check-expiration",
Short: "Check certificates expiration for a Kubernetes cluster",
Run: func(cmd *cobra.Command, args []string) {
util.CheckErr(o.Run())
},
}
o.CommonOptions.AddCommonFlag(cmd)
o.AddFlags(cmd)
return cmd
}
func (o *CertListOptions) Run() error {
arg := common.Argument{
FilePath: o.ClusterCfgFile,
Debug: o.CommonOptions.Verbose,
}
return pipelines.CheckCerts(arg)
}
func (o *CertListOptions) AddFlags(cmd *cobra.Command) {
cmd.Flags().StringVarP(&o.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
}

View File

@ -0,0 +1,48 @@
package cert
import (
"github.com/kubesphere/kubekey/cmd/ctl/options"
"github.com/kubesphere/kubekey/cmd/ctl/util"
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/spf13/cobra"
)
type CertRenewOptions struct {
CommonOptions *options.CommonOptions
ClusterCfgFile string
}
func NewCertRenewOptions() *CertRenewOptions {
return &CertRenewOptions{
CommonOptions: options.NewCommonOptions(),
}
}
// NewCmdCertRenew creates a new cert renew command
func NewCmdCertRenew() *cobra.Command {
o := NewCertRenewOptions()
cmd := &cobra.Command{
Use: "renew",
Short: "renew a cluster certs",
Run: func(cmd *cobra.Command, args []string) {
util.CheckErr(o.Run())
},
}
o.CommonOptions.AddCommonFlag(cmd)
o.AddFlags(cmd)
return cmd
}
func (o *CertRenewOptions) Run() error {
arg := common.Argument{
FilePath: o.ClusterCfgFile,
Debug: o.CommonOptions.Verbose,
}
return pipelines.RenewCerts(arg)
}
func (o *CertRenewOptions) AddFlags(cmd *cobra.Command) {
cmd.Flags().StringVarP(&o.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
}

View File

@ -14,10 +14,11 @@ See the License for the specific language governing permissions and
limitations under the License.
*/
package cmd
package completion
import (
"fmt"
"github.com/kubesphere/kubekey/cmd/ctl/util"
"github.com/spf13/cobra"
)
@ -26,6 +27,10 @@ type CompletionOptions struct {
Type string
}
func NewCompletionOptions() *CompletionOptions {
return &CompletionOptions{}
}
// ShellTypes contains all types of shell
var ShellTypes = []string{
"zsh", "bash", "powerShell",
@ -33,28 +38,14 @@ var ShellTypes = []string{
var completionOptions CompletionOptions
func init() {
rootCmd.AddCommand(completionCmd)
flags := completionCmd.Flags()
flags.StringVarP(&completionOptions.Type, "type", "t", "",
fmt.Sprintf("Generate different types of shell which are %v", ShellTypes))
err := completionCmd.RegisterFlagCompletionFunc("type", func(cmd *cobra.Command, args []string, toComplete string) (
i []string, directive cobra.ShellCompDirective) {
return ShellTypes, cobra.ShellCompDirectiveDefault
})
if err != nil {
completionCmd.PrintErrf("register flag type for sub-command doc failed %#v\n", err)
}
}
var completionCmd = &cobra.Command{
Use: "completion",
Short: "Generate shell completion scripts",
Long: `Generate shell completion scripts
func NewCmdCompletion() *cobra.Command {
o := NewCompletionOptions()
cmd := &cobra.Command{
Use: "completion",
Short: "Generate shell completion scripts",
Long: `Generate shell completion scripts
Normally you don't need to do more extra work to have this feature if you've installed kk by brew`,
Example: `# Installing bash completion on Linux
Example: `# Installing bash completion on Linux
## If bash-completion is not installed on Linux, please install the 'bash-completion' package
## via your distribution's package manager.
## Load the ks completion code for bash into the current shell
@ -76,20 +67,45 @@ Load the kk completion code for zsh[1] into the current shell
source <(kk completion --type zsh)
Set the kk completion code for zsh[1] to autoload on startup
kk completion --type zsh > "${fpath[1]}/_kk"`,
RunE: func(cmd *cobra.Command, _ []string) (err error) {
shellType := completionOptions.Type
switch shellType {
case "zsh":
err = rootCmd.GenZshCompletion(cmd.OutOrStdout())
case "powerShell":
err = rootCmd.GenPowerShellCompletion(cmd.OutOrStdout())
case "bash":
err = rootCmd.GenBashCompletion(cmd.OutOrStdout())
case "":
err = cmd.Help()
default:
err = fmt.Errorf("unknown shell type %s", shellType)
}
return
},
Run: func(cmd *cobra.Command, _ []string) {
util.CheckErr(o.Run(cmd))
},
}
o.AddFlags(cmd)
if err := completionSetting(cmd); err != nil {
panic(fmt.Sprintf("register flag type for sub-command doc failed %#v\n", err))
}
return cmd
}
func (o *CompletionOptions) Run(cmd *cobra.Command) error {
var err error
shellType := completionOptions.Type
switch shellType {
case "zsh":
err = cmd.GenZshCompletion(cmd.OutOrStdout())
case "powerShell":
err = cmd.GenPowerShellCompletion(cmd.OutOrStdout())
case "bash":
err = cmd.GenBashCompletion(cmd.OutOrStdout())
case "":
err = cmd.Help()
default:
err = fmt.Errorf("unknown shell type %s", shellType)
}
return err
}
func (o *CompletionOptions) AddFlags(cmd *cobra.Command) {
cmd.Flags().StringVarP(&completionOptions.Type, "type", "t", "",
fmt.Sprintf("Generate different types of shell which are %v", ShellTypes))
}
func completionSetting(cmd *cobra.Command) error {
err := cmd.RegisterFlagCompletionFunc("type", func(cmd *cobra.Command, args []string, toComplete string) (
i []string, directive cobra.ShellCompDirective) {
return ShellTypes, cobra.ShellCompDirectiveDefault
})
return err
}

122
cmd/ctl/create/cluster.go Normal file
View File

@ -0,0 +1,122 @@
/*
Copyright 2020 The KubeSphere Authors.
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 create
import (
"fmt"
"github.com/kubesphere/kubekey/apis/kubekey/v1alpha2"
"github.com/kubesphere/kubekey/cmd/ctl/options"
"github.com/kubesphere/kubekey/cmd/ctl/util"
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/kubesphere/kubekey/pkg/version/kubesphere"
"github.com/kubesphere/kubekey/version"
"github.com/spf13/cobra"
"time"
)
type CreateClusterOptions struct {
CommonOptions *options.CommonOptions
ClusterCfgFile string
Kubernetes string
EnableKubeSphere bool
KubeSphere string
LocalStorage bool
SkipPullImages bool
ContainerManager string
DownloadCmd string
}
func NewCreateClusterOptions() *CreateClusterOptions {
return &CreateClusterOptions{
CommonOptions: options.NewCommonOptions(),
}
}
// NewCmdCreateCluster creates a new create cluster command
func NewCmdCreateCluster() *cobra.Command {
o := NewCreateClusterOptions()
cmd := &cobra.Command{
Use: "cluster",
Short: "Create a Kubernetes or KubeSphere cluster",
Run: func(cmd *cobra.Command, args []string) {
util.CheckErr(o.Complete(cmd, args))
util.CheckErr(o.Run())
},
}
o.CommonOptions.AddCommonFlag(cmd)
o.AddFlags(cmd)
if err := completionSetting(cmd); err != nil {
panic(fmt.Sprintf("Got error with the completion setting"))
}
return cmd
}
func (o *CreateClusterOptions) Complete(cmd *cobra.Command, args []string) error {
var ksVersion string
if o.EnableKubeSphere && len(args) > 0 {
ksVersion = args[0]
} else {
ksVersion = kubesphere.Latest().Version
}
o.KubeSphere = ksVersion
return nil
}
func (o *CreateClusterOptions) Run() error {
arg := common.Argument{
FilePath: o.ClusterCfgFile,
KubernetesVersion: o.Kubernetes,
KsEnable: o.EnableKubeSphere,
KsVersion: o.KubeSphere,
SkipPullImages: o.SkipPullImages,
InCluster: o.CommonOptions.InCluster,
DeployLocalStorage: o.LocalStorage,
Debug: o.CommonOptions.Verbose,
IgnoreErr: o.CommonOptions.IgnoreErr,
SkipConfirmCheck: o.CommonOptions.SkipConfirmCheck,
ContainerManager: o.ContainerManager,
}
return pipelines.CreateCluster(arg, o.DownloadCmd)
}
func (o *CreateClusterOptions) AddFlags(cmd *cobra.Command) {
cmd.Flags().StringVarP(&o.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
cmd.Flags().StringVarP(&o.Kubernetes, "with-kubernetes", "", v1alpha2.DefaultKubeVersion, "Specify a supported version of kubernetes")
cmd.Flags().BoolVarP(&o.LocalStorage, "with-local-storage", "", false, "Deploy a local PV provisioner")
cmd.Flags().BoolVarP(&o.EnableKubeSphere, "with-kubesphere", "", false, "Deploy a specific version of kubesphere (default v3.2.0)")
cmd.Flags().BoolVarP(&o.SkipPullImages, "skip-pull-images", "", false, "Skip pre pull images")
cmd.Flags().StringVarP(&o.ContainerManager, "container-manager", "", "docker", "Container runtime: docker, crio, containerd and isula.")
cmd.Flags().StringVarP(&o.DownloadCmd, "download-cmd", "", "curl -L -o %s %s",
`The user defined command to download the necessary binary files. The first param '%s' is output path, the second param '%s', is the URL`)
}
func completionSetting(cmd *cobra.Command) (err error) {
cmd.ValidArgsFunction = func(cmd *cobra.Command, args []string, toComplete string) (
strings []string, directive cobra.ShellCompDirective) {
versionArray := []string{"v2.1.1", "v3.0.0", "v3.1.0", "v3.1.1", "v3.2.0", time.Now().Add(-time.Hour * 24).Format("nightly-20060102")}
return versionArray, cobra.ShellCompDirectiveNoFileComp
}
err = cmd.RegisterFlagCompletionFunc("with-kubernetes", func(cmd *cobra.Command, args []string, toComplete string) (
strings []string, directive cobra.ShellCompDirective) {
return version.SupportedK8sVersionList(), cobra.ShellCompDirectiveNoFileComp
})
return
}

93
cmd/ctl/create/config.go Normal file
View File

@ -0,0 +1,93 @@
/*
Copyright 2020 The KubeSphere Authors.
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 create
import (
"github.com/kubesphere/kubekey/cmd/ctl/options"
"github.com/kubesphere/kubekey/cmd/ctl/util"
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/config"
"github.com/kubesphere/kubekey/pkg/version/kubesphere"
"github.com/spf13/cobra"
)
type CreateConfigOptions struct {
CommonOptions *options.CommonOptions
Name string
ClusterCfgFile string
Kubernetes string
EnableKubeSphere bool
KubeSphere string
FromCluster bool
KubeConfig string
}
func NewCreateConfigOptions() *CreateConfigOptions {
return &CreateConfigOptions{
CommonOptions: options.NewCommonOptions(),
}
}
// NewCmdCreateConfig creates a create config command
func NewCmdCreateConfig() *cobra.Command {
o := NewCreateConfigOptions()
cmd := &cobra.Command{
Use: "config",
Short: "Create cluster configuration file",
Run: func(cmd *cobra.Command, args []string) {
util.CheckErr(o.Complete(cmd, args))
util.CheckErr(o.Run())
},
}
o.CommonOptions.AddCommonFlag(cmd)
o.AddFlags(cmd)
return cmd
}
func (o *CreateConfigOptions) Complete(cmd *cobra.Command, args []string) error {
var ksVersion string
if o.EnableKubeSphere && len(args) > 0 {
ksVersion = args[0]
} else {
ksVersion = kubesphere.Latest().Version
}
o.KubeSphere = ksVersion
return nil
}
func (o *CreateConfigOptions) Run() error {
arg := common.Argument{
FilePath: o.ClusterCfgFile,
KubernetesVersion: o.Kubernetes,
KsEnable: o.EnableKubeSphere,
KsVersion: o.KubeSphere,
FromCluster: o.FromCluster,
KubeConfig: o.KubeConfig,
}
return config.GenerateKubeKeyConfig(arg, o.Name)
}
func (o *CreateConfigOptions) AddFlags(cmd *cobra.Command) {
cmd.Flags().StringVarP(&o.Name, "name", "", "sample", "Specify a name of cluster object")
cmd.Flags().StringVarP(&o.ClusterCfgFile, "filename", "f", "", "Specify a configuration file path")
cmd.Flags().StringVarP(&o.Kubernetes, "with-kubernetes", "", "", "Specify a supported version of kubernetes")
cmd.Flags().BoolVarP(&o.EnableKubeSphere, "with-kubesphere", "", false, "Deploy a specific version of kubesphere (default v3.1.0)")
cmd.Flags().BoolVarP(&o.FromCluster, "from-cluster", "", false, "Create a configuration based on existing cluster")
cmd.Flags().StringVarP(&o.KubeConfig, "kubeconfig", "", "", "Specify a kubeconfig file")
}

View File

@ -13,18 +13,34 @@ 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 cmd
package create
import (
"github.com/kubesphere/kubekey/cmd/ctl/options"
"github.com/spf13/cobra"
)
// createCmd represents the create command
var createCmd = &cobra.Command{
Use: "create",
Short: "Create a cluster or a cluster configuration file",
type CreateOptions struct {
CommonOptions *options.CommonOptions
}
func init() {
rootCmd.AddCommand(createCmd)
func NewCreateOptions() *CreateOptions {
return &CreateOptions{
CommonOptions: options.NewCommonOptions(),
}
}
// NewCmdCreate creates a new create command
func NewCmdCreate() *cobra.Command {
o := NewCreateOptions()
cmd := &cobra.Command{
Use: "create",
Short: "Create a cluster or a cluster configuration file",
}
o.CommonOptions.AddCommonFlag(cmd)
cmd.AddCommand(NewCmdCreateCluster())
cmd.AddCommand(NewCmdCreateConfig())
return cmd
}

View File

@ -13,18 +13,34 @@ 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 cmd
package delete
import (
"github.com/kubesphere/kubekey/cmd/ctl/options"
"github.com/spf13/cobra"
)
// deleteCmd represents the delete command
var deleteCmd = &cobra.Command{
Use: "delete",
Short: "Delete nodes or cluster",
type DeleteOptions struct {
CommonOptions *options.CommonOptions
}
func init() {
rootCmd.AddCommand(deleteCmd)
func NewDeleteOptions() *DeleteOptions {
return &DeleteOptions{
CommonOptions: options.NewCommonOptions(),
}
}
// NewCmdDelete creates a new delete command
func NewCmdDelete() *cobra.Command {
o := NewDeleteOptions()
cmd := &cobra.Command{
Use: "delete",
Short: "Delete nodes or cluster",
}
o.CommonOptions.AddCommonFlag(cmd)
cmd.AddCommand(NewCmdDeleteCluster())
cmd.AddCommand(NewCmdDeleteNode())
return cmd
}

View File

@ -0,0 +1,48 @@
package delete
import (
"github.com/kubesphere/kubekey/cmd/ctl/options"
"github.com/kubesphere/kubekey/cmd/ctl/util"
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/spf13/cobra"
)
type DeleteClusterOptions struct {
CommonOptions *options.CommonOptions
ClusterCfgFile string
}
func NewDeleteClusterOptions() *DeleteClusterOptions {
return &DeleteClusterOptions{
CommonOptions: options.NewCommonOptions(),
}
}
// NewCmdDeleteCluster creates a new delete cluster command
func NewCmdDeleteCluster() *cobra.Command {
o := NewDeleteClusterOptions()
cmd := &cobra.Command{
Use: "cluster",
Short: "Delete a cluster",
Run: func(cmd *cobra.Command, args []string) {
util.CheckErr(o.Run())
},
}
o.CommonOptions.AddCommonFlag(cmd)
o.AddFlags(cmd)
return cmd
}
func (o *DeleteClusterOptions) Run() error {
arg := common.Argument{
FilePath: o.ClusterCfgFile,
Debug: o.CommonOptions.Verbose,
}
return pipelines.DeleteCluster(arg)
}
func (o *DeleteClusterOptions) AddFlags(cmd *cobra.Command) {
cmd.Flags().StringVarP(&o.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
}

View File

@ -0,0 +1,67 @@
package delete
import (
"github.com/kubesphere/kubekey/cmd/ctl/options"
"github.com/kubesphere/kubekey/cmd/ctl/util"
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/pkg/errors"
"github.com/spf13/cobra"
"strings"
)
type DeleteNodeOptions struct {
CommonOptions *options.CommonOptions
ClusterCfgFile string
nodes string
}
func NewDeleteNodeOptions() *DeleteNodeOptions {
return &DeleteNodeOptions{
CommonOptions: options.NewCommonOptions(),
}
}
// NewCmdDeleteNode creates a new delete node command
func NewCmdDeleteNode() *cobra.Command {
o := NewDeleteNodeOptions()
cmd := &cobra.Command{
Use: "node",
Short: "delete a node",
Run: func(cmd *cobra.Command, args []string) {
util.CheckErr(o.Complete(cmd, args))
util.CheckErr(o.Validate())
util.CheckErr(o.Run())
},
}
o.CommonOptions.AddCommonFlag(cmd)
o.AddFlags(cmd)
return cmd
}
func (o *DeleteNodeOptions) Complete(cmd *cobra.Command, args []string) error {
o.nodes = strings.Join(args, "")
return nil
}
func (o *DeleteNodeOptions) Validate() error {
if o.nodes == "" {
return errors.New("node can not be empty")
}
return nil
}
func (o *DeleteNodeOptions) Run() error {
arg := common.Argument{
FilePath: o.ClusterCfgFile,
Debug: o.CommonOptions.Verbose,
NodeName: o.nodes,
}
return pipelines.DeleteNode(arg)
}
func (o *DeleteNodeOptions) AddFlags(cmd *cobra.Command) {
cmd.Flags().StringVarP(&o.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
}

View File

@ -5,7 +5,7 @@ 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
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,
@ -13,18 +13,31 @@ 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 cmd
package init
import (
"github.com/kubesphere/kubekey/cmd/ctl/options"
"github.com/spf13/cobra"
)
// initCmd represents the create command
var initCmd = &cobra.Command{
Use: "init",
Short: "Initializes the installation environment",
type InitOptions struct {
CommonOptions *options.CommonOptions
}
func init() {
rootCmd.AddCommand(initCmd)
func NewInitOptions() *InitOptions {
return &InitOptions{
CommonOptions: options.NewCommonOptions(),
}
}
// NewCmdInit create a new init command
func NewCmdInit() *cobra.Command {
o := NewInitOptions()
cmd := &cobra.Command{
Use: "init",
Short: "Initializes the installation environment",
}
o.CommonOptions.AddCommonFlag(cmd)
cmd.AddCommand(NewCmdInitOs())
return cmd
}

69
cmd/ctl/init/init_os.go Normal file
View File

@ -0,0 +1,69 @@
/*
Copyright 2020 The KubeSphere Authors.
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 init
import (
"github.com/kubesphere/kubekey/cmd/ctl/options"
"github.com/kubesphere/kubekey/cmd/ctl/util"
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/spf13/cobra"
)
type InitOsOptions struct {
CommonOptions *options.CommonOptions
ClusterCfgFile string
SourcesDir string
AddImagesRepo bool
}
func NewInitOsOptions() *InitOsOptions {
return &InitOsOptions{
CommonOptions: options.NewCommonOptions(),
}
}
// NewCmdInitOs creates a new init os command
func NewCmdInitOs() *cobra.Command {
o := NewInitOsOptions()
cmd := &cobra.Command{
Use: "os",
Short: "Init operating system",
Run: func(cmd *cobra.Command, args []string) {
util.CheckErr(o.Run())
},
}
o.CommonOptions.AddCommonFlag(cmd)
o.AddFlags(cmd)
return cmd
}
func (o *InitOsOptions) Run() error {
arg := common.Argument{
FilePath: o.ClusterCfgFile,
SourcesDir: o.SourcesDir,
AddImagesRepo: o.AddImagesRepo,
Debug: o.CommonOptions.Verbose,
}
return pipelines.InitDependencies(arg)
}
func (o *InitOsOptions) AddFlags(cmd *cobra.Command) {
cmd.Flags().StringVarP(&o.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
cmd.Flags().StringVarP(&o.SourcesDir, "sources", "s", "", "Path to the dependencies' dir")
cmd.Flags().BoolVarP(&o.AddImagesRepo, "add-images-repo", "", false, "Create a local images registry")
}

View File

@ -0,0 +1,23 @@
package options
import (
"github.com/spf13/cobra"
)
type CommonOptions struct {
InCluster bool
Verbose bool
SkipConfirmCheck bool
IgnoreErr bool
}
func NewCommonOptions() *CommonOptions {
return &CommonOptions{}
}
func (o *CommonOptions) AddCommonFlag(cmd *cobra.Command) {
cmd.Flags().BoolVar(&o.InCluster, "in-cluster", false, "Running inside the cluster")
cmd.Flags().BoolVar(&o.Verbose, "debug", true, "Print detailed information")
cmd.Flags().BoolVarP(&o.SkipConfirmCheck, "yes", "y", false, "Skip confirm check")
cmd.Flags().BoolVar(&o.IgnoreErr, "ignore-err", false, "Ignore the error message, remove the host which reported error and force to continue")
}

62
cmd/ctl/root.go Normal file
View File

@ -0,0 +1,62 @@
/*
Copyright 2020 The KubeSphere Authors.
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 ctl
import (
"github.com/kubesphere/kubekey/cmd/ctl/add"
"github.com/kubesphere/kubekey/cmd/ctl/cert"
"github.com/kubesphere/kubekey/cmd/ctl/completion"
"github.com/kubesphere/kubekey/cmd/ctl/create"
"github.com/kubesphere/kubekey/cmd/ctl/delete"
initOs "github.com/kubesphere/kubekey/cmd/ctl/init"
"github.com/kubesphere/kubekey/cmd/ctl/upgrade"
"github.com/kubesphere/kubekey/cmd/ctl/version"
"github.com/spf13/cobra"
)
func NewDefaultKubeKeyCommand() *cobra.Command {
return NewDefaultKubeKeyCommandWithArgs()
}
func NewDefaultKubeKeyCommandWithArgs() *cobra.Command {
cmd := NewKubeKeyCommand()
return cmd
}
// NewKubeKeyCommand creates a new kubekey root command
func NewKubeKeyCommand() *cobra.Command {
cmds := &cobra.Command{
Use: "kk",
Short: "Kubernetes/KubeSphere Deploy Tool",
Long: `Deploy a Kubernetes or KubeSphere cluster efficiently, flexibly and easily. There are three scenarios to use KubeKey.
1. Install Kubernetes only
2. Install Kubernetes and KubeSphere together in one command
3. Install Kubernetes first, then deploy KubeSphere on it using https://github.com/kubesphere/ks-installer`,
}
cmds.AddCommand(initOs.NewCmdInit())
cmds.AddCommand(create.NewCmdCreate())
cmds.AddCommand(delete.NewCmdDelete())
cmds.AddCommand(add.NewCmdAdd())
cmds.AddCommand(upgrade.NewCmdUpgrade())
cmds.AddCommand(cert.NewCmdCerts())
cmds.AddCommand(completion.NewCmdCompletion())
cmds.AddCommand(version.NewCmdVersion())
return cmds
}

110
cmd/ctl/upgrade/upgrade.go Normal file
View File

@ -0,0 +1,110 @@
/*
Copyright 2020 The KubeSphere Authors.
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 upgrade
import (
"fmt"
"github.com/kubesphere/kubekey/cmd/ctl/options"
"github.com/kubesphere/kubekey/cmd/ctl/util"
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/kubesphere/kubekey/pkg/version/kubesphere"
"github.com/kubesphere/kubekey/version"
"github.com/spf13/cobra"
"time"
)
type UpgradeOptions struct {
CommonOptions *options.CommonOptions
ClusterCfgFile string
Kubernetes string
EnableKubeSphere bool
KubeSphere string
SkipPullImages bool
DownloadCmd string
}
func NewUpgradeOptions() *UpgradeOptions {
return &UpgradeOptions{
CommonOptions: options.NewCommonOptions(),
}
}
// NewCmdUpgrade creates a new upgrade command
func NewCmdUpgrade() *cobra.Command {
o := NewUpgradeOptions()
cmd := &cobra.Command{
Use: "upgrade",
Short: "Upgrade your cluster smoothly to a newer version with this command",
Run: func(cmd *cobra.Command, args []string) {
util.CheckErr(o.Complete(cmd, args))
util.CheckErr(o.Run())
},
}
o.CommonOptions.AddCommonFlag(cmd)
o.AddFlags(cmd)
if err := completionSetting(cmd); err != nil {
panic(fmt.Sprintf("Got error with the completion setting"))
}
return cmd
}
func (o *UpgradeOptions) Complete(cmd *cobra.Command, args []string) error {
var ksVersion string
if o.EnableKubeSphere && len(args) > 0 {
ksVersion = args[0]
} else {
ksVersion = kubesphere.Latest().Version
}
o.KubeSphere = ksVersion
return nil
}
func (o *UpgradeOptions) Run() error {
arg := common.Argument{
FilePath: o.ClusterCfgFile,
KubernetesVersion: o.Kubernetes,
KsEnable: o.EnableKubeSphere,
KsVersion: o.KubeSphere,
SkipPullImages: o.SkipPullImages,
Debug: o.CommonOptions.Verbose,
}
return pipelines.UpgradeCluster(arg, o.DownloadCmd)
}
func (o *UpgradeOptions) AddFlags(cmd *cobra.Command) {
cmd.Flags().StringVarP(&o.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
cmd.Flags().StringVarP(&o.Kubernetes, "with-kubernetes", "", "", "Specify a supported version of kubernetes")
cmd.Flags().BoolVarP(&o.EnableKubeSphere, "with-kubesphere", "", false, "Deploy a specific version of kubesphere (default v3.2.0)")
cmd.Flags().BoolVarP(&o.SkipPullImages, "skip-pull-images", "", false, "Skip pre pull images")
cmd.Flags().StringVarP(&o.DownloadCmd, "download-cmd", "", "curl -L -o %s %s",
`The user defined command to download the necessary binary files. The first param '%s' is output path, the second param '%s', is the URL`)
}
func completionSetting(cmd *cobra.Command) (err error) {
cmd.ValidArgsFunction = func(cmd *cobra.Command, args []string, toComplete string) (
strings []string, directive cobra.ShellCompDirective) {
versionArray := []string{"v2.1.1", "v3.0.0", "v3.1.0", "v3.1.1", "v3.2.0", time.Now().Add(-time.Hour * 24).Format("nightly-20060102")}
return versionArray, cobra.ShellCompDirectiveNoFileComp
}
err = cmd.RegisterFlagCompletionFunc("with-kubernetes", func(cmd *cobra.Command, args []string, toComplete string) (
strings []string, directive cobra.ShellCompDirective) {
return version.SupportedK8sVersionList(), cobra.ShellCompDirectiveNoFileComp
})
return
}

45
cmd/ctl/util/helpers.go Normal file
View File

@ -0,0 +1,45 @@
package util
import (
"fmt"
"os"
"strings"
)
const DefaultErrorExitCode = 1
var ErrExit = fmt.Errorf("exit")
func fatal(msg string, code int) {
if len(msg) > 0 {
// add newline if needed
if !strings.HasSuffix(msg, "\n") {
msg += "\n"
}
fmt.Fprint(os.Stderr, msg)
}
os.Exit(code)
}
var fatalErrHandler = fatal
func CheckErr(err error) {
checkErr(err, fatalErrHandler)
}
func checkErr(err error, handleErr func(string, int)) {
if err == nil {
return
}
switch {
case err == ErrExit:
handleErr("", DefaultErrorExitCode)
default:
msg := err.Error()
if !strings.HasPrefix(msg, "error: ") {
msg = fmt.Sprintf("error: %s", msg)
}
handleErr(msg, DefaultErrorExitCode)
}
}

View File

@ -14,7 +14,7 @@ See the License for the specific language governing permissions and
limitations under the License.
*/
package cmd
package version
import (
"fmt"
@ -24,25 +24,36 @@ import (
"strings"
)
var shortVersion bool
var showSupportedK8sVersionList bool
// versionCmd represents the version command
var versionCmd = &cobra.Command{
Use: "version",
Short: "print the client version information",
RunE: func(cmd *cobra.Command, _ []string) error {
if showSupportedK8sVersionList {
return printSupportedK8sVersionList(cmd.OutOrStdout())
}
return printVersion(shortVersion)
},
type VersionOptions struct {
ShortVersion bool
ShowSupportedK8sVersionList bool
}
func init() {
rootCmd.AddCommand(versionCmd)
versionCmd.Flags().BoolVarP(&shortVersion, "short", "", false, "print the version number")
versionCmd.Flags().BoolVarP(&showSupportedK8sVersionList, "show-supported-k8s", "", false,
func NewVersionOptions() *VersionOptions {
return &VersionOptions{}
}
// NewCmdVersion creates a new version command
func NewCmdVersion() *cobra.Command {
o := NewVersionOptions()
cmd := &cobra.Command{
Use: "version",
Short: "print the client version information",
RunE: func(cmd *cobra.Command, _ []string) error {
if o.ShowSupportedK8sVersionList {
return printSupportedK8sVersionList(cmd.OutOrStdout())
}
return printVersion(o.ShortVersion)
},
}
o.AddFlags(cmd)
return cmd
}
func (o *VersionOptions) AddFlags(cmd *cobra.Command) {
cmd.Flags().BoolVarP(&o.ShortVersion, "short", "", false, "print the version number")
cmd.Flags().BoolVarP(&o.ShowSupportedK8sVersionList, "show-supported-k8s", "", false,
`print the version of supported k8s`)
}

View File

@ -1,25 +0,0 @@
package cmd
import (
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/spf13/cobra"
)
var deleteClusterCmd = &cobra.Command{
Use: "cluster",
Short: "Delete a cluster",
RunE: func(cmd *cobra.Command, args []string) error {
arg := common.Argument{
FilePath: opt.ClusterCfgFile,
Debug: opt.Verbose,
}
return pipelines.DeleteCluster(arg)
},
}
func init() {
deleteCmd.AddCommand(deleteClusterCmd)
deleteClusterCmd.Flags().StringVarP(&opt.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
}

View File

@ -1,33 +0,0 @@
package cmd
import (
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/pkg/errors"
"github.com/spf13/cobra"
"strings"
)
var deleteNodeCmd = &cobra.Command{
Use: "node",
Short: "delete a node",
PreRunE: func(cmd *cobra.Command, args []string) error {
if len(args) == 0 {
return errors.New("node can not be empty")
}
return nil
},
RunE: func(cmd *cobra.Command, args []string) error {
arg := common.Argument{
FilePath: opt.ClusterCfgFile,
Debug: opt.Verbose,
NodeName: strings.Join(args, ""),
}
return pipelines.DeleteNode(arg)
},
}
func init() {
deleteCmd.AddCommand(deleteNodeCmd)
deleteNodeCmd.Flags().StringVarP(&opt.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
}

View File

@ -1,44 +0,0 @@
/*
Copyright 2020 The KubeSphere Authors.
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 cmd
import (
"github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/spf13/cobra"
)
// osCmd represents the os command
var osCmd = &cobra.Command{
Use: "os",
Short: "Init operating system",
RunE: func(cmd *cobra.Command, args []string) error {
arg := common.Argument{
FilePath: opt.ClusterCfgFile,
SourcesDir: opt.SourcesDir,
AddImagesRepo: opt.AddImagesRepo,
Debug: opt.Verbose,
}
return pipelines.InitDependencies(arg)
},
}
func init() {
initCmd.AddCommand(osCmd)
osCmd.Flags().StringVarP(&opt.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
osCmd.Flags().StringVarP(&opt.SourcesDir, "sources", "s", "", "Path to the dependencies' dir")
osCmd.Flags().BoolVarP(&opt.AddImagesRepo, "add-images-repo", "", false, "Create a local images registry")
}

View File

@ -1,34 +0,0 @@
/*
Copyright 2020 The KubeSphere Authors.
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 cmd
import (
"github.com/spf13/cobra"
)
// osCmd represents the os command
var registryCmd = &cobra.Command{
Use: "registry",
Short: "Init a local image registry",
RunE: func(cmd *cobra.Command, args []string) error {
return nil
},
}
func init() {
initCmd.AddCommand(registryCmd)
registryCmd.Flags().StringVarP(&opt.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
}

View File

@ -1,25 +0,0 @@
package cmd
import (
common2 "github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/spf13/cobra"
)
var listClusterCertsCmd = &cobra.Command{
Use: "check-expiration",
Short: "Check certificates expiration for a Kubernetes cluster",
RunE: func(cmd *cobra.Command, args []string) error {
arg := common2.Argument{
FilePath: opt.ClusterCfgFile,
Debug: opt.Verbose,
}
return pipelines.CheckCerts(arg)
},
}
func init() {
certsCmd.AddCommand(listClusterCertsCmd)
listClusterCertsCmd.Flags().StringVarP(&opt.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
}

View File

@ -17,10 +17,21 @@ limitations under the License.
package main
import (
"github.com/kubesphere/kubekey/cmd"
"github.com/kubesphere/kubekey/cmd/ctl"
"os"
"os/exec"
)
// Using a separate entry-point can reduce the size of the binary file
func main() {
cmd.Execute()
cmd := ctl.NewDefaultKubeKeyCommand()
_ = exec.Command("/bin/bash", "-c", "ulimit -u 65535").Run()
_ = exec.Command("/bin/bash", "-c", "ulimit -n 65535").Run()
// Execute adds all child commands to the root command and sets flags appropriately.
// This is called by main.main(). It only needs to happen once to the rootCmd.
if err := cmd.Execute(); err != nil {
//fmt.Println(err)
os.Exit(1)
}
}

View File

@ -1,25 +0,0 @@
package cmd
import (
common2 "github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/spf13/cobra"
)
var renewClusterCertsCmd = &cobra.Command{
Use: "renew",
Short: "renew a cluster certs",
RunE: func(cmd *cobra.Command, args []string) error {
arg := common2.Argument{
FilePath: opt.ClusterCfgFile,
Debug: opt.Verbose,
}
return pipelines.RenewCerts(arg)
},
}
func init() {
certsCmd.AddCommand(renewClusterCertsCmd)
renewClusterCertsCmd.Flags().StringVarP(&opt.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
}

View File

@ -1,82 +0,0 @@
/*
Copyright 2020 The KubeSphere Authors.
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 cmd
import (
"github.com/spf13/cobra"
"os"
"os/exec"
)
type Options struct {
Verbose bool
IgnoreErr bool
Addons string
Name string
ClusterCfgPath string
Kubeconfig string
FromCluster bool
ClusterCfgFile string
Kubernetes string
Kubesphere bool
LocalStorage bool
SkipPullImages bool
KsVersion string
Registry string
SourcesDir string
AddImagesRepo bool
ContainerManager string
InCluster bool
DownloadCmd string
SkipConfirmCheck bool
}
var (
opt Options
)
// rootCmd represents the base command when called without any subcommands
var rootCmd = &cobra.Command{
Use: "kk",
Short: "Kubernetes/KubeSphere Deploy Tool",
Long: `Deploy a Kubernetes or KubeSphere cluster efficiently, flexibly and easily. There are three scenarios to use KubeKey.
1. Install Kubernetes only
2. Install Kubernetes and KubeSphere together in one command
3. Install Kubernetes first, then deploy KubeSphere on it using https://github.com/kubesphere/ks-installer`,
}
// Execute adds all child commands to the root command and sets flags appropriately.
// This is called by main.main(). It only needs to happen once to the rootCmd.
func Execute() {
_ = exec.Command("/bin/bash", "-c", "ulimit -u 65535").Run()
_ = exec.Command("/bin/bash", "-c", "ulimit -n 65535").Run()
if err := rootCmd.Execute(); err != nil {
//fmt.Println(err)
os.Exit(1)
}
}
func init() {
// Here you will define your flags and configuration settings.
// Cobra supports persistent flags, which, if defined here,
// will be global for your application.
rootCmd.PersistentFlags().BoolVar(&opt.InCluster, "in-cluster", false, "Running inside the cluster")
rootCmd.PersistentFlags().BoolVar(&opt.Verbose, "debug", true, "Print detailed information")
rootCmd.PersistentFlags().BoolVarP(&opt.SkipConfirmCheck, "yes", "y", false, "Skip confirm check")
rootCmd.PersistentFlags().BoolVar(&opt.IgnoreErr, "ignore-err", false, "Ignore the error message, remove the host which reported error and force to continue")
// Cobra also supports local flags, which will only run
// when this action is called directly.
}

View File

@ -1,64 +0,0 @@
/*
Copyright 2020 The KubeSphere Authors.
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 cmd
import (
"fmt"
common2 "github.com/kubesphere/kubekey/pkg/common"
"github.com/kubesphere/kubekey/pkg/pipelines"
"github.com/spf13/cobra"
)
// upgradeCmd represents the upgrade command
var upgradeCmd = &cobra.Command{
Use: "upgrade",
Short: "Upgrade your cluster smoothly to a newer version with this command",
RunE: func(cmd *cobra.Command, args []string) error {
var ksVersion string
if opt.Kubesphere && len(args) > 0 {
ksVersion = args[0]
} else {
ksVersion = ""
}
arg := common2.Argument{
FilePath: opt.ClusterCfgFile,
KubernetesVersion: opt.Kubernetes,
KsEnable: opt.Kubesphere,
KsVersion: ksVersion,
SkipConfirmCheck: opt.SkipConfirmCheck,
SkipPullImages: opt.SkipPullImages,
InCluster: opt.InCluster,
DeployLocalStorage: opt.LocalStorage,
Debug: opt.Verbose,
}
return pipelines.UpgradeCluster(arg, opt.DownloadCmd)
},
}
func init() {
rootCmd.AddCommand(upgradeCmd)
upgradeCmd.Flags().StringVarP(&opt.ClusterCfgFile, "filename", "f", "", "Path to a configuration file")
upgradeCmd.Flags().StringVarP(&opt.Kubernetes, "with-kubernetes", "", "", "Specify a supported version of kubernetes")
upgradeCmd.Flags().BoolVarP(&opt.Kubesphere, "with-kubesphere", "", false, "Deploy a specific version of kubesphere (default v3.1.0)")
upgradeCmd.Flags().BoolVarP(&opt.SkipPullImages, "skip-pull-images", "", false, "Skip pre pull images")
upgradeCmd.Flags().StringVarP(&opt.DownloadCmd, "download-cmd", "", "curl -L -o %s %s",
`The user defined command to download the necessary binary files. The first param '%s' is output path, the second param '%s', is the URL`)
if err := setValidArgs(upgradeCmd); err != nil {
panic(fmt.Sprintf("Got error with the completion setting"))
}
}

1
go.sum
View File

@ -920,7 +920,6 @@ github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXf
github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4=
github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA=
github.com/stretchr/testify v1.6.1 h1:hDPOHmpOpP40lSULcqw7IrRb/u7w6RpDC9399XyoNd0=
github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5CcY=
github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=