Application Development Blog Posts
Learn and share on deeper, cross technology development topics such as integration and connectivity, automation, cloud extensibility, developing at scale, and security.
cancel
Showing results for 
Search instead for 
Did you mean: 
sourav_das25
Discoverer
0 Kudos
773
  • SAP Managed Tags:

Testing with Strategies


Writing test cases with strategies, testing can be automated entirely by using Test automation strategies.

Writing test cases with strategies


Getter Setter Strategy


Getter Setter POJO for testing


package com.jtester.pojo;

// a getter setter class for testing
public class Student {

private String name, id, roll_no, department;
private List<String> projects;

public String getName() {
return name;
}

public void setName(String name) {
this.name = name;
}

public String getId() {
return id;
}

public void setId(String id) {
this.id = id;
}

public String getRollNo() {
return roll_no;
}

public void setRollNo(String roll_no) {
this.roll_no = roll_no;
}

public String getDepartment() {
return department;
}

public void setDepartment(String department) {
this.department = department;
}

public List<String> getProjects() {
return projects;
}

public void setProjects(List<String> projects) {
this.projects = projects;
}

}

Normal Test JUnit


import org.junit.Test;
import com.jtester.pojo.Student;

public class ClassTest {

@Test
public void studentTest(){
Student student = new Student();
student.setName("Student1");
assertEqual("Student1",student.getName());

student.setId("1");
assertEqual("1",student.getId());

student.setRollNo("1234");
assertEqual("1234",student.getRollNo());

student.setDepartment("Science");
assertEqual("Science",student.getDepartment());

List<String> projects = Arrays.asList("quantamMechanis","gravityIllusion");
student.setProjects(projects);

List<String> returnedProjects = student.getProjects();
assertEqual(projects.size(),returnedProjects.size());

for(int i = 0 ; i< project.size() ; i++) {
assertEqual(projects.get(i),returnedProjects.get(i));
}

// other getter setter can go here.
}

}

Automated Test Unit


import org.junit.Test;
import com.jtester.pojo.Student;

public class ClassTest {

@Test
public void classTest(){

new ClassUnit(Student.class) // specify the class to be tested
.addStrategy(GetterSetterStrategy.class) // specify the strategy to be followed while testing
.test(); // test the class

}

}

The JTester Test Engine automates the tedious task of testing each getter setter to a few lines of


code, The GetterSetterStrategy.class scans the given class by the following convention :




  • any method name starting with set is a setter method.

  • any method name starting with get or is is a getter method.

  • getter setter is associated together with the rest of the method name.






























Method Name Separation Association
setName set + Name Name
getName get + Name Name
setValid set + Valid Valid
isValid is + Valid Valid

The GetterSetterStrategy.class uses convention over configuration.

Package Level Testing


import org.junit.Test;
import com.jtester.units.PackageUnit;

public class PackageTest {

@Test
public void classTest(){
// this line will test all classes in package
new PackageUnit("com.jtester.pojo")
.addStrategy(GetterSetterStrategy.class)
.test();
}

}


Generic Strategy


A strategy that can test any kind of class.

A Normal Class for Testing


package com.jtester.pojo;

public class Student {

protected Database db = Database.getDefaultConnection() ;

protected String department;

protected String loadDept() {
this.department = db.getDepartmentOfStudent(1);
}

public void getDept(String name) {
if(department==null)
this.loadDept();
return this.department;
}

public List<String> getProjects(String subjects){
return db.getProjectsFromSubjects(subjects);
}

public void setTeacher(Teacher teacher){
db.setTeacherForStudent(1,teacher);
}

}

Normal Test Unit ( without automation )


import org.junit.Test;
import com.jtester.units.ClassUnit;
import org.mockito.InjectMocks;
import org.mockito.Mock;
import org.mockito.Mockito;

public class PackageTest {

@InjectMock
Student student;

@Mock
private Database db;

@Test
public void classTest(){

List<String> projects = Arrays.asList("quantamMechanis","gravityIllusion");

Mockito.when(db.getDepartmentOfStudent()).thenReturn("Science");
Mockito.when(db.getProjectsFromSubjects()).thenReturn(projects);

String department = student.getDept();
assertEqual("Science",department);


List<String> returnedProjects = student.getProjects();
assertEqual(projects.size(),returnedProjects.size());

for(int i = 0 ; i< project.size() ; i++) {
assertEqual(projects.get(i),returnedProjects.get(i));
}

}

}


