80f4340b77
This PR changes the e2e helper thingy to set -detach option when registering a job with the CLI instead of the API. This is necessary for jobs which never become healthy, as the deployment never finishes for failing jobs and the command never returns, causing the test to timeout after 10 minutes.
178 lines
4.7 KiB
Go
178 lines
4.7 KiB
Go
package e2eutil
|
|
|
|
import (
|
|
"fmt"
|
|
"io"
|
|
"io/ioutil"
|
|
"os/exec"
|
|
"regexp"
|
|
"strings"
|
|
)
|
|
|
|
// Register registers a jobspec from a file but with a unique ID.
|
|
// The caller is responsible for recording that ID for later cleanup.
|
|
func Register(jobID, jobFilePath string) error {
|
|
cmd := exec.Command("nomad", "job", "run", "-detach", "-")
|
|
stdin, err := cmd.StdinPipe()
|
|
if err != nil {
|
|
return fmt.Errorf("could not open stdin?: %w", err)
|
|
}
|
|
|
|
content, err := ioutil.ReadFile(jobFilePath)
|
|
if err != nil {
|
|
return fmt.Errorf("could not open job file: %w", err)
|
|
}
|
|
|
|
// hack off the first line to replace with our unique ID
|
|
var re = regexp.MustCompile(`(?m)^job ".*" \{`)
|
|
jobspec := re.ReplaceAllString(string(content),
|
|
fmt.Sprintf("job \"%s\" {", jobID))
|
|
|
|
go func() {
|
|
defer stdin.Close()
|
|
io.WriteString(stdin, jobspec)
|
|
}()
|
|
|
|
out, err := cmd.CombinedOutput()
|
|
if err != nil {
|
|
return fmt.Errorf("could not register job: %w\n%v", err, string(out))
|
|
}
|
|
return nil
|
|
}
|
|
|
|
// PeriodicForce forces a periodic job to dispatch
|
|
func PeriodicForce(jobID string) error {
|
|
// nomad job periodic force
|
|
cmd := exec.Command("nomad", "job", "periodic", "force", jobID)
|
|
|
|
out, err := cmd.CombinedOutput()
|
|
if err != nil {
|
|
return fmt.Errorf("could not register job: %w\n%v", err, string(out))
|
|
}
|
|
|
|
return nil
|
|
}
|
|
|
|
// Dispatch dispatches a parameterized job
|
|
func Dispatch(jobID string, meta map[string]string, payload string) error {
|
|
// nomad job periodic force
|
|
args := []string{"job", "dispatch"}
|
|
for k, v := range meta {
|
|
args = append(args, "-meta", fmt.Sprintf("%v=%v", k, v))
|
|
}
|
|
args = append(args, jobID)
|
|
if payload != "" {
|
|
args = append(args, "-")
|
|
}
|
|
|
|
cmd := exec.Command("nomad", args...)
|
|
cmd.Stdin = strings.NewReader(payload)
|
|
|
|
out, err := cmd.CombinedOutput()
|
|
if err != nil {
|
|
return fmt.Errorf("could not dispatch job: %w\n%v", err, string(out))
|
|
}
|
|
|
|
return nil
|
|
}
|
|
|
|
// JobInspectTemplate runs nomad job inspect and formats the output
|
|
// using the specified go template
|
|
func JobInspectTemplate(jobID, template string) (string, error) {
|
|
cmd := exec.Command("nomad", "job", "inspect", "-t", template, jobID)
|
|
out, err := cmd.CombinedOutput()
|
|
if err != nil {
|
|
return "", fmt.Errorf("could not inspect job: %w\n%v", err, string(out))
|
|
}
|
|
outStr := string(out)
|
|
outStr = strings.TrimSuffix(outStr, "\n")
|
|
return outStr, nil
|
|
}
|
|
|
|
// Register registers a jobspec from a string, also with a unique ID.
|
|
// The caller is responsible for recording that ID for later cleanup.
|
|
func RegisterFromJobspec(jobID, jobspec string) error {
|
|
|
|
cmd := exec.Command("nomad", "job", "run", "-")
|
|
stdin, err := cmd.StdinPipe()
|
|
if err != nil {
|
|
return fmt.Errorf("could not open stdin?: %w", err)
|
|
}
|
|
|
|
// hack off the first line to replace with our unique ID
|
|
var re = regexp.MustCompile(`^job "\w+" \{`)
|
|
jobspec = re.ReplaceAllString(jobspec,
|
|
fmt.Sprintf("job \"%s\" {", jobID))
|
|
|
|
go func() {
|
|
defer stdin.Close()
|
|
io.WriteString(stdin, jobspec)
|
|
}()
|
|
|
|
out, err := cmd.CombinedOutput()
|
|
if err != nil {
|
|
return fmt.Errorf("could not register job: %w\n%v", err, string(out))
|
|
}
|
|
return nil
|
|
}
|
|
|
|
func ChildrenJobSummary(jobID string) ([]map[string]string, error) {
|
|
out, err := Command("nomad", "job", "status", jobID)
|
|
if err != nil {
|
|
return nil, fmt.Errorf("nomad job status failed: %w", err)
|
|
}
|
|
|
|
section, err := GetSection(out, "Children Job Summary")
|
|
if err != nil {
|
|
section, err = GetSection(out, "Parameterized Job Summary")
|
|
if err != nil {
|
|
return nil, fmt.Errorf("could not find children job summary section: %w", err)
|
|
}
|
|
}
|
|
|
|
summary, err := ParseColumns(section)
|
|
if err != nil {
|
|
return nil, fmt.Errorf("could not parse children job summary section: %w", err)
|
|
}
|
|
|
|
return summary, nil
|
|
}
|
|
|
|
func PreviouslyLaunched(jobID string) ([]map[string]string, error) {
|
|
out, err := Command("nomad", "job", "status", jobID)
|
|
if err != nil {
|
|
return nil, fmt.Errorf("nomad job status failed: %w", err)
|
|
}
|
|
|
|
section, err := GetSection(out, "Previously Launched Jobs")
|
|
if err != nil {
|
|
return nil, fmt.Errorf("could not find previously launched jobs section: %w", err)
|
|
}
|
|
|
|
summary, err := ParseColumns(section)
|
|
if err != nil {
|
|
return nil, fmt.Errorf("could not parse previously launched jobs section: %w", err)
|
|
}
|
|
|
|
return summary, nil
|
|
}
|
|
|
|
func DispatchedJobs(jobID string) ([]map[string]string, error) {
|
|
out, err := Command("nomad", "job", "status", jobID)
|
|
if err != nil {
|
|
return nil, fmt.Errorf("nomad job status failed: %w", err)
|
|
}
|
|
|
|
section, err := GetSection(out, "Dispatched Jobs")
|
|
if err != nil {
|
|
return nil, fmt.Errorf("could not find previously launched jobs section: %w", err)
|
|
}
|
|
|
|
summary, err := ParseColumns(section)
|
|
if err != nil {
|
|
return nil, fmt.Errorf("could not parse previously launched jobs section: %w", err)
|
|
}
|
|
|
|
return summary, nil
|
|
}
|