summaryrefslogtreecommitdiff
path: root/pylint
diff options
context:
space:
mode:
authorahirnish <ahirnish@gmail.com>2017-09-15 21:15:32 +0530
committerClaudiu Popa <pcmanticore@gmail.com>2017-09-15 17:45:32 +0200
commit3691a25bc5f4c6692508042656e0e936954034e5 (patch)
tree6c245dbe40a86e708e66924468c4d247edb5e508 /pylint
parenta80810644b3533de5c2455f33ec63838bf731f62 (diff)
downloadpylint-git-3691a25bc5f4c6692508042656e0e936954034e5.tar.gz
Adding a warning about keyword argument appearing before variable args list in the function definition (#1636)
Diffstat (limited to 'pylint')
-rw-r--r--pylint/checkers/design_analysis.py12
-rw-r--r--pylint/checkers/python3.py1
-rw-r--r--pylint/config.py4
-rw-r--r--pylint/test/functional/keyword_arg_before_vararg.py35
-rw-r--r--pylint/test/functional/keyword_arg_before_vararg.txt4
5 files changed, 53 insertions, 3 deletions
diff --git a/pylint/checkers/design_analysis.py b/pylint/checkers/design_analysis.py
index c34ec4dce..899dd708e 100644
--- a/pylint/checkers/design_analysis.py
+++ b/pylint/checkers/design_analysis.py
@@ -57,6 +57,12 @@ MSGS = {
'too-many-boolean-expressions',
'Used when a if statement contains too many boolean '
'expressions'),
+ 'W0917': ('Keyword argument before variable positional arguments list '
+ 'in the definition of %s function',
+ 'keyword-arg-before-vararg',
+ 'When defining a keyword argument before variable positional arguments, one can '
+ 'end up in having multiple values passed for the aforementioned parameter in '
+ 'case the method is called with keyword arguments.'),
}
@@ -211,7 +217,7 @@ class MisdesignChecker(BaseChecker):
@check_messages('too-many-return-statements', 'too-many-branches',
'too-many-arguments', 'too-many-locals',
- 'too-many-statements')
+ 'too-many-statements', 'keyword-arg-before-vararg')
def visit_functiondef(self, node):
"""check function name, docstring, arguments, redefinition,
variable names, max locals
@@ -237,6 +243,10 @@ class MisdesignChecker(BaseChecker):
if locnum > self.config.max_locals:
self.add_message('too-many-locals', node=node,
args=(locnum, self.config.max_locals))
+ # check for keyword arg before varargs
+ if node.args.vararg and node.args.defaults:
+ self.add_message('keyword-arg-before-vararg', node=node,
+ args=(node.name))
# init statements counter
self._stmts = 1
diff --git a/pylint/checkers/python3.py b/pylint/checkers/python3.py
index 2d96f19ad..c6c525fb4 100644
--- a/pylint/checkers/python3.py
+++ b/pylint/checkers/python3.py
@@ -558,6 +558,7 @@ class Python3Checker(checkers.BaseChecker):
self._branch_stack = []
super(Python3Checker, self).__init__(*args, **kwargs)
+ # pylint: disable=keyword-arg-before-vararg
def add_message(self, msg_id, always_warn=False, # pylint: disable=arguments-differ
*args, **kwargs):
if always_warn or not (self._branch_stack and self._branch_stack[-1].is_py2_only):
diff --git a/pylint/config.py b/pylint/config.py
index 325739267..2bde09eff 100644
--- a/pylint/config.py
+++ b/pylint/config.py
@@ -310,7 +310,7 @@ class Option(optparse.Option):
class OptionParser(optparse.OptionParser):
- def __init__(self, option_class=Option, *args, **kwargs):
+ def __init__(self, option_class, *args, **kwargs):
optparse.OptionParser.__init__(self, option_class=Option, *args, **kwargs)
def format_option_help(self, formatter=None):
@@ -461,7 +461,7 @@ class OptionsManagerMixIn(object):
# configuration file parser
self.cfgfile_parser = configparser.ConfigParser(inline_comment_prefixes=('#', ';'))
# command line parser
- self.cmdline_parser = OptionParser(usage=usage, version=version)
+ self.cmdline_parser = OptionParser(Option, usage=usage, version=version)
self.cmdline_parser.options_manager = self
self._optik_option_attrs = set(self.cmdline_parser.option_class.ATTRS)
diff --git a/pylint/test/functional/keyword_arg_before_vararg.py b/pylint/test/functional/keyword_arg_before_vararg.py
new file mode 100644
index 000000000..7c037d7e2
--- /dev/null
+++ b/pylint/test/functional/keyword_arg_before_vararg.py
@@ -0,0 +1,35 @@
+"""Unittests for W1125 (kw args before *args)"""
+from __future__ import absolute_import, print_function
+
+# pylint: disable=unused-argument
+def check_kwargs_before_args(param1, param2=2, *args): # [keyword-arg-before-vararg]
+ """docstring"""
+ pass
+
+check_kwargs_before_args(5)
+
+# pylint: disable=too-few-public-methods, invalid-name
+class AAAA(object):
+ """class AAAA"""
+ def func_in_class(self, param1, param2=2, *args): # [keyword-arg-before-vararg]
+ "method in class AAAA"
+ pass
+
+ @staticmethod
+ def static_method_in_class(param1, param2=3, *args): # [keyword-arg-before-vararg]
+ "static method in class AAAA"
+ pass
+
+ @classmethod
+ def class_method_in_class(cls, param1, param2=4, *args): # [keyword-arg-before-vararg]
+ "class method in class AAAA"
+ pass
+
+some_var = AAAA()
+some_var.func_in_class(3)
+
+some_var.static_method_in_class(4)
+AAAA.static_method_in_class(4)
+
+some_var.class_method_in_class(5)
+AAAA.class_method_in_class(5)
diff --git a/pylint/test/functional/keyword_arg_before_vararg.txt b/pylint/test/functional/keyword_arg_before_vararg.txt
new file mode 100644
index 000000000..c83ff733d
--- /dev/null
+++ b/pylint/test/functional/keyword_arg_before_vararg.txt
@@ -0,0 +1,4 @@
+keyword-arg-before-vararg:5:check_kwargs_before_args:Keyword argument before variable positional arguments list in the definition of check_kwargs_before_args function
+keyword-arg-before-vararg:14:AAAA.func_in_class:Keyword argument before variable positional arguments list in the definition of func_in_class function
+keyword-arg-before-vararg:19:AAAA.static_method_in_class:Keyword argument before variable positional arguments list in the definition of static_method_in_class function
+keyword-arg-before-vararg:24:AAAA.class_method_in_class:Keyword argument before variable positional arguments list in the definition of class_method_in_class function