Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
84 changes: 84 additions & 0 deletions performance_benchmark/ReadMe.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
Best way to performance test it is with
Apache Benchmark. ---- https://httpd.apache.org/docs/2.4/programs/ab.html


EG ab -n 1000 -c 99 http://localhost:4567/task/501
would send 1000 requests, with a concurrency of 99 to the URL.

If you want to test PUT for example

With a file called data containing :
{"description":"whatever description","resolved":false, "id":1}

Perf test:::

ab -n 1000 -c 2 -k -u data -m PUT -T "application/json" http://localhost:4567/task/1234


Would make 1000 requests at a concurrency level of 2 with keep alive requests PUT'ing the data to the specific task.
This would be a BAD test as you will have issues with optimistic locking on that resource.
the code does a get in one session and a write in another session - allowing the other request to update in the background



an example output for the GET request

Limited to 99 concurrent requests as the DB connection pool is only set to 100.


ab -n 1000 -c 99 http://localhost:4567/task/501
This is ApacheBench, Version 2.3 <$Revision: 1843412 $>
Copyright 1996 Adam Twiss, Zeus Technology Ltd, http://www.zeustech.net/
Licensed to The Apache Software Foundation, http://www.apache.org/

Benchmarking localhost (be patient)
Completed 100 requests
Completed 200 requests
Completed 300 requests
Completed 400 requests
Completed 500 requests
Completed 600 requests
Completed 700 requests
Completed 800 requests
Completed 900 requests
Completed 1000 requests
Finished 1000 requests


Server Software: Jetty(9.4.z-SNAPSHOT)
Server Hostname: localhost
Server Port: 4567

Document Path: /task/501
Document Length: 4 bytes

Concurrency Level: 99
Time taken for tests: 0.153 seconds
Complete requests: 1000
Failed requests: 0
Non-2xx responses: 1000
Total transferred: 137000 bytes
HTML transferred: 4000 bytes
Requests per second: 6556.60 [#/sec] (mean)
Time per request: 15.099 [ms] (mean)
Time per request: 0.153 [ms] (mean, across all concurrent requests)
Transfer rate: 877.20 [Kbytes/sec] received

Connection Times (ms)
min mean[+/-sd] median max
Connect: 0 5 2.3 4 13
Processing: 2 9 6.8 7 33
Waiting: 1 7 7.0 5 32
Total: 4 14 7.8 11 41

Percentage of the requests served within a certain time (ms)
50% 11
66% 14
75% 16
80% 18
90% 25
95% 33
98% 38
99% 39
100% 41 (longest request)

1 change: 1 addition & 0 deletions performance_benchmark/data
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"description":"whatever description","resolved":false, "id":1}
1 change: 1 addition & 0 deletions performance_benchmark/data_no_id
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"description":"whatever description","resolved":false}
10 changes: 10 additions & 0 deletions performance_benchmark/run_all.sh
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,16 @@

set -o errexit

if [ "x$1" = "x" ] ; then
echo "Parameters :
<base_url> <number of repeats> <req_count> <interval>
eg
http://localhost:4567/ 10 100 1
would make 10 sets of 100 requests with a 1 sec pause between sets
"
exit
fi

