Ist die Ausgabe eines Bash-Befehls in einem beliebigen Register gespeichert? Z.B. Ähnlich wie $?
die Ausgabe anstelle des Beendigungsstatus erfasst.
Ich könnte die Ausgabe einer Variablen zuweisen mit:
output=$(command)
aber das ist mehr tippen ...
Sie können Folgendes verwenden: $(!!)
, um die Ausgabe des letzten Befehls erneut zu berechnen (nicht erneut zu verwenden).
Der !!
alleine führt den letzten Befehl aus.
$ > echo pierre
pierre
$ > echo my name is $(!!)
echo my name is $(echo pierre)
my name is pierre
Die Antwort ist nein. Bash weist keinem Parameter oder Block in seinem Speicher keine Ausgabe zu. Außerdem können Sie nur über die zulässigen Schnittstellenvorgänge auf Bash zugreifen. Auf die privaten Daten von Bash kann nur zugegriffen werden, wenn Sie sie hacken.
Eine Möglichkeit, dies zu tun, ist die Verwendung von trap DEBUG
:
f() { bash -c "$BASH_COMMAND" >& /tmp/out.log; }
trap 'f' DEBUG
Die zuletzt ausgeführten Befehle stdout und stderr sind jetzt in /tmp/out.log
verfügbar.
Der einzige Nachteil ist, dass ein Befehl zweimal ausgeführt wird: einmal, um die Ausgabe und den Fehler zu /tmp/out.log
umzuleiten, und einmal normal. Wahrscheinlich gibt es auch eine Möglichkeit, dieses Verhalten zu verhindern.
Inspiriert von der Antwort von anubhava, die meiner Meinung nach nicht akzeptabel ist, da sie jeden Befehl zweimal ausführt.
save_output() {
exec 1>&3
{ [ -f /tmp/current ] && mv /tmp/current /tmp/last; }
exec > >(tee /tmp/current)
}
exec 3>&1
trap save_output DEBUG
Auf diese Weise befindet sich die Ausgabe des letzten Befehls in/tmp/last und der Befehl wird nicht zweimal aufgerufen.
Wenn Sie sich auf einem Mac befinden und die Ausgabe in der Zwischenablage speichern möchten, anstatt in eine Variable zu schreiben, können Sie pbcopy und pbpaste als Workaround verwenden.
Anstatt zum Beispiel eine Datei zu finden und deren Inhalt mit einer anderen Datei zu vergleichen:
$ find app -name 'one.php'
/var/bar/app/one.php
$ diff /var/bar/app/one.php /var/bar/two.php
Sie könnten das tun:
$ find app -name 'one.php' | pbcopy
$ diff $(pbpaste) /var/bar/two.php
Die Zeichenfolge /var/bar/app/one.php
befindet sich in der Zwischenablage, wenn Sie den ersten Befehl ausführen.
Übrigens stehen pb in pbcopy
und pbpaste
für Pasteboard, ein Synonym für Zwischenablage.
Wie Konsolebox sagte, müsste man sich in Bash selbst hacken. hier ist ein recht gutes Beispiel dafür, wie man dies erreichen könnte. Das stderred-Repository (eigentlich zum Ausmalen von stdout gedacht) enthält Anweisungen zum Erstellen.
Ich habe es ausprobiert: Definieren eines neuen Dateideskriptors in .bashrc
mögen
exec 41>/tmp/my_console_log
(Nummer ist beliebig) und ändere stderred.c
dementsprechend, damit der Inhalt auch in fd 41 geschrieben wird. Es hat eine Art von funktioniert, enthält aber viele NUL-Bytes, seltsame Formatierungen und ist im Grunde genommen binäre Daten, nicht lesbar. Vielleicht könnte jemand mit guten Kenntnissen von C das ausprobieren.
Wenn ja, ist alles, was benötigt wird, um die letzte gedruckte Zeile zu erhalten, tail -n 1 [logfile]
.
Ich habe eine Idee, die ich nicht sofort umsetzen kann.
Was aber, wenn Sie so etwas wie das Folgende tun:
$ MY_HISTORY_FILE = `get_temp_filename`
$ MY_HISTORY_FILE=$MY_HISTORY_FILE bash -i 2>&1 | tee $MY_HISTORY_FILE
$ some_command
$ cat $MY_HISTORY_FILE
$ # ^You'll want to filter that down in practice!
Möglicherweise gibt es Probleme mit der Pufferung von IO. Auch die Datei könnte zu groß werden. Man müsste eine Lösung für diese Probleme finden.
Sie wissen nicht genau, wofür Sie dies benötigen, daher ist diese Antwort möglicherweise nicht relevant. Sie können die Ausgabe eines Befehls immer speichern: netstat >> output.txt
, aber ich glaube nicht, dass Sie danach suchen.
Es gibt natürlich Programmiermöglichkeiten; Sie können einfach ein Programm zum Lesen der obigen Textdatei erhalten, nachdem der Befehl ausgeführt und mit einer Variablen verknüpft wurde. In Ruby, meiner bevorzugten Sprache, können Sie eine Variable außerhalb der Befehlsausgabe mithilfe von 'backticks' erstellen:
output = `ls` #(this is a comment) create variable out of command
if output.include? "Downloads" #if statement to see if command includes 'Downloads' folder
print "there appears to be a folder named downloads in this directory."
else
print "there is no directory called downloads in this file."
end
Stecken Sie dies in eine .rb-Datei und führen Sie es aus: Ruby file.rb
und es wird eine Variable aus dem Befehl erstellt und Sie können sie bearbeiten.