From 2c7c18dd9b2dbdef95d682de62c15bff0d89e601 Mon Sep 17 00:00:00 2001 From: Zbynek Roubalik <726523+zroubalik@users.noreply.github.com> Date: Thu, 8 Oct 2020 15:32:46 +0200 Subject: [PATCH] chore: commands are checking that Function is initialized (#162) Signed-off-by: Zbynek Roubalik --- cmd/build.go | 36 +++++++++++++++++++++++++---------- cmd/delete.go | 12 +++++++++++- cmd/describe.go | 10 ++++++++++ cmd/run.go | 49 ++++++++++++++++++++++++++++++++++++------------ docs/commands.md | 4 ++-- 5 files changed, 86 insertions(+), 25 deletions(-) diff --git a/cmd/build.go b/cmd/build.go index 789866ad..f69fbd9d 100644 --- a/cmd/build.go +++ b/cmd/build.go @@ -50,21 +50,39 @@ or reference to builderMaps in the config file e.g. "default". } func runBuild(cmd *cobra.Command, _ []string) (err error) { - config := newBuildConfig() + config := newBuildConfig().Prompt() + function, err := functionWithOverrides(config.Path, functionOverrides{Builder: config.Builder, Image: config.Image}) if err != nil { return } - // If the Function does not yet have an image name, and one was not provided - // on the command line AND a --registry was not provided, then we need to - // prompt for a registry from which we can derive an image name. - if function.Image == "" && config.Registry == "" { - fmt.Print("A registry for Function images is required. For example, 'docker.io/tigerteam'.\n\n") - config.Registry = prompt.ForString("Registry for Function images", "") + // Check if the Function has been initialized + if !function.Initialized() { + return fmt.Errorf("the given path '%v' does not contain an initialized Function. Please create one at this path before deploying.", config.Path) + } + + // If the Function does not yet have an image name and one was not provided on the command line + if function.Image == "" { + // AND a --registry was not provided, then we need to + // prompt for a registry from which we can derive an image name. if config.Registry == "" { - return fmt.Errorf("Unable to determine Function image name") + fmt.Print("A registry for Function images is required. For example, 'docker.io/tigerteam'.\n\n") + config.Registry = prompt.ForString("Registry for Function images", "") + if config.Registry == "" { + return fmt.Errorf("Unable to determine Function image name") + } } + + // We have the registry, so let's use it to derive the Function image name + config.Image = deriveImage(config.Image, config.Registry, config.Path) + function.Image = config.Image + } + + // All set, let's write changes in the config to the disk + err = function.WriteConfig() + if err != nil { + return } builder := buildpacks.NewBuilder() @@ -75,8 +93,6 @@ func runBuild(cmd *cobra.Command, _ []string) (err error) { faas.WithRegistry(config.Registry), // for deriving image name when --image not provided explicitly. faas.WithBuilder(builder)) - config.Prompt() - return client.Build(config.Path) } diff --git a/cmd/delete.go b/cmd/delete.go index de557fe7..d566512b 100644 --- a/cmd/delete.go +++ b/cmd/delete.go @@ -1,6 +1,8 @@ package cmd import ( + "fmt" + "github.com/ory/viper" "github.com/spf13/cobra" @@ -44,7 +46,15 @@ func runDelete(cmd *cobra.Command, args []string) (err error) { remover.Verbose = config.Verbose remover.Namespace = config.Namespace - function := faas.Function{Root: config.Path, Name: config.Name} + function, err := faas.NewFunction(config.Path) + if err != nil { + return + } + + // Check if the Function has been initialized + if !function.Initialized() { + return fmt.Errorf("the given path '%v' does not contain an initialized Function.", config.Path) + } client := faas.New( faas.WithVerbose(config.Verbose), diff --git a/cmd/describe.go b/cmd/describe.go index 81f2f260..0047922b 100644 --- a/cmd/describe.go +++ b/cmd/describe.go @@ -49,6 +49,16 @@ using the --namespace or -n flag, and if so this will overwrite the value in faa func runDescribe(cmd *cobra.Command, args []string) (err error) { config := newDescribeConfig(args) + function, err := faas.NewFunction(config.Path) + if err != nil { + return + } + + // Check if the Function has been initialized + if !function.Initialized() { + return fmt.Errorf("the given path '%v' does not contain an initialized Function.", config.Path) + } + describer, err := knative.NewDescriber(config.Namespace) if err != nil { return diff --git a/cmd/run.go b/cmd/run.go index f577bf5e..7a7e742e 100644 --- a/cmd/run.go +++ b/cmd/run.go @@ -1,6 +1,8 @@ package cmd import ( + "fmt" + "github.com/ory/viper" "github.com/spf13/cobra" @@ -11,6 +13,7 @@ import ( func init() { // Add the run command as a subcommand of root. root.AddCommand(runCmd) + runCmd.Flags().StringP("path", "p", cwd(), "Path to the Function project directory - $FAAS_PATH") } var runCmd = &cobra.Command{ @@ -18,28 +21,50 @@ var runCmd = &cobra.Command{ Short: "Runs the Function locally", Long: `Runs the Function locally -Runs the project in the deployable image. The project must already have been -built as an OCI container image using the 'build' command. +Runs the Function project in the current directory or in the directory +specified by the -p or --path flag in the deployable image. The project must +already have been built as an OCI container image using the 'build' command. `, - RunE: runRun, + SuggestFor: []string{"rnu"}, + PreRunE: bindEnv("path"), + RunE: runRun, } func runRun(cmd *cobra.Command, args []string) (err error) { - var ( - path = "" // defaults to current working directory - verbose = viper.GetBool("verbose") - ) + config := newRunConfig() - if len(args) == 1 { - path = args[0] + function, err := faas.NewFunction(config.Path) + if err != nil { + return + } + + // Check if the Function has been initialized + if !function.Initialized() { + return fmt.Errorf("the given path '%v' does not contain an initialized Function.", config.Path) } runner := docker.NewRunner() - runner.Verbose = verbose + runner.Verbose = config.Verbose client := faas.New( faas.WithRunner(runner), - faas.WithVerbose(verbose)) + faas.WithVerbose(config.Verbose)) - return client.Run(path) + return client.Run(config.Path) +} + +type runConfig struct { + // Path of the Function implementation on local disk. Defaults to current + // working directory of the process. + Path string + + // Verbose logging. + Verbose bool +} + +func newRunConfig() runConfig { + return runConfig{ + Path: viper.GetString("path"), + Verbose: viper.GetBool("verbose"), // defined on root + } } diff --git a/docs/commands.md b/docs/commands.md index 0e4bf596..696d16ca 100644 --- a/docs/commands.md +++ b/docs/commands.md @@ -36,7 +36,7 @@ kn faas build [-i -r -p ] ## `run` -Runs the Function project locally in the container. If a container has not yet been created, prompts the user to run `faas build`. Note: there is no option to specify a path to the project. +Runs the Function project locally in the container. If a container has not yet been created, prompts the user to run `faas build`. The user may specify a path to the project directory using the `--path` or `-p` flag. Similar `kn` command: none. @@ -47,7 +47,7 @@ faas run When run as a `kn` plugin. ```console -kn faas run +kn faas run [-p ] ``` ## `deploy`