Skip to content

Commit

Permalink
Enhanced benchmark tool, more options, greater control.
Browse files Browse the repository at this point in the history
  • Loading branch information
nmihajlovski committed Mar 29, 2017
1 parent 9cec548 commit 2a23b09
Show file tree
Hide file tree
Showing 6 changed files with 197 additions and 43 deletions.
Expand Up @@ -23,13 +23,20 @@
import org.rapidoid.RapidoidThing;
import org.rapidoid.annotation.Authors;
import org.rapidoid.annotation.Since;
import org.rapidoid.config.Conf;
import org.rapidoid.env.Env;

@Authors("Nikolche Mihajlovski")
@Since("5.3.0")
public class BenchmarkCenter extends RapidoidThing {

public static void main(String[] args) {
BenchmarkForker forker = new BenchmarkForker(args);
Env.setArgs(args);
run();
}

public static void run() {
BenchmarkForker forker = new BenchmarkForker();
forker.clear();

if (forker.hasTarget()) {
Expand All @@ -45,11 +52,19 @@ public static void main(String[] args) {

private static void runBuiltInBenchmarks(BenchmarkForker forker) {

forker.benchmark(org.rapidoid.benchmark.lowlevel.Main.class, "/plaintext");
forker.benchmark(org.rapidoid.benchmark.lowlevel.Main.class, "/json");
String run = Conf.BENCHMARK.entry("run").or("/plaintext,/json,/fortunes,http-fast");

forker.benchmark(org.rapidoid.benchmark.highlevel.Main.class, "/plaintext");
forker.benchmark(org.rapidoid.benchmark.highlevel.Main.class, "/json");
for (String demo : run.split(",")) {
demo = demo.trim();
if (!demo.isEmpty()) {
if (demo.equals("http-fast")) {
forker.benchmark(org.rapidoid.benchmark.lowlevel.Main.class, "/plaintext");
forker.benchmark(org.rapidoid.benchmark.lowlevel.Main.class, "/json");
} else {
forker.benchmark(org.rapidoid.benchmark.highlevel.Main.class, demo);
}
}
}
}

}
Expand Up @@ -23,14 +23,18 @@
import org.rapidoid.RapidoidThing;
import org.rapidoid.annotation.Authors;
import org.rapidoid.annotation.Since;
import org.rapidoid.config.Conf;
import org.rapidoid.env.Env;
import org.rapidoid.io.IO;
import org.rapidoid.log.Log;
import org.rapidoid.process.Proc;
import org.rapidoid.process.ProcessHandle;
import org.rapidoid.scan.ClasspathUtil;
import org.rapidoid.u.U;

import java.io.File;
import java.io.IOException;
import java.util.List;

@Authors("Nikolche Mihajlovski")
@Since("5.3.0")
Expand All @@ -40,15 +44,17 @@ public class BenchmarkForker extends RapidoidThing {
private final String plan;
private final String target;

public BenchmarkForker(String[] args) {
public BenchmarkForker() {
try {
this.resultsFile = File.createTempFile("benchmark", ".txt").getAbsolutePath();
} catch (IOException e) {
throw new RuntimeException("Couldn't create temporary file!", e);
}

this.plan = args.length > 0 ? args[0] : "2x3";
this.target = args.length > 1 ? args[1] : null;
this.plan = Conf.BENCHMARK.entry("plan").str().getOrNull();
this.target = Conf.BENCHMARK.entry("target").str().getOrNull();

Log.info("!Starting benchmark", "!configuration", Conf.BENCHMARK.toMap());
}

public void clear() {
Expand All @@ -61,24 +67,33 @@ public ProcessHandle benchmark(Class<?> mainClass, String uri) {
String runner = BenchmarkRunner.class.getCanonicalName();
String main = mainClass.getCanonicalName();

List<String> cmdWithArgs = U.list("java", "-Xms1g", "-Xmx1g", "-Dfile.encoding=UTF-8", "-classpath", classpath, runner);

cmdWithArgs.add("benchmark.target=" + uri);
cmdWithArgs.add("benchmark.main=" + main);
cmdWithArgs.add("benchmark.file=" + resultsFile);

cmdWithArgs.addAll(Env.args());

ProcessHandle proc = Proc.printingOutput(true)
.linePrefix("[BENCHMARK] ")
.run("java", "-Dfile.encoding=UTF-8", "-classpath", classpath, runner, main, uri, resultsFile, plan)
.run(U.arrayOf(cmdWithArgs))
.waitFor();

return proc;
}

public void printResults() {
void printResults() {
U.print("");
U.print(IO.load(resultsFile));
}

public boolean hasTarget() {
boolean hasTarget() {
return target != null;
}

public void benchmark() {
BenchmarkRunner.benchmark(target, target, resultsFile, plan);
BenchmarkRunner.benchmark(target, plan, resultsFile, target);
}

}
Expand Up @@ -24,42 +24,95 @@
import org.rapidoid.annotation.Authors;
import org.rapidoid.annotation.Since;
import org.rapidoid.cls.Cls;
import org.rapidoid.config.Conf;
import org.rapidoid.io.IO;
import org.rapidoid.log.Log;
import org.rapidoid.setup.App;
import org.rapidoid.u.U;
import org.rapidoid.util.Msc;

import java.util.Arrays;

@Authors("Nikolche Mihajlovski")
@Since("5.3.0")
public class BenchmarkRunner extends RapidoidThing {

public static void main(String[] args) {
String mainClass = args[0];
String uri = args[1];
String filename = args[2];
String plan = args[3];
Msc.setPlatform(true);
App.run(args);

String mainClass = Conf.BENCHMARK.entry("main").str().getOrNull();
String uri = Conf.BENCHMARK.entry("target").str().getOrNull();
boolean passive = Conf.BENCHMARK.entry("passive").or(false);

String desc = mainClass + " " + uri + (passive ? " [PASSIVE]" : "");

// start the app that will be benchmarked
Msc.invokeMain(Cls.get(mainClass), new String[0]);

String desc = mainClass + " " + uri;
benchmark(desc, uri, filename, plan);
if (!passive) {

String plan = Conf.BENCHMARK.entry("plan").str().getOrNull();
String filename = Conf.BENCHMARK.entry("file").str().getOrNull();
String url = Conf.BENCHMARK.entry("target").str().getOrNull();

System.exit(0);
benchmark(desc, plan, filename, url);

System.exit(0);
}
}

public static void benchmark(String desc, String url, String filename, String plan) {
public static void benchmark(String desc, String plan, String filename, String url) {

WrkSetup wrk = Perf.wrk()
.url(url);

for (String part : plan.split(":")) {
part = part.toLowerCase();

char flag = part.charAt(0);
String val = part.substring(1);

switch (flag) {
case 't':
wrk.threads(U.num(val));
break;

case 'r':
wrk.rounds(U.num(val));
break;

case 'd':
int duration = U.num(val);
wrk.duration(duration);
if (wrk.warmUp() < 0) wrk.warmUp(duration);
wrk.pause(duration);
break;

case 'c':
wrk.connections(Arrays.stream(val.split(",")).mapToInt(U::num).toArray());
break;

case 'p':
wrk.pipeline(U.num(val));
break;

case 's':
wrk.showDetails(false).showWarmUpDetails(false);
break;

case 'w':
wrk.warmUp(U.num(val));
break;

default:
throw U.rte("Unknown benchmark option: " + flag);
}
}

String[] parts = plan.split("x");
int rounds = U.num(parts[0]);
int duration = U.num(parts[1]);
Log.info("Running benchmark", "setup", wrk);

BenchmarkResults results = Perf.wrk()
.url(url)
.duration(duration)
.warmUp(duration)
.rounds(rounds)
.pause(duration)
.showDetails(false)
.run();
BenchmarkResults results = wrk.run();

String info = U.frmt("%s => %s", desc, results.bestThroughput());
U.print(info);
Expand Down

0 comments on commit 2a23b09

Please sign in to comment.