From 07e66e551960c7c2c5e6dab941dade0b6255d6cc Mon Sep 17 00:00:00 2001 From: bdchatham Date: Thu, 30 Apr 2026 14:52:44 -0700 Subject: [PATCH 1/2] feat: add --duration flag for self-terminated load runs Wraps the load-test ctx in context.WithTimeout when --duration > 0. When the timeout fires, the existing graceful-shutdown path runs (background tasks unwind via ctx.Done(), final stats emit, post- summary flush completes), and the existing errors.Is check at exit boundary treats DeadlineExceeded as exit 0. Motivation: K8s Job-level activeDeadlineSeconds always sets the Job condition to Failed/DeadlineExceeded regardless of container exit code. With --duration set inside the deadline, seiload exits cleanly before K8s force-terminates, so the Job goes Complete. Co-Authored-By: Claude Opus 4.7 (1M context) --- main.go | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/main.go b/main.go index d382bf6..6c0f794 100644 --- a/main.go +++ b/main.go @@ -71,6 +71,7 @@ func init() { rootCmd.Flags().Uint64("target-gas", 10_000_000, "Target gas per block") rootCmd.Flags().Int("num-blocks-to-write", 100, "Number of blocks to write") rootCmd.Flags().Duration("post-summary-flush-delay", 25*time.Second, "In-process delay after run-summary metrics are recorded, allowing Prometheus to scrape them before exit") + rootCmd.Flags().Duration("duration", 0, "Run duration; the load test ctx is canceled after this elapses, the existing graceful-shutdown path runs, and the process exits 0. 0 means run until SIGTERM/SIGINT.") // Initialize Viper with proper error handling if err := config.InitializeViper(rootCmd); err != nil { @@ -189,6 +190,13 @@ func runLoadTest(ctx context.Context, cmd *cobra.Command, args []string) error { } }() + if duration, _ := cmd.Flags().GetDuration("duration"); duration > 0 { + log.Printf("⏰ Run duration: %s", duration) + var cancel context.CancelFunc + ctx, cancel = context.WithTimeout(ctx, duration) + defer cancel() + } + ctx, runSpan := otel.Tracer("github.com/sei-protocol/sei-load").Start(ctx, "seiload.run") defer runSpan.End() From fe88df64c7b7366b94c9d91cc8077e0bd3945fb1 Mon Sep 17 00:00:00 2001 From: bdchatham Date: Thu, 30 Apr 2026 14:54:40 -0700 Subject: [PATCH 2/2] chore: trim --duration help string Co-Authored-By: Claude Opus 4.7 (1M context) --- main.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/main.go b/main.go index 6c0f794..66c73f0 100644 --- a/main.go +++ b/main.go @@ -71,7 +71,7 @@ func init() { rootCmd.Flags().Uint64("target-gas", 10_000_000, "Target gas per block") rootCmd.Flags().Int("num-blocks-to-write", 100, "Number of blocks to write") rootCmd.Flags().Duration("post-summary-flush-delay", 25*time.Second, "In-process delay after run-summary metrics are recorded, allowing Prometheus to scrape them before exit") - rootCmd.Flags().Duration("duration", 0, "Run duration; the load test ctx is canceled after this elapses, the existing graceful-shutdown path runs, and the process exits 0. 0 means run until SIGTERM/SIGINT.") + rootCmd.Flags().Duration("duration", 0, "Run duration (0 = until SIGTERM/SIGINT)") // Initialize Viper with proper error handling if err := config.InitializeViper(rootCmd); err != nil {