2015-05-10 8 views
6

Ich benutze Kommandozeilen-Perl, um eine Inplace-Substitution in einer Datei durchzuführen. Dies ist der Code: (notieren Sie die Root-Dauerwelle mit sudo)

sudo perl -i -pe "s/foo/bar/" config.txt 

Wenn dies gelingt, "Echo $?" Rückgabe von 0. Jetzt mache ich die Datei nicht-beschreibbaren auch für root wie dies mit chattr:

sudo chattr +i config.txt 

ich den gleichen Perl-Befehl ausführen, und es schlägt mit diesem Fehler:

Can't remove config.txt: Operation not permitted, skipping file.

was in Ordnung ist. "Echo $?" gibt in diesem Fall immer noch 0 zurück. Warum ist das so? Sollte es nicht einen Wert ungleich null zurückgeben, der einen Fehler anzeigt?

Antwort

2

Das Problem ist, dass Perl nicht mit einem Nicht-Null-Exit-Status für diese Bedingung zurückkommt (sudo übergibt den Exit-Status des Befehls, den es gegeben wurde), was ein wenig ärgerlich ist. Sie können erkennen, dass die Line-Leseschleife eingegeben wird nie um das Problem zu umgehen, wenn die Datei umbenannt werden ausfällt und damit umgehen mit einer Flagge:

sudo perl -i -ne 's/foo/bar/; print; $wrk = 1; }{ $wrk or exit 1' config.txt 

Der Eskimo Gruß (oder Schmetterling) „Betreibern“ }{ einleiten ein END Block, in gewisser Weise; was kommt nachdem es ausgeführt wird, wenn die Schleife, die Zeilen aus der Datei liest, beendet ist. Die Funktionsweise ist beschrieben unter here.

Der Vorbehalt ist, dass dies auch einen Fehler meldet, wenn config.txt leer ist. Ein kürzere, wenn ein bisschen hackier Weg ist, den speziell $. Zeilenzähler Variable für den gleichen Zweck zu verwenden:

sudo perl -i -ne 's/foo/bar/; print; }{ $. or exit 1' config.txt 
+0

Danke. funktioniert perfekt. –

Verwandte Themen