davetron5000 / optparse-plus

Start your command line scripts off right in Ruby
http://davetron5000.github.com/optparse-plus
Apache License 2.0
521 stars 54 forks source link

A way to tell that logging to a pipe should be as if it's tty #130

Open ledestin opened 3 years ago

ledestin commented 3 years ago

I'm testing my program with RSpec, by calling it with backticks ./bin/name, and the output includes timestamps. They get in the way.

If there was a way to make it output user-facing output, it'd be awesome. For example, OPTPARSE_PLUS_TTY=1 ./bin/name.

davetron5000 commented 3 years ago

Is that due to the built-in logging?

If so, a few options you could try:

ledestin commented 3 years ago

I need error messages, just without timestamps on non-tty ios. I want to emit good error messages if arguments are invalid, and I test expect(conversion_output).to eq "foo: Invalid amount, please use a number".

I do have a workaround by using socat(1), but I'd prefer not to come up with it and replicate it in future projects. When I run my program with socat(1), it thinks it's talking to a tty.

  def run_cmd_with_tty(cmd)
    `LUMIONE_CACHE_DIR=./cache socat -ly - EXEC:'#{cmd}',pty,ctty,stderr`.rstrip
  end

I could use include instead of eq in RSpec, but it adds cognitive load over time, so I'd rather fix this problem than think about it in every test.

davetron5000 commented 3 years ago

Ah, ok, thanks for the details.

The code right now omits timestamps if it's not a TTY like so:

https://github.com/davetron5000/optparse-plus/blob/3c0a84a6280d81bab38e5ca2a2701c48cefc8935/lib/optparse_plus/cli_logger.rb#L97-L98

This is what BLANK_FORMAT looks like:

https://github.com/davetron5000/optparse-plus/blob/3c0a84a6280d81bab38e5ca2a2701c48cefc8935/lib/optparse_plus/cli_logger.rb#L41-L43

Since that's public, you could use that either always or only when a flag is given.

In your main executable, you should be able to do something like:

main do
  logger.formatter = OptparsePlus::CLILogger::BLANK_FORMAT

  # ...
end

# or

main do

  if options["omit-message-timestamps"]
    logger.formatter = OptparsePlus::CLILogger::BLANK_FORMAT
  end

  # ...
end

# set this in your tests when you invoke the function
on("--omit-message-timestamps")

That all being said, I could see making this more of a builtin feature, but let me know if this works for you

ledestin commented 3 years ago

Thanks for a quick and comprehensive reply. It would work for me, and having a builtin feature would be great. I originally thought an option would just pollute option list, but now I think that somebody might pipe program output and the option would come in handy.