Skip to content
This repository was archived by the owner on Aug 8, 2023. It is now read-only.

Commit b3a4e09

Browse files
committed
Merge pull request #46 from mobify/python-pylint-pep8
Python pylint pep8
2 parents 81522d2 + cfeabd9 commit b3a4e09

3 files changed

Lines changed: 547 additions & 0 deletions

File tree

README.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,3 +31,8 @@ eslint:{
3131
```
3232
## CSS
3333
Our Client Services team's [CSS Style Guide](/css/Readme.md). Written with a lot of tender care by @kpeatt and @jeffkamo.
34+
35+
## Python
36+
37+
See the `python` directory of this repo for a standardized `pylintrc` file and
38+
instructions on using `pep8`, `pylint` and `pyflakes` to check Python code.

python/README.md

Lines changed: 171 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,171 @@
1+
# Coding Style
2+
3+
Our Python coding style is [PEP8](http://www.python.org/dev/peps/pep-0008/).
4+
5+
We have an additional standard for import order:
6+
7+
# Standard libs first in alpha order.
8+
import abc
9+
import urlparse
10+
11+
# Third party modules.
12+
import requests
13+
14+
# Project modules (using relative paths where necessary)
15+
from . import mymodule
16+
17+
It's easy to check your code for PEP8 compliance:
18+
19+
**Checking from the command line**
20+
21+
Install the `pep8` package and run it on one or more directories or files:
22+
23+
$ pip install pep8
24+
$ # check an individual file
25+
$ pep8 portal/core/admin.py
26+
$ # check a whole directory
27+
$ pep8 portal/mailers
28+
29+
**Checking in IDEs/editors**
30+
31+
1. In PyCharm, enable the `PEP8 Coding Style violation` and `PEP8 Naming
32+
Convention violation` inspection rules to have all PEP8 problems marked.
33+
34+
2. In Sublime Text, install one of the PEP8 plugins, e.g. [PEP8 Autoformat]
35+
(https://packagecontrol.io/packages/Python%20PEP8%20Autoformat) or [Sublime
36+
Linter PEP8](https://packagecontrol.io/packages/SublimeLinter-pep8).
37+
38+
**Automatically fixing PEP8 issues**
39+
40+
Probably the best solution is *autopep8*:
41+
42+
$ pip install autopep8
43+
$ # Spot PEP8 issues and generate a diff
44+
$ autopep8 --diff portal/core/admin.py
45+
$ # Fix PEP8 issues directly in a file
46+
$ autopep8 --in-place portal/core/admin.py
47+
$ # Fix all PEP8 issues in files in a directory
48+
$ autopep8 -i portal/core/*
49+
$ # Fix all PEP8 issues in all files in a directory tree, recursively
50+
$ find portal/core -name '*.py' -print -exec autopep8 --in-place {} \;
51+
52+
However, if fixing all the PEP8 issues in a file is scary, and all you did is
53+
touch a few lines, you can use `pep8radius`. This will apply `autopep8` to
54+
just the areas of any files that you have changed (it uses `git` to detect
55+
the changes).
56+
57+
$ # Install pep8radius
58+
$ # Make your edits.... get all tests running...
59+
$ # Use pep8radius to fix issues in the code changed. The -vv
60+
$ # sets verbose mode so that the output shows progress.
61+
$ pep8radius -vv --in-place
62+
$ # Now rerun tests, then commit
63+
64+
Note that `pep8radius` will only look at files modified but not yet committed,
65+
so your workflow should include it *before* commit.
66+
67+
68+
# Code Inspection
69+
70+
There are a number of tools that can be used to check Python code for
71+
potential errors. You should run these on code that's already been checked
72+
for PEP8 compliance, so that PEP8 issues don't get flagged.
73+
74+
## PyCharm
75+
76+
The PyCharm IDE has built-in support for Python checking using the
77+
*Inspect Code...* tool. The default set of inspections (all of them)
78+
is suitable for use on our code.
79+
80+
## PyLint
81+
82+
Like `pep8`, `pylint` is a pip-installable package providing a command
83+
line tool that can be run on one or more files to check them.
84+
85+
$ pip install pylint
86+
$ # Run on a single file
87+
$ pylint portal/core/admin.py
88+
$ # Run on a whole directory
89+
$ pylint portal/core
90+
91+
By default, pylint will dump output to stdout showing:
92+
93+
* Errors found, with the numbers of the offending lines
94+
* Statistics about the code
95+
* A tree of external Python module dependencies
96+
* A measure of duplications found (i.e., where the code could
97+
be DRY'd up)
98+
* A rating out of 10 for the code
99+
100+
You may find the HTML output more useful:
101+
102+
$ pylint -f html portal/core/admin.py > pylint.html
103+
104+
It gives more detailed output, including function or class+method names
105+
to make it easier to locate the code that flagged an error. It's most useful
106+
when running pylint over a whole set of files (or a whole directory).
107+
108+
PyLint is very configurable, and a reference config file is included in
109+
this repo (`pylint.rc`). You can save this in your project root, and pylint
110+
will use it by default (when you run `pylint` from that directory).
111+
112+
$ pylint --rcfile=pylint.rc mystuff/myapp/myfile.py
113+
114+
...or save it to `~/.py
115+
116+
### Fixing PyLint issues
117+
118+
There are two ways to fix an issue that pylint flags (three if you include *ignore
119+
it and hope someone else fixes it*).
120+
121+
1. Modify the code to fix the issue.
122+
2. Include a comment to flag to PyLint that it should suppress the check. These
123+
comments take the form `# pylint: disable=<message-type-or-number>` and apply
124+
to the block in which the comment occurs. For example:
125+
126+
class Foo(object):
127+
def unused_arg1(self, arg):
128+
"""This method is flagged because it has an unused argument"""
129+
print self
130+
131+
def unused_arg2(self, arg):
132+
"""
133+
This method is not flagged because we suppress the
134+
check for unused argument.
135+
"""
136+
# pylint: disable=unused-argument
137+
print self
138+
139+
Checking this, we get:
140+
141+
************* Module a
142+
a.py:line 1: : C0111:missing-docstring:Missing module docstring
143+
a.py:line 1: Foo: C0111:missing-docstring:Missing class docstring
144+
a.py:line 2: Foo.unused_arg1: W0613:unused-argument:Unused argument 'arg'
145+
146+
...i.e., the unused-argument message is flagged only for method `unused_arg1`
147+
148+
There's a full list of all the pylint message codes and names here: http://pylint-messages.wikidot.com/all-codes
149+
and detailed documentation of what they mean here: http://docs.pylint.org/features.html
150+
151+
Because the pylint disabling comments work for the whole block in which they
152+
occur, you can include them at module level to suppress a warning across the
153+
whole module.
154+
155+
## Pyflakes
156+
157+
Pyflakes is another pip-installable code analysis tool that focuses on
158+
identifying coding issues (and less on code layout and formatting). _"Pyflakes
159+
makes a simple promise: it will never complain about style, and it will try
160+
very, very hard to never emit false positives."_
161+
162+
$ pip install pyflakes
163+
$ # Check one file
164+
$ pyflakes portal/core/admin.py
165+
$ # Check all the files in a tree
166+
$ pyflakes portal/core
167+
168+
Pyflakes has no configuration, and there is no way to suppress a warning
169+
by adding comments. However, it spots a smaller set of issues than PyLint
170+
(for example, it doesn't spot unused arguments). This does mean that anything
171+
it spots is worth checking.

0 commit comments

Comments
 (0)