Skip to content

Commit 82299ed

Browse files
authored
chore: better output on errors (#2879)
## Overview Minor updates to make it easier to trace errors Extracted from #2836
1 parent 178b4fe commit 82299ed

File tree

2 files changed

+18
-7
lines changed

2 files changed

+18
-7
lines changed

pkg/cmd/run_node.go

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ import (
77
"os"
88
"os/signal"
99
"path/filepath"
10+
"runtime"
1011
"strings"
1112
"syscall"
1213
"time"
@@ -155,8 +156,10 @@ func StartNode(
155156
go func() {
156157
defer func() {
157158
if r := recover(); r != nil {
158-
err := fmt.Errorf("node panicked: %v", r)
159-
logger.Error().Interface("panic", r).Msg("Recovered from panic in node")
159+
buf := make([]byte, 1024)
160+
n := runtime.Stack(buf, false)
161+
err := fmt.Errorf("node panicked: %v\nstack trace:\n%s", r, buf[:n])
162+
logger.Error().Interface("panic", r).Str("stacktrace", string(buf[:n])).Msg("Recovered from panic in node")
160163
select {
161164
case errCh <- err:
162165
default:

test/e2e/sut_helper.go

Lines changed: 13 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -76,25 +76,33 @@ func (s *SystemUnderTest) RunCmd(cmd string, args ...string) (string, error) {
7676
}
7777

7878
// ExecCmd starts a process for the given command and manages it cleanup on test end.
79-
func (s *SystemUnderTest) ExecCmd(cmd string, args ...string) {
79+
func (s *SystemUnderTest) ExecCmd(cmd string, args ...string) *os.Process {
80+
return s.ExecCmdWithLogPrefix("", cmd, args...)
81+
}
82+
83+
// ExecCmdWithLogPrefix same as ExecCmd but prepends the given prefix to the log output
84+
func (s *SystemUnderTest) ExecCmdWithLogPrefix(prefix, cmd string, args ...string) *os.Process {
85+
8086
executable := locateExecutable(cmd)
8187
c := exec.Command( //nolint:gosec // used by tests only
8288
executable,
8389
args...,
8490
)
8591
c.Dir = WorkDir
86-
s.watchLogs(c)
92+
s.watchLogs(prefix, c)
8793

8894
err := c.Start()
8995
require.NoError(s.t, err)
9096
if s.debug {
91-
s.logf("Exec cmd (pid: %d): %s %s", c.Process.Pid, executable, strings.Join(c.Args, " "))
97+
s.logf("Exec cmd (pid: %d): %s %s", c.Process.Pid, executable, strings.Join(args, " "))
9298
}
9399
// cleanup when stopped
94100
s.awaitProcessCleanup(c)
101+
return c.Process
95102
}
96103

97104
// AwaitNodeUp waits until a node is operational by checking both liveness and readiness.
105+
// Fails tests when node is not up within the specified timeout.
98106
func (s *SystemUnderTest) AwaitNodeUp(t *testing.T, rpcAddr string, timeout time.Duration) {
99107
t.Helper()
100108
t.Logf("Await node is up: %s", rpcAddr)
@@ -168,7 +176,7 @@ func (s *SystemUnderTest) awaitProcessCleanup(cmd *exec.Cmd) {
168176
}()
169177
}
170178

171-
func (s *SystemUnderTest) watchLogs(cmd *exec.Cmd) {
179+
func (s *SystemUnderTest) watchLogs(prefix string, cmd *exec.Cmd) {
172180
errReader, err := cmd.StderrPipe()
173181
require.NoError(s.t, err)
174182
outReader, err := cmd.StdoutPipe()
@@ -178,7 +186,7 @@ func (s *SystemUnderTest) watchLogs(cmd *exec.Cmd) {
178186
logDir := filepath.Join(WorkDir, "testnet")
179187
require.NoError(s.t, os.MkdirAll(logDir, 0o750))
180188
testName := strings.ReplaceAll(s.t.Name(), "/", "-")
181-
logfileName := filepath.Join(logDir, fmt.Sprintf("exec-%s-%s-%d.out", filepath.Base(cmd.Args[0]), testName, time.Now().UnixNano()))
189+
logfileName := filepath.Join(logDir, prefix+fmt.Sprintf("exec-%s-%s-%d.out", filepath.Base(cmd.Args[0]), testName, time.Now().UnixNano()))
182190
logfile, err := os.Create(logfileName)
183191
require.NoError(s.t, err)
184192
errReader = io.NopCloser(io.TeeReader(errReader, logfile))

0 commit comments

Comments
 (0)