sed kończy się niepowodzeniem z błędem „nieznana opcja dla„ s ””

158

Próbuję użyć

sed -i -e "s/.*seb.*/    \"$ftp_login_template\"/" $ftp_dir

jednak otrzymuję ten błąd:

sed: -e expression #1, char 34: unknown option to `s'

Nie rozumiem, dlaczego to działa idealnie:

sed -i -e "s/.*wbspassword.*/    \"wbspassword\": \"$password\",/" $user_conf

Jakieś pomysły, co robię źle?

Czy to może być problem? ftp_login_template=\${user}:${password}:24:86::\/var\/lib\/clit.${user}\/downloads:\/bin\/false\"

Panie King
źródło
8
Komunikat o błędzie * BSD (w tym OSX) to „zła flaga w poleceniu substytutu:” - dołączam ją tutaj, aby uczynić ją bardziej widoczną w Google.
tripleee

Odpowiedzi:

355

Problem jest z ukośnikami: twoja zmienna je zawiera, a ostatecznym poleceniem będzie coś w rodzaju sed "s/string/path/to/something/g", zawierające zbyt wiele ukośników.

Ponieważ sedmoże przyjąć dowolny znak jako separator (bez konieczności deklarowania nowego separatora), możesz spróbować użyć innego, który nie pojawia się w zastępującym ciągu:

replacement="/my/path"
sed --expression "s@pattern@$replacement@"

Zauważ, że to nie jest punkt kulminacyjny: jeśli zastępujący łańcuch później @będzie zawierał , zepsuje się z tego samego powodu, a wszelkie sekwencje odwrotnego ukośnika, takie jak, \1będą nadal interpretowane zgodnie z sedregułami. Używanie |jako separatora jest również miłą opcją, ponieważ jest podobne w czytelności do /.

Tomas Pruzina
źródło
38
Tylko uwaga, aby pomóc przyszłym użytkownikom, ponieważ ta odpowiedź była również pomocna. Oryginalny plakat najprawdopodobniej miał w swoim zamienniku coś (najprawdopodobniej ukryte w zmiennej), które zawierało ukośniki. Po napotkaniu pierwszego z tych ukośników sed uważał, że zamiana została zakończona, a cokolwiek przyszło później jako opcja (na przykład g).
Brian Warshaw,
4
Dobra robota (pamiętaj tylko, aby zawijać wyrażenia zmienne "'$content$content
1
@AbstractDissonance Może, jeśli zmieniasz hasło lub coś dziwnego lub losowego, nadal masz w nim znak @. Musisz znaleźć separator, który nie jest zawarty w twoim ciągu podstawienia.
Xavi Montero,
5
@ppumkin po prostu zamień ograniczniki „ukośnika w przód”, takie jak np .: sed -i "s/../../g"innym znakiem, tj .: sed -i "s@...@...@g", wtedy problem wielu ukośników powinien zniknąć. A jeśli używasz "zamiast tego ', powinno również działać dobrze ze zmiennymi wewnątrz, tj export var1=bar; sed -i "s@foo@${var1}@g". : . Więcej informacji można znaleźć w niesamowitej dokumentacji seda
Egel
1
Zobacz info sed(źródło: unix.stackexchange.com/questions/259083/… ): "Składnia polecenia s (jak w zastępstwie) to 's / regexp / replace / flags'. Znaki / mogą być jednolicie zastąpione przez dowolne inne pojedynczy znak w ramach dowolnego polecenia s. "
Gabriel Staples