[Python-checkins] r59014 - in sandbox/trunk/pep362: pep362.py pep362_fodder.py pep362_py2_fodder.py pep362_py3k_fodder.py test_pep362.py tests tests/pep362_fodder.py tests/pep362_py2_fodder.py tests/pep362_py3k_fodder.py tests/test_pep362.py

brett.cannon python-checkins at python.org
Fri Nov 16 07:35:42 CET 2007


Author: brett.cannon
Date: Fri Nov 16 07:35:42 2007
New Revision: 59014

Added:
   sandbox/trunk/pep362/tests/
   sandbox/trunk/pep362/tests/pep362_fodder.py
      - copied unchanged from r58028, sandbox/trunk/pep362/pep362_fodder.py
   sandbox/trunk/pep362/tests/pep362_py2_fodder.py
      - copied unchanged from r59013, sandbox/trunk/pep362/pep362_py2_fodder.py
   sandbox/trunk/pep362/tests/pep362_py3k_fodder.py
      - copied unchanged from r58028, sandbox/trunk/pep362/pep362_py3k_fodder.py
   sandbox/trunk/pep362/tests/test_pep362.py   (contents, props changed)
Removed:
   sandbox/trunk/pep362/pep362_fodder.py
   sandbox/trunk/pep362/pep362_py2_fodder.py
   sandbox/trunk/pep362/pep362_py3k_fodder.py
   sandbox/trunk/pep362/test_pep362.py
Modified:
   sandbox/trunk/pep362/   (props changed)
   sandbox/trunk/pep362/pep362.py
Log:
Move tests into a test directory.


Modified: sandbox/trunk/pep362/pep362.py
==============================================================================
--- sandbox/trunk/pep362/pep362.py	(original)
+++ sandbox/trunk/pep362/pep362.py	Fri Nov 16 07:35:42 2007
@@ -75,7 +75,11 @@
         """Initialize from a function or method object."""
         if hasattr(func, 'im_func'):
             func = func.im_func
-        func_code = func.__code__
+        try:
+            func_code = func.__code__
+        except AttributeError:
+            # Compatibility for versions < 2.6.
+            func_code = func.func_code
 
         self.name = func.__name__
 
@@ -97,8 +101,13 @@
         positional = argspec[0]
         keyword_only = func_code.co_varnames[pos_count:
                                                 pos_count+keyword_only_count]
-        if func.__defaults__:
-            pos_default_count = len(func.__defaults__)
+        try:
+            fxn_defaults = func.__defaults__
+        except AttributeError:
+            # Deal with old names prior to 2.6.
+            fxn_defaults = func.func_defaults
+        if fxn_defaults:
+            pos_default_count = len(fxn_defaults)
         else:
             pos_default_count = 0
 
@@ -114,7 +123,7 @@
         for offset, name in enumerate(positional[non_default_count:]):
             name = self._convert_name(name)
             has_annotation, annotation = self._find_annotation(func, name)
-            default_value = func.__defaults__[offset]
+            default_value = fxn_defaults[offset]
             param = Parameter(name, offset+non_default_count,
                                 has_default=True, default_value=default_value,
                                 has_annotation=has_annotation,
@@ -124,7 +133,9 @@
         for offset, name in enumerate(keyword_only):
             has_annotation, annotation = self._find_annotation(func, name)
             has_default, default_value = False, None
-            if func.__kwdefaults__ and name in func.__kwdefaults__:
+            # hasattr check only needed for versions < 2.6.
+            if (hasattr(func, '__kwdefaults__') and func.__kwdefaults__ and
+                    name in func.__kwdefaults__):
                 has_default = True
                 default_value = func.__kwdefaults__[name]
             param = Parameter(name, offset+pos_count, keyword_only=True,

Deleted: /sandbox/trunk/pep362/pep362_fodder.py
==============================================================================
--- /sandbox/trunk/pep362/pep362_fodder.py	Fri Nov 16 07:35:42 2007
+++ (empty file)
@@ -1,14 +0,0 @@
-def no_args():
-    pass
-
-def var_args(*args):
-    pass
-
-def var_kw_args(**kwargs):
-    pass
-
-def no_default_args(a):
-    pass
-
-def default_args(a=42):
-    pass

Deleted: /sandbox/trunk/pep362/pep362_py2_fodder.py
==============================================================================
--- /sandbox/trunk/pep362/pep362_py2_fodder.py	Fri Nov 16 07:35:42 2007
+++ (empty file)
@@ -1,8 +0,0 @@
-def tuple_args((a, (b,))):
-    return a, b
-
-def default_tuple_args((a, (b,))=(1, (2,))):
-    pass
-
-def all_args(a, (b, (c,)), d=0, (e, (f,))=(4, (5,)), *g, **h):
-    return a, b, c, d, e, f, g, h

Deleted: /sandbox/trunk/pep362/pep362_py3k_fodder.py
==============================================================================
--- /sandbox/trunk/pep362/pep362_py3k_fodder.py	Fri Nov 16 07:35:42 2007
+++ (empty file)
@@ -1,24 +0,0 @@
-def keyword_only(*, a):
-    pass
-
-def keyword_only_default(*, a=42):
-    pass
-
-def arg_annotation(a:int):
-    pass
-
-def arg_annotation_default(a:int=42):
-    pass
-
-def arg_annotation_var(*args:int, **kwargs:int):
-    pass
-
-def arg_annotation_keyword_only(*, a:int):
-    pass
-
-def return_annotation() -> int:
-    pass
-
-def all_args(a:int, d=0, *args:int,
-                g:int, h:int=8, **kwargs:int) -> int:
-    return a, d, g, h, args, kwargs

Deleted: /sandbox/trunk/pep362/test_pep362.py
==============================================================================
--- /sandbox/trunk/pep362/test_pep362.py	Fri Nov 16 07:35:42 2007
+++ (empty file)
@@ -1,393 +0,0 @@
-import pep362
-
-import unittest
-from test import test_support
-import pep362_fodder
-try:
-    import pep362_py2_fodder
-except SyntaxError:
-    import pep362_py3k_fodder
-from sys import version_info
-
-
-def version_specific(major_number):
-    def inner(fxn):
-        if version_info[0] == major_number:
-            return fxn
-        else:
-            return lambda self: self
-    return inner
-
-
-class ParameterObjectTests(unittest.TestCase):
-
-    """Test the Parameter object."""
-
-    def test_name(self):
-        # Test that 'name' attribute works.
-        # Must test both using a string and a tuple of strings.
-        name = "test"
-        param = pep362.Parameter(name, 0)
-        self.failUnlessEqual(param.name, name)
-        name = ('a', ('b',))
-        param = pep362.Parameter(name, 0)
-        self.failUnlessEqual(param.name, name)
-
-    def test_position(self):
-        # Test the 'position' attribute.
-        pos = 42
-        param = pep362.Parameter("_", pos)
-        self.failUnlessEqual(param.position, pos)
-
-    def test_default_values(self):
-        # Test the 'has_default' attribute.
-        # Testing that 'default_value' is not set is handled in the testing of
-        # that attribute.
-        default_value = 42
-        param = pep362.Parameter('_', 0, True, default_value)
-        self.failUnlessEqual(param.has_default, True)
-        self.failUnlessEqual(param.default_value, default_value)
-        param = pep362.Parameter('_', 0, False)
-        self.failUnlessEqual(param.has_default, False)
-        self.failUnless(not hasattr(param, 'default_value'))
-
-    def test_keyword_only(self):
-        # Setting the value for keyword_only should create an attribute.
-        for value in (True, False):
-            param = pep362.Parameter('_', 0, keyword_only=value)
-            self.failUnlessEqual(param.keyword_only, value)
-
-    def test_annotations(self):
-        # If has_annotation is False then 'annotation' should not exist.
-        param = pep362.Parameter('_', 0, has_annotation=False)
-        self.failUnlessEqual(param.has_annotation, False)
-        self.failUnless(not hasattr(param, 'annotation'))
-        annotation = 42
-        param = pep362.Parameter('_', 0, has_annotation=True,
-                                    annotation=annotation)
-        self.failUnlessEqual(param.has_annotation, True)
-        self.failUnlessEqual(param.annotation, annotation)
-
-
-class SignatureObjectTests(unittest.TestCase):
-
-    def test_no_args(self):
-        # Test a function with no arguments.
-        sig = pep362.Signature(pep362_fodder.no_args)
-        self.failUnlessEqual('no_args', sig.name)
-        self.failUnless(not sig.var_args)
-        self.failUnless(not sig.var_kw_args)
-        self.failUnlessEqual(0, len(sig.parameters))
-
-    def test_var_args(self):
-        # Test the var_args attribute.
-        sig = pep362.Signature(pep362_fodder.var_args)
-        self.failUnlessEqual('args', sig.var_args)
-        self.failUnlessEqual(0, len(sig.parameters))
-        sig = pep362.Signature(pep362_fodder.no_args)
-        self.failUnlessEqual('', sig.var_args)
-
-    def test_var_kw_args(self):
-        # Test the var_kw_args attribute.
-        sig = pep362.Signature(pep362_fodder.var_kw_args)
-        self.failUnlessEqual('var_kw_args', sig.name)
-        self.failUnlessEqual('kwargs', sig.var_kw_args)
-        self.failUnlessEqual(0, len(sig.parameters))
-        sig = pep362.Signature(pep362_fodder.no_args)
-        self.failUnlessEqual('', sig.var_kw_args)
-
-    def test_parameter_positional(self):
-        # A function with positional arguments should work.
-        sig = pep362.Signature(pep362_fodder.no_default_args)
-        self.failUnlessEqual('no_default_args', sig.name)
-        param = sig.parameters[0]
-        self.failUnlessEqual('a', param.name)
-        self.failUnlessEqual(0, param.position)
-        self.failUnless(not param.has_default)
-        self.failUnless(not hasattr(param, 'default_value'))
-
-    def test_parameter_default(self):
-        # Default parameters for a function should work.
-        sig = pep362.Signature(pep362_fodder.default_args)
-        self.failUnlessEqual('default_args', sig.name)
-        param = sig.parameters[0]
-        self.failUnlessEqual('a', param.name)
-        self.failUnlessEqual(0, param.position)
-        self.failUnless(param.has_default)
-        self.failUnlessEqual(42, param.default_value)
-
-    @version_specific(2)
-    def test_parameter_tuple(self):
-        # A function with a tuple as a parameter should work.
-        sig = pep362.Signature(pep362_py2_fodder.tuple_args)
-        self.failUnlessEqual('tuple_args', sig.name)
-        param = sig.parameters[0]
-        self.failUnless(isinstance(param.name, tuple))
-        self.failUnlessEqual(('a', ('b',)), param.name)
-        self.failUnlessEqual(0, param.position)
-        self.failUnless(not param.has_default)
-        self.failUnless(not hasattr(param, 'default_value'))
-
-    @version_specific(2)
-    def test_parameter_tuple_default(self):
-        # A default argument for a tuple parameter needs to work.
-        sig = pep362.Signature(pep362_py2_fodder.default_tuple_args)
-        self.failUnlessEqual('default_tuple_args', sig.name)
-        param = sig.parameters[0]
-        self.failUnlessEqual(('a', ('b',)), param.name)
-        self.failUnlessEqual(0, param.position)
-        self.failUnless(param.has_default)
-        self.failUnlessEqual((1, (2,)), param.default_value)
-
-    @version_specific(3)
-    def test_keyword_only(self):
-        # Is a function containing keyword-only parameters handled properly?
-        sig = pep362.Signature(pep362_py3k_fodder.keyword_only)
-        param = sig.parameters[0]
-        self.failUnlessEqual(param.name, 'a')
-        self.failUnless(param.keyword_only)
-        self.failUnlessEqual(param.position, 0)
-
-    @version_specific(3)
-    def test_keyword_only_default(self):
-        # Default arguments can work for keyword-only parameters.
-        sig = pep362.Signature(pep362_py3k_fodder.keyword_only_default)
-        param = sig.parameters[0]
-        self.failUnlessEqual(param.name, 'a')
-        self.failUnless(param.keyword_only)
-        self.failUnlessEqual(param.position, 0)
-        self.failUnless(param.has_default)
-        self.failUnlessEqual(param.default_value, 42)
-
-    @version_specific(3)
-    def test_annotations(self):
-        # Make sure the proper annotation is found.
-        sig = pep362.Signature(pep362_py3k_fodder.arg_annotation)
-        param = sig.parameters[0]
-        self.failUnlessEqual(param.name, 'a')
-        self.failUnless(param.has_annotation)
-        self.failUnlessEqual(param.annotation, int)
-
-    @version_specific(3)
-    def test_annotations_default(self):
-        # Annotations with a default value should work.
-        sig = pep362.Signature(pep362_py3k_fodder.arg_annotation_default)
-        param = sig.parameters[0]
-        self.failUnlessEqual(param.name, 'a')
-        self.failUnless(param.has_annotation)
-        self.failUnlessEqual(param.annotation, int)
-        self.failUnless(param.has_default)
-        self.failUnlessEqual(param.default_value, 42)
-
-    @version_specific(3)
-    def test_annotation_keyword_only(self):
-        # Keyword-only parameters can have an annotation.
-        sig = pep362.Signature(pep362_py3k_fodder.arg_annotation_keyword_only)
-        param = sig.parameters[0]
-        self.failUnlessEqual(param.name, 'a')
-        self.failUnless(param.has_annotation)
-        self.failUnlessEqual(param.annotation, int)
-        self.failUnless(param.keyword_only)
-
-    @version_specific(3)
-    def test_return_annotation(self):
-        # The return value annotation.
-        sig = pep362.Signature(pep362_py3k_fodder.return_annotation)
-        self.failUnless(sig.has_annotation)
-        self.failUnlessEqual(sig.annotation, int)
-
-    @version_specific(3)
-    def test_var_annotations(self):
-        # Annotation on variable arguments (*args & **kwargs).
-        sig = pep362.Signature(pep362_py3k_fodder.arg_annotation_var)
-        self.failUnlessEqual(sig.var_annotations[sig.var_args], int)
-        self.failUnlessEqual(sig.var_annotations[sig.var_kw_args], int)
-
-    def test_signature(self):
-        def fresh_func():
-            pass
-        self.failUnless(not hasattr(fresh_func, '__signature__'))
-        sig = pep362.signature(fresh_func)
-        self.failUnlessEqual(sig, fresh_func.__signature__)
-        sig2 = pep362.signature(fresh_func)
-        self.failUnlessEqual(sig, sig2)
-        class FreshClass(object):
-            def fresh_method(self):
-                pass
-        sig = pep362.signature(FreshClass.fresh_method)
-        self.failUnlessEqual(sig, FreshClass.fresh_method.im_func.__signature__)
-
-
-class SignatureBindTests(unittest.TestCase):
-
-    """Test Signature.bind()."""
-
-    def test_no_parameters(self):
-        sig = pep362.Signature(pep362_fodder.no_args)
-        binding = sig.bind()
-        self.failUnlessEqual({}, binding)
-        self.failUnlessRaises(pep362.BindError, sig.bind, 42)
-        self.failUnlessRaises(pep362.BindError, sig.bind, a=0)
-
-    def test_var_parameters(self):
-        sig = pep362.Signature(pep362_fodder.var_args)
-        binding = sig.bind(0, 1, 2)
-        self.failUnlessEqual({'args':(0, 1, 2)}, binding)
-        binding = sig.bind()
-        self.failUnlessEqual({'args':tuple()}, binding)
-        self.failUnlessRaises(pep362.BindError, sig.bind, a=0)
-
-    def test_var_kw_parameters(self):
-        sig = pep362.Signature(pep362_fodder.var_kw_args)
-        binding = sig.bind(a=0)
-        self.failUnlessEqual({'kwargs':{'a':0}}, binding)
-        binding = sig.bind()
-        self.failUnlessEqual({'kwargs':{}}, binding)
-        self.failUnlessRaises(pep362.BindError, sig.bind, 42)
-
-    def test_positional_parameters(self):
-        sig = pep362.Signature(pep362_fodder.no_default_args)
-        binding = sig.bind(42)
-        self.failUnlessEqual({'a':42}, binding)
-        binding = sig.bind(a=42)
-        self.failUnlessEqual({'a':42}, binding)
-        self.failUnlessRaises(pep362.BindError, sig.bind)
-        self.failUnlessRaises(pep362.BindError, sig.bind, 0, 1)
-        self.failUnlessRaises(pep362.BindError, sig.bind, b=0)
-
-    def test_keyword_parameters(self):
-        sig = pep362.Signature(pep362_fodder.default_args)
-        binding = sig.bind()
-        self.failUnlessEqual({'a':42}, binding)
-        binding = sig.bind(0)
-        self.failUnlessEqual({'a':0}, binding)
-        binding = sig.bind(a=0)
-        self.failUnlessEqual({'a':0}, binding)
-        self.failUnlessRaises(pep362.BindError, sig.bind, 0, 1)
-        self.failUnlessRaises(pep362.BindError, sig.bind, a=0, b=1)
-        self.failUnlessRaises(pep362.BindError, sig.bind, b=1)
-
-    @version_specific(2)
-    def test_tuple_parameter(self):
-        sig = pep362.Signature(pep362_py2_fodder.tuple_args)
-        arg = (1, ((2,),))
-        binding = sig.bind(arg)
-        self.failUnlessEqual({'a':1, 'b':(2,)}, binding)
-        self.failUnlessRaises(pep362.BindError, sig.bind, (1,2,3))
-        self.failUnlessRaises(pep362.BindError, sig.bind, (1, 2))
-
-    @version_specific(2)
-    def test_default_tuple_parameter(self):
-        sig = pep362.Signature(pep362_py2_fodder.default_tuple_args)
-        binding = sig.bind()
-        self.failUnlessEqual({'a':1, 'b':2}, binding)
-        arg = (0, (1,))
-        binding = sig.bind(arg)
-        self.failUnlessEqual({'a':0, 'b':1}, binding)
-
-    @version_specific(2)
-    def test_py2_all_args(self):
-        sig = pep362.Signature(pep362_py2_fodder.all_args)
-        # a, (b, (c,)), d=0, (e, (f,))=(4, (5,)), *g, **h
-        # name, position, has_default, default value
-        expect = (('a', 0, False, None),
-                    (('b', ('c',)), 1, False, None),
-                    ('d', 2, True, 0),
-                    (('e', ('f',)), 3, True, (4, (5,))))
-        self.failUnlessEqual(len(sig.parameters), len(expect))
-        for param, check in zip(sig.parameters, expect):
-            name, pos, has_default, default_value = check
-            self.failUnlessEqual(param.name, name)
-            self.failUnlessEqual(param.position, pos)
-            if has_default:
-                self.failUnless(param.has_default)
-                self.failUnlessEqual(param.default_value, default_value)
-            else:
-                self.failUnless(not param.has_default)
-                self.failUnless(not hasattr(param, 'default_value'))
-            self.failUnless(not param.keyword_only)
-            self.failUnless(not param.has_annotation)
-            self.failUnless(not hasattr(param, 'annotation'))
-        self.failUnlessEqual(sig.var_args, 'g')
-        self.failUnlessEqual(sig.var_kw_args, 'h')
-        self.failUnlessEqual(len(sig.var_annotations), 0)
-        binding = sig.bind(0, (1, (2,)), d=3, i=7)
-        expected = {'a':0, 'b':1, 'c':2, 'd':3, 'e':4, 'f':5, 'g':tuple(),
-                    'h':{'i':7}}
-        self.failUnlessEqual(expected, binding)
-
-    @version_specific(3)
-    def test_keyword_only(self):
-        sig = pep362.Signature(pep362_py3k_fodder.keyword_only)
-        binding = sig.bind(a=42)
-        self.failUnlessEqual(binding, {'a':42})
-        self.failUnlessRaises(pep362.BindError, sig.bind)
-        self.failUnlessRaises(pep362.BindError, sig.bind, 42)
-
-    @version_specific(3)
-    def test_keyword_only_default(self):
-        sig = pep362.Signature(pep362_py3k_fodder.keyword_only_default)
-        binding = sig.bind()
-        self.failUnlessEqual(binding, {'a':42})
-        binding = sig.bind(a=1)
-        self.failUnlessEqual(binding, {'a':1})
-        self.failUnlessRaises(pep362.BindError, sig.bind, 1)
-
-    @version_specific(3)
-    def test_all_py3k_args(self):
-        # a, (b, (c,)), d=0, (e, (f,))=(0, (0,)), *args, g, h=8, **kwargs
-        sig = pep362.Signature(pep362_py3k_fodder.all_args)
-        # name, position, kw only, has_default, default, has anno, anno
-        expected = (('a', 0, False, False, None, True, int),
-                    ('d', 1, False, True, 0, False, None),
-                    ('g', 2, True, False, None, True, int),
-                    ('h', 3, True, True, 8, True, int))
-        self.failUnlessEqual(len(sig.parameters), len(expected),
-                "len(%r) != len(%r)" % ([param.name
-                                            for param in sig.parameters],
-                                        [expect[0] for expect in expected]))
-        for param, check in zip(sig.parameters, expected):
-            name, pos, kw_only, has_default, default, has_anno, anno = check
-            self.failUnlessEqual(param.name, name)
-            self.failUnlessEqual(param.position, pos)
-            if kw_only:
-                self.failUnless(param.keyword_only)
-            else:
-                self.failUnless(not param.keyword_only)
-            if has_default:
-                self.failUnless(param.has_default)
-                self.failUnlessEqual(param.default_value, default)
-            else:
-                self.failUnless(not param.has_default)
-                self.failUnless(not hasattr(param, 'default_value'))
-            if has_anno:
-                self.failUnless(param.has_annotation)
-                self.failUnlessEqual(param.annotation, anno)
-            else:
-                self.failUnless(not param.has_annotation)
-                self.failUnless(not hasattr(param, 'annotation'))
-        self.failUnlessEqual(sig.var_args, 'args')
-        self.failUnless(sig.var_args in sig.var_annotations)
-        self.failUnlessEqual(sig.var_annotations[sig.var_args], int)
-        self.failUnlessEqual(sig.var_kw_args, 'kwargs')
-        self.failUnless(sig.var_kw_args in sig.var_annotations)
-        self.failUnlessEqual(sig.var_annotations[sig.var_kw_args], int)
-        binding = sig.bind(0, 3, 6, g=7, i=9)
-        expected = {'a':0, 'd':3, 'g':7, 'h':8, 'args':(6,), 'kwargs':{'i':9}}
-        self.failUnlessEqual(binding, expected)
-
-    def test_too_many_arguments(self):
-        # Only one argument should pair up with a parameter.
-        sig = pep362.Signature(pep362_fodder.no_default_args)
-        self.failUnlessRaises(pep362.BindError, sig.bind, 1, a=1)
-
-
-def test_main():
-    test_support.run_unittest(ParameterObjectTests,
-                                SignatureObjectTests,
-                                SignatureBindTests,
-                             )
-
-
-if __name__ == '__main__':
-    test_main()

Added: sandbox/trunk/pep362/tests/test_pep362.py
==============================================================================
--- (empty file)
+++ sandbox/trunk/pep362/tests/test_pep362.py	Fri Nov 16 07:35:42 2007
@@ -0,0 +1,393 @@
+import pep362
+
+import unittest
+from test import test_support
+from tests import pep362_fodder
+try:
+    from tests import pep362_py2_fodder
+except SyntaxError:
+    from tests import pep362_py3k_fodder
+from sys import version_info
+
+
+def version_specific(major_number):
+    def inner(fxn):
+        if version_info[0] == major_number:
+            return fxn
+        else:
+            return lambda self: self
+    return inner
+
+
+class ParameterObjectTests(unittest.TestCase):
+
+    """Test the Parameter object."""
+
+    def test_name(self):
+        # Test that 'name' attribute works.
+        # Must test both using a string and a tuple of strings.
+        name = "test"
+        param = pep362.Parameter(name, 0)
+        self.failUnlessEqual(param.name, name)
+        name = ('a', ('b',))
+        param = pep362.Parameter(name, 0)
+        self.failUnlessEqual(param.name, name)
+
+    def test_position(self):
+        # Test the 'position' attribute.
+        pos = 42
+        param = pep362.Parameter("_", pos)
+        self.failUnlessEqual(param.position, pos)
+
+    def test_default_values(self):
+        # Test the 'has_default' attribute.
+        # Testing that 'default_value' is not set is handled in the testing of
+        # that attribute.
+        default_value = 42
+        param = pep362.Parameter('_', 0, True, default_value)
+        self.failUnlessEqual(param.has_default, True)
+        self.failUnlessEqual(param.default_value, default_value)
+        param = pep362.Parameter('_', 0, False)
+        self.failUnlessEqual(param.has_default, False)
+        self.failUnless(not hasattr(param, 'default_value'))
+
+    def test_keyword_only(self):
+        # Setting the value for keyword_only should create an attribute.
+        for value in (True, False):
+            param = pep362.Parameter('_', 0, keyword_only=value)
+            self.failUnlessEqual(param.keyword_only, value)
+
+    def test_annotations(self):
+        # If has_annotation is False then 'annotation' should not exist.
+        param = pep362.Parameter('_', 0, has_annotation=False)
+        self.failUnlessEqual(param.has_annotation, False)
+        self.failUnless(not hasattr(param, 'annotation'))
+        annotation = 42
+        param = pep362.Parameter('_', 0, has_annotation=True,
+                                    annotation=annotation)
+        self.failUnlessEqual(param.has_annotation, True)
+        self.failUnlessEqual(param.annotation, annotation)
+
+
+class SignatureObjectTests(unittest.TestCase):
+
+    def test_no_args(self):
+        # Test a function with no arguments.
+        sig = pep362.Signature(pep362_fodder.no_args)
+        self.failUnlessEqual('no_args', sig.name)
+        self.failUnless(not sig.var_args)
+        self.failUnless(not sig.var_kw_args)
+        self.failUnlessEqual(0, len(sig.parameters))
+
+    def test_var_args(self):
+        # Test the var_args attribute.
+        sig = pep362.Signature(pep362_fodder.var_args)
+        self.failUnlessEqual('args', sig.var_args)
+        self.failUnlessEqual(0, len(sig.parameters))
+        sig = pep362.Signature(pep362_fodder.no_args)
+        self.failUnlessEqual('', sig.var_args)
+
+    def test_var_kw_args(self):
+        # Test the var_kw_args attribute.
+        sig = pep362.Signature(pep362_fodder.var_kw_args)
+        self.failUnlessEqual('var_kw_args', sig.name)
+        self.failUnlessEqual('kwargs', sig.var_kw_args)
+        self.failUnlessEqual(0, len(sig.parameters))
+        sig = pep362.Signature(pep362_fodder.no_args)
+        self.failUnlessEqual('', sig.var_kw_args)
+
+    def test_parameter_positional(self):
+        # A function with positional arguments should work.
+        sig = pep362.Signature(pep362_fodder.no_default_args)
+        self.failUnlessEqual('no_default_args', sig.name)
+        param = sig.parameters[0]
+        self.failUnlessEqual('a', param.name)
+        self.failUnlessEqual(0, param.position)
+        self.failUnless(not param.has_default)
+        self.failUnless(not hasattr(param, 'default_value'))
+
+    def test_parameter_default(self):
+        # Default parameters for a function should work.
+        sig = pep362.Signature(pep362_fodder.default_args)
+        self.failUnlessEqual('default_args', sig.name)
+        param = sig.parameters[0]
+        self.failUnlessEqual('a', param.name)
+        self.failUnlessEqual(0, param.position)
+        self.failUnless(param.has_default)
+        self.failUnlessEqual(42, param.default_value)
+
+    @version_specific(2)
+    def test_parameter_tuple(self):
+        # A function with a tuple as a parameter should work.
+        sig = pep362.Signature(pep362_py2_fodder.tuple_args)
+        self.failUnlessEqual('tuple_args', sig.name)
+        param = sig.parameters[0]
+        self.failUnless(isinstance(param.name, tuple))
+        self.failUnlessEqual(('a', ('b',)), param.name)
+        self.failUnlessEqual(0, param.position)
+        self.failUnless(not param.has_default)
+        self.failUnless(not hasattr(param, 'default_value'))
+
+    @version_specific(2)
+    def test_parameter_tuple_default(self):
+        # A default argument for a tuple parameter needs to work.
+        sig = pep362.Signature(pep362_py2_fodder.default_tuple_args)
+        self.failUnlessEqual('default_tuple_args', sig.name)
+        param = sig.parameters[0]
+        self.failUnlessEqual(('a', ('b',)), param.name)
+        self.failUnlessEqual(0, param.position)
+        self.failUnless(param.has_default)
+        self.failUnlessEqual((1, (2,)), param.default_value)
+
+    @version_specific(3)
+    def test_keyword_only(self):
+        # Is a function containing keyword-only parameters handled properly?
+        sig = pep362.Signature(pep362_py3k_fodder.keyword_only)
+        param = sig.parameters[0]
+        self.failUnlessEqual(param.name, 'a')
+        self.failUnless(param.keyword_only)
+        self.failUnlessEqual(param.position, 0)
+
+    @version_specific(3)
+    def test_keyword_only_default(self):
+        # Default arguments can work for keyword-only parameters.
+        sig = pep362.Signature(pep362_py3k_fodder.keyword_only_default)
+        param = sig.parameters[0]
+        self.failUnlessEqual(param.name, 'a')
+        self.failUnless(param.keyword_only)
+        self.failUnlessEqual(param.position, 0)
+        self.failUnless(param.has_default)
+        self.failUnlessEqual(param.default_value, 42)
+
+    @version_specific(3)
+    def test_annotations(self):
+        # Make sure the proper annotation is found.
+        sig = pep362.Signature(pep362_py3k_fodder.arg_annotation)
+        param = sig.parameters[0]
+        self.failUnlessEqual(param.name, 'a')
+        self.failUnless(param.has_annotation)
+        self.failUnlessEqual(param.annotation, int)
+
+    @version_specific(3)
+    def test_annotations_default(self):
+        # Annotations with a default value should work.
+        sig = pep362.Signature(pep362_py3k_fodder.arg_annotation_default)
+        param = sig.parameters[0]
+        self.failUnlessEqual(param.name, 'a')
+        self.failUnless(param.has_annotation)
+        self.failUnlessEqual(param.annotation, int)
+        self.failUnless(param.has_default)
+        self.failUnlessEqual(param.default_value, 42)
+
+    @version_specific(3)
+    def test_annotation_keyword_only(self):
+        # Keyword-only parameters can have an annotation.
+        sig = pep362.Signature(pep362_py3k_fodder.arg_annotation_keyword_only)
+        param = sig.parameters[0]
+        self.failUnlessEqual(param.name, 'a')
+        self.failUnless(param.has_annotation)
+        self.failUnlessEqual(param.annotation, int)
+        self.failUnless(param.keyword_only)
+
+    @version_specific(3)
+    def test_return_annotation(self):
+        # The return value annotation.
+        sig = pep362.Signature(pep362_py3k_fodder.return_annotation)
+        self.failUnless(sig.has_annotation)
+        self.failUnlessEqual(sig.annotation, int)
+
+    @version_specific(3)
+    def test_var_annotations(self):
+        # Annotation on variable arguments (*args & **kwargs).
+        sig = pep362.Signature(pep362_py3k_fodder.arg_annotation_var)
+        self.failUnlessEqual(sig.var_annotations[sig.var_args], int)
+        self.failUnlessEqual(sig.var_annotations[sig.var_kw_args], int)
+
+    def test_signature(self):
+        def fresh_func():
+            pass
+        self.failUnless(not hasattr(fresh_func, '__signature__'))
+        sig = pep362.signature(fresh_func)
+        self.failUnlessEqual(sig, fresh_func.__signature__)
+        sig2 = pep362.signature(fresh_func)
+        self.failUnlessEqual(sig, sig2)
+        class FreshClass(object):
+            def fresh_method(self):
+                pass
+        sig = pep362.signature(FreshClass.fresh_method)
+        self.failUnlessEqual(sig, FreshClass.fresh_method.im_func.__signature__)
+
+
+class SignatureBindTests(unittest.TestCase):
+
+    """Test Signature.bind()."""
+
+    def test_no_parameters(self):
+        sig = pep362.Signature(pep362_fodder.no_args)
+        binding = sig.bind()
+        self.failUnlessEqual({}, binding)
+        self.failUnlessRaises(pep362.BindError, sig.bind, 42)
+        self.failUnlessRaises(pep362.BindError, sig.bind, a=0)
+
+    def test_var_parameters(self):
+        sig = pep362.Signature(pep362_fodder.var_args)
+        binding = sig.bind(0, 1, 2)
+        self.failUnlessEqual({'args':(0, 1, 2)}, binding)
+        binding = sig.bind()
+        self.failUnlessEqual({'args':tuple()}, binding)
+        self.failUnlessRaises(pep362.BindError, sig.bind, a=0)
+
+    def test_var_kw_parameters(self):
+        sig = pep362.Signature(pep362_fodder.var_kw_args)
+        binding = sig.bind(a=0)
+        self.failUnlessEqual({'kwargs':{'a':0}}, binding)
+        binding = sig.bind()
+        self.failUnlessEqual({'kwargs':{}}, binding)
+        self.failUnlessRaises(pep362.BindError, sig.bind, 42)
+
+    def test_positional_parameters(self):
+        sig = pep362.Signature(pep362_fodder.no_default_args)
+        binding = sig.bind(42)
+        self.failUnlessEqual({'a':42}, binding)
+        binding = sig.bind(a=42)
+        self.failUnlessEqual({'a':42}, binding)
+        self.failUnlessRaises(pep362.BindError, sig.bind)
+        self.failUnlessRaises(pep362.BindError, sig.bind, 0, 1)
+        self.failUnlessRaises(pep362.BindError, sig.bind, b=0)
+
+    def test_keyword_parameters(self):
+        sig = pep362.Signature(pep362_fodder.default_args)
+        binding = sig.bind()
+        self.failUnlessEqual({'a':42}, binding)
+        binding = sig.bind(0)
+        self.failUnlessEqual({'a':0}, binding)
+        binding = sig.bind(a=0)
+        self.failUnlessEqual({'a':0}, binding)
+        self.failUnlessRaises(pep362.BindError, sig.bind, 0, 1)
+        self.failUnlessRaises(pep362.BindError, sig.bind, a=0, b=1)
+        self.failUnlessRaises(pep362.BindError, sig.bind, b=1)
+
+    @version_specific(2)
+    def test_tuple_parameter(self):
+        sig = pep362.Signature(pep362_py2_fodder.tuple_args)
+        arg = (1, ((2,),))
+        binding = sig.bind(arg)
+        self.failUnlessEqual({'a':1, 'b':(2,)}, binding)
+        self.failUnlessRaises(pep362.BindError, sig.bind, (1,2,3))
+        self.failUnlessRaises(pep362.BindError, sig.bind, (1, 2))
+
+    @version_specific(2)
+    def test_default_tuple_parameter(self):
+        sig = pep362.Signature(pep362_py2_fodder.default_tuple_args)
+        binding = sig.bind()
+        self.failUnlessEqual({'a':1, 'b':2}, binding)
+        arg = (0, (1,))
+        binding = sig.bind(arg)
+        self.failUnlessEqual({'a':0, 'b':1}, binding)
+
+    @version_specific(2)
+    def test_py2_all_args(self):
+        sig = pep362.Signature(pep362_py2_fodder.all_args)
+        # a, (b, (c,)), d=0, (e, (f,))=(4, (5,)), *g, **h
+        # name, position, has_default, default value
+        expect = (('a', 0, False, None),
+                    (('b', ('c',)), 1, False, None),
+                    ('d', 2, True, 0),
+                    (('e', ('f',)), 3, True, (4, (5,))))
+        self.failUnlessEqual(len(sig.parameters), len(expect))
+        for param, check in zip(sig.parameters, expect):
+            name, pos, has_default, default_value = check
+            self.failUnlessEqual(param.name, name)
+            self.failUnlessEqual(param.position, pos)
+            if has_default:
+                self.failUnless(param.has_default)
+                self.failUnlessEqual(param.default_value, default_value)
+            else:
+                self.failUnless(not param.has_default)
+                self.failUnless(not hasattr(param, 'default_value'))
+            self.failUnless(not param.keyword_only)
+            self.failUnless(not param.has_annotation)
+            self.failUnless(not hasattr(param, 'annotation'))
+        self.failUnlessEqual(sig.var_args, 'g')
+        self.failUnlessEqual(sig.var_kw_args, 'h')
+        self.failUnlessEqual(len(sig.var_annotations), 0)
+        binding = sig.bind(0, (1, (2,)), d=3, i=7)
+        expected = {'a':0, 'b':1, 'c':2, 'd':3, 'e':4, 'f':5, 'g':tuple(),
+                    'h':{'i':7}}
+        self.failUnlessEqual(expected, binding)
+
+    @version_specific(3)
+    def test_keyword_only(self):
+        sig = pep362.Signature(pep362_py3k_fodder.keyword_only)
+        binding = sig.bind(a=42)
+        self.failUnlessEqual(binding, {'a':42})
+        self.failUnlessRaises(pep362.BindError, sig.bind)
+        self.failUnlessRaises(pep362.BindError, sig.bind, 42)
+
+    @version_specific(3)
+    def test_keyword_only_default(self):
+        sig = pep362.Signature(pep362_py3k_fodder.keyword_only_default)
+        binding = sig.bind()
+        self.failUnlessEqual(binding, {'a':42})
+        binding = sig.bind(a=1)
+        self.failUnlessEqual(binding, {'a':1})
+        self.failUnlessRaises(pep362.BindError, sig.bind, 1)
+
+    @version_specific(3)
+    def test_all_py3k_args(self):
+        # a, (b, (c,)), d=0, (e, (f,))=(0, (0,)), *args, g, h=8, **kwargs
+        sig = pep362.Signature(pep362_py3k_fodder.all_args)
+        # name, position, kw only, has_default, default, has anno, anno
+        expected = (('a', 0, False, False, None, True, int),
+                    ('d', 1, False, True, 0, False, None),
+                    ('g', 2, True, False, None, True, int),
+                    ('h', 3, True, True, 8, True, int))
+        self.failUnlessEqual(len(sig.parameters), len(expected),
+                "len(%r) != len(%r)" % ([param.name
+                                            for param in sig.parameters],
+                                        [expect[0] for expect in expected]))
+        for param, check in zip(sig.parameters, expected):
+            name, pos, kw_only, has_default, default, has_anno, anno = check
+            self.failUnlessEqual(param.name, name)
+            self.failUnlessEqual(param.position, pos)
+            if kw_only:
+                self.failUnless(param.keyword_only)
+            else:
+                self.failUnless(not param.keyword_only)
+            if has_default:
+                self.failUnless(param.has_default)
+                self.failUnlessEqual(param.default_value, default)
+            else:
+                self.failUnless(not param.has_default)
+                self.failUnless(not hasattr(param, 'default_value'))
+            if has_anno:
+                self.failUnless(param.has_annotation)
+                self.failUnlessEqual(param.annotation, anno)
+            else:
+                self.failUnless(not param.has_annotation)
+                self.failUnless(not hasattr(param, 'annotation'))
+        self.failUnlessEqual(sig.var_args, 'args')
+        self.failUnless(sig.var_args in sig.var_annotations)
+        self.failUnlessEqual(sig.var_annotations[sig.var_args], int)
+        self.failUnlessEqual(sig.var_kw_args, 'kwargs')
+        self.failUnless(sig.var_kw_args in sig.var_annotations)
+        self.failUnlessEqual(sig.var_annotations[sig.var_kw_args], int)
+        binding = sig.bind(0, 3, 6, g=7, i=9)
+        expected = {'a':0, 'd':3, 'g':7, 'h':8, 'args':(6,), 'kwargs':{'i':9}}
+        self.failUnlessEqual(binding, expected)
+
+    def test_too_many_arguments(self):
+        # Only one argument should pair up with a parameter.
+        sig = pep362.Signature(pep362_fodder.no_default_args)
+        self.failUnlessRaises(pep362.BindError, sig.bind, 1, a=1)
+
+
+def test_main():
+    test_support.run_unittest(ParameterObjectTests,
+                                SignatureObjectTests,
+                                SignatureBindTests,
+                             )
+
+
+if __name__ == '__main__':
+    test_main()


More information about the Python-checkins mailing list