Author: psteitz
Date: Thu Jul 26 23:10:54 2007
New Revision: 560120
URL: http://svn.apache.org/viewvc?view=rev&rev=560120
Log:
Factored out common base of load generators. Also added support for sustained
peak/trough periods.
Added:
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/LoadGenerator.java
(with props)
Modified:
jakarta/commons/sandbox/performance/trunk/README.txt
jakarta/commons/sandbox/performance/trunk/config-dbcp.xml
jakarta/commons/sandbox/performance/trunk/config-pool.xml
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/ClientThread.java
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPClientThread.java
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPSoak.java
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPTest.java
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolClientThread.java
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolSoak.java
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolTest.java
Modified: jakarta/commons/sandbox/performance/trunk/README.txt
URL:
http://svn.apache.org/viewvc/jakarta/commons/sandbox/performance/trunk/README.txt?view=diff&rev=560120&r1=560119&r2=560120
==============================================================================
--- jakarta/commons/sandbox/performance/trunk/README.txt (original)
+++ jakarta/commons/sandbox/performance/trunk/README.txt Thu Jul 26 23:10:54
2007
@@ -1,4 +1,4 @@
-=== Compiling and running ===
+=== Compiling and running the dbcp and pool tests ===
To run the dbcp tests, edit configuration in config-dbcp.xml, make sure the
configured database is running and accepting connections, and run
@@ -33,13 +33,18 @@
consider increasing the number of service nodes (pool maxActive) or decreasing
the delay-min / delay-max.
+=== Making other load test runners ===
+
+PoolClientThread, and PoolSoak (or the corresponding DBCP classes) illustrate
+how to subclass ClientThread and LoadGenerator to create load tests.
LoadGenerators
+spawn ClientThreads, set them running and gather statistics. See the class
+javadoc for ClientThread and LoadGenerator for details.
+
+
=== TODO ===
* Property representation and management is poor. Configuration objects should
be defined and Digester should create and populate configuration beans.
-
-* There is still a fair amount of duplicated / similar code between pool and
- dbcp. This should all be factored out and moved to the performance package.
* Ant build is lame. To change pool impls used - e.g. to grab latest snap -
you need to hack the get-deps. This should be cleaned up.
Modified: jakarta/commons/sandbox/performance/trunk/config-dbcp.xml
URL:
http://svn.apache.org/viewvc/jakarta/commons/sandbox/performance/trunk/config-dbcp.xml?view=diff&rev=560120&r1=560119&r2=560120
==============================================================================
--- jakarta/commons/sandbox/performance/trunk/config-dbcp.xml (original)
+++ jakarta/commons/sandbox/performance/trunk/config-dbcp.xml Thu Jul 26
23:10:54 2007
@@ -25,6 +25,8 @@
<url>jdbc:mysql:///test</url>
<username></username>
<password></password>
+ <!-- integerIndexed, integerScan, or textScan -->
+ <query-type>integerIndexed</query-type>
</database>
<connection-factory>
@@ -68,9 +70,7 @@
</abandoned-config>
<run>
- <!-- integerIndexed, integerScan, or textScan -->
- <query-type>integerIndexed</query-type>
- <iterations>1000</iterations>
+ <iterations>100</iterations>
<clients>50</clients>
<delay-min>250</delay-min>
<delay-max>500</delay-max>
@@ -79,7 +79,9 @@
<delay-type>gaussian</delay-type>
<!-- none, linear, random -->
<ramp-type>random</ramp-type>
- <period>20000</period>
+ <ramp-period>5000</ramp-period>
+ <peak-period>2000</peak-period>
+ <trough-period>5000</trough-period>
<!-- none, oscillating (others?)-->
<cycle-type>oscillating</cycle-type>
</run>
Modified: jakarta/commons/sandbox/performance/trunk/config-pool.xml
URL:
http://svn.apache.org/viewvc/jakarta/commons/sandbox/performance/trunk/config-pool.xml?view=diff&rev=560120&r1=560119&r2=560120
==============================================================================
--- jakarta/commons/sandbox/performance/trunk/config-pool.xml (original)
+++ jakarta/commons/sandbox/performance/trunk/config-pool.xml Thu Jul 26
23:10:54 2007
@@ -66,7 +66,9 @@
<delay-type>gaussian</delay-type>
<!-- none, linear, random -->
<ramp-type>random</ramp-type>
- <period>20000</period>
+ <ramp-period>5000</ramp-period>
+ <peak-period>2000</peak-period>
+ <trough-period>5000</trough-period>
<!-- none, oscillating (others?)-->
<cycle-type>oscillating</cycle-type>
</run>
Modified:
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/ClientThread.java
URL:
http://svn.apache.org/viewvc/jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/ClientThread.java?view=diff&rev=560120&r1=560119&r2=560120
==============================================================================
---
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/ClientThread.java
(original)
+++
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/ClientThread.java
Thu Jul 26 23:10:54 2007
@@ -44,8 +44,12 @@
protected double sigma;
/** Delay type - determines how next start times are computed */
protected String delayType;
- /** Period for cyclic mean delay */
- protected long period;
+ /** Ramp length for cyclic mean delay */
+ protected long rampPeriod;
+ /** Peak length for cyclic mean delay */
+ protected long peakPeriod;
+ /** Trough length for cyclic mean delay */
+ protected long troughPeriod;
/** Cycle type */
protected String cycleType;
/** Ramp type */
@@ -62,8 +66,14 @@
protected double lastMean;
/** Random data generator */
protected RandomData randomData;
- /** Whether or now this thread is ramping up */
- protected boolean rampingUp = true;
+
+ /** Cycle state constants */
+ protected static final int RAMPING_UP = 0;
+ protected static final int RAMPING_DOWN = 1;
+ protected static final int PEAK_LOAD = 2;
+ protected static final int TROUGH_LOAD = 3;
+ /** Cycle state */
+ protected int cycleState = 0;
/**
* Create a client thread.
@@ -72,13 +82,16 @@
* @param minDelay minumum mean time between client requests
* @param maxDelay maximum mean time between client requests
* @param delayType distribution of time between client requests
- * @param period period of cycle for cyclic load
+ * @param rampPeriod ramp period of cycle for cyclic load
+ * @param peakOeriod peak period of cycle for cyclic load
+ * @param troughPeriod trough period of cycle for cyclic load
* @param cycleType type of cycle for mean delay
* @param logger common logger shared by all clients
* @param statsList List of SummaryStatistics to add results to
*/
public ClientThread(long iterations, long minDelay, long maxDelay,
- double sigma, String delayType, long period, String cycleType,
+ double sigma, String delayType, long rampPeriod, long peakPeriod,
+ long troughPeriod, String cycleType,
String rampType, Logger logger,
List <SummaryStatistics> statsList) {
this.iterations = iterations;
@@ -86,7 +99,9 @@
this.maxDelay = maxDelay;
this.sigma = sigma;
this.delayType = delayType;
- this.period = period;
+ this.peakPeriod = peakPeriod;
+ this.rampPeriod = rampPeriod;
+ this.troughPeriod = troughPeriod;
this.cycleType = cycleType;
this.rampType = rampType;
this.logger = logger;
@@ -207,11 +222,11 @@
double delayDifference = dMaxDelay - dMinDelay;
if (cycleType.equals("none")) {
if (rampType.equals("none") ||
- (currentTime - startTime) > period) { // ramped up
+ (currentTime - startTime) > rampPeriod) { // ramped up
mean = dMinDelay;
} else if (rampType.equals("linear")) { // single period linear
double prop =
- (double) (currentTime - startTime) / (double) period;
+ (double) (currentTime - startTime) / (double)
rampPeriod;
mean = dMaxDelay - delayDifference * prop;
} else { // Random jumps down to delay - single period
// TODO: govern size of jumps as in oscillating
@@ -223,27 +238,22 @@
mean = dMaxDelay - delayDifference * prop;
}
} else if (cycleType.equals("oscillating")) {
- // First check if we need to change directions
- if ((currentTime - periodStart) >= period) {
- if (rampingUp) {
- rampingUp = false;
- lastMean = dMinDelay;
- } else {
- rampingUp = true;
- lastMean = dMaxDelay;
- }
- periodStart = currentTime;
- }
- if (rampType.equals("none")) { // minDelay or maxDelay, no ramp
- if (rampingUp) {
+ // First change cycle state if we need to
+ adjustState(currentTime);
+ if (cycleState == PEAK_LOAD) {
+ mean = dMinDelay;
+ } else if (cycleState == TROUGH_LOAD) {
+ mean = dMaxDelay;
+ } else if (rampType.equals("none")) { // minDelay or maxDelay,
no ramp
+ if (cycleState == RAMPING_UP) {
mean = dMaxDelay;
} else {
mean = dMinDelay;
}
} else if (rampType.equals("linear")) { // ramp down, then up
double prop =
- (double)(currentTime - periodStart) / (double) period;
- if (rampingUp) {
+ (double)(currentTime - periodStart) / (double)
rampPeriod;
+ if (cycleState == RAMPING_UP) {
mean = dMaxDelay - delayDifference * prop;
} else {
mean = dMinDelay + delayDifference * prop;
@@ -254,20 +264,22 @@
(dMaxDelay - lastMean) / delayDifference;
// Where we would be if this were a linear ramp
double linearProp =
- (double)(currentTime - periodStart) / (double) period;
+ (double)(currentTime - periodStart) / (double)
rampPeriod;
// Need to govern size of jumps, otherwise "convergence"
// can be too fast - use linear ramp as governor
- if ((rampingUp && (lastProp > linearProp)) ||
- (!rampingUp && ((1 - lastProp) > linearProp)))
- lastProp = rampingUp ? linearProp : (1 - linearProp);
+ if ((cycleState == RAMPING_UP && (lastProp > linearProp))
||
+ (cycleState == RAMPING_DOWN &&
+ ((1 - lastProp) > linearProp)))
+ lastProp = (cycleState == RAMPING_UP) ? linearProp :
+ (1 - linearProp);
double prop = 0;
- if (rampingUp) { // Random jump toward 1
+ if (cycleState == RAMPING_UP) { // Random jump toward 1
prop = randomData.nextUniform(lastProp, 1);
} else { // Random jump toward 0
prop = randomData.nextUniform(0, lastProp);
}
// Make sure sequence is monotone
- if (rampingUp) {
+ if (cycleState == RAMPING_UP) {
mean = Math.min(lastMean,
maxDelay - delayDifference * prop);
} else {
@@ -287,5 +299,70 @@
return Math.round(randomData.nextPoisson(mean));
}
}
+ }
+
+ /**
+ * Adjusts cycleState, periodStart and lastMean if a cycle state
+ * transition needs to happen.
+ *
+ * @param currentTime current time
+ */
+ protected void adjustState(long currentTime) {
+ switch (cycleState) {
+ case RAMPING_UP: {
+ if ((currentTime - periodStart) >= rampPeriod) {
+ if (peakPeriod > 0) {
+ cycleState = PEAK_LOAD;
+ } else {
+ cycleState = RAMPING_DOWN;
+ }
+ lastMean = (double) minDelay;
+ periodStart = currentTime;
+ }
+ break;
+ }
+ case RAMPING_DOWN: {
+ if ((currentTime - periodStart) >= rampPeriod) {
+ if (troughPeriod > 0) {
+ cycleState = TROUGH_LOAD;
+ } else {
+ cycleState = RAMPING_UP;
+ }
+ lastMean = (double) maxDelay;
+ periodStart = currentTime;
+ }
+ break;
+ }
+ case PEAK_LOAD: {
+ if ((currentTime - periodStart) >= peakPeriod) {
+ if (rampPeriod > 0) {
+ cycleState = RAMPING_DOWN;
+ lastMean = (double) minDelay;
+ } else {
+ cycleState = TROUGH_LOAD;
+ lastMean = (double) maxDelay;
+ }
+ periodStart = currentTime;
+ }
+ break;
+ }
+ case TROUGH_LOAD: {
+ if ((currentTime - periodStart) >= peakPeriod) {
+ if (rampPeriod > 0) {
+ cycleState = RAMPING_UP;
+ lastMean = (double) maxDelay;
+ } else {
+ cycleState = PEAK_LOAD;
+ lastMean = (double) minDelay;
+ }
+ periodStart = currentTime;
+ }
+ break;
+ }
+ default: {
+ throw new IllegalStateException(
+ "Illegal cycle state: " + cycleState);
+ }
+ }
}
}
Added:
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/LoadGenerator.java
URL:
http://svn.apache.org/viewvc/jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/LoadGenerator.java?view=auto&rev=560120
==============================================================================
---
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/LoadGenerator.java
(added)
+++
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/LoadGenerator.java
Thu Jul 26 23:10:54 2007
@@ -0,0 +1,198 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.commons.performance;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+import java.util.concurrent.TimeUnit;
+import java.util.logging.Logger;
+import org.apache.commons.digester.Digester;
+import org.apache.commons.math.random.RandomData;
+import org.apache.commons.math.random.RandomDataImpl;
+import org.apache.commons.math.stat.descriptive.SummaryStatistics;
+import org.apache.commons.math.stat.descriptive.SummaryStatisticsImpl;
+import org.apache.commons.performance.ConfigurationException;
+
+/**
+ * <p>Base class for load / peformance test runners.
+ * Uses Commons Digester to parse and load configuration and spawns
+ * ClientThread instances to generate load and gather statistics.
+ * </p>
+ * <p>Subclasses must implement [EMAIL PROTECTED] #makeClientThread()} to
create client thread
+ * instances to be kicked off by execute.</p>
+ * <p> Sublasses may override [EMAIL PROTECTED] #configure()} to load
additional configuration
+ * parameters and pass them on to the client in makeClientThread.
+ * </p>
+ *
+ */
+public abstract class LoadGenerator {
+ protected static Logger logger =
Logger.getLogger(LoadGenerator.class.getName());
+ private static List <SummaryStatistics> statsList =
+ new ArrayList <SummaryStatistics>();
+
+ // Client thread properties
+ protected long minDelay;
+ protected long maxDelay;
+ protected double sigma;
+ protected String delayType;
+ protected String rampType;
+ protected long rampPeriod;
+ protected long peakPeriod;
+ protected long troughPeriod;
+ protected String cycleType;
+
+ // Run properties
+ private long numClients;
+ private long iterations;
+
+ protected Digester digester = new Digester();
+ protected String configFile = null;
+
+ /**
+ * <p>Invokes [EMAIL PROTECTED] #configure()} to load digester rules, then
digster.parse,
+ * then [EMAIL PROTECTED] #init()} to initialize configuration members.
Then spawns and
+ * executes [EMAIL PROTECTED] #numClients} ClientThreads using [EMAIL
PROTECTED] #makeClientThread}
+ * to create the ClientThread instances.
+ * </p>
+ * <p>Subclasses should not need to override this method, but must
implement
+ * makeClientThread and may override configure and init to prepare data to
+ * pass to makeClientThread.</p>
+ *
+ * @throws Exception
+ */
+ public void execute() throws Exception {
+ configure();
+ digester.parse(configFile);
+ init();
+ // Spawn and execute client threads
+ ExecutorService ex =
Executors.newFixedThreadPool((int)numClients);
+ for (int i = 0; i < numClients; i++) {
+ ClientThread clientThread = makeClientThread(iterations, minDelay,
+ maxDelay, sigma, delayType, rampPeriod, peakPeriod,
+ troughPeriod, cycleType, rampType, logger, statsList);
+ ex.execute(clientThread);
+ }
+ ex.shutdown();
+ // hard time limit of one day for now
+ // TODO: make this configurable
+ ex.awaitTermination(60 * 60 * 24, TimeUnit.SECONDS);
+
+ // Compute summary statistics
+ SummaryStatistics meanSummary = new SummaryStatisticsImpl();
+ SummaryStatistics stdSummary = new SummaryStatisticsImpl();
+ SummaryStatistics minSummary = new SummaryStatisticsImpl();
+ SummaryStatistics maxSummary = new SummaryStatisticsImpl();
+ for (int i = 0; i < statsList.size(); i++) {
+ SummaryStatistics stats = (SummaryStatistics) statsList.get(i);
+ meanSummary.addValue(stats.getMean());
+ stdSummary.addValue(stats.getStandardDeviation());
+ minSummary.addValue(stats.getMin());
+ maxSummary.addValue(stats.getMax());
+ }
+ logger.info("Overall statistics for the mean");
+ logger.info(meanSummary.toString());
+ logger.info("Overall statistics for the standard deviation");
+ logger.info(stdSummary.toString());
+ logger.info("Overall statistics for the min");
+ logger.info(minSummary.toString());
+ logger.info("Overall statistics for the max");
+ logger.info(maxSummary.toString());
+ }
+
+ protected abstract ClientThread makeClientThread(
+ long iterations, long minDelay, long maxDelay, double sigma,
+ String delayType, long rampPeriod, long peakPeriod,
+ long troughPeriod, String cycleType, String rampType,
+ Logger logger, List <SummaryStatistics> statsList);
+
+ /**
+ * This method is invoked by [EMAIL PROTECTED] #execute()} after [EMAIL
PROTECTED] #configure()}
+ * and digester parse, just before client threads are created. Objects that
+ * need to be created and passed to client threads using configuration info
+ * parsed from the config file should be created in this method.
+ *
+ * @throws Exception
+ */
+ protected void init() throws Exception {}
+
+ public void configureRun(String iterations, String clients,
+ String minDelay, String maxDelay, String sigma,
+ String delayType, String rampType, String rampPeriod,
+ String peakPeriod, String troughPeriod, String cycleType)
+ throws ConfigurationException {
+
+ this.iterations = Long.parseLong(iterations);
+ this.numClients = Long.parseLong(clients);
+ this.minDelay = Long.parseLong(minDelay);
+ this.maxDelay = Long.parseLong(maxDelay);
+ this.sigma = Double.parseDouble(sigma);
+ this.delayType = delayType;
+ this.rampType = rampType;
+ this.rampPeriod = Long.parseLong(rampPeriod);
+ this.peakPeriod = Long.parseLong(peakPeriod);
+ this.troughPeriod = Long.parseLong(troughPeriod);
+ this.cycleType = cycleType;
+ if (cycleType.equals("oscillating") && this.rampPeriod <= 0) {
+ throw new ConfigurationException(
+ "Ramp period must be positive for oscillating cycle type");
+ }
+ }
+
+ /**
+ * <p>Starts preparing Digester to parse the configuration file, pushing
+ * *this onto the stack and loading rules to configure basic "run"
+ * parameters.
+ * </p>
+ * <p>Subclasses can override this, using super() to load base parameters
+ * and then adding additional addCallMethod sequences for additional
parameters.
+ * </p>
+ *
+ * @throws Exception
+ */
+ protected void configure() throws Exception {
+ digester.push(this);
+
+ digester.addCallMethod("configuration/run",
+ "configureRun", 11);
+ digester.addCallParam(
+ "configuration/run/iterations", 0);
+ digester.addCallParam(
+ "configuration/run/clients", 1);
+ digester.addCallParam(
+ "configuration/run/delay-min", 2);
+ digester.addCallParam(
+ "configuration/run/delay-max", 3);
+ digester.addCallParam(
+ "configuration/run/delay-sigma", 4);
+ digester.addCallParam(
+ "configuration/run/delay-type", 5);
+ digester.addCallParam(
+ "configuration/run/ramp-type", 6);
+ digester.addCallParam(
+ "configuration/run/ramp-period", 7);
+ digester.addCallParam(
+ "configuration/run/peak-period", 8);
+ digester.addCallParam(
+ "configuration/run/trough-period", 9);
+ digester.addCallParam(
+ "configuration/run/cycle-type", 10);
+
+ }
+}
Propchange:
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/LoadGenerator.java
------------------------------------------------------------------------------
svn:eol-style = native
Modified:
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPClientThread.java
URL:
http://svn.apache.org/viewvc/jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPClientThread.java?view=diff&rev=560120&r1=560119&r2=560120
==============================================================================
---
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPClientThread.java
(original)
+++
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPClientThread.java
Thu Jul 26 23:10:54 2007
@@ -60,12 +60,14 @@
* @param statsList List of SummaryStatistics to add results to
*/
public DBCPClientThread(long iterations, long minDelay, long maxDelay,
- double sigma, String delayType, String queryType, long period,
- String cycleType, String rampType, Logger logger,
- DataSource dataSource,List <SummaryStatistics> statsList) {
+ double sigma, String delayType, String queryType, long rampPeriod,
+ long peakPeriod, long troughPeriod, String cycleType,
+ String rampType, Logger logger, DataSource dataSource,
+ List <SummaryStatistics> statsList) {
- super(iterations, minDelay, maxDelay, sigma, delayType, period,
cycleType,
- rampType, logger, statsList);
+ super(iterations, minDelay, maxDelay, sigma, delayType, rampPeriod,
+ peakPeriod, troughPeriod, cycleType, rampType, logger,
+ statsList);
this.dataSource = dataSource;
Modified:
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPSoak.java
URL:
http://svn.apache.org/viewvc/jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPSoak.java?view=diff&rev=560120&r1=560119&r2=560120
==============================================================================
---
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPSoak.java
(original)
+++
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPSoak.java
Thu Jul 26 23:10:54 2007
@@ -17,7 +17,7 @@
package org.apache.commons.performance.dbcp;
-import org.apache.commons.performance.ConfigurationException;
+
import java.sql.Connection;
import java.sql.Driver;
import java.sql.DriverManager;
@@ -25,13 +25,8 @@
import java.util.ArrayList;
import java.util.List;
import java.util.Properties;
-import java.util.concurrent.ExecutorService;
-import java.util.concurrent.Executors;
-import java.util.concurrent.TimeUnit;
import java.util.logging.Logger;
-
import javax.sql.DataSource;
-
import org.apache.commons.dbcp.AbandonedConfig;
import org.apache.commons.dbcp.AbandonedObjectPool;
import org.apache.commons.dbcp.ConnectionFactory;
@@ -40,7 +35,6 @@
import org.apache.commons.dbcp.DriverManagerConnectionFactory;
import org.apache.commons.dbcp.PoolableConnectionFactory;
import org.apache.commons.dbcp.PoolingDataSource;
-import org.apache.commons.digester.Digester;
import org.apache.commons.pool.KeyedObjectPoolFactory;
import org.apache.commons.pool.PoolableObjectFactory;
import org.apache.commons.pool.impl.GenericKeyedObjectPool;
@@ -49,7 +43,10 @@
import org.apache.commons.math.random.RandomData;
import org.apache.commons.math.random.RandomDataImpl;
import org.apache.commons.math.stat.descriptive.SummaryStatistics;
-import org.apache.commons.math.stat.descriptive.SummaryStatisticsImpl;
+import org.apache.commons.performance.ConfigurationException;
+import org.apache.commons.performance.ClientThread;
+import org.apache.commons.performance.LoadGenerator;
+import org.apache.commons.performance.pool.WaiterFactory;
/**
* Configurable load / performance tester for commons dbcp.
@@ -57,33 +54,18 @@
* DBCPClientThread instances to generate load and gather statistics.
*
*/
-public class DBCPSoak {
- private static Logger logger = Logger.getLogger(DBCPSoak.class.getName());
- private static List <SummaryStatistics> statsList =
- new ArrayList <SummaryStatistics>();
+public class DBCPSoak extends LoadGenerator {
+ // Connection properties
private String driverClass;
private String connectUrl;
private String connectUser;
private String connectPassword;
+ private String queryType;
+
+ // Connection pool properties
private String poolType;
private String driverType;
private String factoryType;
- private GenericObjectPool connectionPool;
- private PoolingDataSource dataSource;
- private long numClients;
- private long iterations;
- private int maxActive;
- private int maxIdle;
- private int minIdle;
- private long maxWait;
- private long minDelay;
- private long maxDelay;
- private double sigma;
- private String delayType;
- private String queryType;
- private String rampType;
- private long period;
- private String cycleType;
private boolean autocommit;
private boolean readOnly;
private byte exhaustedAction;
@@ -97,8 +79,19 @@
private AbandonedConfig abandonedConfig = new AbandonedConfig();
private boolean poolPreparedStatements;
private int maxOpenStatements;
+ private int maxActive;
+ private int maxIdle;
+ private int minIdle;
+ private long maxWait;
- public void execute() throws Exception {
+ // Instance variables
+ private GenericObjectPool connectionPool;
+ private PoolingDataSource dataSource;
+
+ /**
+ * Create connection pool and, if necessary, test table.
+ */
+ protected void init() throws Exception {
Class.forName(driverClass);
// Create object pool
@@ -178,49 +171,31 @@
} finally {
conn.close();
}
-
- logger.info("Starting");
-
- // Spawn and execute client threads
- ExecutorService ex =
Executors.newFixedThreadPool((int)numClients);
- for (int i = 0; i < numClients; i++) {
- ex.execute(new DBCPClientThread(iterations, minDelay,
maxDelay,
- sigma, delayType, queryType, period, cycleType, rampType,
- logger, dataSource, statsList));
- }
- ex.shutdown();
- // hard time limit of one day for now
- // TODO: make this configurable
- ex.awaitTermination(60 * 60 * 24, TimeUnit.SECONDS);
-
- // Compute summary statistics
- SummaryStatistics meanSummary = new SummaryStatisticsImpl();
- SummaryStatistics stdSummary = new SummaryStatisticsImpl();
- SummaryStatistics minSummary = new SummaryStatisticsImpl();
- SummaryStatistics maxSummary = new SummaryStatisticsImpl();
- for (int i = 0; i < statsList.size(); i++) {
- SummaryStatistics stats = (SummaryStatistics) statsList.get(i);
- meanSummary.addValue(stats.getMean());
- stdSummary.addValue(stats.getStandardDeviation());
- minSummary.addValue(stats.getMin());
- maxSummary.addValue(stats.getMax());
- }
- logger.info("Overall statistics for the mean");
- logger.info(meanSummary.toString());
- logger.info("Overall statistics for the standard deviation");
- logger.info(stdSummary.toString());
- logger.info("Overall statistics for the min");
- logger.info(minSummary.toString());
- logger.info("Overall statistics for the max");
- logger.info(maxSummary.toString());
- }
+ }
+
+ protected ClientThread makeClientThread(
+ long iterations, long minDelay, long maxDelay, double sigma,
+ String delayType, long rampPeriod, long peakPeriod,
+ long troughPeriod, String cycleType, String rampType,
+ Logger logger, List <SummaryStatistics> statsList) {
+
+ return new DBCPClientThread(iterations, minDelay, maxDelay,
+ sigma, delayType, queryType, rampPeriod, peakPeriod,
+ troughPeriod, cycleType, rampType, logger, dataSource,
+ statsList);
+ }
+ // ------------------------------------------------------------------------
+ // Configuration methods specific to this LoadGenerator invoked by Digester
+ // when superclass execute calls digerster.parse.
+ // ------------------------------------------------------------------------
public void configureDataBase(String driver, String url,
- String username, String password) {
+ String username, String password, String queryType) {
this.driverClass = driver;
this.connectUrl = url;
this.connectUser = username;
this.connectPassword = password;
+ this.queryType = queryType;
}
public void configureConnectionFactory(String type,
@@ -264,7 +239,7 @@
throw new ConfigurationException(
"Bad configuration setting for exhausted action: "
+ exhaustedAction);
- }
+ }
}
public void configureAbandonedConfig(String logAbandoned,
@@ -275,28 +250,7 @@
abandonedConfig.setRemoveAbandonedTimeout(
Integer.parseInt(abandonedTimeout));
}
-
- public void configureRun(String queryType, String iterations,
- String clients, String minDelay, String maxDelay, String sigma,
- String delayType, String rampType, String period, String
cycleType)
- throws ConfigurationException {
- this.queryType = queryType;
- this.iterations = Long.parseLong(iterations);
- this.numClients = Long.parseLong(clients);
- this.minDelay = Long.parseLong(minDelay);
- this.maxDelay = Long.parseLong(maxDelay);
- this.sigma = Double.parseDouble(sigma);
- this.delayType = delayType;
- this.rampType = rampType;
- this.period = Long.parseLong(period);
- this.cycleType = cycleType;
- if (cycleType.equals("oscillating") && this.period <= 0) {
- throw new ConfigurationException(
- "Period must be positive for oscillating cycle type");
- }
- }
-
private void makeTable() throws Exception {
Class.forName(driverClass);
Connection db = DriverManager.getConnection(connectUrl,connectUser,
@@ -326,16 +280,21 @@
}
}
- public void configure() throws Exception {
- Digester digester = new Digester();
- digester.push(this);
+ /**
+ * Add dbcp configuration to parameters loaded by super.
+ * Also set config file name.
+ */
+ protected void configure() throws Exception {
+
+ super.configure();
digester.addCallMethod("configuration/database",
- "configureDataBase", 4);
+ "configureDataBase", 5);
digester.addCallParam("configuration/database/driver", 0);
digester.addCallParam("configuration/database/url", 1);
digester.addCallParam("configuration/database/username", 2);
digester.addCallParam("configuration/database/password", 3);
+ digester.addCallParam("configuration/database/query-type", 4);
digester.addCallMethod("configuration/connection-factory",
"configureConnectionFactory", 4);
@@ -384,29 +343,6 @@
digester.addCallParam(
"configuration/pool/type", 11);
- digester.addCallMethod("configuration/run",
- "configureRun", 10);
- digester.addCallParam(
- "configuration/run/query-type", 0);
- digester.addCallParam(
- "configuration/run/iterations", 1);
- digester.addCallParam(
- "configuration/run/clients", 2);
- digester.addCallParam(
- "configuration/run/delay-min", 3);
- digester.addCallParam(
- "configuration/run/delay-max", 4);
- digester.addCallParam(
- "configuration/run/delay-sigma", 5);
- digester.addCallParam(
- "configuration/run/delay-type", 6);
- digester.addCallParam(
- "configuration/run/ramp-type", 7);
- digester.addCallParam(
- "configuration/run/period", 8);
- digester.addCallParam(
- "configuration/run/cycle-type", 9);
-
digester.addCallMethod("configuration/abandoned-config",
"configureAbandonedConfig", 3);
digester.addCallParam(
@@ -416,7 +352,6 @@
digester.addCallParam(
"configuration/abandoned-config/abandoned-timeout", 2);
- digester.parse("config-dbcp.xml");
-
+ this.configFile = "config-dbcp.xml";
}
}
Modified:
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPTest.java
URL:
http://svn.apache.org/viewvc/jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPTest.java?view=diff&rev=560120&r1=560119&r2=560120
==============================================================================
---
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPTest.java
(original)
+++
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/dbcp/DBCPTest.java
Thu Jul 26 23:10:54 2007
@@ -24,7 +24,6 @@
private static DBCPSoak soaker = new DBCPSoak();
public static void main(String[] args) {
try {
- soaker.configure();
soaker.execute();
} catch (Exception ex) {
ex.printStackTrace();
Modified:
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolClientThread.java
URL:
http://svn.apache.org/viewvc/jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolClientThread.java?view=diff&rev=560120&r1=560119&r2=560120
==============================================================================
---
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolClientThread.java
(original)
+++
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolClientThread.java
Thu Jul 26 23:10:54 2007
@@ -41,18 +41,21 @@
* @param minDelay minumum mean time between client requests
* @param maxDelay minumum mean time between client requests
* @param delayType distribution of time between client requests
- * @param period period of cycle for cyclic load
+ * @param rampPeriod ramp period of cycle for cyclic load
+ * @param peakOeriod peak period of cycle for cyclic load
+ * @param troughPeriod trough period of cycle for cyclic load
* @param cycleType type of cycle for mean delay
* @param logger common logger shared by all clients
* @param statsList List of SummaryStatistics to add results to
*/
public PoolClientThread(long iterations, long minDelay, long maxDelay,
- double sigma, String delayType, long period,
- String cycleType, String rampType, Logger logger,
+ double sigma, String delayType, long rampPeriod, long peakPeriod,
+ long troughPeriod, String cycleType, String rampType, Logger
logger,
List <SummaryStatistics> statsList, ObjectPool pool) {
- super(iterations, minDelay, maxDelay, sigma, delayType, period,
cycleType,
- rampType, logger, statsList);
+ super(iterations, minDelay, maxDelay, sigma, delayType, rampPeriod,
+ peakPeriod, troughPeriod, cycleType,rampType, logger,
+ statsList);
this.pool = pool;
}
Modified:
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolSoak.java
URL:
http://svn.apache.org/viewvc/jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolSoak.java?view=diff&rev=560120&r1=560119&r2=560120
==============================================================================
---
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolSoak.java
(original)
+++
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolSoak.java
Thu Jul 26 23:10:54 2007
@@ -17,39 +17,20 @@
package org.apache.commons.performance.pool;
-import org.apache.commons.performance.ConfigurationException;
-import java.sql.Connection;
-import java.sql.Driver;
-import java.sql.DriverManager;
-import java.sql.Statement;
import java.util.ArrayList;
import java.util.List;
-import java.util.Properties;
-import java.util.concurrent.ExecutorService;
-import java.util.concurrent.Executors;
-import java.util.concurrent.TimeUnit;
import java.util.logging.Logger;
-
-import javax.sql.DataSource;
-
import org.apache.commons.dbcp.AbandonedConfig;
import org.apache.commons.dbcp.AbandonedObjectPool;
-import org.apache.commons.dbcp.ConnectionFactory;
-import org.apache.commons.dbcp.DataSourceConnectionFactory;
-import org.apache.commons.dbcp.DriverConnectionFactory;
-import org.apache.commons.dbcp.DriverManagerConnectionFactory;
-import org.apache.commons.dbcp.PoolableConnectionFactory;
-import org.apache.commons.dbcp.PoolingDataSource;
-import org.apache.commons.digester.Digester;
+import org.apache.commons.math.stat.descriptive.SummaryStatistics;
import org.apache.commons.pool.KeyedObjectPoolFactory;
import org.apache.commons.pool.PoolableObjectFactory;
import org.apache.commons.pool.impl.GenericKeyedObjectPool;
import org.apache.commons.pool.impl.GenericKeyedObjectPoolFactory;
import org.apache.commons.pool.impl.GenericObjectPool;
-import org.apache.commons.math.random.RandomData;
-import org.apache.commons.math.random.RandomDataImpl;
-import org.apache.commons.math.stat.descriptive.SummaryStatistics;
-import org.apache.commons.math.stat.descriptive.SummaryStatisticsImpl;
+import org.apache.commons.performance.ConfigurationException;
+import org.apache.commons.performance.ClientThread;
+import org.apache.commons.performance.LoadGenerator;
/**
* Configurable load / performance tester for commons pool.
@@ -57,16 +38,11 @@
* PoolClientThread instances to generate load and gather statistics.
*
*/
-public class PoolSoak {
- private static Logger logger = Logger.getLogger(PoolSoak.class.getName());
- private static List <SummaryStatistics> statsList =
- new ArrayList <SummaryStatistics>();
-
+public class PoolSoak extends LoadGenerator {
+
// Pool properties
private String poolType;
private GenericObjectPool pool;
- private long numClients;
- private long iterations;
private int maxActive;
private int maxIdle;
private int minIdle;
@@ -80,15 +56,6 @@
private boolean testWhileIdle;
private AbandonedConfig abandonedConfig = new AbandonedConfig();
- // Client thread properties
- private long minDelay;
- private long maxDelay;
- private double sigma;
- private String delayType;
- private String rampType;
- private long period;
- private String cycleType;
-
// WaiterFactory properties
private long activateLatency;
private long destroyLatency;
@@ -97,9 +64,69 @@
private long validateLatency;
private long waiterLatency;
+ /**
+ * Add pool configuration to parameters loaded by super.
+ * Also set config file name.
+ */
+ protected void configure() throws Exception {
+ super.configure();
+ digester.addCallMethod("configuration/factory",
+ "configureFactory", 6);
+ digester.addCallParam(
+ "configuration/factory/activate-latency", 0);
+ digester.addCallParam(
+ "configuration/factory/destroy-latency", 1);
+ digester.addCallParam(
+ "configuration/factory/make-latency", 2);
+ digester.addCallParam(
+ "configuration/factory/passivate-latency", 3);
+ digester.addCallParam(
+ "configuration/factory/validate-latency", 4);
+ digester.addCallParam(
+ "configuration/factory/waiter-latency", 5);
+ digester.addCallMethod("configuration/pool",
+ "configurePool", 12);
+ digester.addCallParam(
+ "configuration/pool/max-active", 0);
+ digester.addCallParam(
+ "configuration/pool/max-idle", 1);
+ digester.addCallParam(
+ "configuration/pool/min-idle", 2);
+ digester.addCallParam(
+ "configuration/pool/max-wait", 3);
+ digester.addCallParam(
+ "configuration/pool/exhausted-action", 4);
+ digester.addCallParam(
+ "configuration/pool/test-on-borrow", 5);
+ digester.addCallParam(
+ "configuration/pool/test-on-return", 6);
+ digester.addCallParam(
+ "configuration/pool/time-between-evictions", 7);
+ digester.addCallParam(
+ "configuration/pool/tests-per-eviction", 8);
+ digester.addCallParam(
+ "configuration/pool/idle-timeout", 9);
+ digester.addCallParam(
+ "configuration/pool/test-while-idle", 10);
+ digester.addCallParam(
+ "configuration/pool/type", 11);
+ digester.addCallMethod("configuration/abandoned-config",
+ "configureAbandonedConfig", 3);
+ digester.addCallParam(
+ "configuration/abandoned-config/log-abandoned", 0);
+ digester.addCallParam(
+ "configuration/abandoned-config/remove-abandoned", 1);
+ digester.addCallParam(
+ "configuration/abandoned-config/abandoned-timeout", 2);
+
+ this.configFile = "config-pool.xml";
+
+ }
- public void execute() throws Exception {
-
+ /**
+ * Create object pool and factory
+ */
+ protected void init() throws Exception {
// Create object pool
if (poolType.equals("GenericObjectPool")) {
pool = new GenericObjectPool(
@@ -117,43 +144,25 @@
// Create factory
pool.setFactory(new WaiterFactory(activateLatency, destroyLatency,
makeLatency, passivateLatency, validateLatency,
waiterLatency));
-
- logger.info("Starting");
-
- // Spawn and execute client threads
- ExecutorService ex =
Executors.newFixedThreadPool((int)numClients);
- for (int i = 0; i < numClients; i++) {
- ex.execute(new PoolClientThread(iterations, minDelay,
maxDelay,
- sigma, delayType, period, cycleType, rampType,
- logger, statsList, pool));
- }
- ex.shutdown();
- // hard time limit of one day for now
- // TODO: make this configurable
- ex.awaitTermination(60 * 60 * 24, TimeUnit.SECONDS);
-
- // Compute summary statistics
- SummaryStatistics meanSummary = new SummaryStatisticsImpl();
- SummaryStatistics stdSummary = new SummaryStatisticsImpl();
- SummaryStatistics minSummary = new SummaryStatisticsImpl();
- SummaryStatistics maxSummary = new SummaryStatisticsImpl();
- for (int i = 0; i < statsList.size(); i++) {
- SummaryStatistics stats = (SummaryStatistics) statsList.get(i);
- meanSummary.addValue(stats.getMean());
- stdSummary.addValue(stats.getStandardDeviation());
- minSummary.addValue(stats.getMin());
- maxSummary.addValue(stats.getMax());
- }
- logger.info("Overall statistics for the mean");
- logger.info(meanSummary.toString());
- logger.info("Overall statistics for the standard deviation");
- logger.info(stdSummary.toString());
- logger.info("Overall statistics for the min");
- logger.info(minSummary.toString());
- logger.info("Overall statistics for the max");
- logger.info(maxSummary.toString());
- }
+ }
+ /**
+ * Create and return a PoolClientThread
+ */
+ protected ClientThread makeClientThread(long iterations, long minDelay,
+ long maxDelay, double sigma, String delayType, long rampPeriod,
+ long peakPeriod, long troughPeriod, String cycleType,
+ String rampType, Logger logger,
+ List <SummaryStatistics> statsList) {
+ return new PoolClientThread(iterations, minDelay, maxDelay,
+ sigma, delayType, rampPeriod, peakPeriod, troughPeriod,
+ cycleType, rampType, logger, statsList, pool);
+ }
+
+ // ------------------------------------------------------------------------
+ // Configuration methods specific to this LoadGenerator invoked by Digester
+ // when superclass execute calls digerster.parse.
+ //
------------------------------------------------------------------------
public void configureFactory(String activateLatency, String destroyLatency,
String makeLatency, String passivateLatency, String
validateLatency,
String waiterLatency) {
@@ -203,105 +212,4 @@
Integer.parseInt(abandonedTimeout));
}
- public void configureRun(String queryType, String iterations,
- String clients, String minDelay, String maxDelay, String sigma,
- String delayType, String rampType, String period, String
cycleType)
- throws ConfigurationException {
-
- this.iterations = Long.parseLong(iterations);
- this.numClients = Long.parseLong(clients);
- this.minDelay = Long.parseLong(minDelay);
- this.maxDelay = Long.parseLong(maxDelay);
- this.sigma = Double.parseDouble(sigma);
- this.delayType = delayType;
- this.rampType = rampType;
- this.period = Long.parseLong(period);
- this.cycleType = cycleType;
- if (cycleType.equals("oscillating") && this.period <= 0) {
- throw new ConfigurationException(
- "Period must be positive for oscillating cycle type");
- }
- }
-
- public void configure() throws Exception {
- Digester digester = new Digester();
- digester.push(this);
-
- digester.addCallMethod("configuration/factory",
- "configureFactory", 6);
- digester.addCallParam(
- "configuration/factory/activate-latency", 0);
- digester.addCallParam(
- "configuration/factory/destroy-latency", 1);
- digester.addCallParam(
- "configuration/factory/make-latency", 2);
- digester.addCallParam(
- "configuration/factory/passivate-latency", 3);
- digester.addCallParam(
- "configuration/factory/validate-latency", 4);
- digester.addCallParam(
- "configuration/factory/waiter-latency", 5);
-
- digester.addCallMethod("configuration/pool",
- "configurePool", 12);
- digester.addCallParam(
- "configuration/pool/max-active", 0);
- digester.addCallParam(
- "configuration/pool/max-idle", 1);
- digester.addCallParam(
- "configuration/pool/min-idle", 2);
- digester.addCallParam(
- "configuration/pool/max-wait", 3);
- digester.addCallParam(
- "configuration/pool/exhausted-action", 4);
- digester.addCallParam(
- "configuration/pool/test-on-borrow", 5);
- digester.addCallParam(
- "configuration/pool/test-on-return", 6);
- digester.addCallParam(
- "configuration/pool/time-between-evictions", 7);
- digester.addCallParam(
- "configuration/pool/tests-per-eviction", 8);
- digester.addCallParam(
- "configuration/pool/idle-timeout", 9);
- digester.addCallParam(
- "configuration/pool/test-while-idle", 10);
- digester.addCallParam(
- "configuration/pool/type", 11);
-
- digester.addCallMethod("configuration/run",
- "configureRun", 10);
- digester.addCallParam(
- "configuration/run/query-type", 0);
- digester.addCallParam(
- "configuration/run/iterations", 1);
- digester.addCallParam(
- "configuration/run/clients", 2);
- digester.addCallParam(
- "configuration/run/delay-min", 3);
- digester.addCallParam(
- "configuration/run/delay-max", 4);
- digester.addCallParam(
- "configuration/run/delay-sigma", 5);
- digester.addCallParam(
- "configuration/run/delay-type", 6);
- digester.addCallParam(
- "configuration/run/ramp-type", 7);
- digester.addCallParam(
- "configuration/run/period", 8);
- digester.addCallParam(
- "configuration/run/cycle-type", 9);
-
- digester.addCallMethod("configuration/abandoned-config",
- "configureAbandonedConfig", 3);
- digester.addCallParam(
- "configuration/abandoned-config/log-abandoned", 0);
- digester.addCallParam(
- "configuration/abandoned-config/remove-abandoned", 1);
- digester.addCallParam(
- "configuration/abandoned-config/abandoned-timeout", 2);
-
- digester.parse("config-pool.xml");
-
- }
}
Modified:
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolTest.java
URL:
http://svn.apache.org/viewvc/jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolTest.java?view=diff&rev=560120&r1=560119&r2=560120
==============================================================================
---
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolTest.java
(original)
+++
jakarta/commons/sandbox/performance/trunk/src/java/org/apache/commons/performance/pool/PoolTest.java
Thu Jul 26 23:10:54 2007
@@ -24,7 +24,6 @@
public static void main(String[] args) {
PoolSoak soaker = new PoolSoak();
try {
- soaker.configure();
soaker.execute();
} catch (Exception ex) {
ex.printStackTrace();
---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]