In the Sandi Metz / Hashrocket lunch-n-learn video, on "The Design of Tests", she says something that I found particularly interesting. While discussing whether or not to test private methods, she mentions:
There's a school of thought that says, you should never have a private method .... anything that's private aught to get moved to another class.
Although she states that she doesn't entirely agree with this sentiment, she admits that it's worth thinking about. And, I tend to agree. I love private methods and I use them all the time. But, the thought of minimizing private methods is fascinating.
While the majority of my private methods feel tightly coupled to their parent class, often providing implementation details for validation and state transformation, some of them are general and could be easily moved to another class. For example, if I'm dealing with a 3rd-party API, I'll often create a private method that deals with hashing and the generation of Message Authentication Codes (MAC). This hashing logic could be factored out and put into something like my Crypto.cfc ColdFusion component.
However, when I move a private method to another class, it means that I now have to inject that class as a dependency into the original class. So, while I remove some duplication, I have an increase in complexity and coupling. I'm not calling this a zero-sum game; but, it's also not a flawless victory either.
Good object design is not something that I have a firm grasp on. So, I love these kind of statements that make me stop and think about how I organize my code and how I might evolve that organization. And, while I am not about to abandon private methods, I think it will be very helpful for me to ask the question: would this private method make more sense as a public method in another class?
NOTE: Sandi Metz has a bunch of great videos - you should be watching them.