From 23df8706058943c8ea014d7e1df7f3c5f1b92ac1 Mon Sep 17 00:00:00 2001 From: Billy Lynch <1844673+wlynch@users.noreply.github.com> Date: Tue, 18 Apr 2023 11:23:17 -0400 Subject: [PATCH] Ensure that io writers are properly closed. (#292) Because the writers were being defered closed in New, this means that some files could be closed before we had the opportunity to write to them. This moves the close to their own func that can be ran in the correct place. Signed-off-by: Billy Lynch --- internal/commands/root/root.go | 1 + internal/io/streams.go | 15 +++++++++++++-- 2 files changed, 14 insertions(+), 2 deletions(-) diff --git a/internal/commands/root/root.go b/internal/commands/root/root.go index c59be2d0..660b7695 100644 --- a/internal/commands/root/root.go +++ b/internal/commands/root/root.go @@ -65,6 +65,7 @@ func New(cfg *config.Config) *cobra.Command { DisableAutoGenTag: true, RunE: func(cmd *cobra.Command, args []string) error { s := io.New(o.Config.LogPath) + defer s.Close() return s.Wrap(func() error { switch { case o.FlagVersion: diff --git a/internal/io/streams.go b/internal/io/streams.go index 5ef731da..c4a6eae8 100644 --- a/internal/io/streams.go +++ b/internal/io/streams.go @@ -31,6 +31,8 @@ type Streams struct { TTYIn io.Reader TTYOut io.Writer + + close []func() error } func New(logPath string) *Streams { @@ -46,7 +48,7 @@ func New(logPath string) *Streams { // As a janky way to preserve error message, tee stderr to // a temp file. if f, err := os.Create(logPath); err == nil { - defer f.Close() + s.close = append(s.close, f.Close) s.Err = io.MultiWriter(s.Err, f) } } @@ -55,7 +57,7 @@ func New(logPath string) *Streams { // set the input/output if we can actually open it. tty, err := tty.Open() if err == nil { - defer tty.Close() + s.close = append(s.close, tty.Close) s.TTYIn = tty.Input() s.TTYOut = tty.Output() } else { @@ -80,3 +82,12 @@ func (s *Streams) Wrap(fn func() error) error { } return nil } + +func (s *Streams) Close() error { + for _, fn := range s.close { + if err := fn(); err != nil { + return err + } + } + return nil +}