Suchen und ersetzen Sie sed im Verzeichnis und in den Unterverzeichnissen

244

Ich führe diesen Befehl aus, um alle Vorkommen von 'apple' in allen Dateien im Stammverzeichnis meiner Site zu finden und durch 'orange' zu ersetzen:

find ./ -exec sed -i 's/apple/orange/g' {} \;

Es werden jedoch keine Unterverzeichnisse durchlaufen.

Was ist falsch an diesem Befehl?

Hier sind einige Ausgabezeilen von find ./:

./index.php
./header.php
./fpd
./fpd/font
./fpd/font/desktop.ini
./fpd/font/courier.php
./fpd/font/symbol.php
hd.
quelle
Könntest du eine Beispielausgabe ausführen find ./und veröffentlichen? Und das Verzeichnis strucuture bitte. edit: danke!
Jacob
Hm dein Fund ist richtig, funktioniert bei mir mit Unterverzeichnissen.
Jacob
1
Woher wissen Sie, dass keine Unterverzeichnisse verarbeitet werden?
Carlpett
weil es diese Fehler gibt: sed: konnte nicht bearbeiten ./fpd: keine reguläre Datei sed: konnte nicht bearbeiten ./fpd/font: keine reguläre Datei sed: konnte nicht bearbeiten ./fpd/font/makefont: keine regula
hd.
Oh ... ich greife nach Apfel und nichts gefunden. Sie wurden alle ersetzt. ;) Danke . Du hast meine Augen geöffnet !!!
hd.

Antworten:

420

Ihr Fund sollte so aussehen, um zu vermeiden, dass Verzeichnisnamen an sed gesendet werden:

find ./ -type f -exec sed -i -e 's/apple/orange/g' {} \;
jfg956
quelle
19
Möglicherweise müssen sich ändern , sed -i 's/apple/orange/g'um sed -i '' 's/apple/orange/g'diese Arbeit zu machen.
Paulmelnikow
7
-inimmt ein Argument: die Erweiterung zum Speichern der temporären Datei. In GNU sed scheint es keinen Raum zwischen -iund seinem Argument zu geben, aber in BSD sed gibt es ... also ist BSD -i '' 's/foo/bar/'gleichbedeutend mit GNU -i 's/foo/bar/.
Paulmelnikow
20
Tatsächlich -efunktioniert das Hinzufügen unter Mac OS nicht. touch a b c d egefolgt von dem obigen Befehl erzeugt eine Verzeichnisliste wie folgt : a a-e b b-e c c-e d d-e e e-e.
Paulmelnikow
6
Für Mac OS beantwortet dies stackoverflow.com/questions/19242275/… theRE error: illegal byte sequence
kakoma
3
Stellen Sie für Benutzer von Fischschalen sicher, dass Sie die leeren Klammern angeben '{}', da Fisch die leeren Klammern automatisch erweitert, wenn sie nicht angegeben werden.
Kevin Cherepski
84

Für größere S & R-Aufgaben ist es besser und schneller, grep und xargs zu verwenden.

grep -rl 'apples' /dir_to_search_under | xargs sed -i 's/apples/oranges/g'
Julius
quelle
20
Danke für diese Antwort, es war sehr hilfreich! Wenn in einem Git-Repository, ist es noch schneller mitgit grep -l 'apples' | xargs sed -i 's/apples/oranges/g'
mrodrigues
4

Das hat bei mir funktioniert:

find ./ -type f -exec sed -i '' 's#NEEDLE#REPLACEMENT#' *.php {} \;
Blackdad
quelle
Die ursprüngliche Frage beschränkt sich nicht auf * .php-Dateien, es gibt auch eine .ini one
knocte
Das nicht zitierte *.phpist wirklich falsch; Sie hatten einfach Glück, dass es im Startverzeichnis nicht erweitert wurde, weil Sie dort zufällig keine passenden Dateien hatten.
Tripleee
3
grep -e apple your_site_root/**/*.* -s -l | xargs sed -i "" "s|apple|orage|"
rocLv
quelle
1

Da es auch MacOS-Leute gibt, die diesen lesen (wie ich), hat der folgende Code für mich funktioniert (am 10.14)

egrep -rl '<pattern>' <dir> | xargs -I@ sed -i '' 's/<arg1>/<arg2>/g' @

Alle anderen Antworten mit -iund-e funktionieren nicht unter macOS.

Quelle

pat-s
quelle
0

Ich denke, wir können dies mit einem einfachen Befehl in einer Zeile tun

for i in `grep -rl eth0 . 2> /dev/null`; do sed -i ‘s/eth0/eth1/’ $i; done

Siehe diese Seite .

Sukrant
quelle
-6

Unter Linux:

sed -i 's/textSerch/textReplace/g' namefile

Wenn "sed" nicht funktioniert, versuchen Sie:

perl -i -pe 's/textSerch/textReplace/g' namefile
ฉัตร ชัย สิทธิ วง ค์
quelle
4
er möchte herausfinden, dass alle Dateien in Unterverzeichnissen diese Zeichenfolge enthalten und ersetzen, nicht nur eine einzelne Datei
phuclv