github.com/ranjib/nomad@v0.1.1-0.20160225204057-97751b02f70b/command/stop.go (about)

     1  package command
     2  
     3  import (
     4  	"fmt"
     5  	"strings"
     6  )
     7  
     8  type StopCommand struct {
     9  	Meta
    10  }
    11  
    12  func (c *StopCommand) Help() string {
    13  	helpText := `
    14  Usage: nomad stop [options] <job>
    15  
    16    Stop an existing job. This command is used to signal allocations
    17    to shut down for the given job ID. Upon successful deregistraion,
    18    an interactive monitor session will start to display log lines as
    19    the job unwinds its allocations and completes shutting down. It
    20    is safe to exit the monitor early using ctrl+c.
    21  
    22  General Options:
    23  
    24    ` + generalOptionsUsage() + `
    25  
    26  Stop Options:
    27  
    28    -detach
    29      Return immediately instead of entering monitor mode. After the
    30      deregister command is submitted, a new evaluation ID is printed
    31      to the screen, which can be used to call up a monitor later if
    32      needed using the eval-monitor command.
    33  
    34    -verbose
    35      Display full information.
    36  `
    37  	return strings.TrimSpace(helpText)
    38  }
    39  
    40  func (c *StopCommand) Synopsis() string {
    41  	return "Stop a running job"
    42  }
    43  
    44  func (c *StopCommand) Run(args []string) int {
    45  	var detach, verbose bool
    46  
    47  	flags := c.Meta.FlagSet("stop", FlagSetClient)
    48  	flags.Usage = func() { c.Ui.Output(c.Help()) }
    49  	flags.BoolVar(&detach, "detach", false, "")
    50  	flags.BoolVar(&verbose, "verbose", false, "")
    51  
    52  	if err := flags.Parse(args); err != nil {
    53  		return 1
    54  	}
    55  
    56  	// Truncate the id unless full length is requested
    57  	length := shortId
    58  	if verbose {
    59  		length = fullId
    60  	}
    61  
    62  	// Check that we got exactly one job
    63  	args = flags.Args()
    64  	if len(args) != 1 {
    65  		c.Ui.Error(c.Help())
    66  		return 1
    67  	}
    68  	jobID := args[0]
    69  
    70  	// Get the HTTP client
    71  	client, err := c.Meta.Client()
    72  	if err != nil {
    73  		c.Ui.Error(fmt.Sprintf("Error initializing client: %s", err))
    74  		return 1
    75  	}
    76  
    77  	// Check if the job exists
    78  	job, _, err := client.Jobs().Info(jobID, nil)
    79  	if err != nil {
    80  		jobs, _, err := client.Jobs().PrefixList(jobID)
    81  		if err != nil {
    82  			c.Ui.Error(fmt.Sprintf("Error deregistering job: %s", err))
    83  			return 1
    84  		}
    85  		if len(jobs) == 0 {
    86  			c.Ui.Error(fmt.Sprintf("No job(s) with prefix or id %q found", jobID))
    87  			return 1
    88  		}
    89  		if len(jobs) > 1 {
    90  			out := make([]string, len(jobs)+1)
    91  			out[0] = "ID|Type|Priority|Status"
    92  			for i, job := range jobs {
    93  				out[i+1] = fmt.Sprintf("%s|%s|%d|%s",
    94  					job.ID,
    95  					job.Type,
    96  					job.Priority,
    97  					job.Status)
    98  			}
    99  			c.Ui.Output(fmt.Sprintf("Prefix matched multiple jobs\n\n%s", formatList(out)))
   100  			return 0
   101  		}
   102  		// Prefix lookup matched a single job
   103  		job, _, err = client.Jobs().Info(jobs[0].ID, nil)
   104  		if err != nil {
   105  			c.Ui.Error(fmt.Sprintf("Error deregistering job: %s", err))
   106  			return 1
   107  		}
   108  	}
   109  
   110  	// Invoke the stop
   111  	evalID, _, err := client.Jobs().Deregister(job.ID, nil)
   112  	if err != nil {
   113  		c.Ui.Error(fmt.Sprintf("Error deregistering job: %s", err))
   114  		return 1
   115  	}
   116  
   117  	// If we are stopping a periodic job there won't be an evalID.
   118  	if evalID == "" {
   119  		return 0
   120  	}
   121  
   122  	if detach {
   123  		c.Ui.Output(evalID)
   124  		return 0
   125  	}
   126  
   127  	// Start monitoring the stop eval
   128  	mon := newMonitor(c.Ui, client, length)
   129  	return mon.monitor(evalID, false)
   130  }