cmd icon indicating copy to clipboard operation
cmd copied to clipboard

Command is still executed if Stop() is called during BeforeExec hooks

Open renard opened this issue 2 years ago • 0 comments

If for some reason a BeforeExec takes some time (to delay a command for example) and Stop() is called while BeforeExec hasn't finished, the command is still executed.

Example:

package main

import (
	"fmt"
	"os/exec"
	"time"

	"github.com/go-cmd/cmd"
)

func main() {
	cmdOptions := cmd.Options{
		Buffered:  true,
		Streaming: true,
		BeforeExec: []func(_c *exec.Cmd){
			func(_c *exec.Cmd) {
				for i := 0; i < 4; i++ {
					fmt.Printf("Waiting %d\n", i)
					time.Sleep(1 * time.Second)
				}
			},
		},
	}

	c := cmd.NewCmdOptions(cmdOptions, "ls", "-l")

	fmt.Printf("Starting\n")
	c.Start()
	time.Sleep(2 * time.Second)

	fmt.Printf("Stopping\n")
	err := c.Stop()
	if err != nil {
		fmt.Printf("E: %s\n", err)
	}

	fmt.Printf("Waiting process to end\n")
	<-c.Done()
	fmt.Printf("Done\n")
	fmt.Printf("Output: %s\n", c.Status().Stdout)
}

Output:

Starting
Waiting 0
Waiting 1
Waiting 2
Stopping
E: command not running
Waiting process to end
Waiting 3
Done
Output: [total 8 -rw-r--r--  1 renard  staff  612 Sep 13 22:24 main.go]

Stop() has no effect if command is not started because of https://github.com/go-cmd/cmd/blob/fa11d77415735b5d02968012dae9a3b0de05ef9f/cmd.go#L290-L297

run() runs all BeforeExec functions and starts the command (https://github.com/go-cmd/cmd/blob/fa11d77415735b5d02968012dae9a3b0de05ef9f/cmd.go#L431-L448).

Would it make sense to add a ForceStop() function like:

// ForceStop forces a command stop by calling Stop(). If the command hasn't
// started yet flags it as stopped to prevent Start() from starting it.
//
// See Stop() for further details
func (c *Cmd) ForceStop() error {
	err := c.Stop()
	// If command hasn't started, return error (or nil) from Stop()
	if err != ErrNotStarted {
		return err
	}
	// flag command as stopped to prevent it from being started later.
	c.stopped = true
	return nil
}

Thanks in advance

renard avatar Sep 13 '22 20:09 renard