Skip to content

Commit 9488121

Browse files
Liam GarvieLiam Garvie
authored andcommitted
BAEL-4672 added content for JMeter extract data to file tutorial
1 parent 7d5be17 commit 9488121

5 files changed

Lines changed: 228 additions & 1 deletion

File tree

jmeter/README.md

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ It contains the code of a simple API for some CRUD operations built using Spring
77

88
- Maven
99
- JDK 8
10-
- MongoDB
10+
- MongoDB (Note: for the Write Extracted Data to a File Using JMeter example MongoDB is not required)
1111

1212
### Running
1313

@@ -36,6 +36,14 @@ Or create a new one via a POST:
3636
$ curl -X POST -H "Content-Type:application/json" -d '{ "firstName" : "Dassi", "lastName" : "Orleando", "phoneNumber": "+237 545454545", "email": "mymail@yahoo.fr" }' localhost:8080/students
3737
```
3838

39+
### Available Test API
40+
41+
You can view the test response using curl:
42+
43+
```bash
44+
$ curl localhost:8080/api/test
45+
```
46+
3947
Now with default configurations it will be available at: [http://localhost:8080](http://localhost:8080)
4048

4149
Enjoy it :)
@@ -44,3 +52,4 @@ Enjoy it :)
4452

4553
- [Intro to Performance Testing using JMeter](https://www.baeldung.com/jmeter)
4654
- [Configure Jenkins to Run and Show JMeter Tests](https://www.baeldung.com/jenkins-and-jmeter)
55+
- [Write Extracted Data to a File Using JMeter](https://www.baeldung.com/jmeter-file-extraction)
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
package com.baeldung.controller;
2+
3+
import com.baeldung.model.Response;
4+
import org.springframework.web.bind.annotation.GetMapping;
5+
import org.springframework.web.bind.annotation.RestController;
6+
7+
import java.util.UUID;
8+
9+
import static java.lang.String.format;
10+
11+
@RestController
12+
public class TestController {
13+
14+
@GetMapping("/api/test")
15+
public Response test() {
16+
return new Response(format("Test message... %s.", UUID.randomUUID()));
17+
}
18+
}
Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
package com.baeldung.model;
2+
3+
import java.time.Instant;
4+
import java.util.UUID;
5+
6+
public class Response {
7+
private Instant timestamp;
8+
private UUID uuid;
9+
private String message;
10+
11+
public Response(String message) {
12+
this.timestamp = Instant.now();
13+
this.uuid = UUID.randomUUID();
14+
this.message = message;
15+
}
16+
17+
public Instant getTimestamp() {
18+
return timestamp;
19+
}
20+
21+
public void setTimestamp(Instant timestamp) {
22+
this.timestamp = timestamp;
23+
}
24+
25+
public UUID getUuid() {
26+
return uuid;
27+
}
28+
29+
public void setUuid(UUID uuid) {
30+
this.uuid = uuid;
31+
}
32+
33+
public String getMessage() {
34+
return message;
35+
}
36+
37+
public void setMessage(String message) {
38+
this.message = message;
39+
}
40+
}
Lines changed: 124 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,124 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<jmeterTestPlan version="1.2" properties="5.0" jmeter="5.4.1">
3+
<hashTree>
4+
<TestPlan guiclass="TestPlanGui" testclass="TestPlan" testname="Test Plan" enabled="true">
5+
<stringProp name="TestPlan.comments">To run this test plan you must also be running the Spring application &quot;JmeterApplication&quot; That can be found in this directory</stringProp>
6+
<boolProp name="TestPlan.functional_mode">false</boolProp>
7+
<boolProp name="TestPlan.tearDown_on_shutdown">true</boolProp>
8+
<boolProp name="TestPlan.serialize_threadgroups">false</boolProp>
9+
<elementProp name="TestPlan.user_defined_variables" elementType="Arguments" guiclass="ArgumentsPanel" testclass="Arguments" testname="User Defined Variables" enabled="true">
10+
<collectionProp name="Arguments.arguments"/>
11+
</elementProp>
12+
<stringProp name="TestPlan.user_define_classpath"></stringProp>
13+
</TestPlan>
14+
<hashTree>
15+
<ThreadGroup guiclass="ThreadGroupGui" testclass="ThreadGroup" testname="Thread Group" enabled="true">
16+
<stringProp name="ThreadGroup.on_sample_error">continue</stringProp>
17+
<elementProp name="ThreadGroup.main_controller" elementType="LoopController" guiclass="LoopControlPanel" testclass="LoopController" testname="Loop Controller" enabled="true">
18+
<boolProp name="LoopController.continue_forever">false</boolProp>
19+
<stringProp name="LoopController.loops">1</stringProp>
20+
</elementProp>
21+
<stringProp name="ThreadGroup.num_threads">1</stringProp>
22+
<stringProp name="ThreadGroup.ramp_time">1</stringProp>
23+
<boolProp name="ThreadGroup.scheduler">false</boolProp>
24+
<stringProp name="ThreadGroup.duration"></stringProp>
25+
<stringProp name="ThreadGroup.delay"></stringProp>
26+
<boolProp name="ThreadGroup.same_user_on_next_iteration">true</boolProp>
27+
</ThreadGroup>
28+
<hashTree>
29+
<HTTPSamplerProxy guiclass="HttpTestSampleGui" testclass="HTTPSamplerProxy" testname="Call GET Test endpoint " enabled="true">
30+
<elementProp name="HTTPsampler.Arguments" elementType="Arguments" guiclass="HTTPArgumentsPanel" testclass="Arguments" testname="User Defined Variables" enabled="true">
31+
<collectionProp name="Arguments.arguments"/>
32+
</elementProp>
33+
<stringProp name="HTTPSampler.domain">localhost</stringProp>
34+
<stringProp name="HTTPSampler.port">8080</stringProp>
35+
<stringProp name="HTTPSampler.protocol">http</stringProp>
36+
<stringProp name="HTTPSampler.contentEncoding"></stringProp>
37+
<stringProp name="HTTPSampler.path">/api/test</stringProp>
38+
<stringProp name="HTTPSampler.method">GET</stringProp>
39+
<boolProp name="HTTPSampler.follow_redirects">true</boolProp>
40+
<boolProp name="HTTPSampler.auto_redirects">false</boolProp>
41+
<boolProp name="HTTPSampler.use_keepalive">true</boolProp>
42+
<boolProp name="HTTPSampler.DO_MULTIPART_POST">false</boolProp>
43+
<stringProp name="HTTPSampler.embedded_url_re"></stringProp>
44+
<stringProp name="HTTPSampler.connect_timeout"></stringProp>
45+
<stringProp name="HTTPSampler.response_timeout"></stringProp>
46+
</HTTPSamplerProxy>
47+
<hashTree>
48+
<JSONPostProcessor guiclass="JSONPostProcessorGui" testclass="JSONPostProcessor" testname="JSON Extractor" enabled="true">
49+
<stringProp name="JSONPostProcessor.referenceNames">message</stringProp>
50+
<stringProp name="JSONPostProcessor.jsonPathExprs">$.message</stringProp>
51+
<stringProp name="JSONPostProcessor.match_numbers">1</stringProp>
52+
<boolProp name="JSONPostProcessor.compute_concat">true</boolProp>
53+
<stringProp name="JSONPostProcessor.defaultValues">NOT_FOUND</stringProp>
54+
</JSONPostProcessor>
55+
<hashTree/>
56+
<BeanShellPostProcessor guiclass="TestBeanGUI" testclass="BeanShellPostProcessor" testname="Response to file using BeanShell PostProcessor" enabled="true">
57+
<stringProp name="filename"></stringProp>
58+
<stringProp name="parameters"></stringProp>
59+
<boolProp name="resetInterpreter">false</boolProp>
60+
<stringProp name="script">FileWriter fWriter = new FileWriter(&quot;/Users/liamgarvie/Documents/result.txt&quot;, true);
61+
BufferedWriter buff = new BufferedWriter(fWriter);
62+
63+
buff.write(&quot;Response Code : &quot; + ctx.getPreviousResult().getResponseCode());
64+
buff.write(System.getProperty(&quot;line.separator&quot;));
65+
buff.write(&quot;Response Headers : &quot; + ctx.getPreviousResult().getResponseHeaders());
66+
buff.write(System.getProperty(&quot;line.separator&quot;));
67+
buff.write(&quot;Response Body : &quot; + new String(ctx.getPreviousResult().getResponseData()));
68+
69+
buff.write(&quot;More complex extraction : &quot; + vars.get(&quot;message&quot;));
70+
71+
buff.close();
72+
fWriter.close();</stringProp>
73+
</BeanShellPostProcessor>
74+
<hashTree/>
75+
<ResultSaver guiclass="ResultSaverGui" testclass="ResultSaver" testname="Response to file using file write Listener" enabled="true">
76+
<stringProp name="FileSaver.filename">response</stringProp>
77+
<boolProp name="FileSaver.errorsonly">false</boolProp>
78+
<boolProp name="FileSaver.successonly">false</boolProp>
79+
<boolProp name="FileSaver.skipsuffix">false</boolProp>
80+
<boolProp name="FileSaver.skipautonumber">false</boolProp>
81+
</ResultSaver>
82+
<hashTree/>
83+
</hashTree>
84+
<ResultCollector guiclass="ViewResultsFullVisualizer" testclass="ResultCollector" testname="View Results Tree" enabled="true">
85+
<boolProp name="ResultCollector.error_logging">false</boolProp>
86+
<objProp>
87+
<name>saveConfig</name>
88+
<value class="SampleSaveConfiguration">
89+
<time>true</time>
90+
<latency>true</latency>
91+
<timestamp>true</timestamp>
92+
<success>true</success>
93+
<label>true</label>
94+
<code>true</code>
95+
<message>true</message>
96+
<threadName>true</threadName>
97+
<dataType>true</dataType>
98+
<encoding>false</encoding>
99+
<assertions>true</assertions>
100+
<subresults>true</subresults>
101+
<responseData>false</responseData>
102+
<samplerData>false</samplerData>
103+
<xml>false</xml>
104+
<fieldNames>true</fieldNames>
105+
<responseHeaders>false</responseHeaders>
106+
<requestHeaders>false</requestHeaders>
107+
<responseDataOnError>false</responseDataOnError>
108+
<saveAssertionResultsFailureMessage>true</saveAssertionResultsFailureMessage>
109+
<assertionsResultsToSave>0</assertionsResultsToSave>
110+
<bytes>true</bytes>
111+
<sentBytes>true</sentBytes>
112+
<url>true</url>
113+
<threadCounts>true</threadCounts>
114+
<idleTime>true</idleTime>
115+
<connectTime>true</connectTime>
116+
</value>
117+
</objProp>
118+
<stringProp name="filename"></stringProp>
119+
</ResultCollector>
120+
<hashTree/>
121+
</hashTree>
122+
</hashTree>
123+
</hashTree>
124+
</jmeterTestPlan>
Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
package com.baeldung;
2+
3+
import org.junit.jupiter.api.Test;
4+
import org.springframework.boot.test.context.SpringBootTest;
5+
import org.springframework.mock.web.MockHttpServletResponse;
6+
import org.springframework.test.web.servlet.MockMvc;
7+
import org.springframework.test.web.servlet.setup.MockMvcBuilders;
8+
import org.springframework.web.context.WebApplicationContext;
9+
10+
import static org.assertj.core.api.Assertions.assertThat;
11+
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
12+
import static org.springframework.test.web.servlet.result.MockMvcResultHandlers.print;
13+
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
14+
15+
@SpringBootTest
16+
class JmeterIntegrationTest {
17+
18+
MockMvc mvc;
19+
20+
public JmeterIntegrationTest(WebApplicationContext wac) {
21+
this.mvc = MockMvcBuilders.webAppContextSetup(wac).build();
22+
}
23+
24+
@Test
25+
void whenCallingTestController_thenWeShouldRecieveRandomizedResponse() throws Exception {
26+
MockHttpServletResponse response = mvc.perform(get("/api/test"))
27+
.andDo(print())
28+
.andExpect(status().isOk())
29+
.andReturn()
30+
.getResponse();
31+
32+
assertThat(response.getContentAsString())
33+
.contains("Test message...");
34+
}
35+
36+
}

0 commit comments

Comments
 (0)