From a90f7eb6a1c538972eaf52898dd65fa76f26b1d3 Mon Sep 17 00:00:00 2001 From: Paul Buetow Date: Fri, 20 Mar 2026 22:53:55 +0200 Subject: internal/repl: Reorder functions per Go best practices - Moved public RunREPL function before private functions - Constructor-like getRPNState immediately follows type definition - This aligns with project Go best practices for file organization --- internal/repl/repl.go | 80 +++++++++++++++++++++++++-------------------------- 1 file changed, 40 insertions(+), 40 deletions(-) (limited to 'internal') diff --git a/internal/repl/repl.go b/internal/repl/repl.go index 3e2d4c9..0234e49 100644 --- a/internal/repl/repl.go +++ b/internal/repl/repl.go @@ -24,9 +24,9 @@ type RPNState struct { rpnCalc *rpn.RPN } +// getRPNState returns or creates the RPN state var rpnState *RPNState -// getRPNState returns or creates the RPN state func getRPNState() *RPNState { if rpnState == nil { vars := rpn.NewVariables() @@ -38,6 +38,45 @@ func getRPNState() *RPNState { return rpnState } +// RunREPL starts the interactive REPL +func RunREPL() error { + // Check if stdin is a TTY + if !isatty.IsTerminal(os.Stdin.Fd()) { + fmt.Fprintln(os.Stderr, "REPL mode requires a TTY. Use 'perc ' for non-interactive mode.") + return fmt.Errorf("stdin is not a TTY") + } + + history := loadHistory() + + p := prompt.New( + executor, + completer, + prompt.OptionTitle("perc - Percentage Calculator"), + prompt.OptionPrefix("perc> "), + prompt.OptionLivePrefix(func() (string, bool) { + return "perc> ", true + }), + prompt.OptionHistory(history), + ) + + // Handle SIGINT gracefully + sigChan := make(chan os.Signal, 1) + signal.Notify(sigChan, syscall.SIGINT) + + go func() { + <-sigChan + fmt.Println("\nUse 'quit' or 'exit' to exit, or Ctrl+D") + }() + + // Run the prompt + p.Run() + + // Note: History is not saved automatically in this version + // The prompt library stores it in memory but doesn't expose a getter + + return nil +} + // executor runs a calculation command and returns the result func executor(input string) { input = strings.TrimSpace(input) @@ -186,45 +225,6 @@ func saveHistory(history []string) error { return writer.Flush() } -// RunREPL starts the interactive REPL -func RunREPL() error { - // Check if stdin is a TTY - if !isatty.IsTerminal(os.Stdin.Fd()) { - fmt.Fprintln(os.Stderr, "REPL mode requires a TTY. Use 'perc ' for non-interactive mode.") - return fmt.Errorf("stdin is not a TTY") - } - - history := loadHistory() - - p := prompt.New( - executor, - completer, - prompt.OptionTitle("perc - Percentage Calculator"), - prompt.OptionPrefix("perc> "), - prompt.OptionLivePrefix(func() (string, bool) { - return "perc> ", true - }), - prompt.OptionHistory(history), - ) - - // Handle SIGINT gracefully - sigChan := make(chan os.Signal, 1) - signal.Notify(sigChan, syscall.SIGINT) - - go func() { - <-sigChan - fmt.Println("\nUse 'quit' or 'exit' to exit, or Ctrl+D") - }() - - // Run the prompt - p.Run() - - // Note: History is not saved automatically in this version - // The prompt library stores it in memory but doesn't expose a getter - - return nil -} - // completer provides auto-completion for built-in commands func completer(d prompt.Document) []prompt.Suggest { text := d.GetWordBeforeCursor() -- cgit v1.2.3