Revert "Issue #219: added PreRunChain and PostRunChain hooks"

This reverts commit 3dbb5be47c.
As part of https://github.com/spf13/cobra/pull/220
PreRunChain and PostRunChain aren't required - the PersistentRun functions
need to be modified
This commit is contained in:
Anthony Rebello 2016-01-13 21:52:37 +05:30
parent 3dbb5be47c
commit 348f909d8b
2 changed files with 2 additions and 84 deletions

View file

@ -641,22 +641,15 @@ command.SetUsageTemplate(s string)
## PreRun or PostRun Hooks
It is possible to run functions before or after the main `Run` function of your command. The `PreRunChain`, `PersistentPreRun` and `PreRun` functions will be executed before `Run`. `PersistentPostRun`, `PostRun` and `PostRunChain` will be executed after `Run`. The `Persistent*Run` functions will be inherrited by children if they do not declare their own. These function are run in the following order:
It is possible to run functions before or after the main `Run` function of your command. The `PersistentPreRun` and `PreRun` functions will be executed before `Run`. `PersistentPostRun` and `PostRun` will be executed after `Run`. The `Persistent*Run` functions will be inherrited by children if they do not declare their own. These function are run in the following order:
- `PreRunChain`
- `PersistentPreRun`
- `PreRun`
- `Run`
- `PostRun`
- `PersistentPostRun`
- `PostRunChain`
`PreRunChain` executes all PreRunChain functions from the root to the child. `PostRunChain` executes all PostRunChain functions from the child to the root. These
are useful in cases such as setting the logger and profiling at the root level in `PreRunChain`, and stopping the profiler once the proram finishes in the `PostRunChain`, while still allowing subcommand `PreRunChain` and `PostRunChain` commands to execute for their children.
An example of two commands which use all of these features is below. When the subcommand is executed, it will run the root command's `PersistentPreRun` but not the root command's `PersistentPostRun` - because the subcommand has overridden the root command's `PersistentPostRun`. However, it will still run the root command's `PreRunChain` and `PostRunChain` in addition to the subcommand's `PreRunChain` and `PostRunChain`, because chains are supposed to execute all defined
chain functions, and not just the overridden one.
An example of two commands which use all of these features is below. When the subcommand is executed, it will run the root command's `PersistentPreRun` but not the root command's `PersistentPostRun`:
```go
package main
@ -672,9 +665,6 @@ func main() {
var rootCmd = &cobra.Command{
Use: "root [sub]",
Short: "My root command",
PreRunChain: func(cmd *cobra.Command, args []string) {
fmt.Printf("Inside rootCmd PreRunChain with args: %v\n", args)
},
PersistentPreRun: func(cmd *cobra.Command, args []string) {
fmt.Printf("Inside rootCmd PersistentPreRun with args: %v\n", args)
},
@ -690,17 +680,11 @@ func main() {
PersistentPostRun: func(cmd *cobra.Command, args []string) {
fmt.Printf("Inside rootCmd PersistentPostRun with args: %v\n", args)
},
PostRunChain: func(cmd *cobra.Command, args []string) {
fmt.Printf("Inside rootCmd PostRunChain with args: %v\n", args)
},
}
var subCmd = &cobra.Command{
Use: "sub [no options!]",
Short: "My subcommand",
PreRunChain: func(cmd *cobra.Command, args []string) {
fmt.Printf("Inside subCmd PreRunChain with args: %v\n", args)
},
PreRun: func(cmd *cobra.Command, args []string) {
fmt.Printf("Inside subCmd PreRun with args: %v\n", args)
},
@ -713,9 +697,6 @@ func main() {
PersistentPostRun: func(cmd *cobra.Command, args []string) {
fmt.Printf("Inside subCmd PersistentPostRun with args: %v\n", args)
},
PostRunChain: func(cmd *cobra.Command, args []string) {
fmt.Printf("Inside subCmd PostRunChain with args: %v\n", args)
},
}
rootCmd.AddCommand(subCmd)
@ -733,13 +714,11 @@ func main() {
Cobra also has functions where the return signature is an error. This allows for errors to bubble up to the top, providing a way to handle the errors in one location. The current list of functions that return an error is:
* PreRunChainE
* PersistentPreRunE
* PreRunE
* RunE
* PostRunE
* PersistentPostRunE
* PostRunChainE
**Example Usage using RunE:**

View file

@ -64,18 +64,12 @@ type Command struct {
// Silence Usage is an option to silence usage when an error occurs.
SilenceUsage bool
// The *Run functions are executed in the following order:
// * PreRunChain()
// * PersistentPreRun()
// * PreRun()
// * Run()
// * PostRun()
// * PersistentPostRun()
// * PostRunChain()
// All functions get the same args, the arguments after the command name
// PreRunChain: runs all PreRunChain functions from root to child sequentially
PreRunChain func(cmd *Command, args []string)
// PreRunChainE: PreRunChain but returns an error
PreRunChainE func(cmd *Command, args []string) error
// PersistentPreRun: children of this command will inherit and execute
PersistentPreRun func(cmd *Command, args []string)
// PersistentPreRunE: PersistentPreRun but returns an error
@ -96,10 +90,6 @@ type Command struct {
PersistentPostRun func(cmd *Command, args []string)
// PersistentPostRunE: PersistentPostRun but returns an error
PersistentPostRunE func(cmd *Command, args []string) error
// PostRunChain: runs all PostRunChain functions from child to root sequentially
PostRunChain func(cmd *Command, args []string)
// PostRunChainE: PostRunChain but returns an error
PostRunChainE func(cmd *Command, args []string) error
// DisableAutoGenTag remove
DisableAutoGenTag bool
// Commands is the list of commands supported by this program.
@ -552,10 +542,6 @@ func (c *Command) execute(a []string) (err error) {
c.preRun()
argWoFlags := c.Flags().Args()
if err := c.executePreRunChain(c, argWoFlags); err != nil {
return err
}
for p := c; p != nil; p = p.Parent() {
if p.PersistentPreRunE != nil {
if err := p.PersistentPreRunE(c, argWoFlags); err != nil {
@ -601,10 +587,6 @@ func (c *Command) execute(a []string) (err error) {
}
}
if err := c.executePostRunChain(c, argWoFlags); err != nil {
return err
}
return nil
}
@ -614,49 +596,6 @@ func (c *Command) preRun() {
}
}
// executePreRunChain executes all the PreRunChain functions from
// the root to the child.
func (c *Command) executePreRunChain(cmd *Command, args []string) error {
parent := c.Parent()
if parent != nil {
if err := parent.executePreRunChain(cmd, args); err != nil {
return err
}
}
var err error = nil
switch {
case c.PreRunChainE != nil:
err = c.PreRunChainE(cmd, args)
case c.PreRunChain != nil:
c.PreRunChain(cmd, args)
}
return err
}
// executePostRunChain executes all the PostRunChain functions from
// the child to the root.
func (c *Command) executePostRunChain(cmd *Command, args []string) error {
var err error = nil
switch {
case c.PostRunChainE != nil:
err = c.PostRunChainE(cmd, args)
case c.PostRunChain != nil:
c.PostRunChain(cmd, args)
}
if err != nil {
return err
}
parent := c.Parent()
if parent != nil {
return parent.executePostRunChain(cmd, args)
}
return nil
}
func (c *Command) errorMsgFromParse() string {
s := c.flagErrorBuf.String()