从从stdin读取的Ruby脚本调用时不要停止

时间:2015-09-01 14:15:37

标签: ruby pry

我创建了一个控制台Ruby脚本,该脚本使用ARGF从文件或stdin加载数据,然后调用Pry。

当我传入一个文件(Pry暂停)但是当我使用stdin传递数据时失败(Pry没有停止并退出Ruby)时,这很有效。

这很奇怪,有谁知道为什么?我想通过stdin传递数据并让Pry暂停。

看哪,一个示例脚本:

require 'rubygems'
require 'pry'


def pry_it(str)
    binding.pry
end

pry_it(ARGF.read)

当我用ARGV中的文件调用此应用程序时,我得到了正确的答案 - 撬开暂停

% bundle exec ruby pry_test.rb file.txt

From: /Users/wilcoxr/Development/json_pry/pry_test.rb @ line 8 Object#pry_it:

    6: def pry_it(str)
    7:
 => 8:  binding.pry
    9: end

[1] pry(main)>

大!我可以执行所有我想要的Pry命令

当我尝试使用STDIN将数据发送到我的工具时:

% cat file.txt | bundle exec ruby pry_test.rb

From: /Users/wilcoxr/Development/json_pry/pry_test.rb @ line 8 Object#pry_it:

    6: def pry_it(str)
    7:
 => 8:  binding.pry
    9: end

[1] pry(main)>
% 

仔细观察:注意我回到我的shell提示符,而不是在IRB中暂停。奇怪的!我不明白为什么我会这样做......

1 个答案:

答案 0 :(得分:5)

嘿。这场高尔夫球花了我十分钟的时间才明白是什么驱使这个剧本疯狂。

尝试使用简单的ARGF

require 'rubygems'
require 'pry'
binding.pry

IO现在ARGF.read内部未涵盖ARGF次操作,而且这里明显出现了什么问题。 STDIN被“粘贴”到STDIN,因此传递给pry的任何内容都会直接转到file.txt的输入。

我不确切地知道,你stdin部队的哪些指​​令撬开,但有一条指令。

UPD 如果ruby脚本在$stdin 上产生任何内容(例如通过管道)STDIN和{{1}设置为此管道,弄乱pry的“我从哪里跑”检测到。

我想出了这个不那么优雅的解决方案:

# read input from ARGF
text = ARGF.read

# prepare new stdin to satisfy pry
pry_fd_stdin = IO.sysopen("/dev/tty")
pry_stdin = IO.new(pry_fd_stdin, "r")

# load pry and cheat it with our stdio
require 'pry'
Pry.config.input = pry_stdin

binding.pry

这个解决方案有一些小故障(例如,输入后只显示的pry提示符),但总体思路很明确。