Befehl zum Escapezeichen einer Zeichenfolge in Bash

97

Ich benötige einen Bash-Befehl, der eine Zeichenfolge in etwas konvertiert, das maskiert ist. Hier ist ein Beispiel:

echo "hello\world" | escape | someprog

Wo der Escape - Befehl macht "hello\world"in "hello\\\world". Dann kann someprog "hello\\world"wie erwartet verwenden. Dies ist natürlich ein vereinfachtes Beispiel dafür, was ich wirklich tun werde.

Benutzer1
quelle
5
Was ist die Art der Flucht? Mit anderen Worten, welche Zeichen müssen entkommen? Suchen Sie ein Escape im C ++ - Stil (bei dem Tabulatoren durch \ t, Zeilenumbrüche durch \ n, Anführungszeichen mit \ "usw. ersetzt werden)? Es ist schwer zu helfen, ohne dass das Problem genau definiert ist.
Michael Aaron Safyan
2
Mögliches Duplikat des Echos, das Argumenten entgeht
P Shved
Diese Frage könnte ein Dutzend verschiedener Dinge bedeuten. Anstatt uns raten zu lassen, wäre es hilfreich, wenn Sie genau angeben, nach welcher Art von Flucht Sie suchen.
Don Hatch
1
Die Frage war spezifisch für die Verwendung von \\ für \. Es gibt eine akzeptierte Antwort.
User1

Antworten:

154

In Bash:

printf "%q" "hello\world" | someprog

beispielsweise:

printf "%q" "hello\world"
hello\\world

Dies könnte auch durch Variablen verwendet werden:

printf -v var "%q\n" "hello\world"
echo "$var"
hello\\world
Bis auf weiteres angehalten.
quelle
6
Wohlgemerkt, %qwar mehr als ein Jahrzehnt lang bis etwa 2012 kaputt. Es hatte Probleme mit ~. Es gibt auch tragbare sed Einzeiler stackoverflow.com/a/20053121/1073695
Jo So
1
sed ist in der Tat besser, weil auch Dollarzeichen entkommen können
bis
2
@untore: a='abc$def":'; printf '%q\n' "$a"führt zu abc\$def\":(das Dollarzeichen wird maskiert ). Dies ist Bash 4.3 (ich habe das gleiche Ergebnis in Bash 3.2 erhalten). Welche Version verwenden Sie?
Bis auf weiteres angehalten.
3
printf "%q" 'he$l&lo\world'
Um
bashs printf '%q\n' textzitiert den Text im bashFormat (und für das aktuelle Gebietsschema), sodass dies im Fall des OP nur funktionieren würde, wenn someproggenau dieselbe Anführungszeichen-Syntax verwendet würde, bashdie höchst unwahrscheinlich ist.
Stephane Chazelas
9

Pure Bash, verwenden Sie die Parametersubstitution:

string="Hello\ world"
echo ${string//\\/\\\\} | someprog
Fritz G. Mehner
quelle
1
Auf diese Weise wird "Hallo Welt" nicht zu "Hallo \ Welt" entkommen - printf Ansatz in akzeptierter Antwort macht das.
Vchrizz
1
Außerdem entkommt "% q" nicht '/' wie in "25.03.2017", das ich auf "03 \ / 25 \ / 2017" maskieren musste (damit es in einem durch '/' getrennten Stamm enthalten sein kann Ausdruck).
Wrlee
0

Sie können Perl verwenden, um verschiedene Zeichen zu ersetzen, zum Beispiel:

$ echo "Hello\ world" | perl -pe 's/\\/\\\\/g'
Hello\\ world

Abhängig von der Art Ihrer Flucht können Sie mehrere Anrufe verketten, um den richtigen Zeichen zu entkommen.

Michael Aaron Safyan
quelle
1
Warum nicht sed? $ echo "hallo \ world" | sed 's / \\ / \\\\ /'
Space
1
@ Octopus, das ist auch eine gültige Option. Ich fühle mich mit Perl wohler, aber ja, das funktioniert auch.
Michael Aaron Safyan