Spring Cloud Contract не может создавать json на стороне производителя

Я хочу написать контракт, используя весенний облачный контракт в API производителя.

Мой контроллер выглядит так:

@PostMapping(value = "/employee")
public ResponseEntity<Employee> getEmployee(@RequestBody Request employeeRequest) {
    Optional<Employee> employee = employeeService.getEmployee(employeeRequest);
    if(employee.isPresent()){
        return ResponseEntity.status(HttpStatus.OK).
                contentType(MediaType.APPLICATION_JSON).body(employee.get());
    }else{
        return new ResponseEntity(HttpStatus.INTERNAL_SERVER_ERROR);
    }

}

Класс запроса:

@Setter
@Getter
public class Request {
private Integer id;
 }

Класс Response (Сотрудник):

@Setter
@Getter
@AllArgsConstructor
@NoArgsConstructor
 public class Employee {

public Integer id;

public String fname;

public String lname;

public Double salary;

public String gender;

 }

Dsl написано отличным языком:

import org.springframework.cloud.contract.spec.Contract

 Contract.make {
request {
    method 'POST'
    url '/employee'
    headers {
        contentType(applicationJson())
    }
    body(
            id : 25
    )

}
response {
    status 200
    headers {
        contentType(applicationJson())
    }
    body("""
{
    "id":25,
    "fname":"sara",
    "lname":"ahmadi",
    "salary":"25000.00",
    "gender":"F"
}
  """)

  }
}

Плагин в pom.xml:

<plugin>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-contract-maven-plugin</artifactId>
            <version>2.2.3.RELEASE</version>
            <extensions>true</extensions>
            <configuration>
                <baseClassForTests>example.co.ir.contractproducer.BaseTestClass</baseClassForTests>
                <testFramework>JUNIT5</testFramework>
            </configuration>
        </plugin>

И BaseTestClass:

import io.restassured.config.EncoderConfig;
import io.restassured.module.mockmvc.RestAssuredMockMvc;
import io.restassured.module.mockmvc.config.RestAssuredMockMvcConfig;
import isc.co.ir.contractproducer.controller.EmployeeController;
import isc.co.ir.contractproducer.model.Employee;
import isc.co.ir.contractproducer.model.Request;
import isc.co.ir.contractproducer.service.EmployeeService;
import org.junit.jupiter.api.BeforeEach;
import org.mockito.Mockito;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.boot.test.mock.mockito.MockBean;
import org.springframework.test.web.servlet.setup.MockMvcBuilders;
import org.springframework.test.web.servlet.setup.StandaloneMockMvcBuilder;

import java.util.Optional;

@SpringBootTest
public class BaseTestClass {

@Autowired
private EmployeeController employeeController;

@MockBean
private EmployeeService employeeService;

@BeforeEach
public void setup(){

    Employee employee2=new Employee(25,"Adam","Brown",25000.0,"F");
    Request  request = new Request();
    request.setId(25);
    Mockito.when(employeeService.getEmployee(request)).thenReturn(Optional.of(employee2));

    EncoderConfig encoderConfig = new EncoderConfig().appendDefaultContentCharsetToContentTypeIfUndefined(false);
    RestAssuredMockMvc.config = new RestAssuredMockMvcConfig().encoderConfig(encoderConfig);

    StandaloneMockMvcBuilder standaloneMockMvcBuilder
            = MockMvcBuilders.standaloneSetup(employeeController);
    RestAssuredMockMvc.standaloneSetup(standaloneMockMvcBuilder);

}

}

Сгенерированный тестовый класс:

import isc.co.ir.contractproducer.BaseTestClass;
import com.jayway.jsonpath.DocumentContext;
import com.jayway.jsonpath.JsonPath;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
import      io.restassured.module.mockmvc.specification.MockMvcRequestSpecification;
import io.restassured.response.ResponseOptions;

import static    org.springframework.cloud.contract.verifier.assertion.SpringCloudContractAssertions.assertThat;
import static org.springframework.cloud.contract.verifier.util.ContractVerifierUtil.*;
import static com.toomuchcoding.jsonassert.JsonAssertion.assertThatJson;
import static io.restassured.module.mockmvc.RestAssuredMockMvc.*;

 @SuppressWarnings("rawtypes")
 public class ContractVerifierTest extends BaseTestClass {

@Test
public void validate_shouldReturnEmployee() throws Exception {
    // given:
        MockMvcRequestSpecification request = given()
                .header("Content-Type", "application/json")
                .body("{\"id\":25}");

    // when:
        ResponseOptions response = given().spec(request)
                .post("/employee");

    // then:
        assertThat(response.statusCode()).isEqualTo(200);
        assertThat(response.header("Content-Type")).matches("application/json.*");

    // and:
        DocumentContext parsedJson = JsonPath.parse(response.getBody().asString());
        assertThatJson(parsedJson).field("['id']").isEqualTo(25);
        assertThatJson(parsedJson).field("['fname']").isEqualTo("sara");
        assertThatJson(parsedJson).field("['lname']").isEqualTo("ahmadi");
        assertThatJson(parsedJson).field("['salary']").isEqualTo("25000.00");
        assertThatJson(parsedJson).field("['gender']").isEqualTo("F");
}

}

