Skip to content

Commit

Permalink
feat: migrate on upgrade (#959)
Browse files Browse the repository at this point in the history
* feat: migrate on upgrade

* feat: migrate on upgrade + remove-rds fix

* fix: typos
  • Loading branch information
exu authored Feb 10, 2022
1 parent ec1359f commit cd8145c
Show file tree
Hide file tree
Showing 6 changed files with 159 additions and 103 deletions.
96 changes: 96 additions & 0 deletions cmd/kubectl-testkube/commands/common.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,96 @@
package commands

import (
"fmt"
"os/exec"
"strings"

"github.com/kubeshop/testkube/cmd/kubectl-testkube/commands/common"
"github.com/kubeshop/testkube/internal/migrations"
"github.com/kubeshop/testkube/pkg/process"
"github.com/kubeshop/testkube/pkg/ui"
"github.com/spf13/cobra"
)

func RunMigrations(cmd *cobra.Command) (hasMigrations bool, err error) {
client, _ := common.GetClient(cmd)
info, err := client.GetServerInfo()
ui.ExitOnError("getting server info", err)

if info.Version == "" {
ui.Failf("Can't detect cluster version")
}

migrator := migrations.Migrator
ui.Info("Available migrations for", info.Version)
migrations := migrator.GetValidMigrations(info.Version)
if len(migrations) == 0 {
ui.Warn("No migrations available for", info.Version)
return false, nil
}

for _, migration := range migrations {
fmt.Printf("- %+v - %s\n", migration.Version(), migration.Info())
}

return true, migrator.Run(info.Version)
}

func HelmUpgradeOrInstalTestkube(name, namespace, chart string, noDashboard, noMinio, noJetstack bool) error {
helmPath, err := exec.LookPath("helm")
if err != nil {
return err
}

if !noJetstack {
_, err = process.Execute("kubectl", "get", "crds", "certificates.cert-manager.io")
if err != nil && !strings.Contains(err.Error(), "Error from server (NotFound)") {
return err
}

if err != nil {
ui.Info("Helm installing jetstack cert manager")
_, err = process.Execute(helmPath, "repo", "add", "jetstack", "https://charts.jetstack.io")
if err != nil && !strings.Contains(err.Error(), "Error: repository name (jetstack) already exists") {
return err
}

_, err = process.Execute(helmPath, "repo", "update")
if err != nil {
return err
}

command := []string{"upgrade", "--install", "--create-namespace", "--namespace", namespace, "--set", "installCRDs=true"}
command = append(command, "jetstack", "jetstack/cert-manager")

out, err := process.Execute(helmPath, command...)
if err != nil {
return err
}

ui.Info("Helm install jetstack output", string(out))
}
}

ui.Info("Helm installing testkube framework")
_, err = process.Execute(helmPath, "repo", "add", "kubeshop", "https://kubeshop.github.io/helm-charts")
if err != nil && !strings.Contains(err.Error(), "Error: repository name (kubeshop) already exists, please specify a different name") {
ui.WarnOnError("adding testkube repo", err)
}

_, err = process.Execute(helmPath, "repo", "update")
ui.ExitOnError("updating helm repositories", err)

command := []string{"upgrade", "--install", "--create-namespace", "--namespace", namespace}
command = append(command, "--set", fmt.Sprintf("api-server.minio.enabled=%t", !noMinio))
command = append(command, "--set", fmt.Sprintf("testkube-dashboard.enabled=%t", !noDashboard))
command = append(command, name, chart)

out, err := process.Execute(helmPath, command...)
if err != nil {
return err
}

ui.Info("Helm install testkube output", string(out))
return nil
}
79 changes: 11 additions & 68 deletions cmd/kubectl-testkube/commands/install.go
Original file line number Diff line number Diff line change
@@ -1,82 +1,25 @@
package commands

import (
"fmt"
"os/exec"
"strings"

"github.com/kubeshop/testkube/pkg/process"
"github.com/kubeshop/testkube/pkg/ui"
"github.com/spf13/cobra"
)

var (
noDashboard bool
noMinio bool
noJetstack bool
)

func NewInstallCmd() *cobra.Command {
var chart, name, namespace string
var (
noDashboard bool
noMinio bool
noJetstack bool
chart, name, namespace string
)

cmd := &cobra.Command{
Use: "install",
Short: "Install Helm chart registry in current kubectl context",
Long: `Install can be configured with use of particular `,
Aliases: []string{"update", "upgrade"},
Use: "install",
Short: "Install Helm chart registry in current kubectl context",
Long: `Install can be configured with use of particular `,
Run: func(cmd *cobra.Command, args []string) {

ui.Verbose = true

ui.Logo()
var err error

helmPath, err := exec.LookPath("helm")
ui.ExitOnError("checking helm installation path", err)

if !noJetstack {
_, err = process.Execute("kubectl", "get", "crds", "certificates.cert-manager.io")
if err != nil && !strings.Contains(err.Error(), "Error from server (NotFound)") {
ui.ExitOnError("checking cert manager installation", err)
}

if err != nil {
ui.Info("Helm installing jetstack cert manager")
_, err = process.Execute(helmPath, "repo", "add", "jetstack", "https://charts.jetstack.io")
if err != nil && !strings.Contains(err.Error(), "Error: repository name (jetstack) already exists") {
ui.ExitOnError("adding jetstack repo", err)
}

_, err = process.Execute(helmPath, "repo", "update")
ui.ExitOnError("updating helm repositories", err)

command := []string{"upgrade", "--install", "--create-namespace", "--namespace", namespace, "--set", "installCRDs=true"}
command = append(command, "jetstack", "jetstack/cert-manager")

out, err := process.Execute(helmPath, command...)

ui.ExitOnError("executing helm install jetstack", err)
ui.Info("Helm install jetstack output", string(out))
}
}

ui.Info("Helm installing testkube framework")
_, err = process.Execute(helmPath, "repo", "add", "kubeshop", "https://kubeshop.github.io/helm-charts")
if err != nil && !strings.Contains(err.Error(), "Error: repository name (kubeshop) already exists, please specify a different name") {
ui.WarnOnError("adding testkube repo", err)
}

_, err = process.Execute(helmPath, "repo", "update")
ui.ExitOnError("updating helm repositories", err)

command := []string{"upgrade", "--install", "--create-namespace", "--namespace", namespace}
command = append(command, "--set", fmt.Sprintf("api-server.minio.enabled=%t", !noMinio))
command = append(command, "--set", fmt.Sprintf("testkube-dashboard.enabled=%t", !noDashboard))
command = append(command, name, chart)

out, err := process.Execute(helmPath, command...)

ui.ExitOnError("executing helm install testkube", err)
ui.Info("Helm install testkube output", string(out))
HelmUpgradeOrInstalTestkube(name, namespace, chart, noDashboard, noMinio, noJetstack)
},
}

Expand Down
34 changes: 6 additions & 28 deletions cmd/kubectl-testkube/commands/migrate.go
Original file line number Diff line number Diff line change
@@ -1,10 +1,6 @@
package commands

import (
"fmt"

"github.com/kubeshop/testkube/cmd/kubectl-testkube/commands/common"
"github.com/kubeshop/testkube/internal/migrations"
"github.com/kubeshop/testkube/pkg/ui"
"github.com/spf13/cobra"
)
Expand All @@ -13,33 +9,15 @@ func NewMigrateCmd() *cobra.Command {
var namespace string
cmd := &cobra.Command{
Use: "migrate",
Short: "migrate command",
Long: `migrate command manages migrations`,
Short: "manual migrate command",
Long: `migrate command will run migrations greater or equals current version`,
Run: func(cmd *cobra.Command, args []string) {
ui.Logo()

client, _ := common.GetClient(cmd)
info, err := client.GetServerInfo()
ui.ExitOnError("getting server info", err)

if info.Version == "" {
ui.Failf("Can't detect cluster version")
}

migrator := migrations.Migrator
ui.Info("Available migrations for", info.Version)
migrations := migrator.GetValidMigrations(info.Version)
if len(migrations) == 0 {
ui.Warn("No migrations available for", info.Version)
}

for _, migration := range migrations {
fmt.Printf("- %+v - %s\n", migration.Version(), migration.Info())
hasMigrations, err := RunMigrations(cmd)
ui.ExitOnError("Running migrations", err)
if hasMigrations {
ui.Success("All migrations executed successfully")
}

err = migrator.Run(info.Version)
ui.ExitOnError("running migrations", err)
ui.Success("All migrations executed successfully")
},
}

Expand Down
1 change: 1 addition & 0 deletions cmd/kubectl-testkube/commands/root.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ func init() {
RootCmd.AddCommand(NewCRDsCmd())
RootCmd.AddCommand(NewVersionCmd())
RootCmd.AddCommand(NewInstallCmd())
RootCmd.AddCommand(NewUpgradeCmd())
RootCmd.AddCommand(NewUninstallCmd())
RootCmd.AddCommand(NewDashboardCmd())
RootCmd.AddCommand(NewExecutorsCmd())
Expand Down
7 changes: 0 additions & 7 deletions cmd/kubectl-testkube/commands/uninstall.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,6 @@ import (

func NewUninstallCmd() *cobra.Command {
var name, namespace string
var removeCRDs bool

cmd := &cobra.Command{
Use: "uninstall",
Expand All @@ -21,17 +20,11 @@ func NewUninstallCmd() *cobra.Command {

_, err := process.Execute("helm", "uninstall", "--namespace", namespace, name)
ui.PrintOnError("uninstalling testkube", err)

if removeCRDs {
_, err = process.Execute("kubectl", "delete", "crds", "--namespace", namespace, "scripts.tests.testkube.io", "tests.tests.testkube.io", "executors.executor.testkube.io")
ui.PrintOnError("uninstalling CRDs", err)
}
},
}

cmd.Flags().StringVar(&name, "name", "testkube", "installation name")
cmd.Flags().StringVar(&namespace, "namespace", "testkube", "namespace where to install")
cmd.Flags().BoolVar(&removeCRDs, "remove-crds", false, "wipe out Executors and Scripts CRDs")

return cmd
}
45 changes: 45 additions & 0 deletions cmd/kubectl-testkube/commands/upgrade.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
package commands

import (
"github.com/kubeshop/testkube/pkg/ui"
"github.com/spf13/cobra"
)

func NewUpgradeCmd() *cobra.Command {
var (
noDashboard bool
noMinio bool
noJetstack bool
chart, name, namespace string
)

cmd := &cobra.Command{
Use: "upgrade",
Short: "Upgrade Helm chart and run migrations",
Long: `Upgrade can be configured with use of particular `,
Aliases: []string{"update"},
Run: func(cmd *cobra.Command, args []string) {
ui.Logo()

hasMigrations, err := RunMigrations(cmd)
ui.ExitOnError("Running migrations", err)
if hasMigrations {
ui.Success("All migrations executed successfully")
}

err = HelmUpgradeOrInstalTestkube(name, namespace, chart, noDashboard, noMinio, noJetstack)
ui.ExitOnError("installing Testkube", err)

},
}

cmd.Flags().StringVar(&chart, "chart", "kubeshop/testkube", "chart name")
cmd.Flags().StringVar(&name, "name", "testkube", "installation name")
cmd.Flags().StringVar(&namespace, "namespace", "testkube", "namespace where to install")

cmd.Flags().BoolVar(&noMinio, "no-minio", false, "don't install MinIO")
cmd.Flags().BoolVar(&noDashboard, "no-dashboard", false, "don't install dashboard")
cmd.Flags().BoolVar(&noJetstack, "no-jetstack", false, "don't install Jetstack")

return cmd
}

0 comments on commit cd8145c

Please sign in to comment.