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 kr...@apache.org on 2008/02/13 13:26:47 UTC

svn commit: r627380 - in /db/derby/code/trunk/java: client/org/apache/derby/jdbc/ engine/org/apache/derby/loc/ shared/org/apache/derby/shared/common/reference/ testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/

Author: kristwaa
Date: Wed Feb 13 04:26:40 2008
New Revision: 627380

URL: http://svn.apache.org/viewvc?rev=627380&view=rev
Log:
DERBY-3325: Add 'maxStatements' property to ClientConnectionPoolDataSource.
The patch adds the maxStatements property, but it will not have any effect before DERBY-3329 has been committed.
Adjusted the DataSourceReferenceTest to account for the new property, and added a simple test that tests that the property is handled correctly in the data source.
Patch file: derby-3325-1b-maxStatements.diff

Added:
    db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/ClientConnectionPoolDataSourceTest.java   (with props)
Modified:
    db/derby/code/trunk/java/client/org/apache/derby/jdbc/ClientBaseDataSource.java
    db/derby/code/trunk/java/client/org/apache/derby/jdbc/ClientConnectionPoolDataSource.java
    db/derby/code/trunk/java/engine/org/apache/derby/loc/messages.xml
    db/derby/code/trunk/java/shared/org/apache/derby/shared/common/reference/MessageId.java
    db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/DataSourceReferenceTest.java

Modified: db/derby/code/trunk/java/client/org/apache/derby/jdbc/ClientBaseDataSource.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/client/org/apache/derby/jdbc/ClientBaseDataSource.java?rev=627380&r1=627379&r2=627380&view=diff
==============================================================================
--- db/derby/code/trunk/java/client/org/apache/derby/jdbc/ClientBaseDataSource.java (original)
+++ db/derby/code/trunk/java/client/org/apache/derby/jdbc/ClientBaseDataSource.java Wed Feb 13 04:26:40 2008
@@ -1056,6 +1056,24 @@
         return this.traceFileAppend;
     }
 
+    /**
+     * Returns the maximum number of JDBC prepared statements a connection is
+     * allowed to cache.
+     * <p>
+     * A basic data source will always return zero. If statement caching is
+     * required, use a {@link javax.sql.ConnectionPoolDataSource}.
+     * <p>
+     * This method is used internally by Derby to determine if statement
+     * pooling is to be enabled or not.
+     *
+     * @return Maximum number of statements to cache, or <code>0</code> if
+     *      caching is disabled (default).
+     *
+     * @see ClientConnectionPoolDataSource
+     */
+    public int maxStatementsToPool() {
+        return 0;
+    }
 
     // --- private helper methods
 

Modified: db/derby/code/trunk/java/client/org/apache/derby/jdbc/ClientConnectionPoolDataSource.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/client/org/apache/derby/jdbc/ClientConnectionPoolDataSource.java?rev=627380&r1=627379&r2=627380&view=diff
==============================================================================
--- db/derby/code/trunk/java/client/org/apache/derby/jdbc/ClientConnectionPoolDataSource.java (original)
+++ db/derby/code/trunk/java/client/org/apache/derby/jdbc/ClientConnectionPoolDataSource.java Wed Feb 13 04:26:40 2008
@@ -21,12 +21,15 @@
 
 package org.apache.derby.jdbc;
 
+import java.io.IOException;
+import java.io.ObjectInputStream;
 import java.sql.SQLException;
 import javax.sql.ConnectionPoolDataSource;
-import javax.sql.DataSource;
 import javax.sql.PooledConnection;
 import org.apache.derby.client.am.LogWriter;
 import org.apache.derby.client.am.SqlException;
+import org.apache.derby.shared.common.i18n.MessageUtil;
+import org.apache.derby.shared.common.reference.MessageId;
 
 /**
  * ClientConnectionPoolDataSource is a factory for PooledConnection objects.
@@ -44,8 +47,22 @@
 public class ClientConnectionPoolDataSource extends ClientDataSource 
                                            implements ConnectionPoolDataSource {
     private static final long serialVersionUID = -539234282156481377L;
+    /** Message utility used to obtain localized messages. */
+    private static final MessageUtil msgUtil =
+            new MessageUtil("org.apache.derby.loc.clientmessages");
     public static final String className__ = "org.apache.derby.jdbc.ClientConnectionPoolDataSource";
 
+    /**
+     * Specifies the maximum number of statements that can be cached per
+     * connection by the JDBC driver.
+     * <p>
+     * A value of <code>0</code> disables statement caching, negative values
+     * are not allowed. The default is that caching is disabled.
+     *
+     * @serial
+     */
+    private int maxStatements = 0;
+
     public ClientConnectionPoolDataSource() {
         super();
     }
@@ -100,4 +117,73 @@
             return ClientDriver.getFactory().newClientPooledConnection(ds,
                     dncLogWriter, user, password);
     }   
+
+    /**
+     * Specifies the maximum size of the statement cache.
+     *
+     * @param maxStatements maximum number of cached statements
+     *
+     * @throws IllegalArgumentException if <code>maxStatements</code> is
+     *      negative
+     */
+    public void setMaxStatements(int maxStatements) {
+        // Disallow negative values.
+        if (maxStatements < 0) {
+            throw new IllegalArgumentException(msgUtil.getTextMessage(
+                    MessageId.CONN_NEGATIVE_MAXSTATEMENTS,
+                    new Integer(maxStatements)));
+        }
+        this.maxStatements = maxStatements;
+    }
+
+    /**
+     * Returns the maximum number of JDBC prepared statements a connection is
+     * allowed to cache.
+     *
+     * @return Maximum number of statements to cache, or <code>0</code> if
+     *      caching is disabled (default).
+     */
+    public int getMaxStatements() {
+        return this.maxStatements;
+    }
+
+    /**
+     * Internally used method.
+     *
+     * @see ClientBaseDataSource#maxStatementsToPool
+     */
+    public int maxStatementsToPool() {
+        return this.maxStatements;
+    }
+
+    /**
+     * Make sure the state of the de-serialized object is valid.
+     */
+    private final void validateState() {
+        // Make sure maxStatements is zero or higher.
+        if (maxStatements < 0) {
+            throw new IllegalArgumentException(msgUtil.getTextMessage(
+                    MessageId.CONN_NEGATIVE_MAXSTATEMENTS,
+                    new Integer(maxStatements)));
+        }
+    }
+
+    /**
+     * Read an object from the ObjectInputStream.
+     * <p>
+     * This implementation differs from the default one by initiating state
+     * validation of the object created.
+     *
+     * @param inputStream data stream to read objects from
+     * @throws ClassNotFoundException if instantiating a class fails
+     * @throws IOException if reading from the stream fails
+     */
+    private void readObject(ObjectInputStream inputStream)
+            throws ClassNotFoundException, IOException {
+     // Always perform the default de-serialization first
+     inputStream.defaultReadObject();
+
+     // Ensure that object state has not been corrupted or tampered with.
+     validateState();
+  }
 }

Modified: db/derby/code/trunk/java/engine/org/apache/derby/loc/messages.xml
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/engine/org/apache/derby/loc/messages.xml?rev=627380&r1=627379&r2=627380&view=diff
==============================================================================
--- db/derby/code/trunk/java/engine/org/apache/derby/loc/messages.xml (original)
+++ db/derby/code/trunk/java/engine/org/apache/derby/loc/messages.xml Wed Feb 13 04:26:40 2008
@@ -7459,6 +7459,12 @@
                 <text>The user's password for the connection</text>
             </msg>
 
+            <msg>
+                <name>J134</name>
+                <text>Negative values for the maxStatements property are not allowed: {0}</text>
+                <arg>maxStatements</arg>
+            </msg>
+
         </family>
 
 

Modified: db/derby/code/trunk/java/shared/org/apache/derby/shared/common/reference/MessageId.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/shared/org/apache/derby/shared/common/reference/MessageId.java?rev=627380&r1=627379&r2=627380&view=diff
==============================================================================
--- db/derby/code/trunk/java/shared/org/apache/derby/shared/common/reference/MessageId.java (original)
+++ db/derby/code/trunk/java/shared/org/apache/derby/shared/common/reference/MessageId.java Wed Feb 13 04:26:40 2008
@@ -147,6 +147,11 @@
     String CONN_DRDA_DATASTREAM_SYNTAX_ERROR                = "J131";
     String CONN_USERNAME_DESCRIPTION                        = "J132";
     String CONN_PASSWORD_DESCRIPTION                        = "J133";
+    /**
+     * Error message for negative values for the maxStatements property
+     * of data sources supporting statement pooling.
+     */
+    String CONN_NEGATIVE_MAXSTATEMENTS                      = "J134";
 
 	/*
 	** Authentication

Added: db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/ClientConnectionPoolDataSourceTest.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/ClientConnectionPoolDataSourceTest.java?rev=627380&view=auto
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/ClientConnectionPoolDataSourceTest.java (added)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/ClientConnectionPoolDataSourceTest.java Wed Feb 13 04:26:40 2008
@@ -0,0 +1,158 @@
+/*
+
+   Derby - Class org.apache.derbyTesting.functionTests.tests.jdbcapi.ClientConnectionPoolDataSourceTest
+
+   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.functionTests.tests.jdbcapi;
+
+import java.sql.Connection;
+import java.sql.PreparedStatement;
+import java.sql.ResultSet;
+import java.sql.SQLException;
+import java.sql.Statement;
+
+import javax.sql.PooledConnection;
+
+import junit.framework.Test;
+
+import org.apache.derby.jdbc.ClientConnectionPoolDataSource;
+import org.apache.derbyTesting.junit.BaseJDBCTestCase;
+import org.apache.derbyTesting.junit.J2EEDataSource;
+import org.apache.derbyTesting.junit.JDBC;
+import org.apache.derbyTesting.junit.TestConfiguration;
+
+/**
+ * Basic tests of the <code>ConnectionPoolDataSource</code> in the client
+ * driver.
+ */
+public class ClientConnectionPoolDataSourceTest
+    extends BaseJDBCTestCase {
+
+    public ClientConnectionPoolDataSourceTest(String name) {
+        super(name);
+    }
+
+    /**
+     * Verify that handling of the <code>maxStatements</code> property is
+     * working.
+     */
+    public void testMaxStatementsProperty() {
+        ClientConnectionPoolDataSource cDs =
+                new ClientConnectionPoolDataSource();
+        // Check the default value.
+        assertEquals("Unexpected default value", 0, cDs.getMaxStatements());
+        cDs.setMaxStatements(25);
+        // Verify that the new value has been set.
+        assertEquals("New value not set", 25, cDs.getMaxStatements());
+        // Try a negative value
+        try {
+            cDs.setMaxStatements(-99);
+            fail("Negative values should not be allowed: " +
+                    cDs.getMaxStatements());
+        } catch (IllegalArgumentException iae) {
+            // As expected, continue the test.
+        }
+        // Try setting it to zero to disable statement pooling.
+        cDs.setMaxStatements(0);
+        assertEquals("New value not set", 0, cDs.getMaxStatements());
+    }
+
+    /**
+     * Tests basic connectivity when connection is obtained from a connection
+     * pool data source without statement pooling.
+     *
+     * @throws SQLException if database operations fail
+     */
+    public void testGetConnectionNoStatementPooling()
+            throws SQLException {
+        ClientConnectionPoolDataSource cDs = (ClientConnectionPoolDataSource)
+                J2EEDataSource.getConnectionPoolDataSource();
+        // Make sure statement pooling is disabled.
+        cDs.setMaxStatements(0);
+        assertEquals(0, cDs.getMaxStatements());
+        verifyConnection(cDs);
+    }
+
+    /**
+     * Tests basic connectivity when connection is obtained from a connection
+     * pool data source with statement pooling enabled.
+     *
+     * @throws SQLException if database operations fail
+     */
+    public void testGetConnectionWithStatementPooling()
+            throws SQLException {
+        ClientConnectionPoolDataSource cDs = (ClientConnectionPoolDataSource)
+                J2EEDataSource.getConnectionPoolDataSource();
+        // Enable statement pooling.
+        cDs.setMaxStatements(27);
+        assertTrue(cDs.getMaxStatements() > 0);
+        verifyConnection(cDs);
+    }
+
+    /**
+     * Do some basic verification on a connection obtained from the data source.
+     *
+     * @param cDs data source to get connection from
+     * @throws SQLException if a JDBC operation fails
+     */
+    private void verifyConnection(ClientConnectionPoolDataSource cDs)
+            throws SQLException {
+        PooledConnection pc = null;
+        // Workaround for "bug" in the JUnit framework, where data source
+        // connections do not create the database if it does not exist.
+        // See DERBY-3306 for more information.
+        try {
+            pc = cDs.getPooledConnection();
+        } catch (SQLException sqle) {
+            assertSQLState("08004", sqle);
+            getConnection();
+            pc = cDs.getPooledConnection();
+        }
+        // Get a connection and make sure we can access the database.
+        Connection con = pc.getConnection();
+        Statement stmt = con.createStatement();
+        ResultSet rs = stmt.executeQuery("select * from sys.systables");
+        JDBC.assertDrainResultsHasData(rs);
+        PreparedStatement ps1 = con.prepareStatement("values 31");
+        JDBC.assertSingleValueResultSet(ps1.executeQuery(), "31");
+        ps1.close();
+        PreparedStatement ps2 = con.prepareStatement("values 31");
+        // The physical statement is supposed to be the same, but not the
+        // logical prepared statements (if pooling is used).
+        assertNotSame(ps1, ps2);
+        JDBC.assertSingleValueResultSet(ps2.executeQuery(), "31");
+        // Close everything
+        stmt.close();
+        ps2.close();
+        con.close();
+        pc.close();
+    }
+
+    /**
+     * Returns a suite that will run only in the client-server configuration.
+     *
+     * @return A client-server suite with all the tests.
+     */
+    public static Test suite() {
+        // The tests are run in the client-server configuration only, because
+        // the code being tests does not exist in the embedded driver.
+        return TestConfiguration.clientServerSuite(
+                ClientConnectionPoolDataSourceTest.class);
+    }
+}

Propchange: db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/ClientConnectionPoolDataSourceTest.java
------------------------------------------------------------------------------
    svn:eol-style = native

Modified: db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/DataSourceReferenceTest.java
URL: http://svn.apache.org/viewvc/db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/DataSourceReferenceTest.java?rev=627380&r1=627379&r2=627380&view=diff
==============================================================================
--- db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/DataSourceReferenceTest.java (original)
+++ db/derby/code/trunk/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/DataSourceReferenceTest.java Wed Feb 13 04:26:40 2008
@@ -118,6 +118,14 @@
         BASE_CLIENT_DS.addProperty("traceDirectory", "XX_traceDirectory_1476");
     }
 
+    /** Descriptor for the client connection pool data source. */
+    private static final DataSourceDescriptor POOL_CLIENT_DS =
+            new DataSourceDescriptor("Connection pool client data source",
+                                     BASE_CLIENT_DS);
+
+    static {
+        POOL_CLIENT_DS.addProperty("maxStatements", "10", "0");
+    }
 
     /**
      * Creates a new fixture.
@@ -171,7 +179,7 @@
             // Specify client data source descriptors.
             descriptors = new DataSourceDescriptor[] {
                 BASE_CLIENT_DS, // Base
-                BASE_CLIENT_DS,   // Pool
+                POOL_CLIENT_DS, // Pool
                 BASE_CLIENT_DS  // XA
             };
         } else {