[Python-modules-commits] [pep8-naming] 01/03: Imported Upstream version 0.3.1
Daniel Stender
danstender-guest at moszumanska.debian.org
Tue Jun 23 09:54:50 UTC 2015
This is an automated email from the git hooks/post-receive script.
danstender-guest pushed a commit to branch master
in repository pep8-naming.
commit ebfbc62ef89d54e6de2d01c5ce8a3b7044f15f5a
Author: Daniel Stender <debian at danielstender.com>
Date: Tue Jun 23 11:49:25 2015 +0200
Imported Upstream version 0.3.1
---
.gitignore | 10 ++
.travis.yml | 18 ++++
LICENSE | 23 ++++
README.rst | 116 ++++++++++++++++++++
pep8ext_naming.py | 294 ++++++++++++++++++++++++++++++++++++++++++++++++++
run_tests.py | 81 ++++++++++++++
setup.cfg | 2 +
setup.py | 70 ++++++++++++
testsuite/N801.py | 11 ++
testsuite/N802.py | 72 +++++++++++++
testsuite/N803.py | 50 +++++++++
testsuite/N803_py2.py | 7 ++
testsuite/N803_py3.py | 13 +++
testsuite/N804.py | 13 +++
testsuite/N805.py | 16 +++
testsuite/N806.py | 48 +++++++++
testsuite/N81x.py | 12 +++
tox.ini | 13 +++
18 files changed, 869 insertions(+)
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..6288ced
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,10 @@
+*.egg
+*.egg-info
+*.py[cod]
+.tox
+dist
+.project
+.pydevproject
+.settings/
+build/
+
diff --git a/.travis.yml b/.travis.yml
new file mode 100644
index 0000000..d5e9258
--- /dev/null
+++ b/.travis.yml
@@ -0,0 +1,18 @@
+language: python
+
+sudo: false
+
+install:
+ pip install tox
+
+script: tox
+
+env:
+ matrix:
+ - TOXENV=py26
+ - TOXENV=py27
+ - TOXENV=py32
+ - TOXENV=py33
+ - TOXENV=py34
+ - TOXENV=pypy
+ - TOXENV=pypy3
diff --git a/LICENSE b/LICENSE
new file mode 100644
index 0000000..a7621d3
--- /dev/null
+++ b/LICENSE
@@ -0,0 +1,23 @@
+Copyright © 2013 Florent Xicluna <florent.xicluna at gmail.com>
+
+Licensed under the terms of the Expat License
+
+Permission is hereby granted, free of charge, to any person
+obtaining a copy of this software and associated documentation files
+(the "Software"), to deal in the Software without restriction,
+including without limitation the rights to use, copy, modify, merge,
+publish, distribute, sublicense, and/or sell copies of the Software,
+and to permit persons to whom the Software is furnished to do so,
+subject to the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
+BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
+ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE.
diff --git a/README.rst b/README.rst
new file mode 100644
index 0000000..eb782aa
--- /dev/null
+++ b/README.rst
@@ -0,0 +1,116 @@
+PEP-8 Naming Conventions
+========================
+
+.. image:: https://badge.fury.io/py/pep8-naming.png
+ :target: http://badge.fury.io/py/pep8-naming
+
+.. image:: https://travis-ci.org/flintwork/pep8-naming.png?branch=master
+ :target: https://travis-ci.org/flintwork/pep8-naming
+
+.. image:: https://pypip.in/d/pep8-naming/badge.png
+ :target: https://crate.io/packages/pep8-naming?version=latest
+
+Check the PEP-8 naming conventions.
+
+This module provides a plugin for ``flake8``, the Python code checker.
+
+(It replaces the plugin ``flint-naming`` for the ``flint`` checker.)
+
+
+Installation
+------------
+
+You can install, upgrade, uninstall ``pep8-naming`` with these commands::
+
+ $ pip install pep8-naming
+ $ pip install --upgrade pep8-naming
+ $ pip uninstall pep8-naming
+
+
+Plugin for Flake8
+-----------------
+
+When both ``flake8`` and ``pep8-naming`` are installed, the plugin is
+available in ``flake8``::
+
+ $ flake8 --version
+ 2.0 (pep8: 1.4.3, pyflakes: 0.6.1, naming: 0.2)
+
+By default the plugin is enabled.
+
+These error codes are emitted:
+
++------+-------------------------------------------------------+
+| code | sample message |
++======+=======================================================+
+| N801 | class names should use CapWords convention |
++------+-------------------------------------------------------+
+| N802 | function name should be lowercase |
++------+-------------------------------------------------------+
+| N803 | argument name should be lowercase |
++------+-------------------------------------------------------+
+| N804 | first argument of a classmethod should be named 'cls' |
++------+-------------------------------------------------------+
+| N805 | first argument of a method should be named 'self' |
++------+-------------------------------------------------------+
+| N806 | variable in function should be lowercase |
++------+-------------------------------------------------------+
++------+-------------------------------------------------------+
+| N811 | constant imported as non constant |
++------+-------------------------------------------------------+
+| N812 | lowercase imported as non lowercase |
++------+-------------------------------------------------------+
+| N813 | camelcase imported as lowercase |
++------+-------------------------------------------------------+
+| N814 | camelcase imported as constant |
++------+-------------------------------------------------------+
+
+
+Changes
+-------
+
+0.3.1 - 2015-06-14
+``````````````````
+
+* Fix optparse exception resulting from trying to register an option twice.
+
+
+0.3.0 - 2015-06-14
+``````````````````
+
+* Relaxed N806 checking for use with namedtuples
+
+* Add ``--ignore-names`` which allows the user to specify a list of names to
+ ignore. By default this includes ``setUp``, ``tearDown``, ``setUpClass``,
+ and ``tearDownClass``.
+
+
+0.2.2 - 2014-04-19
+``````````````````
+* Do not require ``setuptools`` in setup.py. It works around an issue
+ with ``pip`` and Python 3.
+
+* ``__new__`` is now considered as ``classmethod`` implicitly
+
+* Run unit tests on travis-ci.org for python2.6, 2.7, 3.2, and 3.3
+
+* Add unit tests and support running them with setup.py
+
+* Support Python 3.4
+
+
+0.2.1 - 2013-02-22
+``````````````````
+* Do not require ``flake8``
+
+
+0.2 - 2013-02-22
+````````````````
+* Rename project ``flint-naming`` to ``pep8-naming``
+
+* Fix a crash when function argument is a tuple of tuples
+
+
+0.1 - 2013-02-11
+````````````````
+* First release
diff --git a/pep8ext_naming.py b/pep8ext_naming.py
new file mode 100644
index 0000000..d5ee9a2
--- /dev/null
+++ b/pep8ext_naming.py
@@ -0,0 +1,294 @@
+# -*- coding: utf-8 -*-
+"""Checker of PEP-8 Naming Conventions."""
+import re
+import sys
+from collections import deque
+
+try:
+ import ast
+ from ast import iter_child_nodes
+except ImportError:
+ from flake8.util import ast, iter_child_nodes
+
+__version__ = '0.3.1'
+
+LOWERCASE_REGEX = re.compile(r'[_a-z][_a-z0-9]*$')
+UPPERCASE_REGEX = re.compile(r'[_A-Z][_A-Z0-9]*$')
+MIXEDCASE_REGEX = re.compile(r'_?[A-Z][a-zA-Z0-9]*$')
+
+
+if sys.version_info[0] < 3:
+ def _unpack_args(args):
+ ret = []
+ for arg in args:
+ if isinstance(arg, ast.Tuple):
+ ret.extend(_unpack_args(arg.elts))
+ else:
+ ret.append(arg.id)
+ return ret
+
+ def get_arg_names(node):
+ return _unpack_args(node.args.args)
+else:
+ def get_arg_names(node):
+ pos_args = [arg.arg for arg in node.args.args]
+ kw_only = [arg.arg for arg in node.args.kwonlyargs]
+ return pos_args + kw_only
+
+
+class _ASTCheckMeta(type):
+ def __init__(self, class_name, bases, namespace):
+ try:
+ self._checks.append(self())
+ except AttributeError:
+ self._checks = []
+
+
+def _err(self, node, code):
+ lineno, col_offset = node.lineno, node.col_offset
+ if isinstance(node, ast.ClassDef):
+ lineno += len(node.decorator_list)
+ col_offset += 6
+ elif isinstance(node, ast.FunctionDef):
+ lineno += len(node.decorator_list)
+ col_offset += 4
+ return (lineno, col_offset, '%s %s' % (code, getattr(self, code)), self)
+BaseASTCheck = _ASTCheckMeta('BaseASTCheck', (object,),
+ {'__doc__': "Base for AST Checks.", 'err': _err})
+
+
+class NamingChecker(object):
+ """Checker of PEP-8 Naming Conventions."""
+ name = 'naming'
+ version = __version__
+ ignore_names = ['setUp', 'tearDown', 'setUpClass', 'tearDownClass']
+
+ def __init__(self, tree, filename):
+ self.visitors = BaseASTCheck._checks
+ self.parents = deque()
+ self._node = tree
+
+ @classmethod
+ def add_options(cls, parser):
+ parser.add_option('--ignore-names', default=cls.ignore_names,
+ action='store', type='string',
+ help="Names that should be ignored.")
+ parser.config_options.append('ignore-names')
+
+ @classmethod
+ def parse_options(cls, options):
+ cls.ignore_names = options.ignore_names.split(' ')
+
+ def run(self):
+ return self.visit_tree(self._node) if self._node else ()
+
+ def visit_tree(self, node):
+ for error in self.visit_node(node):
+ yield error
+ self.parents.append(node)
+ for child in iter_child_nodes(node):
+ for error in self.visit_tree(child):
+ yield error
+ self.parents.pop()
+
+ def visit_node(self, node):
+ if isinstance(node, ast.ClassDef):
+ self.tag_class_functions(node)
+ elif isinstance(node, ast.FunctionDef):
+ self.find_global_defs(node)
+
+ method = 'visit_' + node.__class__.__name__.lower()
+ parents = self.parents
+ ignore_names = self.ignore_names
+ for visitor in self.visitors:
+ visitor_method = getattr(visitor, method, None)
+ if visitor_method is None:
+ continue
+ for error in visitor_method(node, parents, ignore_names):
+ yield error
+
+ def tag_class_functions(self, cls_node):
+ """Tag functions if they are methods, classmethods, staticmethods"""
+ # tries to find all 'old style decorators' like
+ # m = staticmethod(m)
+ late_decoration = {}
+ for node in iter_child_nodes(cls_node):
+ if not (isinstance(node, ast.Assign) and
+ isinstance(node.value, ast.Call) and
+ isinstance(node.value.func, ast.Name)):
+ continue
+ func_name = node.value.func.id
+ if func_name in ('classmethod', 'staticmethod'):
+ meth = (len(node.value.args) == 1 and node.value.args[0])
+ if isinstance(meth, ast.Name):
+ late_decoration[meth.id] = func_name
+
+ # iterate over all functions and tag them
+ for node in iter_child_nodes(cls_node):
+ if not isinstance(node, ast.FunctionDef):
+ continue
+
+ node.function_type = 'method'
+ if node.name == '__new__':
+ node.function_type = 'classmethod'
+
+ if node.name in late_decoration:
+ node.function_type = late_decoration[node.name]
+ elif node.decorator_list:
+ names = [d.id for d in node.decorator_list
+ if isinstance(d, ast.Name) and
+ d.id in ('classmethod', 'staticmethod')]
+ if names:
+ node.function_type = names[0]
+
+ def find_global_defs(self, func_def_node):
+ global_names = set()
+ nodes_to_check = deque(iter_child_nodes(func_def_node))
+ while nodes_to_check:
+ node = nodes_to_check.pop()
+ if isinstance(node, ast.Global):
+ global_names.update(node.names)
+
+ if not isinstance(node, (ast.FunctionDef, ast.ClassDef)):
+ nodes_to_check.extend(iter_child_nodes(node))
+ func_def_node.global_names = global_names
+
+
+class ClassNameCheck(BaseASTCheck):
+ """
+ Almost without exception, class names use the CapWords convention.
+
+ Classes for internal use have a leading underscore in addition.
+ """
+ check = MIXEDCASE_REGEX.match
+ N801 = "class names should use CapWords convention"
+
+ def visit_classdef(self, node, parents, ignore=None):
+ if not self.check(node.name):
+ yield self.err(node, 'N801')
+
+
+class FunctionNameCheck(BaseASTCheck):
+ """
+ Function names should be lowercase, with words separated by underscores
+ as necessary to improve readability.
+ Functions *not* beeing methods '__' in front and back are not allowed.
+
+ mixedCase is allowed only in contexts where that's already the
+ prevailing style (e.g. threading.py), to retain backwards compatibility.
+ """
+ check = LOWERCASE_REGEX.match
+ N802 = "function name should be lowercase"
+
+ def visit_functiondef(self, node, parents, ignore=None):
+ function_type = getattr(node, 'function_type', 'function')
+ name = node.name
+ if ignore and name in ignore:
+ return
+ if ((function_type == 'function' and '__' in (name[:2], name[-2:])) or
+ not self.check(name)):
+ yield self.err(node, 'N802')
+
+
+class FunctionArgNamesCheck(BaseASTCheck):
+ """
+ The argument names of a function should be lowercase, with words separated
+ by underscores.
+
+ A classmethod should have 'cls' as first argument.
+ A method should have 'self' as first argument.
+ """
+ check = LOWERCASE_REGEX.match
+ N803 = "argument name should be lowercase"
+ N804 = "first argument of a classmethod should be named 'cls'"
+ N805 = "first argument of a method should be named 'self'"
+
+ def visit_functiondef(self, node, parents, ignore=None):
+
+ def arg_name(arg):
+ return getattr(arg, 'arg', arg)
+
+ kwarg = arg_name(node.args.kwarg)
+ if kwarg is not None:
+ if not self.check(kwarg):
+ yield self.err(node, 'N803')
+ return
+
+ vararg = arg_name(node.args.vararg)
+ if vararg is not None:
+ if not self.check(vararg):
+ yield self.err(node, 'N803')
+ return
+
+ arg_names = get_arg_names(node)
+ if not arg_names:
+ return
+ function_type = getattr(node, 'function_type', 'function')
+
+ if function_type == 'method':
+ if arg_names[0] != 'self':
+ yield self.err(node, 'N805')
+ elif function_type == 'classmethod':
+ if arg_names[0] != 'cls':
+ yield self.err(node, 'N804')
+ for arg in arg_names:
+ if not self.check(arg):
+ yield self.err(node, 'N803')
+ return
+
+
+class ImportAsCheck(BaseASTCheck):
+ """
+ Don't change the naming convention via an import
+ """
+ check_lower = LOWERCASE_REGEX.match
+ check_upper = UPPERCASE_REGEX.match
+ N811 = "constant imported as non constant"
+ N812 = "lowercase imported as non lowercase"
+ N813 = "camelcase imported as lowercase"
+ N814 = "camelcase imported as constant"
+
+ def visit_importfrom(self, node, parents, ignore=None):
+ for name in node.names:
+ if not name.asname:
+ continue
+ if self.check_upper(name.name):
+ if not self.check_upper(name.asname):
+ yield self.err(node, 'N811')
+ elif self.check_lower(name.name):
+ if not self.check_lower(name.asname):
+ yield self.err(node, 'N812')
+ elif self.check_lower(name.asname):
+ yield self.err(node, 'N813')
+ elif self.check_upper(name.asname):
+ yield self.err(node, 'N814')
+
+
+class VariablesInFunctionCheck(BaseASTCheck):
+ """
+ Local variables in functions should be lowercase
+ """
+ check = LOWERCASE_REGEX.match
+ N806 = "variable in function should be lowercase"
+
+ def visit_assign(self, node, parents, ignore=None):
+ for parent_func in reversed(parents):
+ if isinstance(parent_func, ast.ClassDef):
+ return
+ if isinstance(parent_func, ast.FunctionDef):
+ break
+ else:
+ return
+ for target in node.targets:
+ name = isinstance(target, ast.Name) and target.id
+ if not name or name in parent_func.global_names:
+ return
+ if not self.check(name) and name[:1] != '_':
+ if isinstance(node.value, ast.Call):
+ if isinstance(node.value.func, ast.Attribute):
+ if node.value.func.attr == 'namedtuple':
+ return
+ elif isinstance(node.value.func, ast.Name):
+ if node.value.func.id == 'namedtuple':
+ return
+ yield self.err(target, 'N806')
diff --git a/run_tests.py b/run_tests.py
new file mode 100644
index 0000000..b3d1b93
--- /dev/null
+++ b/run_tests.py
@@ -0,0 +1,81 @@
+import sys
+import os
+import pep8ext_naming
+import re
+
+PyCF_ONLY_AST = 1024
+
+IS_PY3 = sys.version_info[0] == 3
+IS_PY3_TEST = re.compile("^#\s*python3\s*only")
+IS_PY2_TEST = re.compile("^#\s*python2\s*only")
+
+
+def main():
+ print('Running pep8-naming tests')
+ test_count = 0
+ errors = 0
+ for filename in os.listdir('testsuite'):
+ with open(os.path.join('testsuite', filename)) as fd:
+ lines = list(fd)
+ if not is_test_allowed(lines):
+ continue
+
+ for testcase, codes in load_tests(lines):
+ test_count += 1
+ errors += test_file(filename, testcase, codes)
+
+ if errors == 0:
+ print("%s tests run successful" % test_count)
+ sys.exit(0)
+ else:
+ print("%i of %i tests failed" % (errors, test_count))
+ sys.exit(1)
+
+
+def is_test_allowed(lines):
+ if IS_PY3 and any(IS_PY2_TEST.search(line) for line in lines[:3]):
+ return False
+
+ if not IS_PY3 and any(IS_PY3_TEST.search(line) for line in lines[:3]):
+ return False
+
+ return True
+
+
+def load_tests(lines):
+ testcase = []
+ codes = []
+ for line in lines:
+ if line.startswith("#:"):
+ if testcase:
+ yield testcase, codes
+ del testcase[:]
+ codes = line.split()[1:]
+ else:
+ testcase.append(line)
+
+ if testcase and codes:
+ yield testcase, codes
+
+
+def test_file(filename, lines, codes):
+ tree = compile(''.join(lines), '', 'exec', PyCF_ONLY_AST)
+ checker = pep8ext_naming.NamingChecker(tree, filename)
+ found_errors = []
+ for lineno, col_offset, msg, instance in checker.run():
+ found_errors.append(msg.split()[0])
+
+ if not found_errors and codes == ['Okay']:
+ return 0
+
+ errors = 0
+ for code in codes:
+ if code not in found_errors:
+ errors += 1
+ print("ERROR: %s not in %s" % (code, filename))
+
+ return errors
+
+
+if __name__ == '__main__':
+ main()
diff --git a/setup.cfg b/setup.cfg
new file mode 100644
index 0000000..5e40900
--- /dev/null
+++ b/setup.cfg
@@ -0,0 +1,2 @@
+[wheel]
+universal = 1
diff --git a/setup.py b/setup.py
new file mode 100644
index 0000000..dd4d0d0
--- /dev/null
+++ b/setup.py
@@ -0,0 +1,70 @@
+# -*- coding: utf-8 -*-
+from __future__ import with_statement
+from setuptools import setup
+from setuptools.command.test import test as TestCommand
+
+
+def get_version(fname='pep8ext_naming.py'):
+ with open(fname) as f:
+ for line in f:
+ if line.startswith('__version__'):
+ return eval(line.split('=')[-1])
+
+
+def get_long_description():
+ descr = []
+ for fname in ('README.rst',):
+ with open(fname) as f:
+ descr.append(f.read())
+ return '\n\n'.join(descr)
+
+
+class RunTests(TestCommand):
+ def finalize_options(self):
+ TestCommand.finalize_options(self)
+ self.test_args = []
+ self.test_suite = True
+
+ def run_tests(self):
+ import run_tests
+ import sys
+ errno = run_tests.main()
+ sys.exit(errno)
+
+
+setup(
+ name='pep8-naming',
+ version=get_version(),
+ description="Check PEP-8 naming conventions, plugin for flake8",
+ long_description=get_long_description(),
+ keywords='flake8 pep8 naming',
+ author='Florent Xicluna',
+ author_email='florent.xicluna at gmail.com',
+ url='https://github.com/flintwork/pep8-naming',
+ license='Expat license',
+ py_modules=['pep8ext_naming'],
+ zip_safe=False,
+ entry_points={
+ 'flake8.extension': [
+ 'N8 = pep8ext_naming:NamingChecker',
+ ],
+ # Backward compatibility for Flint (now merged into Flake8)
+ 'flint.extension': [
+ 'N80 = pep8ext_naming:NamingChecker',
+ 'N81 = pep8ext_naming:NamingChecker',
+ ],
+ },
+ classifiers=[
+ 'Development Status :: 3 - Alpha',
+ 'Environment :: Console',
+ 'Intended Audience :: Developers',
+ 'License :: OSI Approved :: MIT License',
+ 'Operating System :: OS Independent',
+ 'Programming Language :: Python',
+ 'Programming Language :: Python :: 2',
+ 'Programming Language :: Python :: 3',
+ 'Topic :: Software Development :: Libraries :: Python Modules',
+ 'Topic :: Software Development :: Quality Assurance',
+ ],
+ cmdclass={'test': RunTests},
+)
diff --git a/testsuite/N801.py b/testsuite/N801.py
new file mode 100644
index 0000000..68b50d0
--- /dev/null
+++ b/testsuite/N801.py
@@ -0,0 +1,11 @@
+#: N801
+class notok(object):
+ pass
+#: N801
+class Good(object):
+ class notok(object):
+ pass
+ pass
+#: Okay
+class VeryGood(object):
+ pass
diff --git a/testsuite/N802.py b/testsuite/N802.py
new file mode 100644
index 0000000..9061def
--- /dev/null
+++ b/testsuite/N802.py
@@ -0,0 +1,72 @@
+#: Okay
+def ok():
+ pass
+#: N802
+def __bad():
+ pass
+#: N802
+def bad__():
+ pass
+#: N802
+def __bad__():
+ pass
+#: Okay
+def _ok():
+ pass
+#: Okay
+def ok_ok_ok_ok():
+ pass
+#: Okay
+def _somehow_good():
+ pass
+#: Okay
+def go_od_():
+ pass
+#: Okay
+def _go_od_():
+ pass
+#: N802
+def NotOK():
+ pass
+#: Okay
+def _():
+ pass
+#: Okay
+class Foo(object):
+ def __method(self):
+ pass
+#: Okay
+class Foo(object):
+ def __method__(self):
+ pass
+#: Okay
+class ClassName(object):
+ def __method__(self):
+ pass
+#: N802
+class ClassName(object):
+ def notOk(self):
+ pass
+#: N802
+class ClassName(object):
+ def method(self):
+ def __bad():
+ pass
+#: Okay
+def setUp():
+ pass
+
+#: Okay
+def tearDown():
+ pass
+
+#: Okay
+class TestCase:
+ def setUp(self):
+ pass
+ def tearDown(self):
+ pass
+ def setUpClass(self):
+ pass
+ def tearDownClass(self):
+ pass
diff --git a/testsuite/N803.py b/testsuite/N803.py
new file mode 100644
index 0000000..f619bd6
--- /dev/null
+++ b/testsuite/N803.py
@@ -0,0 +1,50 @@
+#: Okay
+def b1():
+ pass
+#: Okay
+def b2(a):
+ pass
+#: Okay
+def b3(a, b, c, d):
+ pass
+#: Okay
+def b4(a, b, c, *fuck):
+ pass
+#: Okay
+def b5(*fuck):
+ pass
+#: Okay
+def b6(a, b, c, **kwargs):
+ pass
+#: Okay
+def b7(**kwargs):
+ pass
+#: Okay
+def b8(*args, **kwargs):
+ pass
+#: Okay
+def b9(a, b, c, *args, **kwargs):
+ pass
+#: Okay
+def b10(a, b, c=3, d=4, *args, **kwargs):
+ pass
+#: N803
+def b11(**BAD):
+ pass
+#: N803
+def b12(*BAD):
+ pass
+#: N803
+def b13(BAD, *VERYBAD, **EXTRABAD):
+ pass
+#: N803
+def b14(BAD):
+ pass
+#: N803
+class Test(object):
+ def __init__(self, BAD):
+ pass
+
+ @classmethod
+ def test(cls, BAD):
+ pass
diff --git a/testsuite/N803_py2.py b/testsuite/N803_py2.py
new file mode 100644
index 0000000..58a6896
--- /dev/null
+++ b/testsuite/N803_py2.py
@@ -0,0 +1,7 @@
+# python2 only
+#: Okay
+def test(a, b, (good, verygood)):
+ pass
+#: N803
+def bad(a, b, (OHH, NOO)):
+ pass
diff --git a/testsuite/N803_py3.py b/testsuite/N803_py3.py
new file mode 100644
index 0000000..7fdaeec
--- /dev/null
+++ b/testsuite/N803_py3.py
@@ -0,0 +1,13 @@
+# python3 only
+#: Okay
+def compare(a, b, *, key=None):
+ pass
+#: N803
+def compare(a, b, *, BAD=None):
+ pass
+#: N803
+def compare(a, b, *VERY, bad=None):
+ pass
+#: N803
+def compare(a, b, *ok, fine=None, **BAD):
+ pass
diff --git a/testsuite/N804.py b/testsuite/N804.py
new file mode 100644
index 0000000..0fe6c06
--- /dev/null
+++ b/testsuite/N804.py
@@ -0,0 +1,13 @@
+#: N804
+class Foo(object):
+ @classmethod
+ def mmm(cls, ads):
+ pass
+
+ @classmethod
+ def bad(self, ads):
+ pass
+
+ @calling()
+ def test(self, ads):
+ pass
diff --git a/testsuite/N805.py b/testsuite/N805.py
new file mode 100644
index 0000000..2a19e1a
--- /dev/null
+++ b/testsuite/N805.py
@@ -0,0 +1,16 @@
+#: N805
+class Foo(object):
+ def good(self, ads):
+ pass
+
+ def bad(ads, self):
+ pass
+#: Okay
+class Foo(object):
+ def __new__(cls):
+ return object.__new__(Foo)
+#: Okay
+class Foo(object):
+ @classmethod
+ def __prepare__(cls):
+ pass
diff --git a/testsuite/N806.py b/testsuite/N806.py
new file mode 100644
index 0000000..53cb2d0
--- /dev/null
+++ b/testsuite/N806.py
@@ -0,0 +1,48 @@
+#: Okay
+def test():
+ good = 1
+#: Okay
+def test():
+ def test2():
+ good = 1
+#: Okay
+GOOD = 1
+#: Okay
+class Test(object):
+ GOOD = 1
+#: N806
+def test():
+ Bad = 1
+#: N806
+def test():
+ VERY = 2
+#: N806
+def test():
+ def test2():
+ class Foo(object):
+ def test3(self):
+ Bad = 3
+#: Okay
+def good():
+ global Bad
+ Bad = 1
+#: N806
+def bad():
+ global Bad
+
+ def foo():
+ Bad = 1
+
+#: Okay
+def test():
+ # namedtuples are often CamelCased since we treat them a bit like classes
+ import collections
+ Thing = collections.namedtuple('Thing', 'a b c')
+ from collections import namedtuple
+ ThingTwo = namedtuple('ThingTwo', 'a b c')
+
+#: N806
+def bad():
+ # Currently don't support aliased imports of namedtuple
+ from collections import namedtuple as nt
+ Thing = nt('Thing', 'a b c')
diff --git a/testsuite/N81x.py b/testsuite/N81x.py
new file mode 100644
index 0000000..826f331
--- /dev/null
+++ b/testsuite/N81x.py
@@ -0,0 +1,12 @@
+#: Okay
+import good as good
+#: Okay
+from mod import good as nice, NICE as GOOD, Camel as Memel
+#: N811
+from mod import GOOD as bad
+#: N812
+from mod import good as Bad
+#: N813
+from mod import CamelCase as noncamle
+#: N814
+from mod import CamelCase as CONSTANT
diff --git a/tox.ini b/tox.ini
new file mode 100644
index 0000000..ef2173d
--- /dev/null
+++ b/tox.ini
@@ -0,0 +1,13 @@
+[tox]
+envlist = py26,py27,py32,py33,py34,pypy,pypy3
+
+[testenv]
+commands = python run_tests.py
+
+[testenv:release]
+deps =
+ twine >= 1.4.0
+ wheel
... 3 lines suppressed ...
--
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/python-modules/packages/pep8-naming.git
More information about the Python-modules-commits
mailing list