python-2.5.2/win32/Lib/test/test_funcattrs.py
changeset 0 ae805ac0140d
equal deleted inserted replaced
-1:000000000000 0:ae805ac0140d
       
     1 from test.test_support import verbose, TestFailed, verify
       
     2 import types
       
     3 
       
     4 class F:
       
     5     def a(self):
       
     6         pass
       
     7 
       
     8 def b():
       
     9     'my docstring'
       
    10     pass
       
    11 
       
    12 # __module__ is a special attribute
       
    13 verify(b.__module__ == __name__)
       
    14 verify(verify.__module__ == "test.test_support")
       
    15 
       
    16 # setting attributes on functions
       
    17 try:
       
    18     b.publish
       
    19 except AttributeError: pass
       
    20 else: raise TestFailed, 'expected AttributeError'
       
    21 
       
    22 if b.__dict__ <> {}:
       
    23     raise TestFailed, 'expected unassigned func.__dict__ to be {}'
       
    24 
       
    25 b.publish = 1
       
    26 if b.publish <> 1:
       
    27     raise TestFailed, 'function attribute not set to expected value'
       
    28 
       
    29 docstring = 'its docstring'
       
    30 b.__doc__ = docstring
       
    31 if b.__doc__ <> docstring:
       
    32     raise TestFailed, 'problem with setting __doc__ attribute'
       
    33 
       
    34 if 'publish' not in dir(b):
       
    35     raise TestFailed, 'attribute not in dir()'
       
    36 
       
    37 try:
       
    38     del b.__dict__
       
    39 except TypeError: pass
       
    40 else: raise TestFailed, 'del func.__dict__ expected TypeError'
       
    41 
       
    42 b.publish = 1
       
    43 try:
       
    44     b.__dict__ = None
       
    45 except TypeError: pass
       
    46 else: raise TestFailed, 'func.__dict__ = None expected TypeError'
       
    47 
       
    48 d = {'hello': 'world'}
       
    49 b.__dict__ = d
       
    50 if b.func_dict is not d:
       
    51     raise TestFailed, 'func.__dict__ assignment to dictionary failed'
       
    52 if b.hello <> 'world':
       
    53     raise TestFailed, 'attribute after func.__dict__ assignment failed'
       
    54 
       
    55 f1 = F()
       
    56 f2 = F()
       
    57 
       
    58 try:
       
    59     F.a.publish
       
    60 except AttributeError: pass
       
    61 else: raise TestFailed, 'expected AttributeError'
       
    62 
       
    63 try:
       
    64     f1.a.publish
       
    65 except AttributeError: pass
       
    66 else: raise TestFailed, 'expected AttributeError'
       
    67 
       
    68 # In Python 2.1 beta 1, we disallowed setting attributes on unbound methods
       
    69 # (it was already disallowed on bound methods).  See the PEP for details.
       
    70 try:
       
    71     F.a.publish = 1
       
    72 except (AttributeError, TypeError): pass
       
    73 else: raise TestFailed, 'expected AttributeError or TypeError'
       
    74 
       
    75 # But setting it explicitly on the underlying function object is okay.
       
    76 F.a.im_func.publish = 1
       
    77 
       
    78 if F.a.publish <> 1:
       
    79     raise TestFailed, 'unbound method attribute not set to expected value'
       
    80 
       
    81 if f1.a.publish <> 1:
       
    82     raise TestFailed, 'bound method attribute access did not work'
       
    83 
       
    84 if f2.a.publish <> 1:
       
    85     raise TestFailed, 'bound method attribute access did not work'
       
    86 
       
    87 if 'publish' not in dir(F.a):
       
    88     raise TestFailed, 'attribute not in dir()'
       
    89 
       
    90 try:
       
    91     f1.a.publish = 0
       
    92 except (AttributeError, TypeError): pass
       
    93 else: raise TestFailed, 'expected AttributeError or TypeError'
       
    94 
       
    95 # See the comment above about the change in semantics for Python 2.1b1
       
    96 try:
       
    97     F.a.myclass = F
       
    98 except (AttributeError, TypeError): pass
       
    99 else: raise TestFailed, 'expected AttributeError or TypeError'
       
   100 
       
   101 F.a.im_func.myclass = F
       
   102 
       
   103 f1.a.myclass
       
   104 f2.a.myclass
       
   105 f1.a.myclass
       
   106 F.a.myclass
       
   107 
       
   108 if f1.a.myclass is not f2.a.myclass or \
       
   109        f1.a.myclass is not F.a.myclass:
       
   110     raise TestFailed, 'attributes were not the same'
       
   111 
       
   112 # try setting __dict__
       
   113 try:
       
   114     F.a.__dict__ = (1, 2, 3)
       
   115 except (AttributeError, TypeError): pass
       
   116 else: raise TestFailed, 'expected TypeError or AttributeError'
       
   117 
       
   118 F.a.im_func.__dict__ = {'one': 11, 'two': 22, 'three': 33}
       
   119 
       
   120 if f1.a.two <> 22:
       
   121     raise TestFailed, 'setting __dict__'
       
   122 
       
   123 from UserDict import UserDict
       
   124 d = UserDict({'four': 44, 'five': 55})
       
   125 
       
   126 try:
       
   127     F.a.__dict__ = d
       
   128 except (AttributeError, TypeError): pass
       
   129 else: raise TestFailed
       
   130 
       
   131 if f2.a.one <> f1.a.one <> F.a.one <> 11:
       
   132     raise TestFailed
       
   133 
       
   134 # im_func may not be a Python method!
       
   135 import new
       
   136 F.id = new.instancemethod(id, None, F)
       
   137 
       
   138 eff = F()
       
   139 if eff.id() <> id(eff):
       
   140     raise TestFailed
       
   141 
       
   142 try:
       
   143     F.id.foo
       
   144 except AttributeError: pass
       
   145 else: raise TestFailed
       
   146 
       
   147 try:
       
   148     F.id.foo = 12
       
   149 except (AttributeError, TypeError): pass
       
   150 else: raise TestFailed
       
   151 
       
   152 try:
       
   153     F.id.foo
       
   154 except AttributeError: pass
       
   155 else: raise TestFailed
       
   156 
       
   157 try:
       
   158     eff.id.foo
       
   159 except AttributeError: pass
       
   160 else: raise TestFailed
       
   161 
       
   162 try:
       
   163     eff.id.foo = 12
       
   164 except (AttributeError, TypeError): pass
       
   165 else: raise TestFailed
       
   166 
       
   167 try:
       
   168     eff.id.foo
       
   169 except AttributeError: pass
       
   170 else: raise TestFailed
       
   171 
       
   172 # Regression test for a crash in pre-2.1a1
       
   173 def another():
       
   174     pass
       
   175 
       
   176 try:
       
   177     del another.__dict__
       
   178 except TypeError: pass
       
   179 else: raise TestFailed
       
   180 
       
   181 try:
       
   182     del another.func_dict
       
   183 except TypeError: pass
       
   184 else: raise TestFailed
       
   185 
       
   186 try:
       
   187     another.func_dict = None
       
   188 except TypeError: pass
       
   189 else: raise TestFailed
       
   190 
       
   191 try:
       
   192     del another.bar
       
   193 except AttributeError: pass
       
   194 else: raise TestFailed
       
   195 
       
   196 # This isn't specifically related to function attributes, but it does test a
       
   197 # core dump regression in funcobject.c
       
   198 del another.func_defaults
       
   199 
       
   200 def foo():
       
   201     pass
       
   202 
       
   203 def bar():
       
   204     pass
       
   205 
       
   206 def temp():
       
   207     print 1
       
   208 
       
   209 if foo==bar:
       
   210     raise TestFailed
       
   211 
       
   212 d={}
       
   213 d[foo] = 1
       
   214 
       
   215 foo.func_code = temp.func_code
       
   216 
       
   217 d[foo]
       
   218 
       
   219 # Test all predefined function attributes systematically
       
   220 
       
   221 def cantset(obj, name, value, exception=(AttributeError, TypeError)):
       
   222     verify(hasattr(obj, name)) # Otherwise it's probably a typo
       
   223     try:
       
   224         setattr(obj, name, value)
       
   225     except exception:
       
   226         pass
       
   227     else:
       
   228         raise TestFailed, "shouldn't be able to set %s to %r" % (name, value)
       
   229     try:
       
   230         delattr(obj, name)
       
   231     except (AttributeError, TypeError):
       
   232         pass
       
   233     else:
       
   234         raise TestFailed, "shouldn't be able to del %s" % name
       
   235 
       
   236 def test_func_closure():
       
   237     a = 12
       
   238     def f(): print a
       
   239     c = f.func_closure
       
   240     verify(isinstance(c, tuple))
       
   241     verify(len(c) == 1)
       
   242     verify(c[0].__class__.__name__ == "cell") # don't have a type object handy
       
   243     cantset(f, "func_closure", c)
       
   244 
       
   245 def test_empty_cell():
       
   246     def f(): print a
       
   247     try:
       
   248         f.func_closure[0].cell_contents
       
   249     except ValueError:
       
   250         pass
       
   251     else:
       
   252         raise TestFailed, "shouldn't be able to read an empty cell"
       
   253 
       
   254     a = 12
       
   255 
       
   256 def test_func_doc():
       
   257     def f(): pass
       
   258     verify(f.__doc__ is None)
       
   259     verify(f.func_doc is None)
       
   260     f.__doc__ = "hello"
       
   261     verify(f.__doc__ == "hello")
       
   262     verify(f.func_doc == "hello")
       
   263     del f.__doc__
       
   264     verify(f.__doc__ is None)
       
   265     verify(f.func_doc is None)
       
   266     f.func_doc = "world"
       
   267     verify(f.__doc__ == "world")
       
   268     verify(f.func_doc == "world")
       
   269     del f.func_doc
       
   270     verify(f.func_doc is None)
       
   271     verify(f.__doc__ is None)
       
   272 
       
   273 def test_func_globals():
       
   274     def f(): pass
       
   275     verify(f.func_globals is globals())
       
   276     cantset(f, "func_globals", globals())
       
   277 
       
   278 def test_func_name():
       
   279     def f(): pass
       
   280     verify(f.__name__ == "f")
       
   281     verify(f.func_name == "f")
       
   282     f.__name__ = "g"
       
   283     verify(f.__name__ == "g")
       
   284     verify(f.func_name == "g")
       
   285     f.func_name = "h"
       
   286     verify(f.__name__ == "h")
       
   287     verify(f.func_name == "h")
       
   288     cantset(f, "func_globals", 1)
       
   289     cantset(f, "__name__", 1)
       
   290     # test that you can access func.__name__ in restricted mode
       
   291     s = """def f(): pass\nf.__name__"""
       
   292     exec s in {'__builtins__':{}}
       
   293 
       
   294 
       
   295 def test_func_code():
       
   296     a = b = 24
       
   297     def f(): pass
       
   298     def g(): print 12
       
   299     def f1(): print a
       
   300     def g1(): print b
       
   301     def f2(): print a, b
       
   302     verify(type(f.func_code) is types.CodeType)
       
   303     f.func_code = g.func_code
       
   304     cantset(f, "func_code", None)
       
   305     # can't change the number of free vars
       
   306     cantset(f,  "func_code", f1.func_code, exception=ValueError)
       
   307     cantset(f1, "func_code",  f.func_code, exception=ValueError)
       
   308     cantset(f1, "func_code", f2.func_code, exception=ValueError)
       
   309     f1.func_code = g1.func_code
       
   310 
       
   311 def test_func_defaults():
       
   312     def f(a, b): return (a, b)
       
   313     verify(f.func_defaults is None)
       
   314     f.func_defaults = (1, 2)
       
   315     verify(f.func_defaults == (1, 2))
       
   316     verify(f(10) == (10, 2))
       
   317     def g(a=1, b=2): return (a, b)
       
   318     verify(g.func_defaults == (1, 2))
       
   319     del g.func_defaults
       
   320     verify(g.func_defaults is None)
       
   321     try:
       
   322         g()
       
   323     except TypeError:
       
   324         pass
       
   325     else:
       
   326         raise TestFailed, "shouldn't be allowed to call g() w/o defaults"
       
   327 
       
   328 def test_func_dict():
       
   329     def f(): pass
       
   330     a = f.__dict__
       
   331     b = f.func_dict
       
   332     verify(a == {})
       
   333     verify(a is b)
       
   334     f.hello = 'world'
       
   335     verify(a == {'hello': 'world'})
       
   336     verify(f.func_dict is a is f.__dict__)
       
   337     f.func_dict = {}
       
   338     verify(not hasattr(f, "hello"))
       
   339     f.__dict__ = {'world': 'hello'}
       
   340     verify(f.world == "hello")
       
   341     verify(f.__dict__ is f.func_dict == {'world': 'hello'})
       
   342     cantset(f, "func_dict", None)
       
   343     cantset(f, "__dict__", None)
       
   344 
       
   345 def test_im_class():
       
   346     class C:
       
   347         def foo(self): pass
       
   348     verify(C.foo.im_class is C)
       
   349     verify(C().foo.im_class is C)
       
   350     cantset(C.foo, "im_class", C)
       
   351     cantset(C().foo, "im_class", C)
       
   352 
       
   353 def test_im_func():
       
   354     def foo(self): pass
       
   355     class C:
       
   356         pass
       
   357     C.foo = foo
       
   358     verify(C.foo.im_func is foo)
       
   359     verify(C().foo.im_func is foo)
       
   360     cantset(C.foo, "im_func", foo)
       
   361     cantset(C().foo, "im_func", foo)
       
   362 
       
   363 def test_im_self():
       
   364     class C:
       
   365         def foo(self): pass
       
   366     verify(C.foo.im_self is None)
       
   367     c = C()
       
   368     verify(c.foo.im_self is c)
       
   369     cantset(C.foo, "im_self", None)
       
   370     cantset(c.foo, "im_self", c)
       
   371 
       
   372 def test_im_dict():
       
   373     class C:
       
   374         def foo(self): pass
       
   375         foo.bar = 42
       
   376     verify(C.foo.__dict__ == {'bar': 42})
       
   377     verify(C().foo.__dict__ == {'bar': 42})
       
   378     cantset(C.foo, "__dict__", C.foo.__dict__)
       
   379     cantset(C().foo, "__dict__", C.foo.__dict__)
       
   380 
       
   381 def test_im_doc():
       
   382     class C:
       
   383         def foo(self): "hello"
       
   384     verify(C.foo.__doc__ == "hello")
       
   385     verify(C().foo.__doc__ == "hello")
       
   386     cantset(C.foo, "__doc__", "hello")
       
   387     cantset(C().foo, "__doc__", "hello")
       
   388 
       
   389 def test_im_name():
       
   390     class C:
       
   391         def foo(self): pass
       
   392     verify(C.foo.__name__ == "foo")
       
   393     verify(C().foo.__name__ == "foo")
       
   394     cantset(C.foo, "__name__", "foo")
       
   395     cantset(C().foo, "__name__", "foo")
       
   396 
       
   397 def testmore():
       
   398     test_func_closure()
       
   399     test_empty_cell()
       
   400     test_func_doc()
       
   401     test_func_globals()
       
   402     test_func_name()
       
   403     test_func_code()
       
   404     test_func_defaults()
       
   405     test_func_dict()
       
   406     # Tests for instance method attributes
       
   407     test_im_class()
       
   408     test_im_func()
       
   409     test_im_self()
       
   410     test_im_dict()
       
   411     test_im_doc()
       
   412     test_im_name()
       
   413 
       
   414 testmore()