Automated Test Unit


import org.junit.Test;
import com.jtester.units.ClassUnit;

public class GenericClassTest {

@Test
public void classTest(){
ClassUnit classUnit = new ClassUnit(Student.class);
classUnit.addStrategy(GenericStrategy.class);
classUnit.test();
}

}


These kinds of tests are completely Automated, no need to write mocks and asserts, all will be done


automatically. GenericStrategy will call all the visible Declared methods in Student.class and


test them automatically.




  • If the method needs parameters it will create default mock objects of parameters and pass them to the method.

  • If the method throws exceptions it will catch the exception, register them & display them in the console.

  • If the method returns a value it will be displayed in the console.


 

Any internal calls like db.getProjectsFromSubjects(subjects)&

db.getDepartmentOfStudent(1) are automatically intercepted and a default object of the

return type is returned. e.g. db.getDepartmentOfStudent(1) returns a String, so an empty

string is returned when the method is called.

If you want to even customize the generic test scroll on.


 

Automation Test With Customization


import org.junit.Test;
import com.jtester.units.ClassUnit;

public class GenericClassTest {

@Test
public void classTest(){
ClassUnit<Student> classUnit = new ClassUnit(Student.class);
classUnit.addStrategy(GenericStrategy.class);

List<String> projects = Arrays.asList("quantamMechanis","gravityIllusion");

classUnit.caseReturn(projects).getProjects();
classUnit.caseReturn("Science").getDept();

classUnit.caseVoid().setName("Dummy");

classUnit.test();
}

}


This Customization helps in setting passed-on parameters to methods while testing, or if you want to compare the return object with a control object.
classUnit.caseReturn(projects) // the expected return
.getProjects(); // on the method

classUnit.caseVoid() // expect anything on return
.setName("Dummy"); // the parameter to be passed when tested

Mock Class Fields


Now suppose the Database call is falling as the DB is not available in testing. Or if you want to return

a specific string whenever db.getDepartmentOfStudent(1) is called.
import org.junit.Test;
import com.jtester.units.ClassUnit;

public class GenericClassTest {

@JMock
Database database;

@Before
public void setUp(){
MockUnit.init(this);
}

@Test
public void classTest(){

MockUnit.when(database.getDepartmentOfStudent(1))
.thenReturn("Science");

ClassUnit classUnit = new ClassUnit(Student.class);
classUnit.addStrategy(GenericStrategy.class);
classUnit.test();
}

}


Global Mock Unit


MockUnits Can be set across multiple JUnits Using the Default Data Framework
package com.jtester.mock.data; 		// all default mocks has to be in this package.

import com.jtester.interfaces.MockData;
import com.jtester.pojo.Teacher;

public class MockTeacherData extends MockData {

@Override
public Object load() {
Database database = MockUnit.mock(Database.class);

MockUnit.when(database.getDepartmentOfStudent(1))
.thenReturn("Science");
}


}

Default Test Data


The process of creating test cases for each method and then Testing them is tedious, Hence an alternative Default Mock Data, i.e. Test Data is mapped to class names, and every time this class is encountered the mapped data is returned.


e.g.



package com.jtester.mock.data; 		// all default mocks has to be in this package.

import com.jtester.interfaces.DefaultData;
import com.jtester.pojo.Teacher;

public class MockTeacherData extends DefaultData {

public Class<?> getKey() {
return Teacher.class;
}

@Override
public Object getObject() {
Teacher teacher = new Teacher();
teacher.setName("Dummy");
return teacher;
}


}

we have set a mock data  Teacher.class so every time every Teacher class needs this


The mock object is returned. i.e. Whenever setTeacher is called the default object is sent as a


parameter instead of creating a default object. The default object can be used if the Teache class is


in the following places.




  • if the Teacher's class is in a method parameter

  • if the teacher is the return type of an intercepted method.


 
2 Comments
Labels in this area