Übergeben Sie eine Pipe an einen Befehl, der einen Dateinamen erwartet

19

Sagen , dass ich einen Befehl haben , foodie einen Dateinamen - Argument: foo myfile.txt. Lies ärgerlicherweise foonicht von der Standardeingabe. Anstelle einer tatsächlichen Datei möchte ich das Ergebnis eines anderen Befehls übergeben (in Wirklichkeit pvwird die Datei kategorisiert und eine Fortschrittsanzeige als Nebeneffekt ausgegeben).

Gibt es eine Möglichkeit, dies zu erreichen? Nichts in meiner Trickkiste scheint es zu tun.

( fooIn diesem Fall handelt es sich um ein PHP-Skript, das die Datei meines Erachtens sequentiell verarbeitet.)

Ich benutze Ubuntu und Bash

BEARBEITEN Entschuldigung für die etwas unklare Problembeschreibung, aber hier ist die Antwort, die das macht, was ich will:

pv longfile.txt | foo /dev/stdin

Sehr offensichtlich jetzt, wo ich es sehe.

Steve Bennett
quelle
Suchen Sie einen Einzeiler?
Dave Forgac
Sind Sie sicher, dass foo kein Argument von "-" akzeptiert, um es von stdin lesen zu lassen?
Rackandboneman
Leider ja, in diesem Fall handelt es sich um ein PHP-Skript.
Steve Bennett
Ja eigentlich. .
Steve Bennett

Antworten:

19

Wenn ich weiß, was Sie richtig machen wollen, können Sie dies mit der Befehlsersetzungsfunktion von bash tun:

foo <(somecommand | pv)

Dies entspricht in etwa dem, was die mkfifo-basierten Antworten vermuten lassen, mit der Ausnahme, dass die Bash die Details für Sie verwaltet (und dem Befehl nicht eine reguläre Named Pipe, sondern etwas wie / dev / fd / 63 übergeben wird). Möglicherweise können Sie dies auch noch direkter tun:

somecommand | pv | foo /dev/stdin
Gordon Davisson
quelle
1
Oh, schön! Dies pv inputfile.txt | foo /dev/stdinist genau das, was ich suchte, aber nicht zu denken.
Steve Bennett
Woot! / dev / stdin
sage
<(.)arbeitete für mich. Ist diese Syntax im Bash-Handbuch dokumentiert? Ich verstehe, dass (.)die Befehlsersetzung dokumentiert ist, aber nicht die Kombination mit <erklärt wurde.
flow2k
@ flow2k Es heißt "Prozessersetzung" - siehe Abschnitt 3.5.6 des Bash-Handbuchs .
Gordon Davisson
Ich habs. Sie haben Recht - es wird erwähnt, dass Named Pipes / verwendet werden mkfifo.
flow2k
2
ARRAY=(`pv whatever`); for FILE in $ARRAY; do foo $FILE; done
Hyppy
quelle
1

Versuchen Sie es mit mkfifo.

mkfifo file_read_by_foo; pv ... > file_read_by_foo 

Führen Sie in einer anderen Shell foo file_read_by_foo aus

am weisesten werden
quelle
0

xargs scheint dafür gut zu funktionieren:

echo longfile.txt | xargs pv
MadHatter unterstützt Monica
quelle
Das macht etwas anderes: pvmehrmals laufen , jeweils mit einer oder mehreren Linien longfile.txt. Überhaupt nicht das, wonach ich hier strebe.
Steve Bennett