|
Re: JUnit FAQ suggests private methods bad design?
>> <JUnit faq>
>> How do I test private methods?
>> Testing private methods may be an indication that those methods should
>> be moved into another class to promote reusability.
>> But if you must...
>> </JUnit faq>
Private methods are by no means a bad design. To understand the
response in the JUnit faq, you must first understand the question
asked.
>> How do I test private methods?
Private methods are not meant to be called from anything other than
the owning class/object. The point of JUnit testing is to make sure
that the inputs and outputs of an object work as expected. If each
tested input (method call, parameters) yields the expected output
(return value, object state), then the class can be considered
functional. Even if public methods call private methods, if the
outputs and inputs are correct then the private methods can be
considered correct as well. Private methods are tested indirectly by
testing the public methods that use them. This is known as "black box
testing".
Since the correctness of private methods lies in the fact of the
inputs and outputs working correctly, testing private methods directly
is unneccessary. It may even be a bad idea since that would make it
harder to change code internal to your class and not exposed to the
public.
>An alternative to private methods does exist.
>
>Instead of making a method private, you can
>always create a new class whose instance you
>store in a private member/instance -variable.
>
>Your main class can then send message to this
>private data object, but if you don't ever
>return it from any method, no other object can.
>Thus you have "privacy without private methods".
>
>This pattern may be preferable to "private
>methods" in many cases, since it adds more
>structure and reusability into your program.
>
>The class of the private data-object can in
>fact be used separately in different situations
>since it does have its *own* set of public methods.
>And unlike private methods, it can be subclassed
>as well.
>
>So, I would argue: "Private methods considered
>unnecessary".
>
>-Panu Viljamaa
I believe this method of making private data objects may have its
uses, but was put up as more of a work-around to allow JUnit users to
test would-be private methods. It definitely would add complexity to
a class that could otherwise be very simple, and if you choose to use
black box testing, then why test anything but the public interface
anyways?
>> Typically I try to code to an interface, have a class implement that
>> interface and if possible never expose more public methods than are in
>> the interface it implements. But my public methods often invoke a
>> number of private methods. It is these methods that usually do the
>> grunt work of my classes. I can change the private methods as I see
>> fit and never need to worry about breaking other classes. Fewer
>> methods to support (public methods) means fewer dependencies means
>> fewer things to go wrong. I find this to be good way to program, but
>> the answer in the FAQ would seem to suggest it's not. But I'm not sure
>> agree with moving a private method to another class to promote
>> reusability. If certain data is only available via a private method, a
>> client that requires this data can invoke a public methods, receive a
>> high level object and extract the data it requiers from the high level
>> object. Granted this means a little more work for the client, but
>> assuming the high level object the client receives has a well defined
>> interface, I see that approach as promoting stability. I was wondering
>> what other people's thoughts are on this issue.
>> Many thanks
>> Paul
|