Springboot REST API Testcase passing in local but failing in build - java

I have a test case class something like
#RunWith(SpringRunner.class)
#SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.DEFINED_PORT)
#AutoConfigureWebTestClient
public class sampleTests {
when(test.getUrl()).thenReturn("http://localhost:8080/sampletest");
#Test
public void getEndpoint() throws Exception {
webTestClient.get().uri("/sampletest").exchange().expectStatus().isOk().expectBody().consumeWith(System.out::println).json(expectedBody);
}
}
This is passing in local, but got failed with the following error when executed in the azure DevOps pipeline.
java.lang.AssertionError: Status expected:<200 OK> but was:<500 INTERNAL_SERVER_ERROR>
Any insights on the same will be much appreciated.

Related

Springboot Test case failure

I have created JUnit cases for my springboot application, when I try to run the test cases, its always failing, it is giving error ApplicationTest.contextLoads:41 Expecting actual not to be null
Here is my Test Class
//#RunWith(SpringRunner.class)
#SpringBootTest(classes = ServiceApplication.class)
#ActiveProfiles({ Profiles.TEST })
#GraphQLTest
public class ApplicationTest {
#Autowired
TestController controller;
#Test
public void contextLoads() {
then(controller).isNotNull();
}
}
when running the application it works fine but test cases are failing. looks like the controller which I am annotating is not instantiating.
Any help would be apricated.

Is it possible to use Spring Retry with TestNg Spring context

I have TestNg tests and use AbstractTestNGSpringContextTests:
#ContextConfiguration(classes = ContextConfiguration.class)
public class BaseTest extends AbstractTestNGSpringContextTests {
.......
}
And enabled retry in my config class:
#Configuration
#EnableRetry
public class TestContextConfiguration {
...
}
I would like to retry send request method in my service client:
#Service
public class ApiClient {
#Retryable
public Response getUser(String name){
...
return response;
But it does not work, no retry happens when the method throwing exception.
At the same time it works with jUnit spring test runner. Also Spring AOP works properly with AbstractTestNGSpringContextTests.
What could be the problem?

Spring Boot 2: IntegrationTest should not execute CommandLineRunner impl

i don't get it: The Application code is executed during my integration tests.
Here is my Application class:
#SpringBootApplication
public class Application implements CommandLineRunner {
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
#Autowired
SurveyService surveyService;
#Override
public void run(String... args) throws Exception {
System.out.println("Hello world");
// some useage of the autowired service (do all the stuff)
}
}
The SurveyService consume just some REST API.
My test looks something like that:
#ExtendWith(SpringExtension.class)
#RestClientTest({SurveyRestService.class})
#ComponentScan("com.example.app")
#TestPropertySource(properties = "uri=http://testMe.com/")
class SurveyRestServiceTest {
#Autowired
SurveyService classUnderTest;
#Autowired
MockRestServiceServer mockServer;
private void setupMockServerAndRespond(String response) {
mockServer.expect(requestTo("http://testMe.com/surveys")).andRespond(withSuccess(response, APPLICATION_JSON));
}
#Test
void shouldDeserialzeAllFields() {
setupMockServerAndRespond(VALID_JSON_ONE_ENTRY);
List<Survey> surveys = classUnderTest.listSurveys();
assertThat(surveys).hasSize(1);
// ...
}
}
If i execute the test i always see Hello world (see Application class). Why is the Application code executed? It also executed, when I remote the SpringApplication.run call.
In production mode my App should start, execute some REST calls and than terminate. So I put all the executions in my Application class. But this executions should not be called in test case. How can I achieve this?
Thanks :)
add to SurveyRestServiceTest :
#SpringBootTest(classes = Application.class)

Spring Boot PropertySources in test environment

I have an application.properties the values in which I am trying to autoWire in a bean
#Component
public class ConfigurationValues {
#Value("${my.host}") private String myHost
}
This works well when I run the application. However When I run a JUnit test, I get an error
Caused by: java.lang.IllegalArgumentException: Could not resolve placeholder 'my.host' in string value "${my.host}"
And this is my test code
#RunWith(SpringJUnit4ClassRunner.class)
#SpringApplicationConfiguration(classes = {Application.class})
public class AnotherDummyTest {
#Autowired
private ConfigurationValues configurationValues;
#Test
public void testValue() {
Assert.assertEquals("localhost", configurationValues.getMyHost());
}
}
This test case fails with the IllegalArgumentException that I mentioned.
Try this:
#RunWith(SpringJUnit4ClassRunner.class)
#SpringApplicationConfiguration(classes = Application.class,
initializers = ConfigFileApplicationContextInitializer.class)
public class AnotherDummyTest {

Elasticsearch Spring boot integration test

I am looking for the way to add embedded elasticsearch to my spring boot integration test.
I looked at elastic search integration test but it does not work together with spring boot as both should uses different test runner.
I have a class test as below unfortunately it does not work with error:
java.lang.IllegalStateException: No context information for thread:
Thread[id=1, name=main, state=RUNNABLE, group=main]. Is this thread
running under a class
com.carrotsearch.randomizedtesting.RandomizedRunner runner context?
Add #RunWith(class
com.carrotsearch.randomizedtesting.RandomizedRunner.class) to your
test class. Make sure your code accesses random contexts within
#BeforeClass and #AfterClass boundary (for example, static test class
initializers are not permitted to access random contexts).
#RunWith(SpringJUnit4ClassRunner.class)
#SpringApplicationConfiguration(classes = App.class)
#WebAppConfiguration
#IntegrationTest("server.port:0")
public class TestExample extends ElasticsearchIntegrationTest {
TestRestTemplate testRestTemplate = new TestRestTemplate();
#Value("${local.server.port}")
int port;
#Test
public void testOne(){
ResponseEntity<String> results = testRestTemplate.getForEntity(String.format("http://localhost:%d/client/1", port), String.class);
System.out.print(results);
}
}
Does anybody has some ideas how to make them run or what is alternatives ??
You can actually do what you need without any additional elasticsearch testing dependencies. The idea is basically to create an embedded node and then use the NodeClient to communicate with it.
For that, I created my own EmbeddedElasticsearchServer class which looks (more or less) like this:
public class EmbeddedElasticsearchServer implements InitializingBean {
public EmbeddedElasticsearchServer() {
ImmutableSettings.Builder elasticsearchSettings = ImmutableSettings.settingsBuilder()
.put("http.enabled", "false")
.put("path.data", "target/elasticsearch-data");
node = nodeBuilder()
.local(true)
.settings(elasticsearchSettings.build())
.node();
client = node.client();
}
#Override
public void afterPropertiesSet() throws Exception {
// Initialization stuff:
// - create required indices
// - define mappings
// - populate with test data
}
public Client getClient() {
return client;
}
}
Then, in spring configuration (let's call it integration-test-context.xml) I did this:
<bean id="embeddedElasticsearchServer"
class="com.example.EmbeddedElasticsearchServer" />
<bean id="elasticsearchClient"
class="org.elasticsearch.client.node.NodeClient"
factory-bean="embeddedElasticsearchServer"
factory-method="getClient" />
Then you can just autowire the client in your test like this:
#RunWith(SpringJUnit4ClassRunner.class)
#ContextConfiguration("/integration-test-context.xml")
public abstract class AbstractElasticsearchIntegrationTest {
#Autowired
private Client elasticsearchClient;
// Your rests go here...
}

Categories