Skip to content

Commit

Permalink
Bootstrap support of addons for koyeb deploy
Browse files Browse the repository at this point in the history
  • Loading branch information
bchatelard committed Nov 28, 2024
1 parent 0d33b78 commit daec4b2
Show file tree
Hide file tree
Showing 4 changed files with 152 additions and 0 deletions.
40 changes: 40 additions & 0 deletions pkg/koyeb/deploy.go
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,22 @@ func NewDeployCmd() *cobra.Command {
return err
}

// Parse the flags for the addons.
addons, err := serviceHandler.parseAddonsFlags(ctx, cmd.Flags())
if err != nil {
return err
}
addonsHandler, err := NewAddonsHandler(addons)
if err != nil {
return err
}

// Setup the addons.
if err := addonsHandler.Setup(ctx); err != nil {
return err
}
defer addonsHandler.Cleanup(ctx)

if serviceId == "" {
createService := koyeb.NewCreateServiceWithDefaults()
createDefinition := koyeb.NewDeploymentDefinitionWithDefaults()
Expand All @@ -79,10 +95,17 @@ func NewDeployCmd() *cobra.Command {
}
createService.SetDefinition(*createDefinition)

if err = addonsHandler.PreDeploy(ctx, createDefinition); err != nil {
return err
}

log.Infof("Creating the new service `%s`", serviceName)
if err := serviceHandler.Create(ctx, cmd, []string{args[1]}, createService); err != nil {
return err
}
if err = addonsHandler.PostDeploy(ctx, createDefinition); err != nil {
return err
}
} else {
updateService := koyeb.NewUpdateServiceWithDefaults()
latestDeploy, resp, err := ctx.Client.DeploymentsApi.
Expand Down Expand Up @@ -136,17 +159,34 @@ func NewDeployCmd() *cobra.Command {
}
updateService.SetDefinition(*updateDefinition)

if err = addonsHandler.PreDeploy(ctx, updateDefinition); err != nil {
return err
}

log.Infof("Updating the existing service `%s`", serviceName)
if err := serviceHandler.Update(ctx, cmd, []string{args[1]}, updateService); err != nil {
return err
}
if err = addonsHandler.PostDeploy(ctx, updateDefinition); err != nil {
return err
}
}

return nil
}),
}
deployCmd.Flags().String("app", "", "Service application. Can also be provided in the service name with the format <app>/<service>")
serviceHandler.addServiceDefinitionFlagsForAllSources(deployCmd.Flags())
serviceHandler.addServiceDefinitionFlagsForArchiveSource(deployCmd.Flags())

// Add addons flags to the deploy command.
deployCmd.Flags().StringSlice(
"addons",
[]string{},
"List of addons, the addons will be executed localy before the deployment",
)
deployCmd.Flags().MarkHidden("addons")

return deployCmd
}

Expand Down
75 changes: 75 additions & 0 deletions pkg/koyeb/deploy_addons.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
package koyeb

import (
"fmt"

"github.com/koyeb/koyeb-api-client-go/api/v1/koyeb"
)

type addonsHandler struct {
addons []Addon
}

func NewAddonsHandler(addons []string) (*addonsHandler, error) {
handler := &addonsHandler{}

for _, addon := range addons {
err := handler.RegisterAddon(addon)
if err != nil {
return nil, err
}
}

return handler, nil
}

type Addon interface {
Setup(ctx *CLIContext) error
PreDeploy(ctx *CLIContext, definition *koyeb.DeploymentDefinition) error
PostDeploy(ctx *CLIContext, definition *koyeb.DeploymentDefinition) error
Cleanup(ctx *CLIContext) error
}

func (h *addonsHandler) RegisterAddon(name string) error {
switch name {
default:
return fmt.Errorf("unknown addon: %s", name)
}
return nil
}

func (h *addonsHandler) PreDeploy(ctx *CLIContext, definition *koyeb.DeploymentDefinition) error {
for _, addon := range h.addons {
if err := addon.PreDeploy(ctx, definition); err != nil {
return err
}
}
return nil
}

func (h *addonsHandler) PostDeploy(ctx *CLIContext, definition *koyeb.DeploymentDefinition) error {
for _, addon := range h.addons {
if err := addon.PostDeploy(ctx, definition); err != nil {
return err
}
}
return nil
}

func (h *addonsHandler) Setup(ctx *CLIContext) error {
for _, addon := range h.addons {
if err := addon.Setup(ctx); err != nil {
return err
}
}
return nil
}

func (h *addonsHandler) Cleanup(ctx *CLIContext) error {
for _, addon := range h.addons {
if err := addon.Cleanup(ctx); err != nil {
return err
}
}
return nil
}
27 changes: 27 additions & 0 deletions pkg/koyeb/flags_list/addons.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
package flags_list

type FlagAddon struct {
BaseFlag
}

func NewAddonsListFromFlags(values []string) ([]Flag[string], error) {
ret := make([]Flag[string], 0, len(values))

for _, value := range values {
addon := &FlagAddon{BaseFlag: BaseFlag{cliValue: value}}

ret = append(ret, addon)
}
return ret, nil
}

func (f *FlagAddon) IsEqualTo(item string) bool {
return f.cliValue == item
}

func (f *FlagAddon) UpdateItem(item *string) {
}

func (f *FlagAddon) CreateNewItem() *string {
return &f.cliValue
}
10 changes: 10 additions & 0 deletions pkg/koyeb/services.go
Original file line number Diff line number Diff line change
Expand Up @@ -615,6 +615,16 @@ func (h *ServiceHandler) parseDeploymentStrategy(flags *pflag.FlagSet, currentSt
}, nil
}

// Parse --addons
func (h *ServiceHandler) parseAddonsFlags(ctx *CLIContext, flags *pflag.FlagSet) ([]string, error) {
addons := []string{}
parseListFlags("addons", flags_list.NewAddonsListFromFlags, flags, addons)
if !flags.Lookup("addons").Changed {
return addons, nil
}
return addons, nil
}

// parseListFlags is the generic function parsing --env, --port, --routes, --checks, --regions and --volumes
// It gets the arguments given from the command line for the given flag, then
// builds a list of flags_list.Flag entries, and update the service
Expand Down

0 comments on commit daec4b2

Please sign in to comment.