fix: lifecycle-safe logger teardown without global state

Store file handle per module, swap lifecycle logger before closing file,
return teardown errors, remove duplicate Module() func.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
2026-06-29 18:01:08 -07:00
parent 7fcb19ad49
commit 626e1bb5ac
9 changed files with 258 additions and 149 deletions
+57
View File
@@ -0,0 +1,57 @@
package applog_test
import (
"bytes"
"io"
"log/slog"
"os"
"path/filepath"
"testing"
"gitea.auvem.com/go-toolkit/applog"
"gitea.auvem.com/go-toolkit/app"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
)
func TestModuleConsoleOnly(t *testing.T) {
var buf bytes.Buffer
lc := app.NewLifecycle(applog.AppLogOpts{
ConsoleOutput: &buf,
ConsoleLevel: slog.LevelDebug,
DisableAnnouncement: true,
}.Module())
require.NoError(t, lc.Setup())
lc.Logger().Info("hello")
require.NoError(t, lc.Teardown())
assert.Contains(t, buf.String(), "hello")
}
func TestModuleRequiresOutput(t *testing.T) {
lc := app.NewLifecycle(applog.AppLogOpts{}.Module())
err := lc.Setup()
assert.Error(t, err)
}
func TestModuleFileAndTeardown(t *testing.T) {
dir := t.TempDir()
logPath := filepath.Join(dir, "app.log")
lc := app.NewLifecycle(applog.AppLogOpts{
ConsoleOutput: io.Discard,
FileOutput: logPath,
DisableAnnouncement: true,
}.Module())
require.NoError(t, lc.Setup())
lc.Logger().Info("file line")
require.NoError(t, lc.Teardown())
// Logger should not write to closed file after teardown
lc.Logger().Info("after teardown")
data, err := os.ReadFile(logPath)
require.NoError(t, err)
assert.Contains(t, string(data), "file line")
}