откат изменений базы данных от вызова тестового примера удаленного API REST - PullRequest
1 голос
/ 11 марта 2020

Наш проект построен с пружинной загрузкой. В рамках этого проекта мы создали множество реализаций API REST с использованием языка java, причем API-интерфейсы REST можно вызывать в конечных точках URI. Многие из этих реализаций REST API взаимодействуют с базой данных RDBMS на внутреннем уровне (мы используем postgresql). Ответ всех наших REST API - JSON.

. Я пишу тесты API, которые тестируют эти REST API, используя java в тестовом примере и библиотеку JUnit для написания этих тестов.

Я пишу два вида этих тестов API, а именно: 1) Для API REST, которые только читают из базы данных, реализация тестового примера проста. Я использую клиентскую библиотеку HTTP из java в своем тестовом примере и выдаю запрос GET или POST. Затем я делаю 'assert' в ответе JSON в тестовом примере. 2) Для API-интерфейсов REST, которые выполняют одно из следующих действий: создание, обновление или удаление в базе данных, я сталкиваюсь с проблемами откатить из базы данных создание, обновление или удаление изменений, которые выполняет мой тестовый пример. На самом деле, в данный момент я не знаю, как откатить создание, обновление или удаление изменений, которые выполняет мой тестовый пример, непосредственно перед его завершением. Может кто-нибудь, пожалуйста, дать указатели, как решить эту проблему?

Ниже также упоминается настоящий исходный код одного из моих тестовых примеров,



    import static org.junit.Assert.assertEquals;
    import static org.junit.Assert.assertTrue;

    import java.io.IOException;
    import java.io.InputStream;

    import org.apache.http.HttpResponse;
    import org.apache.http.HttpStatus;
    import org.apache.http.client.ClientProtocolException;
    import org.apache.http.client.methods.HttpGet;
    import org.apache.http.entity.ContentType;
    import org.apache.http.impl.client.CloseableHttpClient;
    import org.apache.http.impl.client.HttpClients;
    import org.json.JSONArray;
    import org.json.JSONObject;
    import org.junit.After;
    import org.junit.AfterClass;
    import org.junit.Before;
    import org.junit.BeforeClass;
    import org.junit.Test;

    public class ApplnCommonRestControllerTest {
        private static String API_URI_2 = "http://localhost:8081/appln-restapis/rest/public/common/getalluniversities";
        private static CloseableHttpClient fHttpClient;

        @Before
        public void setUp() throws Exception {
            fHttpClient = HttpClients.createDefault();
        }

        @After
        public void tearDown() throws Exception {
            fHttpClient.close();
        }

        @Test
        public void getAllUniversitiesResponseBodyTest() throws ClientProtocolException, IOException {        
            HttpGet httpGet = new HttpGet(API_URI_2);
            HttpResponse httpResponse = fHttpClient.execute(httpGet);

            InputStream inpStream = (httpResponse.getEntity()).getContent();        
            String respBodyJsonString = Utilities.inputStreamToString(inpStream);
            JSONObject jsonResponeObj = new JSONObject(respBodyJsonString);
            JSONArray dataJsonArray = jsonResponeObj.getJSONArray("data");        

            assertTrue(dataJsonArray.length() >= 2);   // test that array contains at least two elements

            JSONObject arrElem = (JSONObject)dataJsonArray.get(0);   // test first element of array
            int univId = arrElem.getInt("id");
            String univName = arrElem.getString("universityname");
            assertTrue(univId == 1 && univName.length() > 0);

            arrElem = (JSONObject)dataJsonArray.get(dataJsonArray.length() - 1);   
            // test last element of array
            univId = arrElem.getInt("id");
            univName = arrElem.getString("universityname");
            assertTrue(univId > 1 && univName.length() > 0);        
        }
    }


Приведенный выше пример кода тестового примера из нашего проекта, делает HTTP GET база данных только для чтения. Я ищу решение для отката базы данных для тестового примера, в случае если API REST, вызванный тестовым набором, создал / обновил / удалил базу данных (т. Е. Непосредственно перед или после выхода из метода тестового примера, база данных создала / обновить / удалить изменения должны откатиться).

1 Ответ

0 голосов
/ 12 марта 2020

Как правило, все мои методы @Test помечаются как @Transnational. Но поскольку ваш тестовый пример полностью отделен от контекста приложения, конечно, это не поможет. Spring имеет отличную библиотеку тестов интеграции для веб-слоя MockMvc. Используя эту библиотеку, ваш тест будет выглядеть так:

import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;
import org.springframework.test.web.servlet.MockMvc;
import org.springframework.test.web.servlet.request.MockMvcRequestBuilders;
import org.springframework.test.web.servlet.result.MockMvcResultHandlers;
import org.springframework.test.web.servlet.result.MockMvcResultMatchers;
import org.springframework.transaction.annotation.Transactional;

import static org.hamcrest.Matchers.*;

@RunWith(SpringRunner.class)
@SpringBootTest
@AutoConfigureMockMvc
public class ApplnCommonRestControllerTest {
    @Autowired
    MockMvc mockMvc;
    @Test
    @Transactional
    public void getAllUniversitiesResponseBodyTest() throws Exception {
        mockMvc.perform(MockMvcRequestBuilders.get("/appln-restapis/rest/public/common/getalluniversities"))
                .andDo(MockMvcResultHandlers.print())
                .andExpect(MockMvcResultMatchers.jsonPath("$.data")
                        .value(iterableWithSize(2)))
                .andExpect(MockMvcResultMatchers.jsonPath("$.data[0].id", is(1)))
                .andExpect(MockMvcResultMatchers.jsonPath("$.data[0].universityname", not(emptyArray())))
                .andExpect(MockMvcResultMatchers.jsonPath("$.data[1].id", greaterThan(1)))
                .andExpect(MockMvcResultMatchers.jsonPath("$.data[1].universityname", not(emptyArray())));
    }
}

А также ваш тест будет откатываться, так как это не действительно внешний вызов http и @Transactional действительно работают в этом сценарии.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...