Event-based stdout content capturing


#1

Some legacy code produces output to STDOUT during execution. I need to
capture it on even-based model, something like the following:

capture the_legacy_code_lambda do |content|

do something with content each time something appears in STDOUT

end

how can I manage this? Are there any idioms?


#2

On Tue, Feb 3, 2009 at 11:19 AM, Daniel V.
removed_email_address@domain.invalid wrote:

Some legacy code produces output to STDOUT during execution. I need to
capture it on even-based model, something like the following:

capture the_legacy_code_lambda do |content|

do something with content each time something appears in STDOUT

end

how can I manage this? Are there any idioms?

You can reassign to the global $stdout object any object which
provides the method #write. You could use that to capture the output
something like this:

class Capture
def initialize(*args, &block)
@block = block
end
def write(txt)
@block.call(txt)
end
end

def capture(code, &block)
old_stdout = $stdout
begin
$stdout = Capture.new(&block)
code.call
ensure
$stdout = old_stdout
end
end

def legacy_code
puts “hello world”
puts “me again”
raise Exception, “Oh no!”
end

puts “start”
begin
capture(proc { legacy_code }) do |txt|
STDOUT.print “captured [”
STDOUT.print txt
STDOUT.puts “]”
STDOUT.flush
end
rescue Object => e
puts “Got exception”
raise
end
puts “end”

$ ruby capture-stdout.rb

start

captured [hello world]

captured [

]

captured [me again]

captured [

]

Got exception

capture-stdout.rb:23:in `legacy_code’: Oh no! (Exception)

etc.

Regards,
Sean


#3

Thank you very much, great idea! I missed in my mind, that puts just
uses global variable $stdout.