Wie kann ich die Syntax des Python-Skripts überprüfen, ohne es auszuführen?

368

Früher habe ich perl -c programfiledie Syntax eines Perl-Programms überprüft und dann beendet, ohne es auszuführen. Gibt es eine äquivalente Möglichkeit, dies für ein Python-Skript zu tun?

Eugene Yarmash
quelle

Antworten:

590

Sie können die Syntax überprüfen, indem Sie sie kompilieren:

python -m py_compile script.py
Mark Johnson
quelle
9
import script, aber der gesamte Code muss in Funktionen sein. Welches ist sowieso gute Praxis. Ich habe dies sogar für Shell-Skripte übernommen. Von hier aus ist es ein kleiner Schritt zum Unit-Test.
Henk Langeveld
1
funktioniert nicht, wenn Sie eine eingebettete Engine mit eingespritzten Modulen haben
n611x007
57
python -m compileallkann Verzeichnisse auch rekursiv ausführen und verfügt über eine bessere Befehlszeilenschnittstelle.
C2H5OH
9
Tolle Antwort, aber wie kann ich verhindern, dass eine ".pyc" -Datei erstellt wird? Was nützt die ".pyc" -Datei übrigens?
pdubois
4
Wenn für Python 2.7.9 -m py_compilevorhanden ist, stelle ich fest, dass die Erstellung der .pyc- Datei weder unterdrückt -Bnoch PYTHONDONTWRITEBYTECODEunterdrückt wird .
DavidRR
59

Sie können diese Tools verwenden:

user225312
quelle
10
All dies ist viel mehr als nur eine Überprüfung der Syntax. Das ist wirklich nicht die Antwort.
Matt Joiner
22
Alle diese überprüfen die Syntax, sodass die Antwort korrekt ist. Andere Schecks sind ein (sehr nützlicher) Bonus.
Johndodo
19
import sys
filename = sys.argv[1]
source = open(filename, 'r').read() + '\n'
compile(source, filename, 'exec')

Speichern Sie dies als checker.py und führen Sie es aus python checker.py yourpyfile.py.

Rosh Oxymoron
quelle
1
Ein bisschen zu schwer für ein Makefile für eine winzige Skriptsammlung, aber es macht den Job und produziert keine unerwünschten Dateien.
Proski
1
Es ist eine alte Antwort, aber etwas zu beachten ist, dass dies nur die Syntax überprüft, nicht wenn das Skript erfolgreich ausgeführt werden würde.
Vallentin
Vielen Dank. Es klappt. Nur ein Kommentar, es gibt keine Antwort, wenn der Code korrekt ist. Andernfalls werden Fehlermeldungen mit Zeilennummern angezeigt.
Musbach
5

Hier ist eine andere Lösung, die das astModul verwendet:

python -c "import ast; ast.parse(open('programfile').read())"

So machen Sie es sauber aus einem Python-Skript heraus:

import ast, traceback

filename = 'programfile'
with open(filename) as f:
    source = f.read()
valid = True
try:
    ast.parse(source)
except SyntaxError:
    valid = False
    traceback.print_exc()  # Remove to silence any errros
print(valid)
jmd_dk
quelle
1
Fantastischer Einzeiler, der nicht alle importierten Bibliotheken benötigt oder .pyc-Dateien erzeugt. Vielen Dank!
mmell
1

Pyflakes macht das, was Sie verlangen, es überprüft nur die Syntax. Aus den Dokumenten:

Pyflakes macht ein einfaches Versprechen: Es wird sich niemals über Stil beschweren und es wird sehr, sehr schwer sein, niemals falsch positive Ergebnisse zu erzielen.

Pyflakes ist auch schneller als Pylint oder Pychecker. Dies liegt hauptsächlich daran, dass Pyflakes nur den Syntaxbaum jeder Datei einzeln untersucht.

So installieren und verwenden Sie:

$ pip install pyflakes
$ pyflakes yourPyFile.py
Brian C.
quelle
0

Aus irgendeinem Grund (ich bin ein Neuling ...) hat der Anruf -m nicht funktioniert ...

Also hier ist eine Bash-Wrapper-Funktion ...

# ---------------------------------------------------------
# check the python synax for all the *.py files under the
# <<product_version_dir/sfw/python
# ---------------------------------------------------------
doCheckPythonSyntax(){

    doLog "DEBUG START doCheckPythonSyntax"

    test -z "$sleep_interval" || sleep "$sleep_interval"
    cd $product_version_dir/sfw/python
    # python3 -m compileall "$product_version_dir/sfw/python"

    # foreach *.py file ...
    while read -r f ; do \

        py_name_ext=$(basename $f)
        py_name=${py_name_ext%.*}

        doLog "python3 -c \"import $py_name\""
        # doLog "python3 -m py_compile $f"

        python3 -c "import $py_name"
        # python3 -m py_compile "$f"
        test $! -ne 0 && sleep 5

    done < <(find "$product_version_dir/sfw/python" -type f -name "*.py")

    doLog "DEBUG STOP  doCheckPythonSyntax"
}
# eof func doCheckPythonSyntax
Yordan Georgiev
quelle