package main
import (
"context"
"errors"
"flag"
"fmt"
"os"
"strings"
)
func main() {
if err := run(); err != nil && !errors.Is(err, flag.ErrHelp) {
fmt.Fprintln(os.Stderr, err)
os.Exit(1)
}
}
func run() error {
mode, args, done, err := helpCommand(os.Args[1:])
if err != nil || done {
return err
}
command := commands[mode]
all := flag.NewFlagSet(mode, flag.ContinueOnError)
dsn := all.String("db", databaseURL(os.Getenv("DATABASE_URL")), "dedicated assignment_harness_* connection string; overrides DATABASE_URL")
url := all.String("url", "http://127.0.0.1:18000", "target HTTP URL")
dir := all.String("golden", "../fixtures/contract", "reviewed reference captures")
output := all.String("output", "results.json", "output file (directory for export-errors)")
baseline := all.String("baseline", "", "baseline benchmark JSON")
candidate := all.String("candidate", "", "candidate benchmark JSON")
referenceDSN := all.String("reference-db", "", "reference database for full equivalence")
referenceURL := all.String("reference-url", "http://127.0.0.1:18000", "reference HTTP URL")
input := all.String("input", "", "input artifact path")
n := all.Int("requests", 100, "requests per workload and repetition")
concurrency := all.Int("concurrency", 1, "in-flight requests")
repeats := all.Int("repeats", 5, "independent workload repetitions")
pid := all.Int("pid", 0, "server master PID for Linux process-tree resource measurements")
filter := all.String("workload", "", "posts, search, tag, detail, user, email, create, or comment (default: all)")
full := all.Bool("full", false, "use full-scale fixture instead of contract fixture")
f := flag.NewFlagSet(mode, flag.ContinueOnError)
for _, name := range strings.Fields(command.flags) {
option := all.Lookup(name)
f.Var(option.Value, name, option.Usage)
f.Lookup(name).DefValue = option.DefValue
}
// Never include the current connection string or credentials in help output.
if option := f.Lookup("db"); option != nil {
option.DefValue = databaseURL("")
}
f.Usage = func() { printCommandHelp(f.Output(), mode, command, f) }
for _, arg := range args {
if arg == "--help" || arg == "-h" {
f.SetOutput(os.Stdout)
f.Usage()
return nil
}
}
if err := f.Parse(args); err != nil {
return err
}
if f.NArg() != 0 {
return fmt.Errorf("unexpected argument %q; use harness %s --help", f.Arg(0), mode)
}
ctx := context.Background()
switch mode {
case "operations":
return checkOperations(ctx, *dsn, *input, *output)
case "plans":
return queryPlans(ctx, *dsn, *output)
case "waits":
return diagnoseWaits(ctx, *dsn, *url, *output, *n, *concurrency)
case "init-db":
return initializeDatabase(ctx, *dsn)
case "export-transcript":
return exportTranscript(*input, *output)
case "equivalence":
return equivalence(ctx, *referenceDSN, *dsn, *referenceURL, *url, *output)
case "compare":
return compareFiles(*baseline, *candidate, *output, *filter)
case "export-errors":
return exportErrors(*dir, *output)
case "seed":
c, err := openDB(ctx, *dsn)
if err != nil {
return err
}
defer c.Close(ctx)
return seed(ctx, c)
case "bench":
return benchmark(ctx, *dsn, *url, *output, *n, *concurrency, *repeats, *pid, *filter, *full)
case "capture", "verify":
return runContract(ctx, *dsn, *url, *dir, mode == "capture")
case "claim", "fixture":
c, err := openDB(ctx, *dsn)
if err != nil {
return err
}
defer c.Close(ctx)
if mode == "claim" {
return claim(ctx, c)
}
return fixture(ctx, c)
}
return fmt.Errorf("unknown command %q", mode)
}