views:

547

answers:

3

I'm trying to find a tool to check for coding style in python.

For php I've seen there is the Code Sniffer, and a small perl script used by Drupal. Is there such a tool for python code?

Thanks

+2  A: 

Theres a script called reindent.py thats sometimes included in your system's python distribution which will go through and re-indent all your code to the recommended 4 spaces indenting.

Heres a copy of it in case you can't find it in your distribution: http://www.koders.com/python/fid24D30FCD2CE388C67CB980EF55630D25970CFB96.aspx?s=cdef%3Aparser

nbv4
Thanks, although it just checks one thing, it will come in handy.
carlosz
+9  A: 

pylint and pyflakes would be a good start.

pylint in particular is very configurable, and you can enforce quite a few things with it.

David Cournapeau
Great, seems exactly what I'm looking for :)
carlosz
+14  A: 

In the past I've mainly use PyLint - it can highlight when you used an undefined variable, when you import things without using them and so on.

It can be a bit verbose, complaining about things like lines being over 80 character long, variable not matching to specific regex's, classes having too few public methods, methods missing docs-trings.

For example, for script..

import os
import somefakelib

def myfunc(x):
    blah = "Something"
    print os.listdir( x+blh )

PyLint generates the following messages:

C:  1: Missing docstring
F:  2: Unable to import 'somefakelib' (No module named somefakelib)
C:  4:myfunc: Missing docstring
C:  4:myfunc: Invalid name "x" (should match [a-z_][a-z0-9_]{2,30}$)
C:  4:myfunc: Invalid name "x" (should match [a-z_][a-z0-9_]{2,30}$)
E:  6:myfunc: Undefined variable 'blh'
W:  5:myfunc: Unused variable 'blah'
W:  2: Unused import somefakelib

They are all valid complaints, but I tend to disable a lot of the convention and refactoring messages. You can disable specific messages, either as comments in your code:

#pylint:disable-msg=R0903,C0103,R0903,F0401,C0301

..or as command line arguments to the PyLint command:

pylint --disable-msg=R0903,C0103,R0903,F0401,C0301 myfile.py

With the above messages disabled, it generates the following messages for the above code:

C:  1: Missing docstring
C:  4:myfunc: Missing docstring
E:  6:myfunc: Undefined variable 'blh'
W:  5:myfunc: Unused variable 'blah'
W:  2: Unused import somefakelib

PyLint also generates a "code report", including how many lines of code/comments/docstring/whitespace the file has, number of messages per-category, and gives your code a "score" - 10 being no messages, 0 generally being a syntax error

Another option is PyFlakes, which I find a little less excessively-verbose (I've recently started using it in place of PyLint). Again using the above script, PyFlakes gives the following messages:

example.py:2: 'somefakelib' imported but unused
example.py:6: undefined name 'blh'

The final option I use is pep8.py, which as the name suggests enforces PEP8. It is by far the most.. pedantic script, enforcing things like correct blank-lines before/after functions/classes, spacing around code, correct 4-space indentation and so on..

Running on the code above, it produces the following:

example.py:4:1: E302 expected 2 blank lines, found 1
example.py:6:23: E201 whitespace after '('
example.py:6:32: W292 no newline at end of file

It is mostly enforces stylistic things like correct whitespace, it does not do much static-analysis of the code like PyLint or PyFlakes, so I use pep8.py in conjunction with either PyLint or PyFlakes.

pep8.py was originally announced on the python mailing list here, but the download link in this is now dead.. There's a github mirror by cburroughs, with a few minor fixes at github.com/cburroughs/pep8.py, or you can grab the unmodified version from an older revision

PyChecker is another option, although I haven't use it

dbr
wow, kudos for the time taken for the explanation
carlosz