Теперь, когда я создаю проект, я получаю такую ​​ошибку:

[ERROR] Tests run: 1, Failures: 1, Errors: 0, Skipped: 0, Time elapsed: 1.469      s <<< FAILURE! - in example.co.ir.contractproducer.ContractVerifierTest
[ERROR] validate_shouldReturnEmployee  Time elapsed: 0.607 s  <<< FAILURE!
org.opentest4j.AssertionFailedError: 

Expecting:
<500>
to be equal to:
<200>
but was not.

Когда я создаю проект с использованием Junit4, все работает нормально, но при использовании Junit5 у меня возникла эта проблема. Как я могу исправить эту проблему?


person mahdieh    schedule 19.07.2020    source источник
comment
Можете ли вы вставить свой базовый класс и сгенерированный тест вместе со всем импортом?   -  person Marcin Grzejszczak    schedule 20.07.2020
comment
Редактирую вопрос. @ MarcinGrzejszczak   -  person mahdieh    schedule 20.07.2020
comment
Не могли бы вы распечатать всю трассировку стека, пожалуйста?   -  person Marcin Grzejszczak    schedule 20.07.2020
comment
[ОШИБКА] Выполнено тестов: 1, Сбои: 1, Ошибки: 0, Пропущено: 0, Истекшее время: 2,139 с - в ..... контракте производителя.ContractVerifierTest [ERROR] validate_shouldReturnEmployee Истекшее время: 1.217 с org.opentest4j.AssertionFailedError: Ожидалось, что: ‹500› будет равно: ‹200›, но не было. на isc.co.ir.contractproducer.ContractVerifierTest.validate_shouldReturnEmployee (ContractVerifierTest.java:31) @MarcinGrzejszczak Я могу отправить вам весь проект по электронной почте   -  person mahdieh    schedule 20.07.2020
comment
Нет, спасибо. Я вижу, что вы получаете 500, но понятия не имею, почему. Можете ли вы обновить выпуск, чтобы получить всю информацию?   -  person Marcin Grzejszczak    schedule 20.07.2020
comment
Конечно, когда я собираю с помощью junit4, все в порядке. а также здесь: employeeService.getEmployee (employeeRequest) в моем классе контроллера, если я изменяю параметр на employeeRequest.getId и запускаю тест в junit5, он работает. .Поэтому, когда я передаю весь RequestBody своему сервису, он не работает. Спасибо за вашу помощь. @MarcinGrzejszczak   -  person mahdieh    schedule 20.07.2020
comment
Почему вы запускаете springboottest, когда выполняете конфигурацию автономной установки, чтобы не сомневаться? Либо не запускайте весь контекст и используйте автономную настройку, либо запускайте контекст, автоматически подключайте контекст веб-приложения и вставляйте его в версию mockmvc для webappcontext (а не автономную)   -  person Marcin Grzejszczak    schedule 20.07.2020
comment
Вы имеете в виду удалить SpringBootTest из моего BaseTestClass, ввести контекст WebApplicationContext, а затем RestAssuredMockMvc.webAppContextSetup (контекст)? @ MarcinGrzejszczak   -  person mahdieh    schedule 20.07.2020
comment
Либо обновите SpringBootTest и используйте standalonesetup, либо оставьте springboottest и вставьте webappcontext   -  person Marcin Grzejszczak    schedule 20.07.2020
comment
Спасибо @MarcinGrzejszczak. Это решение отлично работает.   -  person mahdieh    schedule 21.07.2020
comment
Большой! Я добавил ответ. Можем ли мы отметить его как правильный?   -  person Marcin Grzejszczak    schedule 21.07.2020


Ответы (1)


Удалите @SpringBootTest и используйте RestAssuredMockMvc.standaloneSetup или оставьте @SpringBootTest, введите WebApplicationContext и используйте RestAssuredMockMvc.webAppContextSetup(context)

person Marcin Grzejszczak    schedule 21.07.2020