diff options
| author | Paul Buetow <paul@buetow.org> | 2026-02-04 09:11:30 +0200 |
|---|---|---|
| committer | Paul Buetow <paul@buetow.org> | 2026-02-04 09:11:30 +0200 |
| commit | 288aa24e8bc4f22cb7de5d60789e1d6ec79f7395 (patch) | |
| tree | be644130fbffaf946e3122ffdf89dc203447124a /internal/debug/signals_test.go | |
| parent | 6d8953d52efa6037b679d7a722b060c687843f3a (diff) | |
add runtime debugging signals and convert to magev0.10.0
- Add SIGUSR1 handler for goroutine stack dumps when app hangs
- Add SIGUSR2 handler for full profiling (heap, cpu, block)
- Add --debug-dir flag for configurable debug output location
- Convert build system from go-task to mage
- Update documentation with debugging workflow
- Bump version to 0.10.0
Diffstat (limited to 'internal/debug/signals_test.go')
| -rw-r--r-- | internal/debug/signals_test.go | 83 |
1 files changed, 83 insertions, 0 deletions
diff --git a/internal/debug/signals_test.go b/internal/debug/signals_test.go new file mode 100644 index 0000000..d7b0d2d --- /dev/null +++ b/internal/debug/signals_test.go @@ -0,0 +1,83 @@ +// +build !windows + +package debug + +import ( + "os" + "path/filepath" + "testing" +) + +func TestSetDebugDir(t *testing.T) { + testDir := "/tmp/test-debug" + SetDebugDir(testDir) + if debugDir != testDir { + t.Errorf("SetDebugDir failed: expected %s, got %s", testDir, debugDir) + } +} + +func TestInitSignalHandlers(t *testing.T) { + // This test just verifies InitSignalHandlers doesn't panic + // We can't easily test actual signal handling without more complex setup + InitSignalHandlers() +} + +func TestDumpGoroutines(t *testing.T) { + // Create a temporary directory for testing + tmpDir := t.TempDir() + SetDebugDir(tmpDir) + + // Call dumpGoroutines + dumpGoroutines() + + // Check that a file was created + files, err := filepath.Glob(filepath.Join(tmpDir, "tasksamurai-goroutines-*.txt")) + if err != nil { + t.Fatalf("failed to glob for goroutine files: %v", err) + } + + if len(files) == 0 { + t.Fatal("no goroutine dump file was created") + } + + // Verify the file is not empty + info, err := os.Stat(files[0]) + if err != nil { + t.Fatalf("failed to stat goroutine dump file: %v", err) + } + + if info.Size() == 0 { + t.Error("goroutine dump file is empty") + } + + t.Logf("Goroutine dump created: %s (%d bytes)", files[0], info.Size()) +} + +func TestWriteProfile(t *testing.T) { + tmpDir := t.TempDir() + + // Test goroutine profile (text format) + goroutineFile := filepath.Join(tmpDir, "test-goroutine.txt") + if err := writeProfile(goroutineFile, "goroutine", 1); err != nil { + t.Errorf("failed to write goroutine profile: %v", err) + } + + // Test heap profile (binary format) + heapFile := filepath.Join(tmpDir, "test-heap.pprof") + if err := writeProfile(heapFile, "heap", 0); err != nil { + t.Errorf("failed to write heap profile: %v", err) + } + + // Verify files exist and are not empty + for _, file := range []string{goroutineFile, heapFile} { + info, err := os.Stat(file) + if err != nil { + t.Errorf("profile file does not exist: %s", file) + continue + } + if info.Size() == 0 { + t.Errorf("profile file is empty: %s", file) + } + t.Logf("Profile created: %s (%d bytes)", file, info.Size()) + } +} |
