I want to use Kernel#system or one of its friends to manipulate some
data I have in a ruby string. Ideally, I’d want the executed command
to read the string from stdin, as if ruby had piped the data to it.
The data may be reasonably large. Any tips?
I want to use Kernel#system or one of its friends to manipulate some
data I have in a ruby string. Ideally, I’d want the executed command
to read the string from stdin, as if ruby had piped the data to it.
The data may be reasonably large. Any tips?
Could you be a bit more clear? Do you want to write a program that will
cooperate with a stream? As in:
Could you be a bit more clear? Do you want to write a program that
will
cooperate with a stream? As in:
data_source | ruby-program | data_dest
Yes?
No, from within a ruby program I want to call some shell command to
act on data stored in a ruby string, so, in the ruby program,
something like, in pseudoruby:
I wonder what happens if the subprocess is killed by the system?
I guess I’ll run some tests, but if you happen to know the answers,
I’d be glad to hear them nonetheless.
I haven’t had a lot of experience with it personally. I came across it
in a
plugin I was using that piped to an external progam and had a bit of a
look. The plugin doesn’t seem to do anything special with it and I
havn’t
had a need to use it otherwise.
No, from within a ruby program I want to call some shell command to
act on data stored in a ruby string, so, in the ruby program,
something like, in pseudoruby:
I want to emphasize there are a dozen ways to do this. This one happens
to
be simple to understand. Another way is File.popen(), but that approach
makes bidirectional communications difficult.
I wonder what happens if the subprocess is killed by the system?
I guess I’ll run some tests, but if you happen to know the answers,
I’d be glad to hear them nonetheless.
The problem with File.popen() is that you want bidirectional
communication
with the child process, and AFAIK that doesn’t offer it – you can
either
read, or write, to the pipe, but not both.
I want to emphasize there are a dozen ways to do this. This one
happens to
be simple to understand. Another way is File.popen(), but that
approach
makes bidirectional communications difficult.
I thought about doing it with echo but then I’d have to escape the
string, and what if I was dealing with binary data, and all that…
so popen looks like a more robust solution.
The problem with File.popen() is that you want bidirectional
communication
with the child process, and AFAIK that doesn’t offer it – you can
either
read, or write, to the pipe, but not both.
Hmm, that’s not cool. I’ll run some tests, but looks like it’s back
to using tempfiles then.
The problem with File.popen() is that you want bidirectional
communication
with the child process, and AFAIK that doesn’t offer it – you can
either
read, or write, to the pipe, but not both.
Hmm, that’s not cool. I’ll run some tests, but looks like it’s back
to using tempfiles then.
Did you read my other post? Piping information to child processes is
easy.
No, from within a ruby program I want to call some shell command to act on
data stored in a ruby string, so, in the ruby program, something like, in
pseudoruby:
my session and open4 lib both abstract this largely, including a good
deal of
error handling. there is also the built-in open3 module. check out the
docs.
my session and open4 lib both abstract this largely, including a
good deal of
error handling. there is also the built-in open3 module. check
out the docs.
Thanks.
Having a separate stdout and stderr is great, in fact, just the next
thing I was going to ask about. So both open3 and open4 seem like
great candidates.
Could you take some time to sell open4 over open3?
The main advantage I see is the greater abstraction, i.e. the spawn
method.
I thought about doing it with echo but then I’d have to escape the
string, and what if I was dealing with binary data, and all that…
so popen looks like a more robust solution.
Yes, except for the fact that you cannot easily find out what the child
process created as a result. But yes, if binary data is an issue,
File.popen() will reliably stream the data for you.
Having a separate stdout and stderr is great, in fact, just the next thing I
was going to ask about. So both open3 and open4 seem like great candidates.
Could you take some time to sell open4 over open3?
The main advantage I see is the greater abstraction, i.e. the spawn method.
you get the child pid returned also with open4
a command that fails to exec raises and error (note this is sent back
from
the child fork)
when using the spawn method a great deal of abstraction is provided,
not
least of which that stdin, stdout, stderr are each handled via a
thread so
you may provide objects that can handle async output
Is Open4 not win32 compatable? With all win32ole hooks, I’m suprised
no one has tackled this yet.
Ara, you helped me a while back with spawning processes in win32,
catching pids and error levels.
–just assumed if I could install it as a gem, it would work.
Microsoft Windows XP [Version 5.1.2600]
(C) Copyright 1985-2001 Microsoft Corp.
C:\Documents and Settings\d0t1q>gem install open4
Attempting local installation of ‘open4’
Local gem file not found: open4*.gem
Attempting remote installation of ‘open4’
Updating Gem source index for: http://gems.rubyforge.org
Successfully installed open4-0.7.0
C:\Documents and Settings\d0t1q>irb
irb(main):001:0> require ‘open4’
=> false
irb(main):002:0> Open4.spawn “echo”, :stdin => “hello”
NameError: uninitialized constant Fcntl::F_SETFD
from
c:/ruby/lib/ruby/gems/1.8/gems/open4-0.7.0/lib/open4.rb:19:in pope n4' from c:/ruby/lib/ruby/gems/1.8/gems/open4-0.7.0/lib/open4.rb:263:in spa
wn’
from c:/ruby/lib/ruby/1.8/timeout.rb:48:in timeout' from c:/ruby/lib/ruby/gems/1.8/gems/open4-0.7.0/lib/open4.rb:262:in spa
wn’
from (irb):2
irb(main):003:0>