Skip to content

Commit

Permalink
Merge pull request #56 from aris-bunnyshell/feat/component-variables
Browse files Browse the repository at this point in the history
feat: add component variables management commands
  • Loading branch information
aris-bunnyshell authored Feb 14, 2024
2 parents a9c7682 + c91de8f commit 8044cc0
Show file tree
Hide file tree
Showing 31 changed files with 1,016 additions and 21 deletions.
12 changes: 12 additions & 0 deletions cmd/component/root.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package component

import (
"bunnyshell.com/cli/cmd/component/action"
"bunnyshell.com/cli/cmd/component/variable"
"bunnyshell.com/cli/pkg/config"
"bunnyshell.com/cli/pkg/util"
"github.com/spf13/cobra"
Expand Down Expand Up @@ -33,6 +34,17 @@ func init() {
},
action.GetMainCommand().Commands(),
)

util.AddGroupedCommands(
mainCmd,
cobra.Group{
ID: "variables",
Title: "Commands for Component Variables:",
},
[]*cobra.Command{variable.GetMainCommand()},
)

config.MainManager.CommandWithGlobalOptions(mainCmd)
}

func GetMainCommand() *cobra.Command {
Expand Down
107 changes: 107 additions & 0 deletions cmd/component/variable/action/create.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
package action

import (
"fmt"
"io"
"os"

"bunnyshell.com/cli/pkg/api/component_variable"
"bunnyshell.com/cli/pkg/config"
"bunnyshell.com/cli/pkg/lib"
"bunnyshell.com/cli/pkg/util"
"bunnyshell.com/sdk"
"github.com/spf13/cobra"
)

func init() {
settings := config.GetSettings()

createOptions := component_variable.NewCreateOptions()
var componentName string

command := &cobra.Command{
Use: "create",

ValidArgsFunction: cobra.NoFileCompletions,

PreRunE: func(cmd *cobra.Command, args []string) error {
hasStdin, err := util.IsStdinPresent()
if err != nil {
return err
}

flags := cmd.Flags()
if !flags.Changed("value") && !hasStdin {
return errMissingValue
}

if flags.Changed("value") && hasStdin {
return errMultipleValueInputs
}

if !flags.Changed("component-name") {
cmd.MarkFlagRequired("component")
}

return nil
},

RunE: func(cmd *cobra.Command, args []string) error {
createOptions.ServiceComponent = settings.Profile.Context.ServiceComponent

if componentName != "" {
component, err := findComponentByName(componentName, &settings.Profile)
if err != nil {
return err
}
createOptions.ServiceComponent = component.GetId()
}

hasStdin, err := util.IsStdinPresent()
if err != nil {
return err
}

if hasStdin {
buf, err := io.ReadAll(os.Stdin)
if err != nil {
return err
}

createOptions.Value = string(buf)
}

model, err := component_variable.Create(createOptions)
if err != nil {
return lib.FormatCommandError(cmd, err)
}

return lib.FormatCommandData(cmd, model)
},
}

flags := command.Flags()

updateComponentIdentifierFlags(command, &componentName)

createOptions.UpdateFlagSet(flags)

mainCmd.AddCommand(command)
}

func findComponentByName(componentName string, profile *config.Profile) (*sdk.ComponentCollection, error) {
matchedComponents, err := findComponentsByName(componentName, profile)
if err != nil {
return nil, fmt.Errorf("failed while searching for the component: %w", err)
}

if matchedComponents.GetTotalItems() == 0 {
return nil, fmt.Errorf("component '%s' not found", componentName)
}

if matchedComponents.GetTotalItems() > 1 {
return nil, fmt.Errorf("multiple components with the name '%s' were found", componentName)
}

return &matchedComponents.GetEmbedded().Item[0], nil
}
53 changes: 53 additions & 0 deletions cmd/component/variable/action/delete.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
package action

import (
"bunnyshell.com/cli/pkg/api/component_variable"
"bunnyshell.com/cli/pkg/config"
"bunnyshell.com/cli/pkg/lib"
"github.com/spf13/cobra"
)

func init() {
var componentName string
var componentVariableName string

settings := config.GetSettings()

deleteOptions := component_variable.NewDeleteOptions()

command := &cobra.Command{
Use: "delete",

ValidArgsFunction: cobra.NoFileCompletions,

RunE: func(cmd *cobra.Command, args []string) error {
if componentVariableName != "" {
componentVariable, err := findComponentVariableByName(componentVariableName, componentName, &settings.Profile)
if err != nil {
return err
}
deleteOptions.ID = componentVariable.GetId()
}

err := component_variable.Delete(deleteOptions)
if err != nil {
return lib.FormatCommandError(cmd, err)
}

cmd.Printf("\nComponent variable %s successfully deleted\n", deleteOptions.ID)

return nil
},
}

flags := command.Flags()

flags.AddFlag(GetIDOption(&deleteOptions.ID).GetFlag("id"))
flags.StringVar(&componentVariableName, "name", componentVariableName, "Component Variable Name")
command.MarkFlagsMutuallyExclusive("name", "id")

updateComponentIdentifierFlags(command, &componentName)
command.MarkFlagsMutuallyExclusive("component-name", "id", "component")

mainCmd.AddCommand(command)
}
94 changes: 94 additions & 0 deletions cmd/component/variable/action/edit.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,94 @@
package action

import (
"io"
"os"

"bunnyshell.com/cli/pkg/api/component_variable"
"bunnyshell.com/cli/pkg/config"
"bunnyshell.com/cli/pkg/lib"
"bunnyshell.com/cli/pkg/util"
"github.com/spf13/cobra"
)

func init() {
var componentName string
var componentVariableName string

settings := config.GetSettings()

editOptions := component_variable.NewEditOptions("")

command := &cobra.Command{
Use: "edit",

ValidArgsFunction: cobra.NoFileCompletions,

PreRunE: func(cmd *cobra.Command, args []string) error {
hasStdin, err := util.IsStdinPresent()
if err != nil {
return err
}

flags := cmd.Flags()
if flags.Changed("value") && hasStdin {
return errMultipleValueInputs
}

if flags.Changed("name") && !flags.Changed("component-name") && settings.Profile.Context.ServiceComponent == "" {
return errComponentRequired
}

return nil
},

RunE: func(cmd *cobra.Command, args []string) error {
flags := cmd.Flags()
if flags.Changed("value") {
editOptions.ServiceComponentVariableEditAction.SetValue(flags.Lookup("value").Value.String())
}

if componentVariableName != "" {
componentVariable, err := findComponentVariableByName(componentVariableName, componentName, &settings.Profile)
if err != nil {
return err
}
editOptions.ID = componentVariable.GetId()
}

hasStdin, err := util.IsStdinPresent()
if err != nil {
return err
}

if hasStdin {
buf, err := io.ReadAll(os.Stdin)
if err != nil {
return err
}

editOptions.ServiceComponentVariableEditAction.SetValue(string(buf))
}

model, err := component_variable.Edit(editOptions)
if err != nil {
return lib.FormatCommandError(cmd, err)
}

return lib.FormatCommandData(cmd, model)
},
}

flags := command.Flags()

flags.AddFlag(GetIDOption(&editOptions.ID).GetFlag("id"))
flags.StringVar(&componentVariableName, "name", componentVariableName, "Component Variable Name")
command.MarkFlagsMutuallyExclusive("name", "id")

updateComponentIdentifierFlags(command, &componentName)
command.MarkFlagsMutuallyExclusive("component-name", "id", "component")

editOptions.UpdateFlagSet(flags)

mainCmd.AddCommand(command)
}
112 changes: 112 additions & 0 deletions cmd/component/variable/action/root.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,112 @@
package action

import (
"errors"
"fmt"

"bunnyshell.com/cli/pkg/api/component"
"bunnyshell.com/cli/pkg/api/component_variable"
"bunnyshell.com/cli/pkg/build"
"bunnyshell.com/cli/pkg/config"
"bunnyshell.com/cli/pkg/config/option"
"bunnyshell.com/sdk"
"github.com/spf13/cobra"
)

var (
errMissingValue = errors.New("the plain value must be provided")
errMultipleValueInputs = errors.New("the value must be provided either by argument or by stdin, not both")
errComponentRequired = errors.New("either the 'component' or the 'component-name' arguments are required")
)

var mainCmd = &cobra.Command{}

func GetMainCommand() *cobra.Command {
return mainCmd
}

func GetIDOption(value *string) *option.String {
help := fmt.Sprintf(
`Find available component variables with "%s variables list"`,
build.Name,
)

idOption := option.NewStringOption(value)

idOption.AddFlagWithExtraHelp("id", "Component Variable Id", help)

return idOption
}

func updateComponentIdentifierFlags(cmd *cobra.Command, componentName *string) {
options := config.GetOptions()

flags := cmd.Flags()

flags.AddFlag(options.ServiceComponent.AddFlagWithExtraHelp(
"component",
"Component for the variable",
"Components contain multiple variables",
))

flags.StringVar(componentName, "component-name", *componentName, "Component Name")
cmd.MarkFlagsMutuallyExclusive("component-name", "component")

flags.AddFlag(options.Organization.GetFlag("organization"))
flags.AddFlag(options.Project.GetFlag("project"))
flags.AddFlag(options.Environment.GetFlag("environment"))
}

func findComponentsByName(componentName string, profile *config.Profile) (*sdk.PaginatedComponentCollection, error) {
listOptions := component.NewListOptions()

listOptions.Organization = profile.Context.Organization
listOptions.Project = profile.Context.Project
listOptions.Environment = profile.Context.Environment
listOptions.Name = componentName

components, error := component.List(listOptions)
if error != nil {
return nil, error
}

return components, nil
}

func findComponentVariablesByName(componentVariableName string, componentName string, profile *config.Profile) (*sdk.PaginatedServiceComponentVariableCollection, error) {
listOptions := component_variable.NewListOptions()

listOptions.Organization = profile.Context.Organization
listOptions.Project = profile.Context.Project
listOptions.Environment = profile.Context.Environment
listOptions.Component = profile.Context.ServiceComponent
listOptions.Name = componentVariableName

if componentName != "" {
listOptions.ComponentName = componentName
}

component_variables, error := component_variable.List(listOptions)
if error != nil {
return nil, error
}

return component_variables, nil
}

func findComponentVariableByName(componentVariableName string, componentName string, profile *config.Profile) (*sdk.ServiceComponentVariableCollection, error) {
matchedComponentVariables, err := findComponentVariablesByName(componentVariableName, componentName, profile)
if err != nil {
return nil, fmt.Errorf("failed while searching for the component variable: %w", err)
}

if matchedComponentVariables.GetTotalItems() == 0 {
return nil, fmt.Errorf("component variable '%s' not found", componentVariableName)
}

if matchedComponentVariables.GetTotalItems() > 1 {
return nil, fmt.Errorf("multiple component variables '%s' were found", componentVariableName)
}

return &matchedComponentVariables.GetEmbedded().Item[0], nil
}
Loading

0 comments on commit 8044cc0

Please sign in to comment.