1

I am having trouble deciding how I should unit test a set of classes I have been writing for a game. I am working on the Player abstract class and have written some methods I need to unit test for correctness, but Player is still abstract and I haven't created an implementation yet, and it depends on other classes I have yet to implement. Does anyone have an idea of how to test this?

Please note that thees methods are just utility methods that don't need an implementation of Player to work, but is seems wrong to take them out of the class just so I can test them.

Carlos Bribiescas
  • 4,197
  • 9
  • 35
  • 66
J Atkin
  • 3,080
  • 2
  • 19
  • 33
  • You could use a mocking framework like mockito to test your abstract-class'es methods: http://stackoverflow.com/questions/1087339/using-mockito-to-test-abstract-classes – Christoph Giesche May 12 '15 at 15:05
  • Could those methods be static? Should they even exist in player? If you separate the data from the function its easier to unit test – Carlos Bribiescas May 12 '15 at 15:11
  • @CarlosBribiescas see my comment on McMonster's answer. How would I separate the data from the functionality? Most of the player is built around moving the player around a board/game. – J Atkin May 12 '15 at 15:17
  • @ChristophGiesche Can you call the empty methods defined by mockito? – J Atkin May 12 '15 at 15:44
  • @JAtkin If your functions can act on Players regardless of implementation, they could (maybe) be a static function that can be tested with a mocking framework. So instead of working with local members of the class, the function accepts the data it needs to work with and you mock the outcomes so you can test the functions. The already mentioned Mockito framework is good for this. – Carlos Bribiescas May 12 '15 at 17:51
  • @CarlosBribiescas The methods depend heavily on the players non abstract state, and I don't want 5 or 6 args to each helper method... – J Atkin May 12 '15 at 18:42
  • In that case I would go with @ChristophGiesche's response – Carlos Bribiescas May 13 '15 at 00:40

2 Answers2

3

If the methods in question really are no-ops for this test object, just create a subclass, either named or anonymous, that has empty bodies for the abstract methods.

chrylis -cautiouslyoptimistic-
  • 75,269
  • 21
  • 115
  • 152
0

The shortest answer is that you are approaching the problem from the wrong end. Start with something simple that works, then you'll be able to test it. Add abstractions as you develop the program, don't start from abstractions, because you won't know what you will really need before you do it.

Also if you have utility methods that don't actually depend on your Player implementation then those clearly shouldn't be part of Player class.

McMonster
  • 171
  • 1
  • 10
  • Well, I do need an abstraction for player because I will end up with 2-3 different types of player. Also the methods, as best I can tell, do belong in the `Player` class, not a static helper, as many of the non abstract methods use them, and they will never be used by another class. – J Atkin May 12 '15 at 15:17
  • 1
    Start with the simplest implementation of Player, add basic test and create the abstraction as you code when you'll need this. Experienced developers do sometimes start by thinking out the architecture ahead, but this rarely produces good results. It's easier to start from simple implementation and add complexity than starting with some predesigned architecture and adapting it to requirements. – McMonster May 12 '15 at 15:24
  • Sounds like a bit of a pain starting a project and giving it basic functionality, then rewrite it to match your architecture... Sounds like I have a ways to go to reach "Experienced developer" status. :) (+1) – J Atkin May 12 '15 at 15:39
  • 1
    It's not rewriting, it's evolution. In perfect world you would be able to think the entire implementation from the ground up, but this is not really possible. When you start doing everything at once you run into the problems just as you described, namely not being able to test anything before writing almost everything. Then imagine you did write everything and realize after just a few tests that this does not work, that's when you'll have to rewrite half of your work. If you start from simple things it is easier to adapt as you go. – McMonster May 12 '15 at 15:46
  • 1
    huge +1 for this answer - you're making huge assumptions about what your architecture is going to be rather than letting it evolve according to your actual needs- this is exactly what TDD teaches us to do- evolution, not anticipation. For example you insist you need inheritance, but only until you have a second use case will you know if you need inheritance or composition, or neither – tddmonkey May 12 '15 at 15:59
  • @McMonster Now I'm wondering how to start over, or if I should (I have put a lot of work into what I have now)... – J Atkin May 12 '15 at 16:05
  • 1
    @McMonster "Experienced developers do sometimes start by thinking out the architecture ahead, but this rarely produces good results." You're grouping developers who architecture a whole system in with developers with intelligent foresight. To an extent, this must always happen. When you write a function, do you give it no parameters, then on the first line realize you need a variable and add it to a signature? And repeat for every single variable in the method signature? No, you think i need these 3 things and you go with it. Given the info, abstracting a player for a game sounds good. – Carlos Bribiescas May 12 '15 at 17:41