Code Review Doctor suggests fixes if your code appears to introduce a bug, or if it looks like the code is not doing what your intended.
This gives you another line of defense against human error because if one human can commit a bug then another human certainly can miss it during code review.
1 | + | async def task(): | |
2 | + | download_files() |
Calling a coroutine without the await
statement just returns the coroutine without actually running the function.
3 | + | ||
4 | + | async def download_files(): | |
5 | + | pass |
1 | + | class FooBarClass: | |
2 | + | @classmethod | |
3 | + | def from_dict(self): |
Class methods should take cls
as the first argument.
- | def from_dict(self): |
+ | def from_dict(cls): |
4 | + | pass |
1 | + | if value is 1: |
Primitive data types such as strings and integers should be compared using ==
and !=
rather than is
and is not
.
- | if value is 1: |
+ | if value == 1: |
2 | + | pass |
1 | + | if value == False: |
Singleton data types such as booleans should be compared using is
and is not
rather than ==
and !=
.
- | if value == False: |
+ | if value is False: |
2 | + | pass |
1 | + | from dataclasses import dataclass | |
2 | + | ||
3 | + | @dataclass |
Use frozen=True
to make the dataclasses
immutable and hashable.
4 | + | class FooBarClass: | |
5 | + | pass |
1 | + | values = ( | |
2 | + | 'yes', | |
3 | + | 'correct' |
Missing commas in tuples results in implicit string concatenation. Probably not what you intended to do.
Read more4 | + | 'agreed', | |
5 | + | ) |
1 | + | if value == 1 and False: | |
2 | + | foo_bar() |
This code will always evaluate the same value regardless of the inputs.
Read more1 | + | try: | |
2 | + | foo() | |
3 | + | except ValueError or TypeError: |
Catch multiple exception types using a tuple, not with or
operator.
- | except ValueError or TypeError: |
+ | except (ValueError, TypeError): |
4 | + | pass |
1 | + | class HomeView(View): | |
2 | + | def get(self, request): | |
3 | + | import pdb; pdb.set_trace() |
Don't commit breakpoints. This will pause execution in prod and break the app.
Read more- | import pdb; pdb.set_trace() |
4 | + | ... |
1 | + | REST_FRAMEWORK = { | |
2 | + | 'DEFAULT_PERMISSION_CLASSES': ( | |
3 | + | 'rest_framework.permissions.IsAuthenticated' |
A tuple
with only one element must end with a comma. Python won't know it's a tuple
without the comma. Probably not what you intended to do.
- | 'rest_framework.permissions.IsAuthenticated' | |||
+ | 'rest_framework.permissions.IsAuthenticated', | |||
Expand 2 lines ... |
4 | + | ) | |
5 | + | } |
1 | + | title = 'Hello world', |
A comma after a value turns it into tuple
. Probably not what you intended to do.
- | title = 'Hello world', |
+ | title = 'Hello world' |
1 | + | content = open('some/path.txt').read() |
Leaving files open degrades application performance and increases the risk of unexpected side effects. Using open
as a context manager will close it automatically for you.
- | content = open('some/path.txt').read() |
+ | with open('some/path.txt') as f: |
+ | content = f.read() |
1 | + | with open('some/path.txt') as f: |
Read and write calls will fail at runtime if open
is called with incorrect modes
.
- | with open('some/path.txt') as f: |
+ | with open('some/path.txt', 'w') as f: |
2 | + | content = f.write('foo') |
1 | + | with open('some/path.txt') as f: | |
2 | + | line_one = f.readline() | |
3 | + | ||
4 | + | line_two = f.readline() |
Accidentally trying to read or write files that are closed will cause a ValueError
at runtime.
1 | + | with open('some/path.txt') as f: |
Not specifying encoding
when reading a file can cause UnicodeDecodeError
because Python assumes the file is encoded with the OS's default text encoding, but that's often an invalid assumption.
- | with open('some/path.txt') as f: |
+ | with open('some/path.txt', encoding='utf_8') as f: |
2 | + | line_one = f.read() |
1 | + | with open('some/path.txt', 'w') as f: |
Not specifying encoding
when writing a file can cause UnicodeEncodeError
because Python assumes the string's characters can fit in the OS's default text encoding, but that's often an invalid assumption.
- | with open('some/path.txt', 'w') as f: |
+ | with open('some/path.txt', 'w', encoding='utf-8') as f: |
2 | + | f.write('foo') |
1 | + | with open('sample-chinese.txt', encoding='utf_8') as f: |
Specifying incorrect encoding
when reading a file can cause UnicodeDecodeError
if the contents of the file is incompatible with the specified encoding.
- | with open('sample-chinese.txt', encoding='utf_8') as f: |
+ | with open('sample-chinese.txt', encoding='big5') as f: |
2 | + | content = f.read() |
1 | + | raise ValidationError('{value} is not allowed') |
An f-string will not work if the f
prefix is missing.
- | raise ValidationError('{value} is not allowed') |
+ | raise ValidationError(f'{value} is not allowed') |
Are you ready to improve your team agility through lower tech debt? Add Code Review Doctor to GitHub.