run() {
# input parameters
local base_url=$1
Expand Down
39 changes: 22 additions & 17 deletions sparkjava/src/main/java/me/vitor/taskapp_sparkjava/App.java
Original file line number Diff line number Diff line change
Expand Up @@ -7,26 +7,31 @@
import static spark.Spark.delete;

import me.vitor.taskapp_sparkjava.controller.TaskController;
import me.vitor.taskapp_sparkjava.model.TaskRepositoryHibernate;
import me.vitor.taskapp_sparkjava.service.TaskService;
import me.vitor.taskapp_sparkjava.transformer.JsonTransformer;

public class App {

private static final String PATH_TASK = "/task";
private static final String PATH_ID = ":id";
private static final String PATH_TASK_WITH_ID = PATH_TASK + "/" + PATH_ID;

public static void main(String[] args) {
App app = new App();
app.setup();
}

private void setup() {
get(PATH_TASK, TaskController::getTasks, new JsonTransformer());
get(PATH_TASK_WITH_ID, TaskController::getTask, new JsonTransformer());
post(PATH_TASK, TaskController::postTask);
put(PATH_TASK_WITH_ID, TaskController::putTask);
patch(PATH_TASK_WITH_ID, TaskController::patchTask);
delete(PATH_TASK_WITH_ID, TaskController::deleteTask);
}
private static final String PATH_TASK = "/task";
private static final String PATH_ID = ":id";
private static final String PATH_TASK_WITH_ID = PATH_TASK + "/" + PATH_ID;

public static void main(String[] args) {
App app = new App();
app.setup();
}

private void setup() {

TaskController controller = new TaskController(new TaskService(new TaskRepositoryHibernate()));

get(PATH_TASK, controller::getTasks, new JsonTransformer());
get(PATH_TASK_WITH_ID, controller::getTask, new JsonTransformer());
post(PATH_TASK, controller::postTask);
put(PATH_TASK_WITH_ID, controller::putTask);
patch(PATH_TASK_WITH_ID, controller::patchTask);
delete(PATH_TASK_WITH_ID, controller::deleteTask);
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@

import java.util.List;
import me.vitor.taskapp_sparkjava.model.Task;
import me.vitor.taskapp_sparkjava.model.TaskRepositoryHibernate;
import me.vitor.taskapp_sparkjava.service.TaskService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
Expand All @@ -11,84 +10,83 @@

public class TaskController {

private static final String H_LOCATION = "Location";
private static final Logger log = LoggerFactory.getLogger(TaskController.class);

public static List<Task> getTasks(Request request, Response response) {
TaskService taskService = new TaskService(new TaskRepositoryHibernate());
List<Task> taskList = taskService.findAll();
return taskList;
}

public static String postTask(Request request, Response response) {
TaskService taskService = new TaskService(new TaskRepositoryHibernate());
Task task = ControllerUtils.getTaskFromRequestBody(request);
Long taskId = taskService.insert(task);
response.header(H_LOCATION, ControllerUtils.generateUri(request, taskId));
response.status(201);

// can't return null here otherwise will get a 404
// https://github.com/perwendel/spark/issues/620
return "";
}

public static Task getTask(Request request, Response response) {
Long id = Long.parseLong(request.params("id"));
TaskService taskService = new TaskService(new TaskRepositoryHibernate());
Task task = taskService.findById(id);

if (task == null) {
response.status(404);
return null;
private static final String H_LOCATION = "Location";
private final TaskService taskService;
private static final Logger log = LoggerFactory.getLogger(TaskController.class);

public TaskController(TaskService taskService) {
this.taskService = taskService;
}

public List<Task> getTasks(Request request, Response response) {
List<Task> taskList = taskService.findAll();
return taskList;
}

return task;
}
public String postTask(Request request, Response response) {
Task task = ControllerUtils.getTaskFromRequestBody(request);
Long taskId = taskService.insert(task);
response.header(H_LOCATION, ControllerUtils.generateUri(request, taskId));
response.status(201);

public static String putTask(Request request, Response response) {
String paramId = request.params("id");
Long id = Long.parseLong(paramId);
// can't return null here otherwise will get a 404
// https://github.com/perwendel/spark/issues/620
return "";
}

public Task getTask(Request request, Response response) {
Long id = Long.parseLong(request.params("id"));
Task task = taskService.findById(id);

Task task = ControllerUtils.getTaskFromRequestBody(request);
TaskService taskService = new TaskService(new TaskRepositoryHibernate());
Long putId = taskService.put(task, id).getId();
if (task == null) {
response.status(404);
return null;
}

response.header(H_LOCATION, ControllerUtils.generateUri(request, putId));
response.status(204);
return "";
}
return task;
}

public static String patchTask(Request request, Response response) {
String paramId = request.params("id");
Long id = Long.parseLong(paramId);
TaskService taskService = new TaskService(new TaskRepositoryHibernate());
public String putTask(Request request, Response response) {
String paramId = request.params("id");
Long id = Long.parseLong(paramId);

boolean taskExists = taskService.taskExists(id);
Task task = ControllerUtils.getTaskFromRequestBody(request);
Long putId = taskService.put(task, id).getId();

if (!taskExists) {
response.status(404);
return "Not found";
response.header(H_LOCATION, ControllerUtils.generateUri(request, putId));
response.status(204);
return "";
}

Task task = ControllerUtils.getTaskFromRequestBody(request);
taskService.patch(task, id);
response.status(204);
return "";
}

public static String deleteTask(Request request, Response response) {
String paramId = request.params("id");
Long id = Long.parseLong(paramId);
TaskService taskService = new TaskService(new TaskRepositoryHibernate());
boolean taskExists = taskService.taskExists(id);

if (!taskExists) {
response.status(404);
return "Not found";
public String patchTask(Request request, Response response) {
String paramId = request.params("id");
Long id = Long.parseLong(paramId);

boolean taskExists = taskService.taskExists(id);

if (!taskExists) {
response.status(404);
return "Not found";
}

Task task = ControllerUtils.getTaskFromRequestBody(request);
taskService.patch(task, id);
response.status(204);
return "";
}

taskService.delete(id);
return "";
}
public String deleteTask(Request request, Response response) {
String paramId = request.params("id");
Long id = Long.parseLong(paramId);
boolean taskExists = taskService.taskExists(id);

if (!taskExists) {
response.status(404);
return "Not found";
}

taskService.delete(id);
return "";
}

}
Loading