Как отформатировать документы Spring REST в теле ответа с помощью mockMvc

Я пишу документацию по API с помощью Spring REST Docs.

Пример кода:

@Override
public void getById(String urlTemplate, PathParametersSnippet pathParametersSnippet, Object... urlVariables) throws Exception {
    resultActions = mockMvc.perform(get(urlTemplate, urlVariables)
            .principal(principal)
            .contentType(APPLICATION_JSON))
            .andExpect(status().isOk())
            .andDo(print());

    // do..
}

Но проблема в том, что результат теста дается одной строкой. И понять структуру возвращаемых данных очень сложно.

Пример ответа:

MockHttpServletResponse:
           Status = 200
    Error message = null
          Headers = {Content-Type=[application/json;charset=UTF-8]}
     Content type = application/json;charset=UTF-8
             Body = {"creator":null,"modifier":null,"modificationTime":null,"creationTime":null,"id":100,"deleted":false,"name":"Name","description":null,"report":[{"creator":"System","modifier":"System","modificationTime":"2019-01-30T14:21:50","creationTime":"2019-01-30T14:21:50","id":1,"name":"Form name","reportType":{"creator":"System","modifier":"System","modificationTime":"2019-01-30T14:21:50","creationTime":"2019-01-30T14:21:50","id":1,"deleted":false,"name":"Raport"},"unmodifiable":true}]}
    Forwarded URL = null
   Redirected URL = null
          Cookies = []

Далее формирую документацию из полученного ответа и в документации еще и неформатированный JSON

Что я делаю не так? Как включить форматирование для json?


person FreeOnGoo    schedule 30.01.2019    source источник


Ответы (2)


Если вы не в состоянии настроить свое приложение для получения красиво напечатанных ответов, вы можете попросить REST Docs сделать это за вас до того, как они будут задокументированы. Это описано в разделе Настройка Раздел документации «Запросы и ответы»:

Предварительная обработка настраивается вызовом document с помощью OperationRequestPreprocessor и/или OperationResponsePreprocessor. Экземпляры можно получить с помощью статических методов preprocessRequest и preprocessResponse на Preprocessors. Например:

this.mockMvc.perform(get("/")).andExpect(status().isOk())
    .andDo(document("index", preprocessRequest(removeHeaders("Foo")), 
            preprocessResponse(prettyPrint()))); 

В приведенном выше случае запрос предварительно обрабатывается для удаления заголовка Foo, а ответ предварительно обрабатывается, чтобы он выглядел красиво напечатанным.

person Andy Wilkinson    schedule 30.01.2019
comment
Спасибо за ответы. Не думал, что автор библиотеки мне ответит, спасибо :) - person FreeOnGoo; 30.01.2019

Вы можете попробовать получить объект ResultActions из mockMvc, а затем получить объект MockHttpServletResponse. После этого вы можете получить все значения полей, которые пришли в ответ. В этом случае вам не нужно будет анализировать строку.

resultActions = mockMvc.perform(get(urlTemplate, urlVariables)
    .principal(principal)
    .contentType(APPLICATION_JSON))
    .andExpect(status().isOk())
    .andDo(print());

MockHttpServletResponse content = resultActions.andReturn().getResponse();

Также вы можете преобразовать данные объекта MockHttpServletResponse в json. Если вы используете Jacson, напишите свой собственный сериализатор для этого объекта, добавьте его в MockHttpServletResponse и зарегистрируйте в ObjectMapper.

ObjectMapper mapper = new ObjectMapper();
SimpleModule module = new SimpleModule();
module.addSerializer(MockHttpServletResponse.class, CustomSerializer.class);
mapper.registerModule(module);
String jsonResult = mapper.writeValueAsString(content);

CustomSerializer должен расширять StdSerializer<MockHttpServletResponse> и переопределять метод serialize.

person Andrey Nikolaev    schedule 30.01.2019