Search code examples
pythonunit-testingrefactoringtdd

How do I unit test the methods in a method object?


I've performed the "Replace Method with Method Object" refactoring described by Beck.

Now, I have a class with a "run()" method and a bunch of member functions that decompose the computation into smaller units. How do I test those member functions?

My first idea is that my unit tests be basically copies of the "run()" method (with different initializations), but with assertions between each call to the member functions to check the state of the computation.

(I'm using Python and the unittest module.)

class Train: 

    def __init__(self, options, points): 
        self._options = options 
        self._points = points 
        # other initializations

    def run(self): 
        self._setup_mappings_dict() 
        self._setup_train_and_estimation_sets() 
        if self._options.estimate_method == 'per_class': 
            self._setup_priors() 
        self._estimate_all_mappings() 
        self._save_mappings() 

    def _estimate_all_mappings(): 
        # implementation, calls to methods in this class

    #other method definitions

I definitely have expectations about what the the states of the member attributes should be before and after calls to the the different methods as part of the implementation of the run() method. Should I be making assertions about these "private" attributes? I don't know how else to unittest these methods.

The other option is that I really shouldn't be testing these.


Solution

  • I'll answer my own question. After a bit of reading and thinking, I believe I shouldn't be unit testing these private methods. I should just test the public interface. If the private methods that do the internal processing are important enough to test independently and are not just coincidences of the current implementation, then perhaps this is a sign that they should be refactored out into a separate class.