Syntaxfehler in der Nähe eines unerwarteten Tokens `('

11

Wenn ich den folgenden Code im Ubuntu-Terminal verwende, funktioniert es einwandfrei:

rm !(*.sh) -rf

Wenn ich jedoch denselben Zeilencode in ein Shell-Skript (clean.sh) einfüge und das Shell-Skript vom Terminal aus ausführe, wird ein Fehler ausgegeben:

clean.sh-Skript:

#!/bin/bash
rm !(*.sh) -rf

Der Fehler, den ich bekomme:

./clean.sh: line 2: syntax error near unexpected token `('
./clean.sh: line 2: `rm !(*.sh) -rf'

kannst du helfen?

Tal
quelle

Antworten:

23

rm !(*.sh)ist eine extglobSyntax, die bedeutet, dass alle Dateien außer denen mit der .shErweiterung entfernt werden.

In Ihrer interaktiven bashInstanz ist die Shell-Option extglobaktiviert:

$ shopt extglob 
extglob         on

Jetzt, da Ihr Skript in einer Subshell ausgeführt wird, müssen Sie dies aktivieren, extglobindem Sie dies am Anfang des Skripts hinzufügen:

shopt -s extglob

Ihr Skript sieht also so aus:

#!/bin/bash
shopt -s extglob
rm -rf -- !(*.sh)

EDIT:

So entfernen Sie alle Dateien mit Ausnahme der .shErweiterungsdateien GLOBIGNORE(da Sie diese nicht aktivieren möchten extglob):

#!/bin/bash
GLOBIGNORE='*.sh'
rm -rf *

Beispiel:

$ ls -1
barbar
bar.sh
egg
foo.sh
spam

$ GLOBIGNORE='*.sh'

$ rm *

$ ls -1
bar.sh
foo.sh
heemayl
quelle
Kann ich meinen Befehl ändern, der dasselbe tut, ohne dies auszuführen? shopt -s extglob?
Tal
@ Tal überprüfen meine Änderungen ..
heemayl
1
danke :) (Stack Overflaw lassen Sie mich 15 Zeichen in Kommentar schreiben :( :( :()
Tal
aber hier gibt es zwei gute antworten!
Tal
1
Dies sollte die akzeptierte Antwort sein, da sie die Frage tatsächlich beantwortet, während die andere nur eine Problemumgehung beschreibt.
Guntram Blohm unterstützt Monica
4

Ok, es ist ein Cross-Post, aber ich muss eine Antwort schreiben. ;)

Sie könnten findstattdessen verwenden

find . -maxdepth 1 ! -name '*.sh' -exec rm -rf {} \;
AB
quelle
2

Sie müssen einschalten extglob:

shopt -s extglob
Choroba
quelle
1
@ Pilot6: Siehe man bash. Es ermöglicht ein erweitertes Globbing wie !(...).
Choroba
Kann ich meinen Befehl ändern, der dasselbe tut, ohne dies auszuführen? shopt -s extglob
Tal