Tengo un simple script Ruby que se parece a esto¿Cómo hacer que la producción de tubería desde un script Ruby a 'cabeza' sin conseguir una tubería rota de error
require 'csv'
while line = STDIN.gets
array = CSV.parse_line(line)
puts array[2]
end
Pero cuando intento usar este script en una tubería de Unix de esta manera, me da 10 líneas de salida, seguido por un error:
ruby lib/myscript.rb < data.csv | head
12080450
12080451
12080517
12081046
12081048
12081050
12081051
12081052
12081054
lib/myscript.rb:4:in `write': Broken pipe - <STDOUT> (Errno::EPIPE)
¿hay una manera de escribir el guión de rubíes de una manera que impide la excepción tubería rota de ser levantado?
Si la cabeza se cierra la corriente, entonces ¿por qué '' Todavía $ stdout.closed return false y por qué el error no ocurrirá de inmediato, pero sólo después de que se hayan escrito muchas líneas en el vacío? Creo que la cabeza realmente mantiene la secuencia abierta, pero ya no lee, lo que hace que la memoria intermedia esté llena en algún punto que causa el punto roto. – sepp2k
@ sepp2k - Lo más probable es que ocurran un par de cosas aquí: 1, el modo de almacenamiento en búfer predeterminado para cambios estándar desde orientados a la línea a orientados a bloques cuando se utiliza una interconexión, por lo que deberá realizar un ciclo entre cada escritura. 2, 'head' necesita una oportunidad de ejecutarse para cerrar la secuencia, pero es posible que se hayan escrito muchos más bytes de datos antes de que se ejecute. Escribí una variante del script con '$ stdout.flush; duerma 0.1' entre cada 'write', y en este caso' $ stdout.closed? 'funciona. –
@AidanCully: Ah, muy interesante. – sepp2k