简体   繁体   中英

How to test native queries in Spring Boot application?

I am completely new in coding by following TDD approach. Now, I'm not sure whether every code needs test case, before it is written. How do I test native queries with if-else conditions?

I've researched some of the ways like following but didn't satisfy my question though:

Testing a Spring Boot application?

https://stackoverflow.com/search?q=test+entitymanager

https://stackoverflow.com/search?q=entitymanager+returned+null+in+testing

JUnit test if else case

@Transactional
public class ProfileRepositoryCustomImpl implements ProfileRepositoryCustom {

    @PersistenceContext
    private EntityManager entityManager;

    @Override
    public List<ProfileMinimalResponseDTO> searchProfile(ProfileDTO profileDTO) {

        Query query = entityManager.createNativeQuery(QueryCreator.createQueryToSearchProfile.apply(profileDTO));

        List<Object[]> list = query.getResultList();

        if (ObjectUtils.isEmpty(list))
            throw new NoContentFoundException(NoRecordsFound.MESSAGE, NoRecordsFound.DEVELOPER_MESSAGE);

        return list.stream().map(
                ProfileUtils.convertObjectToProfileResponseDTO)
                .collect(Collectors.toList());
    }
}

Entity looks like:

@Entity
@Table(name = "profile")
@AllArgsConstructor
@NoArgsConstructor
@Builder
@Data
public class Profile implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;

    @Column(name = "name")
    private String name;

    @Column(name = "description")
    private String description;

    @Column(name = "status")
    private Character status;

    @Column(name = "department_id")
    private Long departmentId;

    @Column(name = "sub_department_id")
    private Long subDepartmentId;

}

public class QueryCreator {

    public static Function<ProfileDTO, String> createQueryToSearchProfile = (profileDTO -> {
        String query = "";

        query += " SELECT" +
                " p.id," +                          //[0]
                " p.name," +                        //[1]
                " p.status," +                      //[2]
                " p.department_id," +               //[3]
                " p.sub_department_id" +            //[4]
                " FROM" +
                " profile p" +
                " WHERE p.id!=0";

        if (!Objects.isNull(profileDTO)) {
            if (!Objects.isNull(profileDTO.getName()))
                query += " AND p.name='" + profileDTO.getName() + "'";

            if (!Objects.isNull(profileDTO.getDepartmentId()))
                query += " AND p.department_id=" + profileDTO.getDepartmentId();

            if (!Objects.isNull(profileDTO.getSubDepartmentId()))
                query += " AND p.sub_department_id=" + profileDTO.getDepartmentId();
        }

        return query;
    });

}

 public static Function<Object[], ProfileMinimalResponseDTO> convertObjectToProfileResponseDTO = (objects) -> {

        final Integer ID = 0;
        final Integer NAME = 1;
        final Integer STATUS = 2;
        final Integer DEPARTMENT_ID = 3;
        final Integer SUB_DEPARTMENT_ID = 4;

        return ProfileMinimalResponseDTO.builder()
                .id(Long.parseLong(objects[ID].toString()))
                .name(objects[NAME].toString())
                .status(objects[STATUS].toString().charAt(0))
                .departmentId(Long.parseLong(objects[DEPARTMENT_ID].toString()))
                .subDepartmentId(Long.parseLong(objects[SUB_DEPARTMENT_ID].toString()))
                .build();
    };

I am expecting answers on how to write test case for above scenerio. Also, any references to learning TDD would be very kind and helpful.

regarding references for learning TDD I would definitely recommend a classic book, Kent Beck's "TDD by example": https://www.amazon.co.uk/Test-Driven-Development-Addison-Wesley-Signature/dp/0321146530

One approach would be to use some in-memory database (H2 being a natural choice in case of Spring Boot). You could then create schema.sql and data.sql scripts to insert specific data to test your corner cases.

Another option is to use Mockito to mock EntityManager and Query objects. You then don't need to create SQL with inserts and 'create tables', but you prepare a set of objects manually which will be returned by these mocks.

Hope this helps. Let me know if you want me to elaborate on this a bit.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM