You are viewing a plain text version of this content. The canonical link for it is here.
Posted to derby-commits@db.apache.org by rh...@apache.org on 2010/03/04 21:17:54 UTC
svn commit: r919159 -
/db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/
Author: rhillegas
Date: Thu Mar 4 20:17:54 2010
New Revision: 919159
URL: http://svn.apache.org/viewvc?rev=919159&view=rev
Log:
DERBY-4565: Add a client for testing the concurrency of sequence generators.
Added:
db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SequenceGeneratorConcurrency.java (with props)
Modified:
db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/BackToBackLoadGenerator.java
db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/BankTransactionClient.java
db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/Client.java
db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/GroupByClient.java
db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/IndexJoinClient.java
db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/PoissonLoadGenerator.java
db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/Runner.java
db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SingleRecordSelectClient.java
db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SingleRecordUpdateClient.java
Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/BackToBackLoadGenerator.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/BackToBackLoadGenerator.java?rev=919159&r1=919158&r2=919159&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/BackToBackLoadGenerator.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/BackToBackLoadGenerator.java Thu Mar 4 20:17:54 2010
@@ -52,6 +52,8 @@
client = c;
}
+ public Client getClient() { return client; }
+
public void run() {
try {
while (!stop) {
@@ -128,5 +130,10 @@
out.println("Test duration (s):\t" + ((double) time / 1000));
out.println("Number of transactions:\t" + count);
out.println("Average throughput (tx/s):\t" + tps);
+
+ for (int i = 0; i < threads.length; i++)
+ {
+ threads[i].getClient().printReport( out );
+ }
}
}
Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/BankTransactionClient.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/BankTransactionClient.java?rev=919159&r1=919158&r2=919159&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/BankTransactionClient.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/BankTransactionClient.java Thu Mar 4 20:17:54 2010
@@ -21,6 +21,7 @@
package org.apache.derbyTesting.perf.clients;
+import java.io.PrintStream;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
@@ -165,6 +166,8 @@
conn.commit();
}
+ public void printReport(PrintStream out) {}
+
/**
* Generate a random teller id.
*/
Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/Client.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/Client.java?rev=919159&r1=919158&r2=919159&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/Client.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/Client.java Thu Mar 4 20:17:54 2010
@@ -21,6 +21,7 @@
package org.apache.derbyTesting.perf.clients;
+import java.io.PrintStream;
import java.sql.Connection;
import java.sql.SQLException;
@@ -47,4 +48,11 @@
* @throws SQLException if a database error occurs
*/
void doWork() throws SQLException;
+
+ /**
+ * Print a report from the test run.
+ *
+ * @param out stream to print the report to
+ */
+ void printReport(PrintStream out);
}
Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/GroupByClient.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/GroupByClient.java?rev=919159&r1=919158&r2=919159&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/GroupByClient.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/GroupByClient.java Thu Mar 4 20:17:54 2010
@@ -21,6 +21,7 @@
package org.apache.derbyTesting.perf.clients;
+import java.io.PrintStream;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.Statement;
@@ -214,4 +215,6 @@
conn.commit();
}
+ public void printReport(PrintStream out) {}
+
}
Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/IndexJoinClient.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/IndexJoinClient.java?rev=919159&r1=919158&r2=919159&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/IndexJoinClient.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/IndexJoinClient.java Thu Mar 4 20:17:54 2010
@@ -21,6 +21,7 @@
package org.apache.derbyTesting.perf.clients;
+import java.io.PrintStream;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.SQLException;
@@ -52,4 +53,6 @@
conn.commit();
}
+ public void printReport(PrintStream out) {}
+
}
Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/PoissonLoadGenerator.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/PoissonLoadGenerator.java?rev=919159&r1=919158&r2=919159&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/PoissonLoadGenerator.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/PoissonLoadGenerator.java Thu Mar 4 20:17:54 2010
@@ -70,6 +70,8 @@
client = c;
}
+ public Client getClient() { return client; }
+
/**
* Tell the client to stop waiting.
*/
@@ -195,5 +197,10 @@
out.println("Average response time (ms):\t" + avgResp);
out.println("Minimum response time (ms):\t" + min);
out.println("Maximum response time (ms):\t" + max);
+
+ for (int i = 0; i < threads.length; i++)
+ {
+ threads[i].getClient().printReport( out );
+ }
}
}
Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/Runner.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/Runner.java?rev=919159&r1=919158&r2=919159&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/Runner.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/Runner.java Thu Mar 4 20:17:54 2010
@@ -244,6 +244,12 @@
" in the database has (default: 10)\n" +
" - accountsPerBranch=NN: specifies the number of accounts in\n" +
" each branch (default: 100000)\n" +
+" * seq_gen - sequence generator concurrency. Accepts\n" +
+" the following load-specific options (see also -load_opts):\n" +
+" - numberOfGenerators: number of sequences to create\n" +
+" - tablesPerGenerator: number of tables to create per sequence\n" +
+" - insertsPerTransaction: number of inserts to perform per transaction\n" +
+" - debugging: 1 means print debug chatter, 0 means do not print the chatter\n" +
" -load_opts: comma-separated list of load-specific options\n" +
" -gen: load generator, default: b2b, valid types:\n" +
" * b2b - clients perform operations back-to-back\n" +
@@ -311,6 +317,8 @@
getLoadOpt("branches", 1),
getLoadOpt("tellersPerBranch", 10),
getLoadOpt("accountsPerBranch", 100000));
+ } else if (load.equals("seq_gen")) {
+ return new SequenceGeneratorConcurrency.Filler();
}
System.err.println("unknown load: " + load);
printUsage(System.err);
@@ -347,6 +355,8 @@
getLoadOpt("branches", 1),
getLoadOpt("tellersPerBranch", 10),
getLoadOpt("accountsPerBranch", 100000));
+ } else if (load.equals("seq_gen")) {
+ return new SequenceGeneratorConcurrency.SGClient();
}
System.err.println("unknown load: " + load);
printUsage(System.err);
Added: db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SequenceGeneratorConcurrency.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SequenceGeneratorConcurrency.java?rev=919159&view=auto
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SequenceGeneratorConcurrency.java (added)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SequenceGeneratorConcurrency.java Thu Mar 4 20:17:54 2010
@@ -0,0 +1,326 @@
+/*
+
+Derby - Class org.apache.derbyTesting.perf.clients.SequenceGeneratorConcurrency
+
+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.derbyTesting.perf.clients;
+
+import java.io.PrintStream;
+import java.sql.Connection;
+import java.sql.PreparedStatement;
+import java.sql.SQLException;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Random;
+
+/**
+ * <p>
+ * Machinery to test the concurrency of sequence generators.
+ * </p>
+ */
+public class SequenceGeneratorConcurrency
+{
+ ///////////////////////////////////////////////////////////////////////////////////
+ //
+ // LOAD OPTIONS FOR THIS TEST
+ //
+ ///////////////////////////////////////////////////////////////////////////////////
+
+ /**
+ * <p>
+ * Describes the load options specific to a run of the SequenceGeneratorConcurrency test.
+ * </p>
+ */
+ public static final class LoadOptions
+ {
+ private int _numberOfGenerators;
+ private int _tablesPerGenerator;
+ private int _insertsPerTransaction;
+ private boolean _debugging;
+
+ public LoadOptions()
+ {
+ _numberOfGenerators = Runner.getLoadOpt( "numberOfGenerators", 1 );
+ _tablesPerGenerator = Runner.getLoadOpt( "tablesPerGenerator", 1 );
+ _insertsPerTransaction = Runner.getLoadOpt( "insertsPerTransaction", 1 );
+ _debugging = ( Runner.getLoadOpt( "debugging", 0 ) == 1 );
+ }
+
+ /** Get the number of generators created by this test run */
+ public int getNumberOfGenerators() { return _numberOfGenerators; }
+
+ /** Get the number of tables created for each generator */
+ public int getTablesPerGenerator() { return _tablesPerGenerator; }
+
+ /** Get the number of inserts performed per transaction */
+ public int getInsertsPerTransaction() { return _insertsPerTransaction; }
+
+ /** Return whether we are in debugging mode */
+ public boolean debugging() { return _debugging; }
+
+ public String toString()
+ {
+ StringBuffer buffer = new StringBuffer();
+
+ buffer.append( "LoadOptions( " );
+ buffer.append( " generators = " + _numberOfGenerators );
+ buffer.append( ", tablesPerGenerator = " + _tablesPerGenerator );
+ buffer.append( ", insertsPerTransaction = " + _insertsPerTransaction );
+ buffer.append( ", debugging = " + _debugging );
+ buffer.append( " )" );
+
+ return buffer.toString();
+ }
+
+ }
+
+ ///////////////////////////////////////////////////////////////////////////////////
+ //
+ // DBFiller IMPLEMENTATION
+ //
+ ///////////////////////////////////////////////////////////////////////////////////
+
+ /**
+ * <p>
+ * Create the schema necessary to support this test run.
+ * </p>
+ */
+ public static final class Filler implements DBFiller
+ {
+ private LoadOptions _loadOptions;
+
+ public Filler()
+ {
+ _loadOptions = new LoadOptions();
+ }
+
+ public void fill( Connection conn ) throws SQLException
+ {
+ int numberOfGenerators = _loadOptions.getNumberOfGenerators();
+ int tablesPerGenerator = _loadOptions.getTablesPerGenerator();
+
+ for ( int sequence = 0; sequence < numberOfGenerators; sequence++ )
+ {
+ runDDL( conn, "create sequence " + makeSequenceName( sequence ) );
+
+ for ( int table = 0; table < tablesPerGenerator; table++ )
+ {
+ runDDL( conn, "create table " + makeTableName( sequence, table ) + "( a int )" );
+ }
+ }
+ }
+
+ /** Run a DDL statement */
+ private void runDDL( Connection conn, String ddl ) throws SQLException
+ {
+ PreparedStatement ps = prepareStatement( conn, _loadOptions.debugging(), ddl );
+ ps.execute();
+ ps.close();
+ }
+ }
+
+ ///////////////////////////////////////////////////////////////////////////////////
+ //
+ // Client IMPLEMENTATION
+ //
+ ///////////////////////////////////////////////////////////////////////////////////
+
+ public static final class SGClient implements Client
+ {
+ private LoadOptions _loadOptions;
+ private Connection _conn;
+ private PreparedStatement _psArray[][];
+ private Random _randomNumberGenerator;
+ private int _clientNumber;
+ private int _transactionCount;
+ private int _errorCount = 0;
+ private HashMap _errorLog;
+
+ private static int _clientCount = 0;
+
+ // filled in at reporting time
+ private static int _totalErrorCount = 0;
+ private static int _totalTransactionCount = 0;
+
+ public SGClient()
+ {
+ _clientNumber = _clientCount++;
+ _transactionCount = 0;
+ _errorLog = new HashMap();
+ _loadOptions = new LoadOptions();
+
+ _psArray = new PreparedStatement[ _loadOptions.getNumberOfGenerators() ] [ _loadOptions.getTablesPerGenerator() ];
+ _randomNumberGenerator = new Random();
+
+ if ( _loadOptions.debugging() )
+ {
+ debugPrint( "Creating client " + _clientNumber + " with " + _loadOptions.toString() );
+ }
+ }
+
+ /** Create the PreparedStatements needed by the test run. */
+ public void init( Connection conn ) throws SQLException
+ {
+ _conn = conn;
+
+ int numberOfGenerators = _loadOptions.getNumberOfGenerators();
+ int tablesPerGenerator = _loadOptions.getTablesPerGenerator();
+ boolean debugging = _loadOptions.debugging();
+
+ for ( int sequence = 0; sequence < numberOfGenerators; sequence++ )
+ {
+ String sequenceName = makeSequenceName( sequence );
+
+ for ( int table = 0; table < tablesPerGenerator; table++ )
+ {
+ String tableName = makeTableName( sequence, table );
+
+ _psArray[ sequence ][ table ] = prepareStatement
+ ( _conn, debugging, "insert into " + tableName + "( a ) values ( next value for " + sequenceName + " )" );
+ }
+ }
+
+ _conn.setAutoCommit( false );
+ }
+
+ /** A transaction performed by this thread */
+ public void doWork() throws SQLException
+ {
+ int sequence = getPositiveRandomNumber() % _loadOptions.getNumberOfGenerators();
+ int table = getPositiveRandomNumber() % _loadOptions.getTablesPerGenerator();
+ int insertsPerTransaction = _loadOptions.getInsertsPerTransaction();
+ boolean debugging = _loadOptions.debugging();
+
+ int rowNumber = 0;
+
+ try {
+ for ( ; rowNumber < insertsPerTransaction; rowNumber++ )
+ {
+ _psArray[ sequence ][ table ].executeUpdate();
+ }
+ }
+ catch (SQLException t)
+ {
+ debugPrint
+ (
+ "Error on client " + _clientNumber +
+ " on sequence " + sequence +
+ " in transaction " + _transactionCount +
+ " on row " + rowNumber
+ );
+
+ addError( t );
+ _conn.rollback();
+
+ return;
+ }
+
+ _conn.commit();
+
+ _transactionCount++;
+ }
+
+ private int getPositiveRandomNumber()
+ {
+ int raw = _randomNumberGenerator.nextInt();
+
+ if ( raw < 0 ) { return -raw; }
+ else { return raw; }
+ }
+
+ public void printReport(PrintStream out)
+ {
+ Iterator keyIterator = _errorLog.keySet().iterator();
+
+ while ( keyIterator.hasNext() )
+ {
+ String key = (String) keyIterator.next();
+ int[] value = (int[]) _errorLog.get( key );
+
+ String message = " Client " + _clientNumber + " saw " + value[0] + " instances of this error: " + key;
+
+ out.println( message );
+ }
+
+ _totalErrorCount += _errorCount;
+ _totalTransactionCount += _transactionCount;
+
+ // last client reports the totals
+ if ( _clientNumber == ( _clientCount - 1 ) )
+ {
+ out.println( "\n" );
+ out.println( _loadOptions.toString() );
+ out.println( _totalErrorCount + " errors, including warmup phase." );
+ out.println( _totalTransactionCount + " successful transactions, including warmup phase." );
+ }
+ }
+
+ // error management
+
+ /** Bump the error count for this problem */
+ private void addError( Throwable t )
+ {
+ _errorCount++;
+
+ String key = t.getClass().getName() + ": " + t.getMessage();
+ int[] value = (int[]) _errorLog.get( key );
+
+ if ( value != null ) { value[ 0 ] = value[ 0 ] + 1; }
+ else
+ {
+ _errorLog.put( key, new int[] { 1 } );
+ }
+ }
+ }
+
+ ///////////////////////////////////////////////////////////////////////////////////
+ //
+ // UTILITY METHODS
+ //
+ ///////////////////////////////////////////////////////////////////////////////////
+
+ /** make the name of a sequence */
+ public static String makeSequenceName( int sequence )
+ { return "seq_" + sequence; }
+
+ /** make the name of a table */
+ public static String makeTableName( int sequence, int table )
+ { return "t_" + sequence + "_" + table; }
+
+ public static PreparedStatement prepareStatement
+ ( Connection conn, boolean debugging, String text ) throws SQLException
+ {
+ if ( debugging ) { debugPrint( text ); }
+
+ return conn.prepareStatement( text );
+ }
+
+ public static void debugPrint( String text )
+ {
+ print( "DEBUG: " + text );
+ }
+
+ public static void print( String text )
+ {
+ System.out.println( text );
+ }
+
+}
+
+
Propchange: db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SequenceGeneratorConcurrency.java
------------------------------------------------------------------------------
svn:eol-style = native
Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SingleRecordSelectClient.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SingleRecordSelectClient.java?rev=919159&r1=919158&r2=919159&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SingleRecordSelectClient.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SingleRecordSelectClient.java Thu Mar 4 20:17:54 2010
@@ -21,6 +21,7 @@
package org.apache.derbyTesting.perf.clients;
+import java.io.PrintStream;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
@@ -114,6 +115,8 @@
conn.commit();
}
+ public void printReport(PrintStream out) {}
+
/**
* Make sure the text column is retrieved and read. Different methods
* are used for the retrieval based on whether the column is a VARCHAR,
Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SingleRecordUpdateClient.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SingleRecordUpdateClient.java?rev=919159&r1=919158&r2=919159&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SingleRecordUpdateClient.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/perf/clients/SingleRecordUpdateClient.java Thu Mar 4 20:17:54 2010
@@ -22,6 +22,7 @@
package org.apache.derbyTesting.perf.clients;
import java.io.ByteArrayInputStream;
+import java.io.PrintStream;
import java.io.StringReader;
import java.sql.Connection;
import java.sql.PreparedStatement;
@@ -116,4 +117,6 @@
conn.commit();
}
+ public void printReport(PrintStream out) {}
+
}