Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > Python > Avoid converting functions to methods in a class

Reply
Thread Tools

Avoid converting functions to methods in a class

 
 
Steven D'Aprano
Guest
Posts: n/a
 
      02-20-2010
I have a convention when writing unit tests to put the target of the test
into a class attribute, as follows:

class MyTest(unittest.TestCase):
target = mymodule.someclass

def test_spam(self):
"""Test that someclass has a spam attribute."""
self.failUnless(hasattr(self.target, 'spam'))


It works well until I write a test for stand-alone functions:

class AnotherTest(unittest.TestCase):
target = mymodule.function

def test_foo(self):
self.assertEquals(self.target('a', 'b'), 'foo')

The problem is that target is turned into a method of my test class, not
a standalone function, and I get errors like:

TypeError: function() takes exactly 2 arguments (3 given)

The solution I currently use is to drop the target attribute in this
class, and just refer to mymodule.function in each individual test. I
don't like this solution because it violates Once And Only Once: if the
function changes name, I have to make many edits to the test suite rather
than just one.

Are there any better solutions?


--
Steven
 
Reply With Quote
 
 
 
 
Arnaud Delobelle
Guest
Posts: n/a
 
      02-20-2010
On 20 Feb, 03:33, Steven D'Aprano <st...@REMOVE-THIS-
cybersource.com.au> wrote:
> I have a convention when writing unit tests to put the target of the test
> into a class attribute, as follows:
>
> class MyTest(unittest.TestCase):
> * * target = mymodule.someclass
>
> * * def test_spam(self):
> * * * * """Test that someclass has a spam attribute."""
> * * * * self.failUnless(hasattr(self.target, 'spam'))
>
> It works well until I write a test for stand-alone functions:
>
> class AnotherTest(unittest.TestCase):
> * * target = mymodule.function
>
> * * def test_foo(self):
> * * * * self.assertEquals(self.target('a', 'b'), 'foo')
>
> The problem is that target is turned into a method of my test class, not
> a standalone function, and I get errors like:
>
> TypeError: function() takes exactly 2 arguments (3 given)
>
> The solution I currently use is to drop the target attribute in this
> class, and just refer to mymodule.function in each individual test. I
> don't like this solution because it violates Once And Only Once: if the
> function changes name, I have to make many edits to the test suite rather
> than just one.
>
> Are there any better solutions?
>
> --
> Steven


Why not define target in the TestCase.setUp() method?

class AnotherTest(unittest.TestCase):

def setUp(self):
self.target = mymodule.function

def test_foo(self):
self.assertEquals(self.target('a', 'b'), 'foo')

--
Arnaud



class
--
Arnaud
 
Reply With Quote
 
 
 
 
Jean-Michel Pichavant
Guest
Posts: n/a
 
      02-23-2010
Steven D'Aprano wrote:
> I have a convention when writing unit tests to put the target of the test
> into a class attribute, as follows:
>
> class MyTest(unittest.TestCase):
> target = mymodule.someclass
>
> def test_spam(self):
> """Test that someclass has a spam attribute."""
> self.failUnless(hasattr(self.target, 'spam'))
>
>
> It works well until I write a test for stand-alone functions:
>
> class AnotherTest(unittest.TestCase):
> target = mymodule.function
>
> def test_foo(self):
> self.assertEquals(self.target('a', 'b'), 'foo')
>
> The problem is that target is turned into a method of my test class, not
> a standalone function, and I get errors like:
>
> TypeError: function() takes exactly 2 arguments (3 given)
>
> The solution I currently use is to drop the target attribute in this
> class, and just refer to mymodule.function in each individual test. I
> don't like this solution because it violates Once And Only Once: if the
> function changes name, I have to make many edits to the test suite rather
> than just one.
>
> Are there any better solutions?
>
>
>


It looks like it works when declaring foo as static:

import unittest

def foo(a,b):
return 'fooo'

class AnotherTest(unittest.TestCase):
target = staticmethod(foo)

def test_foo(self):
self.assertEquals(self.target('a', 'b'), 'foo')

def runTest(self):
self.test_foo()

AnotherTest().runTest()
....AssertionError: 'fooo' != 'foo'

JM
 
Reply With Quote
 
Daniel Fetchinson
Guest
Posts: n/a
 
      02-23-2010
> I have a convention when writing unit tests to put the target of the test
> into a class attribute, as follows:
>
> class MyTest(unittest.TestCase):
> target = mymodule.someclass
>
> def test_spam(self):
> """Test that someclass has a spam attribute."""
> self.failUnless(hasattr(self.target, 'spam'))
>
>
> It works well until I write a test for stand-alone functions:
>
> class AnotherTest(unittest.TestCase):
> target = mymodule.function
>
> def test_foo(self):
> self.assertEquals(self.target('a', 'b'), 'foo')
>
> The problem is that target is turned into a method of my test class, not
> a standalone function, and I get errors like:
>
> TypeError: function() takes exactly 2 arguments (3 given)
>
> The solution I currently use is to drop the target attribute in this
> class, and just refer to mymodule.function in each individual test. I
> don't like this solution because it violates Once And Only Once: if the
> function changes name, I have to make many edits to the test suite rather
> than just one.


Isn't staticmethod the trick you need?

HTH,
Daniel


--
Psss, psss, put it down! - http://www.cafepress.com/putitdown
 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
calling class methods from class methods, help? Oltmans Python 6 03-11-2009 07:59 PM
Is there a way to find the class methods of a class, just like'methods' finds the instance methods? Kenneth McDonald Ruby 5 09-26-2008 03:09 PM
Avoid having a SQL express for web parts and avoid personalization Roger23 ASP .Net 2 10-12-2006 10:54 PM
Avoid calling non-final methods in a constructor: Applies to static methods too? Oliver Wong Java 14 06-13-2006 09:18 AM
Avoid wasting time or how to avoid initialization Alexander Malkis C++ 8 04-13-2004 11:23 PM



Advertisments