Adding JMCR-Stable version
[Benchmarks_CSolver.git] / JMCR-Stable / real-world application / derby-10.3.2.1 / java / engine / org / apache / derby / jdbc / EmbeddedDataSource.java
diff --git a/JMCR-Stable/real-world application/derby-10.3.2.1/java/engine/org/apache/derby/jdbc/EmbeddedDataSource.java b/JMCR-Stable/real-world application/derby-10.3.2.1/java/engine/org/apache/derby/jdbc/EmbeddedDataSource.java
new file mode 100644 (file)
index 0000000..1f07b06
--- /dev/null
@@ -0,0 +1,582 @@
+/*\r
+\r
+   Derby - Class org.apache.derby.jdbc.EmbeddedDataSource\r
+\r
+   Licensed to the Apache Software Foundation (ASF) under one or more\r
+   contributor license agreements.  See the NOTICE file distributed with\r
+   this work for additional information regarding copyright ownership.\r
+   The ASF licenses this file to You under the Apache License, Version 2.0\r
+   (the "License"); you may not use this file except in compliance with\r
+   the License.  You may obtain a copy of the License at\r
+\r
+      http://www.apache.org/licenses/LICENSE-2.0\r
+\r
+   Unless required by applicable law or agreed to in writing, software\r
+   distributed under the License is distributed on an "AS IS" BASIS,\r
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r
+   See the License for the specific language governing permissions and\r
+   limitations under the License.\r
+\r
+ */\r
+\r
+package org.apache.derby.jdbc;\r
+\r
+import org.apache.derby.iapi.reference.Attribute;\r
+\r
+import java.sql.Connection;\r
+import java.sql.DriverManager;\r
+import java.sql.SQLException;\r
+import java.sql.SQLFeatureNotSupportedException;\r
+import java.io.PrintWriter;\r
+import java.util.Hashtable;\r
+import java.util.Properties;\r
+\r
+import java.util.logging.Logger;\r
+\r
+/* -- New jdbc 20 extension types --- */\r
+import javax.naming.Context;\r
+import javax.naming.Name;\r
+import javax.sql.DataSource;\r
+\r
+\r
+\r
+import org.apache.derby.iapi.reference.Attribute;\r
+import org.apache.derby.iapi.reference.MessageId;\r
+import org.apache.derby.iapi.reference.SQLState;\r
+import org.apache.derby.iapi.error.ExceptionSeverity;\r
+import org.apache.derby.iapi.services.i18n.MessageService;\r
+import org.apache.derby.impl.jdbc.Util;\r
+\r
+/** \r
+       \r
+\r
+       EmbeddedDataSource is Derby's DataSource implementation for JDBC3.0.\r
+       \r
+\r
+       <P>A DataSource  is a factory for Connection objects. An object that\r
+       implements the DataSource interface will typically be registered with a\r
+       JNDI service provider.\r
+       <P>\r
+       EmbeddedDataSource automatically supports the correct JDBC specification version\r
+       for the Java Virtual Machine's environment.\r
+       <UL>\r
+       <LI> JDBC 3.0 - Java 2 - JDK 1.4, J2SE 5.0\r
+       </UL>\r
+\r
+       <P>The following is a list of properties that can be set on a Derby\r
+       DataSource object:\r
+       <P><B>Standard DataSource properties</B> (from JDBC 3.0 specification).\r
+\r
+       <UL><LI><B><code>databaseName</code></B> (String): <I>Mandatory</I>\r
+       <BR>This property must be set and it\r
+       identifies which database to access.  If a database named wombat located at\r
+       g:/db/wombat is to be accessed, then one should call\r
+       <code>setDatabaseName("g:/db/wombat")</code> on the data source object.</LI>\r
+\r
+       <LI><B><code>dataSourceName</code></B> (String): <I>Optional</I>\r
+       <BR> Name for DataSource.  Not used by the data source object.  Used for\r
+       informational purpose only.</LI>\r
+\r
+       <LI><B><code>description</code></B> (String): <I>Optional</I>\r
+       <BR>Description of the data source.  Not\r
+       used by the data source object.  Used for informational purpose only.</LI> \r
+\r
+       <LI><B><code>password</code></B> (String): <I>Optional</I>\r
+       <BR>Database password for the no argument <code>DataSource.getConnection()</code>,\r
+       <code>ConnectionPoolDataSource.getPooledConnection()</code>\r
+       and <code>XADataSource.getXAConnection()</code> methods.\r
+\r
+       <LI><B><code>user</code></B> (String): <I>Optional</I>\r
+       <BR>Database user for the no argument <code>DataSource.getConnection()</code>,\r
+       <code>ConnectionPoolDataSource.getPooledConnection()</code>\r
+       and <code>XADataSource.getXAConnection()</code> methods.\r
+       </UL>\r
+\r
+       <BR><B>Derby specific DataSource properties.</B>\r
+\r
+  <UL>\r
+\r
+  <LI><B><code>attributesAsPassword</code></B> (Boolean): <I>Optional</I>\r
+       <BR>If true, treat the password value in a\r
+       <code>DataSource.getConnection(String user, String password)</code>,\r
+       <code>ConnectionPoolDataSource.getPooledConnection(String user, String password)</code>\r
+       or <code>XADataSource.getXAConnection(String user, String password)</code> as a set\r
+       of connection attributes. The format of the attributes is the same as the format\r
+       of the attributes in the property connectionAttributes. If false the password value\r
+       is treated normally as the password for the given user.\r
+       Setting this property to true allows a connection request from an application to\r
+       provide more authentication information that just a password, for example the request\r
+       can include the user's password and an encrypted database's boot password.</LI>\r
+\r
+  <LI><B><code>connectionAttributes</code></B> (String): <I>Optional</I>\r
+  <BR>Defines a set of Derby connection attributes for use in all connection requests.\r
+  The format of the String matches the format of the connection attributes in a Derby JDBC URL.\r
+  That is a list of attributes in the form <code><I>attribute</I>=<I>value</I></code>, each separated by semi-colon (';').\r
+  E.g. <code>setConnectionAttributes("bootPassword=erd3234dggd3kazkj3000");</code>.\r
+  <BR>The database name must be set by the DataSource property <code>databaseName</code> and not by setting the <code>databaseName</code>\r
+  connection attribute in the <code>connectionAttributes</code> property.\r
+       <BR>\r
+   Any attributes that can be set using a property of this DataSource implementation\r
+   (e.g user, password) should not be set in connectionAttributes. Conflicting\r
+   settings in connectionAttributes and properties of the DataSource will lead to\r
+   unexpected behaviour. \r
+  <BR>Please see the Derby documentation for a complete list of connection attributes. </LI>\r
+\r
+  <LI><B><code>createDatabase</code></B> (String): <I>Optional</I>\r
+       <BR>If set to the string "create", this will\r
+       cause a new database of <code>databaseName</code> if that database does not already\r
+       exist.  The database is created when a connection object is obtained from\r
+       the data source. </LI> \r
+\r
+       <LI><B><code>shutdownDatabase</code></B> (String): <I>Optional</I>\r
+       <BR>If set to the string "shutdown",\r
+       this will cause the database to shutdown when a java.sql.Connection object\r
+       is obtained from the data source.  E.g., If the data source is an\r
+       XADataSource, a getXAConnection().getConnection() is necessary to cause the\r
+       database to shutdown.\r
+\r
+       </UL>\r
+\r
+       <P><B>Examples.</B>\r
+\r
+       <P>This is an example of setting a property directly using Derby's\r
+       EmbeddedDataSource object.  This code is typically written by a system integrator :\r
+       <PRE> \r
+       *\r
+       * import org.apache.derby.jdbc.*;\r
+       *\r
+       * // dbname is the database name\r
+       * // if create is true, create the database if necessary\r
+       * javax.sql.DataSource makeDataSource (String dbname, boolean create)\r
+       *       throws Throwable \r
+       * { \r
+       *       EmbeddedDataSource ds = new EmbeddedDataSource(); \r
+       *       ds.setDatabaseName(dbname);\r
+       *\r
+       *       if (create)\r
+       *               ds.setCreateDatabase("create");\r
+    *   \r
+       *       return ds;\r
+       * }\r
+       </PRE>\r
+\r
+       <P>Example of setting properties thru reflection.  This code is typically\r
+       generated by tools or written by a system integrator: <PRE>\r
+       *       \r
+       * javax.sql.DataSource makeDataSource(String dbname) \r
+       *       throws Throwable \r
+       * {\r
+       *       Class[] parameter = new Class[1];\r
+       *       parameter[0] = dbname.getClass();\r
+       *       DataSource ds =  new EmbeddedDataSource();\r
+       *       Class cl = ds.getClass();\r
+       *\r
+       *       Method setName = cl.getMethod("setDatabaseName", parameter);\r
+       *       Object[] arg = new Object[1];\r
+       *       arg[0] = dbname;\r
+       *       setName.invoke(ds, arg);\r
+       *\r
+       *       return ds;\r
+       * }\r
+       </PRE>\r
+\r
+       <P>Example on how to register a data source object with a JNDI naming\r
+       service.\r
+       <PRE>\r
+       * DataSource ds = makeDataSource("mydb");\r
+       * Context ctx = new InitialContext();\r
+       * ctx.bind("jdbc/MyDB", ds);\r
+       </PRE>\r
+\r
+       <P>Example on how to retrieve a data source object from a JNDI naming\r
+       service. \r
+       <PRE>\r
+       * Context ctx = new InitialContext();\r
+       * DataSource ds = (DataSource)ctx.lookup("jdbc/MyDB");\r
+       </PRE>\r
+\r
+*/\r
+public class EmbeddedDataSource extends ReferenceableDataSource implements\r
+                               javax.sql.DataSource\r
+{\r
+\r
+       private static final long serialVersionUID = -4945135214995641181L;\r
+\r
+       /** instance variables that will be serialized */\r
+\r
+       /**\r
+        * The database name.\r
+        * @serial\r
+        */\r
+       private String databaseName;\r
+\r
+       /**\r
+        * The data source name.\r
+        * @serial\r
+        */\r
+       private String dataSourceName;\r
+\r
+       /**\r
+        * Description of the database.\r
+        * @serial\r
+        */\r
+       private String description;\r
+\r
+       /**\r
+        * Set to "create" if the database should be created.\r
+        * @serial\r
+        */\r
+       private String createDatabase;\r
+\r
+       /**\r
+        * Set to "shutdown" if the database should be shutdown.\r
+        * @serial\r
+        */\r
+       private String shutdownDatabase;\r
+\r
+       /**\r
+        * Derby specific connection attributes.\r
+        * @serial\r
+        */\r
+       private String connectionAttributes;\r
+\r
+       /**\r
+               Set password to be a set of connection attributes.\r
+       */\r
+       private boolean attributesAsPassword;\r
+\r
+       /** instance variables that will not be serialized */\r
+       transient private PrintWriter printer;\r
+       transient private int loginTimeout;\r
+\r
+       // Unlike a DataSource, LocalDriver is shared by all\r
+       // Derby databases in the same jvm.\r
+       transient InternalDriver driver;\r
+\r
+       transient private String jdbcurl;\r
+\r
+       /**\r
+               No-arg constructor.\r
+        */\r
+       public EmbeddedDataSource() {\r
+               // needed by Object Factory\r
+\r
+               // don't put anything in here or in any of the set method because this\r
+               // object may be materialized in a remote machine and then sent thru\r
+               // the net to the machine where it will be used.\r
+       }\r
+\r
+\r
+  //Most of our customers would be using jndi to get the data\r
+  //sources. Since we don't have a jndi to test this, we are\r
+  //adding this method to fake it. This is getting used in\r
+  //xaJNDI test so we can compare the 2 data sources.\r
+       public boolean equals(Object p0) {\r
+    if (p0 instanceof EmbeddedDataSource) {\r
+      EmbeddedDataSource ds = (EmbeddedDataSource)p0;\r
+\r
+      boolean match = true;\r
+      \r
+                       if (databaseName != null) {\r
+        if  (!(databaseName.equals(ds.databaseName)))\r
+                                       match = false;\r
+                       } else if (ds.databaseName != null)\r
+        match = false;\r
+\r
+                       if (dataSourceName != null) {\r
+        if  (!(dataSourceName.equals(ds.dataSourceName)))\r
+                                       match = false;\r
+                       } else if (ds.dataSourceName != null)\r
+        match = false;\r
+\r
+                       if (description != null) {\r
+        if  (!(description.equals(ds.description)))\r
+                                       match = false;\r
+                       } else if (ds.description != null)\r
+        match = false;\r
+\r
+                       if (createDatabase != null) {\r
+        if  (!(createDatabase.equals(ds.createDatabase)))\r
+                                       match = false;\r
+                       } else if (ds.createDatabase != null)\r
+        match = false;\r
+\r
+                       if (shutdownDatabase != null) {\r
+        if  (!(shutdownDatabase.equals(ds.shutdownDatabase)))\r
+                                       match = false;\r
+                       } else if (ds.shutdownDatabase != null)\r
+        match = false;\r
+\r
+                       if (connectionAttributes != null) {\r
+        if  (!(connectionAttributes.equals(ds.connectionAttributes)))\r
+                                       match = false;\r
+                       } else if (ds.connectionAttributes != null)\r
+        match = false;\r
+\r
+      if (loginTimeout != ds.loginTimeout)\r
+        match = false;\r
+\r
+      return match;\r
+\r
+    }\r
+\r
+    return false;\r
+       }\r
+\r
+       /*\r
+        * Properties to be seen by Bean - access thru reflection.\r
+        */\r
+\r
+       /**\r
+               Set this property to create a new database.  If this\r
+               property is not set, the database (identified by databaseName) is\r
+               assumed to be already existing.\r
+\r
+               @param create if set to the string "create", this data source will try\r
+               to create a new database of databaseName, or boot the database if one\r
+               by that name already exists.\r
+        */\r
+       public final void setCreateDatabase(String create) {\r
+               if (create != null && create.toLowerCase(java.util.Locale.ENGLISH).equals("create"))\r
+                       createDatabase = create;\r
+               else\r
+                       createDatabase = null;\r
+       }\r
+       /** @return "create" if create is set, or null if not */\r
+       public final String getCreateDatabase() {\r
+               return createDatabase;\r
+       }\r
+\r
+\r
+       /**\r
+               Set this property if one wishes to shutdown the database identified by\r
+               databaseName. \r
+\r
+               @param shutdown if set to the string "shutdown", this data source will \r
+               shutdown the database if it is running.\r
+        */\r
+       public final void setShutdownDatabase(String shutdown) {\r
+               if (shutdown != null && shutdown.equalsIgnoreCase("shutdown"))\r
+                       shutdownDatabase = shutdown;\r
+               else\r
+                       shutdownDatabase = null;\r
+       }\r
+       /** @return "shutdown" if shutdown is set, or null if not */\r
+       public final String getShutdownDatabase() {\r
+               return shutdownDatabase;\r
+       }\r
+\r
+       /**\r
+               Set this property to pass in more Derby specific\r
+               connection URL attributes.\r
+               <BR>\r
+       Any attributes that can be set using a property of this DataSource implementation\r
+       (e.g user, password) should not be set in connectionAttributes. Conflicting\r
+       settings in connectionAttributes and properties of the DataSource will lead to\r
+       unexpected behaviour. \r
+\r
+               @param prop set to the list of Derby connection\r
+               attributes separated by semi-colons.   E.g., to specify an encryption\r
+               bootPassword of "x8hhk2adf", and set upgrade to true, do the following: \r
+               <PRE>\r
+                       ds.setConnectionAttributes("bootPassword=x8hhk2adf;upgrade=true");\r
+               </PRE>\r
+               See the Derby documentation for complete list.\r
+        */\r
+       public final void setConnectionAttributes(String prop) {\r
+                connectionAttributes = prop;\r
+                update();\r
+       }\r
+       /** @return Derby specific connection URL attributes */\r
+       public final String getConnectionAttributes() {\r
+               return connectionAttributes;\r
+       }\r
+\r
+\r
+       /**\r
+               Set attributeAsPassword property to enable passing connection request attributes in the password argument of getConnection.\r
+               If the property is set to true then the password argument of the DataSource.getConnection(String user, String password)\r
+               method call is taken to be a list of connection attributes with the same format as the connectionAttributes property.\r
+\r
+               @param attributesAsPassword true to encode password argument as a set of connection attributes in a connection request.\r
+       */\r
+       public final void setAttributesAsPassword(boolean attributesAsPassword) {\r
+               this.attributesAsPassword = attributesAsPassword;\r
+                update();\r
+       }\r
+\r
+       /**\r
+               Return the value of the attributesAsPassword property.\r
+       */\r
+       public final boolean getAttributesAsPassword() {\r
+               return attributesAsPassword;\r
+       }\r
+\r
+       /*\r
+        * DataSource methods \r
+        */\r
+\r
+\r
+       /**\r
+        * Attempt to establish a database connection.\r
+        *\r
+        * @return  a Connection to the database\r
+        * @exception SQLException if a database-access error occurs.\r
+        */\r
+       public final Connection getConnection() throws SQLException\r
+       {\r
+               return this.getConnection(getUser(), getPassword(), false);\r
+       }\r
+\r
+       /**\r
+        * Attempt to establish a database connection with the given username and password.\r
+          If the attributeAsPassword property is set to true then the password argument is taken to be a list of\r
+          connection attributes with the same format as the connectionAttributes property.\r
+\r
+        *\r
+        * @param username the database user on whose behalf the Connection is \r
+        *  being made\r
+        * @param password the user's password\r
+        * @return  a Connection to the database\r
+        * @exception SQLException if a database-access error occurs.\r
+        */\r
+       public final Connection getConnection(String username, String password) \r
+                throws SQLException\r
+       {\r
+               return this.getConnection(username, password, true);\r
+       }\r
+\r
+       /**\r
+               @param  requestPassword true if the password came from the getConnection() call.\r
+       */\r
+       final Connection getConnection(String username, String password, boolean requestPassword)\r
+               throws SQLException {\r
+\r
+               Properties info = new Properties();\r
+               if (username != null)\r
+                       info.put(Attribute.USERNAME_ATTR, username);\r
+\r
+               if (!requestPassword || !attributesAsPassword)\r
+               {\r
+                       if (password != null)\r
+                               info.put(Attribute.PASSWORD_ATTR, password);\r
+               }\r
+\r
+               if (createDatabase != null)\r
+                       info.put(Attribute.CREATE_ATTR, "true");\r
+               if (shutdownDatabase != null)\r
+                       info.put(Attribute.SHUTDOWN_ATTR, "true");\r
+\r
+               String url = jdbcurl;\r
+\r
+               if (attributesAsPassword && requestPassword && password != null) {\r
+\r
+\r
+                       StringBuffer sb = new StringBuffer(url.length() + password.length() + 1);\r
+\r
+                       sb.append(url);\r
+                       sb.append(';');\r
+                       sb.append(password); // these are now request attributes on the URL\r
+\r
+                       url = sb.toString();\r
+\r
+               }\r
+               Connection conn =  findDriver().connect(url, info);\r
+\r
+       // JDBC driver's getConnection method returns null if\r
+       // the driver does not handle the request's URL.\r
+        if (conn == null)\r
+           throw Util.generateCsSQLException(SQLState.PROPERTY_INVALID_VALUE,Attribute.DBNAME_ATTR,getDatabaseName());\r
+\r
+        return conn;\r
+       }\r
+   \r
+       InternalDriver findDriver() throws SQLException\r
+       {\r
+               String url = jdbcurl;\r
+\r
+               if (driver == null || !driver.acceptsURL(url))\r
+               {\r
+                       synchronized(this)\r
+                       {\r
+                               // The driver has either never been booted, or it has been\r
+                               // shutdown by a 'jdbc:derby:;shutdown=true'\r
+                               if (driver == null || !driver.acceptsURL(url))\r
+                               {\r
+\r
+                                       new org.apache.derby.jdbc.EmbeddedDriver();\r
+\r
+                                       // If we know the driver, we loaded it.   Otherwise only\r
+                                       // work if DriverManager has already loaded it.\r
+\r
+                                       AutoloadedDriver        autoloadedDriver =\r
+                                               (AutoloadedDriver) DriverManager.getDriver(url);\r
+                                       driver = (InternalDriver) autoloadedDriver.getDriverModule();\r
+                                       // DriverManager will throw an exception if it cannot find the driver\r
+                               }\r
+                       }\r
+               }\r
+               return driver;\r
+               // else driver != null and driver can accept url\r
+       }\r
+\r
+       void update()\r
+       {\r
+               StringBuffer sb = new StringBuffer(64);\r
+\r
+               sb.append(Attribute.PROTOCOL);\r
+\r
+\r
+               // Set the database name from the databaseName property\r
+               String dbName = getDatabaseName();\r
+\r
+               if (dbName != null) {\r
+                       dbName = dbName.trim();\r
+               }\r
+\r
+               if (dbName == null || dbName.length() == 0) {\r
+                       // need to put something in so that we do not allow the\r
+                       // database name to be set from the request or from the\r
+                       // connection attributes.\r
+\r
+                       // this space will selected as the database name (and trimmed to an empty string)\r
+                       // See the getDatabaseName() code in InternalDriver. Since this is a non-null\r
+                       // value, it will be selected over any databaseName connection attribute.\r
+                       dbName = " ";\r
+               }\r
+\r
+               sb.append(dbName);\r
+\r
+\r
+               String connAttrs = getConnectionAttributes();\r
+               if (connAttrs != null) {\r
+                       connAttrs = connAttrs.trim();\r
+                       if (connAttrs.length() != 0) {\r
+                               sb.append(';');\r
+                               sb.append(connectionAttributes);\r
+                       }\r
+               }\r
+\r
+               jdbcurl = sb.toString();\r
+       }\r
+\r
+\r
+       public boolean isWrapperFor(Class<?> iface) throws SQLException {\r
+               // TODO Auto-generated method stub\r
+               return false;\r
+       }\r
+\r
+\r
+       public <T> T unwrap(Class<T> iface) throws SQLException {\r
+               // TODO Auto-generated method stub\r
+               return null;\r
+       }\r
+\r
+\r
+       public Logger getParentLogger() throws SQLFeatureNotSupportedException {\r
+               // TODO Auto-generated method stub\r
+               return null;\r
+       }\r
+\r
+\r
+}\r