Skip to content

Commit

Permalink
Add througput graph
Browse files Browse the repository at this point in the history
  • Loading branch information
Lucas Pouzac committed Mar 6, 2014
1 parent 00405fb commit a8efde4
Show file tree
Hide file tree
Showing 12 changed files with 328 additions and 99 deletions.
8 changes: 7 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,9 @@
.idea/
*.iml
target/
target/

# Other IDE's#
##############
\.classpath
\.project
\.settings
19 changes: 17 additions & 2 deletions src/main/java/com/lazerycode/jmeter/analyzer/AnalyzeMojo.java
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,21 @@ public class AnalyzeMojo extends AbstractMojo {
@Parameter(defaultValue = "50000")
private int maxSamples = Environment.DEFAULT_MAXSAMPLES;

/**
* Width use to generate a chart.
* defaultValue = "800"
*/
@Parameter(defaultValue = "800")
private int chartWidth;


/**
* Height use to generate a chart.
* defaultValue = "600"
*/
@Parameter(defaultValue = "600")
private int chartHeight;

/**
* True if all files found by pattern used in ${source} should be processed
* defaultValue = "false" for following reasons:
Expand Down Expand Up @@ -200,13 +215,13 @@ private void initializeEnvironment() throws MojoExecutionException {
writers.add(new HtmlWriter());
writers.add(new DetailsToCsvWriter());
writers.add(new DetailsToHtmlWriter());
writers.add(new ChartWriter());
writers.add(new ChartWriter(chartWidth, chartHeight));
}

ENVIRONMENT.setWriters(writers);

//MUST be called after initialization of writers List !!!
ENVIRONMENT.setGenerateCharts(writers.contains(new ChartWriter()));
ENVIRONMENT.setGenerateCharts(writers.contains(new ChartWriter(chartWidth, chartHeight)));
ENVIRONMENT.setGenerateDetails(writers.contains(new DetailsToHtmlWriter()));


Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,11 @@ public class AggregatedResponses {
*/
private Samples duration;

/**
* Number of thread
*/
private Samples activeThreads;

/**
* duration of the responses splitted by uri
*/
Expand Down Expand Up @@ -107,6 +112,20 @@ protected void setDuration(Samples duration) {
this.duration = duration;
}

/**
* @return
*/
public Samples getActiveThreads() {
return activeThreads;
}

/**
* @param activeThreads
*/
protected void setActiveThreads(Samples activeThreads) {
this.activeThreads = activeThreads;
}

/**
* @return aggregated status codes of responses
*/
Expand Down Expand Up @@ -153,7 +172,9 @@ protected void finish() {
if( duration != null ) {
duration.finish();
}

if ( activeThreads != null ) {
activeThreads.finish();
}
if( sizeByUri != null ) {
for( Samples s : sizeByUri.values() ) {
s.finish();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -143,35 +143,23 @@ public void startElement(String u, String localName, String qName, Attributes at


// --- parse bytes
long bytes = -1;
String byteString = attributes.getValue("by");
try {
bytes = Long.parseLong(byteString);
}
catch (Exception e) {
getLog().warn("Error parsing bytes: '"+byteString+"'");
}

long bytes = parseLong(attributes, "by");

// --- parse duration
long duration = -1;
String durationString = attributes.getValue("t");
try {
duration = Long.parseLong(durationString);
}
catch (Exception e) {
getLog().warn("Error parsing duration '"+durationString+"'");
}
long duration = parseLong(attributes, "t");

// --- parse active thread for all groups
long activeThreads = parseLong(attributes, "na");

// --- parse responseCode
int responseCode = getResponseCode(attributes);

// ==== add data to the resultContainer
addData(resultContainer, uri, timestamp, bytes, duration, responseCode, success);
addData(resultContainer, uri, timestamp, bytes, duration, activeThreads, responseCode, success);


parsedCount++;

// write a log message every 10000 entries
if( parsedCount % LOGMESSAGE_ITEMS == 0 ) {
getLog().info("Parsed "+parsedCount+" entries ...");
Expand Down Expand Up @@ -205,12 +193,15 @@ public void endDocument() throws SAXException {
* @param success httpSample success
*/
private void addData(AggregatedResponses resultContainer, String uri,
long timestamp, long bytes, long duration, int responseCode, boolean success) {
long timestamp, long bytes, long duration, long activeThreads, int responseCode, boolean success) {


StatusCodes statusCodes = resultContainer.getStatusCodes();
statusCodes.increment(responseCode);

Samples activeThreadResult = resultContainer.getActiveThreads();
activeThreadResult.addSample(timestamp + duration, activeThreads);

// -- register data
if( !success || bytes == -1 || duration == -1 ||
responseCode >= HTTPCODE_ERROR || responseCode == HTTPCODE_CONNECTIONERROR ) {
Expand Down Expand Up @@ -259,6 +250,7 @@ private AggregatedResponses getResult(String key) {

//initialize new AggregatedResponses
resultContainer = new AggregatedResponses();
resultContainer.setActiveThreads(new Samples(maxSamples, true));
resultContainer.setDuration(new Samples(maxSamples, true));
resultContainer.setSize(new Samples(maxSamples, false));
resultContainer.setStatusCodes(new StatusCodes());
Expand Down Expand Up @@ -368,6 +360,19 @@ private void add(Map<String, Samples> uriSamples, String uri, long timestamp, lo
}
}

private long parseLong(Attributes attributes, String qName) {
long result = -1;
String valueString = attributes.getValue(qName);
if (null != valueString) {
try {
result = Long.parseLong(valueString);
} catch (Exception e) {
getLog().warn("Error parsing bytes: '" + valueString + "'");
}
}
return result;
}

}

}
84 changes: 84 additions & 0 deletions src/main/java/com/lazerycode/jmeter/analyzer/writer/ChartUtil.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
/**
*
*/
package com.lazerycode.jmeter.analyzer.writer;

import java.awt.Color;
import java.text.SimpleDateFormat;
import java.util.TimeZone;

import org.jfree.chart.axis.DateAxis;
import org.jfree.chart.axis.NumberAxis;
import org.jfree.chart.axis.ValueAxis;
import org.jfree.chart.plot.CombinedDomainXYPlot;
import org.jfree.chart.plot.PlotOrientation;
import org.jfree.chart.plot.XYPlot;
import org.jfree.chart.renderer.xy.XYBarRenderer;
import org.jfree.chart.renderer.xy.XYItemRenderer;
import org.jfree.chart.renderer.xy.XYLineAndShapeRenderer;
import org.jfree.data.xy.XYDataset;

/**
*
*/
public final class ChartUtil {

private static final String DATE_FORMAT = "HH:mm:ss";

private ChartUtil() {

}

public static XYPlot createPlot(String rangeAxisName) {
XYPlot plot = new XYPlot();
plot.setDomainAxis(createDateAxis());
NumberAxis rangeAxis = new NumberAxis(rangeAxisName);
plot.setRangeAxis(rangeAxis);
return plot;
}

public static CombinedDomainXYPlot createCombinedDomainPlot() {
CombinedDomainXYPlot combineddomainxyplot = new CombinedDomainXYPlot(createDateAxis());
combineddomainxyplot.setGap(10d);
combineddomainxyplot.setOrientation(PlotOrientation.VERTICAL);
return combineddomainxyplot;
}

private static ValueAxis createDateAxis() {
DateAxis timeAxis = new DateAxis("Timestamp (" + DATE_FORMAT + ")");
SimpleDateFormat sdf = new SimpleDateFormat(DATE_FORMAT);
sdf.setTimeZone(TimeZone.getTimeZone("UTC"));
timeAxis.setDateFormatOverride(sdf);
timeAxis.setLowerMargin(0.02D);
timeAxis.setUpperMargin(0.02D);
timeAxis.setAutoRange(true);
return timeAxis;
}

public static XYPlot addDatasetRender(XYPlot plot, XYDataset dataset, XYItemRenderer renderer) {
int index = plot.getDatasetCount();
plot.setDataset(index, dataset);
plot.setRenderer(index, renderer);
return plot;
}

public static XYItemRenderer createLineAndShapeRenderer() {
XYLineAndShapeRenderer renderer = new XYLineAndShapeRenderer();
renderer.setBaseShapesVisible(false);
return renderer;
}

public static XYItemRenderer createSecondaryLineAndShapeRenderer() {
XYLineAndShapeRenderer renderer = new XYLineAndShapeRenderer();
renderer.setSeriesPaint(0, Color.GRAY);
renderer.setBaseShapesVisible(false);
return renderer;
}

public static XYItemRenderer createBarRenderer() {
XYBarRenderer renderer = new XYBarRenderer();
renderer.setShadowVisible(false);
return renderer;
}

}
Loading

0 comments on commit a8efde4

Please sign in to comment.