Consider the following POJO structure in my main code. I want to create some testing framework for this kind of hierarchical classes, where the calling test method can specify if they want to modify a particular attribute only like for second Attributes
set the height to a particular number and using default values for other attributes.
I thought about annotations, but due to this hierarchal and many objects in a list, it is becoming infeasible.
class Player {
private PlayerCurrentCondition currentCondition;
private List<Attributes> playerAttributes
private List<Addresses> addresses;
}
class Attributes {
private Integer height;
private List<Sibling> siblings;
private String name;
}
class Addresses {
private List<Secondary> secondary;
}
In different JUnit tests, we want to build the Player
object based on different criteria like in some test case setting a paritcular Attributes
and then assert on that. How can we build Player
object in a good design fashion so we do not clutter the code with creating new
objects and then setting them manually.
2 Answers 2
If I understand, you don't want each test to be filled with logic for creating a Player. You only want each test to specify how the player should vary from a default player.
You can reset a shared reference to a Player for each test using @Before annotation.
class MyTest {
private static Player player;
@Before
public void createDefaultPlayer() {
player = new Player();
player.setCurrentCondition(new PlayerCurrentCondition());
player.setAttributes(new ArrayList<Attributes>());
player.getAttributes().add(new Attribute());
// etc, etc
}
@Test
public void testSecondAttrHeightIsAParticularNumber() {
//player is rebuilt to default before running this test
player.getAttributes().get(1).setHeight(42)
Assert.assertTrue(player.canDoTheThing());
}
@Test
public void testFirstAttrHeightIsAParticularNumber() {
//player is rebuilt to default before running this test
player.getAttributes().get(0).setHeight(42)
Assert.assertTrue(player.canDoTheThing());
}
// more tests...
}
-
Jeremy : Thanks for the answer! If there are more overrides, the test code is going to be not that clean I guess.Novice User– Novice User2019年09月28日 04:43:10 +00:00Commented Sep 28, 2019 at 4:43
In different JUnit tests, we want to build the Player object based on different criteria like in some test case setting a particular Attributes and then assert on that. How can we build Player object in a good design fashion so we do not clutter the code with creating new objects and then setting them manually.
Player
seems reasonably complex for you to implement some sort of support code. We usually refer to it as Testing domain-specific language. DLS are usually a set of utilities (functions most of the times) addressed to reproduce common scenarios, setups, etc.
Say your game has a system of "races" and each "race" have a different set of attributes. It's likely the testing DSL will evoke that with functions such as crateOrkPlayer("name")
, createHumanPlayer()
, etc.
If you consider testing code to be as important as the production one (and in many sense it's), then you will find that a DLS is of the much help because it makes the testing code cleaner and more expressive, easier to reason about (read) and easy to change.
In their most basic form, DSL' are (or can be) static and pure functions in helper-like classes. For example Players
might gather a set o factory methods addressed to build players with a very concrete set of attributes. At the same time, Players
may rely on Attributes
another supporting class to build presets of attributes.
Explore related questions
See similar questions with these tags.
Player
object based on different criteria like in some test case setting a paritcularAttributes
and then assert on that. How can we buildPlayer
object in a good design fashion so we do not clutter the code with creatingnew
objects and then setting them manually.int goalAttempts;
member variable on the player object.