| /* |
| |
| |
| Derby - Class org.apache.derby.impl.tools.optional.DBMDWrapper |
| |
| 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.derby.impl.tools.optional; |
| |
| import java.lang.reflect.InvocationTargetException; |
| import java.lang.reflect.Method; |
| import java.lang.reflect.Modifier; |
| import java.sql.Connection; |
| import java.sql.DriverManager; |
| import java.sql.DatabaseMetaData; |
| import java.sql.PreparedStatement; |
| import java.sql.ResultSet; |
| import java.sql.ResultSetMetaData; |
| import java.sql.SQLException; |
| import java.sql.Types; |
| |
| import org.apache.derby.iapi.sql.dictionary.OptionalTool; |
| |
| /** |
| * <p> |
| * OptionalTool to create wrapper functions which allow you to invoke DatabaseMetaData methods |
| * via SQL. The wrapper functions slightly change the signature of the metadata |
| * methods as follows: |
| * </p> |
| * |
| * <ul> |
| * <li>Arguments of type int[] and String[] have been eliminated--they are |
| * automatically wildcarded.</li> |
| * <li>The method getRowIdLifetime() has been commented out--Derby does not |
| * support object types.</li> |
| * <li>The method getSchemas() has been |
| * commented out--it can be uncommented when the registration logic is made |
| * smarter to handle the dropping of different overloads.</li> |
| * <li>The method supportsConvert() has been |
| * commented out because Derby only allows one function by a given name and |
| * the supportsConvert( int, int ) overload is more general.</li> |
| * </ul> |
| * |
| * <p> |
| * Methods which return ResultSet are mapped to table functions. You can join |
| * the metadata table functions like this: |
| * </p> |
| * |
| * <pre> |
| * -- list all of the columns in the connected Derby database |
| * select t.table_schem, t.table_name, c.column_name, c.type_name |
| * from table( getTables( null, null, null ) ) t, |
| * table( getColumns( null, null, null, null ) ) c |
| * where c.table_schem = t.table_schem |
| * and c.table_name = t.table_name |
| * and t.table_type = 'TABLE' |
| * ; |
| * |
| * |
| * -- now list metadata in a foreign database |
| * call setDatabaseURL( 'com.mysql.jdbc.Driver', 'jdbc:mysql://localhost/world?user=root&password=' ); |
| * |
| * select t.table_schem, t.table_name, c.column_name, c.type_name |
| * from table( getTables( 'WORLD', null, null ) ) t, |
| * table( getColumns( 'WORLD', null, null, null) ) c |
| * where c.table_name = t.table_name |
| * and t.table_type = 'TABLE' |
| * ; |
| * |
| * -- release the foreign connection |
| * call setDatabaseURL( '', '' ); |
| * </pre> |
| */ |
| public class DBMDWrapper implements OptionalTool |
| { |
| /////////////////////////////////////////////////////////////////////////////////// |
| // |
| // CONSTANTS |
| // |
| /////////////////////////////////////////////////////////////////////////////////// |
| |
| private static final int DEFAULT_PRECISION = 128; |
| |
| /////////////////////////////////////////////////////////////////////////////////// |
| // |
| // STATE |
| // |
| /////////////////////////////////////////////////////////////////////////////////// |
| |
| /////////////////////////////////////////////////////////////////////////////////// |
| // |
| // CONSTRUCTOR |
| // |
| /////////////////////////////////////////////////////////////////////////////////// |
| |
| /** 0-arg constructor to satisfy the OptionalTool contract */ |
| public DBMDWrapper() {} |
| |
| /////////////////////////////////////////////////////////////////////////////////// |
| // |
| // OptionalTool BEHAVIOR |
| // |
| /////////////////////////////////////////////////////////////////////////////////// |
| |
| public void loadTool( String... configurationParameters ) |
| throws SQLException |
| { |
| register( true ); |
| } |
| |
| public void unloadTool( String... configurationParameters ) |
| throws SQLException |
| { |
| register( false ); |
| } |
| |
| /** |
| * <p> |
| * Workhorse to register or unregister all public static methods as |
| * Derby routines. |
| * </p> |
| */ |
| private void register( boolean register ) |
| throws SQLException |
| { |
| Connection conn = getDefaultConnection(); |
| |
| Method[] methods = getClass().getDeclaredMethods(); |
| int count = methods.length; |
| |
| for ( int midx = 0; midx < count; midx++ ) |
| { |
| Method method = methods[ midx ]; |
| int modifiers = method.getModifiers(); |
| |
| if ( |
| isSet( modifiers, Modifier.PUBLIC ) && |
| isSet( modifiers, Modifier.STATIC ) |
| ) |
| { |
| if ( register ) { registerFunction( conn, method ); } |
| else { unregisterFunction( conn, method ); } |
| } |
| } |
| } |
| |
| /////////////////////////////////////////////////////////////////////////////////// |
| // |
| // WRAPPER FUNCTIONS WHICH ARE REGISTERED WITH DERBY |
| // |
| /////////////////////////////////////////////////////////////////////////////////// |
| |
| public static boolean allProceduresAreCallable() throws SQLException |
| { return getDBMD().allProceduresAreCallable(); } |
| |
| public static boolean allTablesAreSelectable() throws SQLException |
| { return getDBMD().allTablesAreSelectable(); } |
| |
| public static boolean autoCommitFailureClosesAllResultSets() throws SQLException |
| { return getDBMD().autoCommitFailureClosesAllResultSets(); } |
| |
| public static boolean dataDefinitionCausesTransactionCommit() throws SQLException |
| { return getDBMD().dataDefinitionCausesTransactionCommit(); } |
| |
| public static boolean dataDefinitionIgnoredInTransactions() throws SQLException |
| { return getDBMD().dataDefinitionIgnoredInTransactions(); } |
| |
| public static boolean deletesAreDetected(int type) throws SQLException |
| { return getDBMD().deletesAreDetected( type); } |
| |
| public static boolean doesMaxRowSizeIncludeBlobs() throws SQLException |
| { return getDBMD().doesMaxRowSizeIncludeBlobs(); } |
| |
| public static ResultSet getAttributes( String catalog, String schemaPattern, String typeNamePattern, String attributeNamePattern) throws SQLException |
| { return getDBMD().getAttributes( catalog, schemaPattern, typeNamePattern, attributeNamePattern); } |
| |
| |
| public static ResultSet getBestRowIdentifier(String catalog, String schema, String table, int scope, boolean nullable ) throws SQLException |
| { return getDBMD().getBestRowIdentifier( catalog, schema, table, scope, nullable ); } |
| |
| |
| public static ResultSet getCatalogs() throws SQLException |
| { return getDBMD().getCatalogs(); } |
| |
| public static String getCatalogSeparator() throws SQLException |
| { return getDBMD().getCatalogSeparator(); } |
| |
| public static String getCatalogTerm() throws SQLException |
| { return getDBMD().getCatalogTerm(); } |
| |
| public static ResultSet getClientInfoProperties() throws SQLException |
| { return getDBMD().getClientInfoProperties(); } |
| |
| public static ResultSet getColumnPrivileges(String catalog, String schema, String table, String columnNamePattern) throws SQLException |
| { return getDBMD().getColumnPrivileges( catalog, schema, table, columnNamePattern); } |
| |
| public static ResultSet getColumns(String catalog, String schemaPattern, String tableNamePattern, String columnNamePattern) throws SQLException |
| { return getDBMD().getColumns( catalog, schemaPattern, tableNamePattern, columnNamePattern); } |
| |
| public static ResultSet getCrossReference(String parentCatalog, String parentSchema, String parentTable, String foreignCatalog, String foreignSchema, String foreignTable) throws SQLException |
| { return getDBMD().getCrossReference( parentCatalog, parentSchema, parentTable, foreignCatalog, foreignSchema, foreignTable); } |
| |
| public static int getDatabaseMajorVersion() throws SQLException |
| { return getDBMD().getDatabaseMajorVersion(); } |
| |
| public static int getDatabaseMinorVersion() throws SQLException |
| { return getDBMD().getDatabaseMinorVersion(); } |
| |
| public static String getDatabaseProductName() throws SQLException |
| { return getDBMD().getDatabaseProductName(); } |
| |
| public static String getDatabaseProductVersion() throws SQLException |
| { return getDBMD().getDatabaseProductVersion(); } |
| |
| public static int getDefaultTransactionIsolation() throws SQLException |
| { return getDBMD().getDefaultTransactionIsolation(); } |
| |
| public static int getDriverMajorVersion() throws SQLException |
| { return getDBMD().getDriverMajorVersion(); } |
| |
| public static int getDriverMinorVersion() throws SQLException |
| { return getDBMD().getDriverMinorVersion(); } |
| |
| public static String getDriverName() throws SQLException |
| { return getDBMD().getDriverName(); } |
| |
| public static String getDriverVersion() throws SQLException |
| { return getDBMD().getDriverVersion(); } |
| |
| public static ResultSet getExportedKeys(String catalog, String schema, String table) throws SQLException |
| { return getDBMD().getExportedKeys( catalog, schema, table); } |
| |
| public static String getExtraNameCharacters() throws SQLException |
| { return getDBMD().getExtraNameCharacters(); } |
| |
| public static ResultSet getFunctionColumns(String catalog, String schemaPattern, String functionNamePattern, String columnNamePattern) throws SQLException |
| { return getDBMD().getFunctionColumns( catalog, schemaPattern, functionNamePattern, columnNamePattern); } |
| |
| public static ResultSet getFunctions(String catalog, String schemaPattern, String functionNamePattern) throws SQLException |
| { return getDBMD().getFunctions( catalog, schemaPattern, functionNamePattern); } |
| |
| public static String getIdentifierQuoteString() throws SQLException |
| { return getDBMD().getIdentifierQuoteString(); } |
| |
| public static ResultSet getImportedKeys(String catalog, String schema, String table) throws SQLException |
| { return getDBMD().getImportedKeys( catalog, schema, table); } |
| |
| |
| public static ResultSet getIndexInfo(String catalog, String schema, String table, boolean unique, boolean approximate) throws SQLException |
| { return getDBMD().getIndexInfo( catalog, schema, table, unique, approximate ); } |
| |
| |
| public static int getJDBCMajorVersion() throws SQLException |
| { return getDBMD().getJDBCMajorVersion(); } |
| |
| public static int getJDBCMinorVersion() throws SQLException |
| { return getDBMD().getJDBCMinorVersion(); } |
| |
| public static int getMaxBinaryLiteralLength() throws SQLException |
| { return getDBMD().getMaxBinaryLiteralLength(); } |
| |
| public static int getMaxCatalogNameLength() throws SQLException |
| { return getDBMD().getMaxCatalogNameLength(); } |
| |
| public static int getMaxCharLiteralLength() throws SQLException |
| { return getDBMD().getMaxCharLiteralLength(); } |
| |
| public static int getMaxColumnNameLength() throws SQLException |
| { return getDBMD().getMaxColumnNameLength(); } |
| |
| public static int getMaxColumnsInGroupBy() throws SQLException |
| { return getDBMD().getMaxColumnsInGroupBy(); } |
| |
| public static int getMaxColumnsInIndex() throws SQLException |
| { return getDBMD().getMaxColumnsInIndex(); } |
| |
| public static int getMaxColumnsInOrderBy() throws SQLException |
| { return getDBMD().getMaxColumnsInOrderBy(); } |
| |
| public static int getMaxColumnsInSelect() throws SQLException |
| { return getDBMD().getMaxColumnsInSelect(); } |
| |
| public static int getMaxColumnsInTable() throws SQLException |
| { return getDBMD().getMaxColumnsInTable(); } |
| |
| public static int getMaxConnections() throws SQLException |
| { return getDBMD().getMaxConnections(); } |
| |
| public static int getMaxCursorNameLength() throws SQLException |
| { return getDBMD().getMaxCursorNameLength(); } |
| |
| public static int getMaxIndexLength() throws SQLException |
| { return getDBMD().getMaxIndexLength(); } |
| |
| public static int getMaxProcedureNameLength() throws SQLException |
| { return getDBMD().getMaxProcedureNameLength(); } |
| |
| public static int getMaxRowSize() throws SQLException |
| { return getDBMD().getMaxRowSize(); } |
| |
| public static int getMaxSchemaNameLength() throws SQLException |
| { return getDBMD().getMaxSchemaNameLength(); } |
| |
| public static int getMaxStatementLength() throws SQLException |
| { return getDBMD().getMaxStatementLength(); } |
| |
| public static int getMaxStatements() throws SQLException |
| { return getDBMD().getMaxStatements(); } |
| |
| public static int getMaxTableNameLength() throws SQLException |
| { return getDBMD().getMaxTableNameLength(); } |
| |
| public static int getMaxTablesInSelect() throws SQLException |
| { return getDBMD().getMaxTablesInSelect(); } |
| |
| public static int getMaxUserNameLength() throws SQLException |
| { return getDBMD().getMaxUserNameLength(); } |
| |
| public static String getNumericFunctions() throws SQLException |
| { return getDBMD().getNumericFunctions(); } |
| |
| public static ResultSet getPrimaryKeys(String catalog, String schema, String table) throws SQLException |
| { return getDBMD().getPrimaryKeys( catalog, schema, table); } |
| |
| public static ResultSet getProcedureColumns(String catalog, String schemaPattern, String procedureNamePattern, String columnNamePattern) throws SQLException |
| { return getDBMD().getProcedureColumns( catalog, schemaPattern, procedureNamePattern, columnNamePattern); } |
| |
| public static ResultSet getProcedures(String catalog, String schemaPattern, String procedureNamePattern) throws SQLException |
| { return getDBMD().getProcedures( catalog, schemaPattern, procedureNamePattern); } |
| |
| public static String getProcedureTerm() throws SQLException |
| { return getDBMD().getProcedureTerm(); } |
| |
| public static int getResultSetHoldability() throws SQLException |
| { return getDBMD().getResultSetHoldability(); } |
| |
| // Comment out this method because we don't support this datatype |
| //public static RowIdLifetime getRowIdLifetime() throws SQLException |
| //{ return getDBMD().getRowIdLifetime(); } |
| |
| // Comment out this method so that we don't drop the following method |
| //public static ResultSet getSchemas() throws SQLException |
| //{ return getDBMD().getSchemas(); } |
| |
| public static ResultSet getSchemas(String catalog, String schemaPattern) throws SQLException |
| { return getDBMD().getSchemas( catalog, schemaPattern); } |
| |
| public static String getSchemaTerm() throws SQLException |
| { return getDBMD().getSchemaTerm(); } |
| |
| public static String getSearchStringEscape() throws SQLException |
| { return getDBMD().getSearchStringEscape(); } |
| |
| public static String getSQLKeywords() throws SQLException |
| { return getDBMD().getSQLKeywords(); } |
| |
| public static int getSQLStateType() throws SQLException |
| { return getDBMD().getSQLStateType(); } |
| |
| public static String getStringFunctions() throws SQLException |
| { return getDBMD().getStringFunctions(); } |
| |
| public static ResultSet getSuperTables(String catalog, String schemaPattern, String tableNamePattern) throws SQLException |
| { return getDBMD().getSuperTables( catalog, schemaPattern, tableNamePattern); } |
| |
| public static ResultSet getSuperTypes(String catalog, String schemaPattern, String typeNamePattern) throws SQLException |
| { return getDBMD().getSuperTypes( catalog, schemaPattern, typeNamePattern); } |
| |
| public static String getSystemFunctions() throws SQLException |
| { return getDBMD().getSystemFunctions(); } |
| |
| public static ResultSet getTablePrivileges(String catalog, String schemaPattern, String tableNamePattern) throws SQLException |
| { return getDBMD().getTablePrivileges( catalog, schemaPattern, tableNamePattern); } |
| |
| // Needs to cast String[] to something else |
| public static ResultSet getTables(String catalog, String schemaPattern, String tableNamePattern ) throws SQLException |
| { return getDBMD().getTables( catalog, schemaPattern, tableNamePattern, (String[]) null ); } |
| |
| public static ResultSet getTableTypes() throws SQLException |
| { return getDBMD().getTableTypes(); } |
| |
| public static String getTimeDateFunctions() throws SQLException |
| { return getDBMD().getTimeDateFunctions(); } |
| |
| public static ResultSet getTypeInfo() throws SQLException |
| { return getDBMD().getTypeInfo(); } |
| |
| // Eliminated the final "int[] types" argument |
| public static ResultSet getUDTs(String catalog, String schemaPattern, String typeNamePattern) throws SQLException |
| { return getDBMD().getUDTs( catalog, schemaPattern, typeNamePattern, (int[]) null ); } |
| |
| public static String getURL() throws SQLException |
| { return getDBMD().getURL(); } |
| |
| public static String getUserName() throws SQLException |
| { return getDBMD().getUserName(); } |
| |
| public static ResultSet getVersionColumns(String catalog, String schema, String table) throws SQLException |
| { return getDBMD().getVersionColumns( catalog, schema, table); } |
| |
| public static boolean insertsAreDetected(int type) throws SQLException |
| { return getDBMD().insertsAreDetected(type); } |
| |
| public static boolean isCatalogAtStart() throws SQLException |
| { return getDBMD().isCatalogAtStart(); } |
| |
| public static boolean isReadOnly() throws SQLException |
| { return getDBMD().isReadOnly(); } |
| |
| public static boolean locatorsUpdateCopy() throws SQLException |
| { return getDBMD().locatorsUpdateCopy(); } |
| |
| public static boolean nullPlusNonNullIsNull() throws SQLException |
| { return getDBMD().nullPlusNonNullIsNull(); } |
| |
| public static boolean nullsAreSortedAtEnd() throws SQLException |
| { return getDBMD().nullsAreSortedAtEnd(); } |
| |
| public static boolean nullsAreSortedAtStart() throws SQLException |
| { return getDBMD().nullsAreSortedAtStart(); } |
| |
| public static boolean nullsAreSortedHigh() throws SQLException |
| { return getDBMD().nullsAreSortedHigh(); } |
| |
| public static boolean nullsAreSortedLow() throws SQLException |
| { return getDBMD().nullsAreSortedLow(); } |
| |
| public static boolean othersDeletesAreVisible(int type) throws SQLException |
| { return getDBMD().othersDeletesAreVisible( type); } |
| |
| public static boolean othersInsertsAreVisible(int type) throws SQLException |
| { return getDBMD().othersInsertsAreVisible(type); } |
| |
| public static boolean othersUpdatesAreVisible(int type) throws SQLException |
| { return getDBMD().othersUpdatesAreVisible( type); } |
| |
| public static boolean ownDeletesAreVisible(int type) throws SQLException |
| { return getDBMD().ownDeletesAreVisible(type); } |
| |
| public static boolean ownInsertsAreVisible(int type) throws SQLException |
| { return getDBMD().ownInsertsAreVisible(type); } |
| |
| public static boolean ownUpdatesAreVisible(int type) throws SQLException |
| { return getDBMD().ownUpdatesAreVisible(type); } |
| |
| public static boolean storesLowerCaseIdentifiers() throws SQLException |
| { return getDBMD().storesLowerCaseIdentifiers(); } |
| |
| public static boolean storesLowerCaseQuotedIdentifiers() throws SQLException |
| { return getDBMD().storesLowerCaseQuotedIdentifiers(); } |
| |
| public static boolean storesMixedCaseIdentifiers() throws SQLException |
| { return getDBMD().storesMixedCaseIdentifiers(); } |
| |
| public static boolean storesMixedCaseQuotedIdentifiers() throws SQLException |
| { return getDBMD().storesMixedCaseQuotedIdentifiers(); } |
| |
| public static boolean storesUpperCaseIdentifiers() throws SQLException |
| { return getDBMD().storesUpperCaseIdentifiers(); } |
| |
| public static boolean storesUpperCaseQuotedIdentifiers() throws SQLException |
| { return getDBMD().storesUpperCaseQuotedIdentifiers(); } |
| |
| public static boolean supportsAlterTableWithAddColumn() throws SQLException |
| { return getDBMD().supportsAlterTableWithAddColumn(); } |
| |
| public static boolean supportsAlterTableWithDropColumn() throws SQLException |
| { return getDBMD().supportsAlterTableWithDropColumn(); } |
| |
| public static boolean supportsANSI92EntryLevelSQL() throws SQLException |
| { return getDBMD().supportsANSI92EntryLevelSQL(); } |
| |
| public static boolean supportsANSI92FullSQL() throws SQLException |
| { return getDBMD().supportsANSI92FullSQL(); } |
| |
| public static boolean supportsANSI92IntermediateSQL() throws SQLException |
| { return getDBMD().supportsANSI92IntermediateSQL(); } |
| |
| public static boolean supportsBatchUpdates() throws SQLException |
| { return getDBMD().supportsBatchUpdates(); } |
| |
| public static boolean supportsCatalogsInDataManipulation() throws SQLException |
| { return getDBMD().supportsCatalogsInDataManipulation(); } |
| |
| public static boolean supportsCatalogsInIndexDefinitions() throws SQLException |
| { return getDBMD().supportsCatalogsInIndexDefinitions(); } |
| |
| public static boolean supportsCatalogsInPrivilegeDefinitions() throws SQLException |
| { return getDBMD().supportsCatalogsInPrivilegeDefinitions(); } |
| |
| public static boolean supportsCatalogsInProcedureCalls() throws SQLException |
| { return getDBMD().supportsCatalogsInProcedureCalls(); } |
| |
| public static boolean supportsCatalogsInTableDefinitions() throws SQLException |
| { return getDBMD().supportsCatalogsInTableDefinitions(); } |
| |
| public static boolean supportsColumnAliasing() throws SQLException |
| { return getDBMD().supportsColumnAliasing(); } |
| |
| // Comment this out in favor of the more general overload which follows. |
| // Derby only allows one function by a given name in a given schema. |
| //public static boolean supportsConvert() throws SQLException |
| //{ return getDBMD().supportsConvert(); } |
| |
| public static boolean supportsConvert(int fromType, int toType) throws SQLException |
| { return getDBMD().supportsConvert( fromType, toType); } |
| |
| public static boolean supportsCoreSQLGrammar() throws SQLException |
| { return getDBMD().supportsCoreSQLGrammar(); } |
| |
| public static boolean supportsCorrelatedSubqueries() throws SQLException |
| { return getDBMD().supportsCorrelatedSubqueries(); } |
| |
| public static boolean supportsDataDefinitionAndDataManipulationTransactions() throws SQLException |
| { return getDBMD().supportsDataDefinitionAndDataManipulationTransactions(); } |
| |
| public static boolean supportsDataManipulationTransactionsOnly() throws SQLException |
| { return getDBMD().supportsDataManipulationTransactionsOnly(); } |
| |
| public static boolean supportsDifferentTableCorrelationNames() throws SQLException |
| { return getDBMD().supportsDifferentTableCorrelationNames(); } |
| |
| public static boolean supportsExpressionsInOrderBy() throws SQLException |
| { return getDBMD().supportsExpressionsInOrderBy(); } |
| |
| public static boolean supportsExtendedSQLGrammar() throws SQLException |
| { return getDBMD().supportsExtendedSQLGrammar(); } |
| |
| public static boolean supportsFullOuterJoins() throws SQLException |
| { return getDBMD().supportsFullOuterJoins(); } |
| |
| public static boolean supportsGetGeneratedKeys() throws SQLException |
| { return getDBMD().supportsGetGeneratedKeys(); } |
| |
| public static boolean supportsGroupBy() throws SQLException |
| { return getDBMD().supportsGroupBy(); } |
| |
| public static boolean supportsGroupByBeyondSelect() throws SQLException |
| { return getDBMD().supportsGroupByBeyondSelect(); } |
| |
| public static boolean supportsGroupByUnrelated() throws SQLException |
| { return getDBMD().supportsGroupByUnrelated(); } |
| |
| public static boolean supportsIntegrityEnhancementFacility() throws SQLException |
| { return getDBMD().supportsIntegrityEnhancementFacility(); } |
| |
| public static boolean supportsLikeEscapeClause() throws SQLException |
| { return getDBMD().supportsLikeEscapeClause(); } |
| |
| public static boolean supportsLimitedOuterJoins() throws SQLException |
| { return getDBMD().supportsLimitedOuterJoins(); } |
| |
| public static boolean supportsMinimumSQLGrammar() throws SQLException |
| { return getDBMD().supportsMinimumSQLGrammar(); } |
| |
| public static boolean supportsMixedCaseIdentifiers() throws SQLException |
| { return getDBMD().supportsMixedCaseIdentifiers(); } |
| |
| public static boolean supportsMixedCaseQuotedIdentifiers() throws SQLException |
| { return getDBMD().supportsMixedCaseQuotedIdentifiers(); } |
| |
| public static boolean supportsMultipleOpenResults() throws SQLException |
| { return getDBMD().supportsMultipleOpenResults(); } |
| |
| public static boolean supportsMultipleResultSets() throws SQLException |
| { return getDBMD().supportsMultipleResultSets(); } |
| |
| public static boolean supportsMultipleTransactions() throws SQLException |
| { return getDBMD().supportsMultipleTransactions(); } |
| |
| public static boolean supportsNamedParameters() throws SQLException |
| { return getDBMD().supportsNamedParameters(); } |
| |
| public static boolean supportsNonNullableColumns() throws SQLException |
| { return getDBMD().supportsNonNullableColumns(); } |
| |
| public static boolean supportsOpenCursorsAcrossCommit() throws SQLException |
| { return getDBMD().supportsOpenCursorsAcrossCommit(); } |
| |
| public static boolean supportsOpenCursorsAcrossRollback() throws SQLException |
| { return getDBMD().supportsOpenCursorsAcrossRollback(); } |
| |
| public static boolean supportsOpenStatementsAcrossCommit() throws SQLException |
| { return getDBMD().supportsOpenStatementsAcrossCommit(); } |
| |
| public static boolean supportsOpenStatementsAcrossRollback() throws SQLException |
| { return getDBMD().supportsOpenStatementsAcrossRollback(); } |
| |
| public static boolean supportsOrderByUnrelated() throws SQLException |
| { return getDBMD().supportsOrderByUnrelated(); } |
| |
| public static boolean supportsOuterJoins() throws SQLException |
| { return getDBMD().supportsOuterJoins(); } |
| |
| public static boolean supportsPositionedDelete() throws SQLException |
| { return getDBMD().supportsPositionedDelete(); } |
| |
| public static boolean supportsPositionedUpdate() throws SQLException |
| { return getDBMD().supportsPositionedUpdate(); } |
| |
| public static boolean supportsResultSetConcurrency(int type, int concurrency) throws SQLException |
| { return getDBMD().supportsResultSetConcurrency( type, concurrency); } |
| |
| public static boolean supportsResultSetHoldability(int holdability) throws SQLException |
| { return getDBMD().supportsResultSetHoldability( holdability); } |
| |
| public static boolean supportsResultSetType(int type) throws SQLException |
| { return getDBMD().supportsResultSetType( type); } |
| |
| public static boolean supportsSavepoints() throws SQLException |
| { return getDBMD().supportsSavepoints(); } |
| |
| public static boolean supportsSchemasInDataManipulation() throws SQLException |
| { return getDBMD().supportsSchemasInDataManipulation(); } |
| |
| public static boolean supportsSchemasInIndexDefinitions() throws SQLException |
| { return getDBMD().supportsSchemasInIndexDefinitions(); } |
| |
| public static boolean supportsSchemasInPrivilegeDefinitions() throws SQLException |
| { return getDBMD().supportsSchemasInPrivilegeDefinitions(); } |
| |
| public static boolean supportsSchemasInProcedureCalls() throws SQLException |
| { return getDBMD().supportsSchemasInProcedureCalls(); } |
| |
| public static boolean supportsSchemasInTableDefinitions() throws SQLException |
| { return getDBMD().supportsSchemasInTableDefinitions(); } |
| |
| public static boolean supportsSelectForUpdate() throws SQLException |
| { return getDBMD().supportsSelectForUpdate(); } |
| |
| public static boolean supportsStatementPooling() throws SQLException |
| { return getDBMD().supportsStatementPooling(); } |
| |
| public static boolean supportsStoredFunctionsUsingCallSyntax() throws SQLException |
| { return getDBMD().supportsStoredFunctionsUsingCallSyntax(); } |
| |
| public static boolean supportsStoredProcedures() throws SQLException |
| { return getDBMD().supportsStoredProcedures(); } |
| |
| public static boolean supportsSubqueriesInComparisons() throws SQLException |
| { return getDBMD().supportsSubqueriesInComparisons(); } |
| |
| public static boolean supportsSubqueriesInExists() throws SQLException |
| { return getDBMD().supportsSubqueriesInExists(); } |
| |
| public static boolean supportsSubqueriesInIns() throws SQLException |
| { return getDBMD().supportsSubqueriesInIns(); } |
| |
| public static boolean supportsSubqueriesInQuantifieds() throws SQLException |
| { return getDBMD().supportsSubqueriesInQuantifieds(); } |
| |
| public static boolean supportsTableCorrelationNames() throws SQLException |
| { return getDBMD().supportsTableCorrelationNames(); } |
| |
| public static boolean supportsTransactionIsolationLevel(int level) throws SQLException |
| { return getDBMD().supportsTransactionIsolationLevel(level); } |
| |
| public static boolean supportsTransactions() throws SQLException |
| { return getDBMD().supportsTransactions(); } |
| |
| public static boolean supportsUnion() throws SQLException |
| { return getDBMD().supportsUnion(); } |
| |
| public static boolean supportsUnionAll() throws SQLException |
| { return getDBMD().supportsUnionAll(); } |
| |
| public static boolean updatesAreDetected(int type) throws SQLException |
| { return getDBMD().updatesAreDetected(type); } |
| |
| public static boolean usesLocalFilePerTable() throws SQLException |
| { return getDBMD().usesLocalFilePerTable(); } |
| |
| public static boolean usesLocalFiles() throws SQLException |
| { return getDBMD().usesLocalFiles(); } |
| |
| |
| |
| |
| /////////////////////////////////////////////////////////////////////////////////// |
| // |
| // REGISTRATION MINIONS |
| // |
| /////////////////////////////////////////////////////////////////////////////////// |
| |
| /** <p>Return true if the requested modifer is set</p> */ |
| private boolean isSet( int allModifiers, int requestedModifier ) |
| { |
| return ( ( allModifiers & requestedModifier ) != 0 ); |
| } |
| |
| /** <p>Drop the function with this method name.</p> */ |
| private void unregisterFunction( Connection conn, Method method ) |
| throws SQLException |
| { |
| // maybe the method doesn't exist. swallow the exception. |
| try { |
| executeDDL( conn, "drop function " + method.getName() ); |
| } catch (SQLException se) {} |
| } |
| |
| /** <p>Register the method as a Derby function.</p> */ |
| private void registerFunction( Connection conn, Method method ) |
| throws SQLException |
| { |
| StringBuffer buffer = new StringBuffer(); |
| String name = method.getName(); |
| boolean isTableFunction = isTableFunction( method ); |
| |
| buffer.append( "create function " + name + "\n(" ); |
| appendArgs( buffer, method ); |
| buffer.append( "\n)\n" ); |
| buffer.append( "returns " ); |
| appendReturnType( buffer, conn, method ); |
| buffer.append( "\nlanguage java\nreads sql data\nparameter style " ); |
| if ( isTableFunction ) { buffer.append( "DERBY_JDBC_RESULT_SET" ); } |
| else { buffer.append( "java" ); } |
| buffer.append( "\nexternal name '" + getClass().getName() + "." + name + "'" ); |
| |
| executeDDL( conn, buffer.toString() ); |
| } |
| |
| /** <p>Return true if the method describes a table function.</p> */ |
| private boolean isTableFunction( Method method ) |
| { |
| Class returnType = method.getReturnType(); |
| |
| return ( returnType == java.sql.ResultSet.class ); |
| } |
| |
| /** <p>Append function arguments to an evolving ddl text buffer.</p> */ |
| private void appendArgs( StringBuffer buffer, Method method ) |
| throws SQLException |
| { |
| Class[] parameterTypes = method.getParameterTypes(); |
| int count = parameterTypes.length; |
| String paramStub = "a_"; |
| |
| for ( int pidx = 0; pidx < count; pidx++ ) |
| { |
| Class paramType = parameterTypes[ pidx ]; |
| |
| if ( pidx > 0 ) { buffer.append( "," ); } |
| buffer.append( "\n\t" ); |
| buffer.append( paramStub + pidx ); |
| buffer.append( ' ' ); |
| buffer.append( mapJavaToSQLType( paramType ) ); |
| } |
| } |
| |
| /** <p>Append return type to an evolving ddl text buffer</p> */ |
| private void appendReturnType( StringBuffer buffer, Connection conn, Method method ) |
| throws SQLException |
| { |
| Class returnType = method.getReturnType(); |
| |
| if ( java.sql.ResultSet.class == returnType ) { appendTableFunctionSignature( buffer, conn, method ); } |
| else { buffer.append( mapJavaToSQLType( returnType ) ); } |
| } |
| |
| /** <p>Append the signature of a table function to an evolving ddl text buffer</p> */ |
| private void appendTableFunctionSignature( StringBuffer buffer, Connection conn, Method method ) |
| throws SQLException |
| { |
| buffer.append( "table\n(" ); |
| |
| Class[] parameterTypes = method.getParameterTypes(); |
| int argCount = parameterTypes.length; |
| Object[] argValues = new Object[ argCount ]; |
| for ( int i = 0; i < argCount; i++ ) { argValues[ i ] = getDummyValue( parameterTypes[ i ] ); } |
| ResultSet returnValue; |
| |
| try { |
| returnValue = (ResultSet) method.invoke( null, argValues ); |
| } |
| catch (IllegalAccessException iae) { throw wrap( iae ); } |
| catch (InvocationTargetException ite) { throw wrap( ite ); } |
| |
| ResultSetMetaData rsmd = returnValue.getMetaData(); |
| int columnCount = rsmd.getColumnCount(); |
| |
| for ( int i = 0; i < columnCount; i++ ) |
| { |
| int columnNumber = i + 1; |
| |
| if ( i > 0 ) { buffer.append( "," ); } |
| buffer.append( "\n\t" ); |
| buffer.append( rsmd.getColumnName( columnNumber ) ); |
| buffer.append( "\t" ); |
| stringifyJDBCType( buffer, rsmd, columnNumber ); |
| } |
| |
| buffer.append( "\n)" ); |
| } |
| |
| /** <p>Get a dummy value for an argument to a DBMD method.</p> */ |
| private Object getDummyValue( Class type ) |
| { |
| if ( String.class == type ) { return ""; } |
| else if ( Integer.TYPE == type ) { return 1; } |
| else if ( Short.TYPE == type ) { return (short) 1; } |
| else if ( Boolean.TYPE == type ) { return Boolean.TRUE; } |
| else { return null; } |
| } |
| |
| /** <p>Append the name of a SQL type to an evolving ddl text buffer</p> */ |
| private void stringifyJDBCType( StringBuffer buffer, ResultSetMetaData rsmd, int columnNumber ) |
| throws SQLException |
| { |
| switch ( rsmd.getColumnType( columnNumber ) ) |
| { |
| case Types.CHAR: |
| case Types.VARCHAR: |
| buffer.append( rsmd.getColumnTypeName( columnNumber ) ); |
| buffer.append( "( " ); |
| int precision = rsmd.getPrecision( columnNumber ); |
| if ( precision <= 0 ) { precision = DEFAULT_PRECISION; } |
| buffer.append( precision ); |
| buffer.append( " )" ); |
| break; |
| default: |
| buffer.append( rsmd.getColumnTypeName( columnNumber ) ); |
| break; |
| } |
| } |
| |
| /**<p>Get the SQL type which corresponds to a Java type.</p> */ |
| private String mapJavaToSQLType( Class javaType ) |
| throws SQLException |
| { |
| if ( Short.TYPE == javaType ) { return "smallint"; } |
| else if ( Integer.TYPE == javaType ) { return "int"; } |
| else if ( Boolean.TYPE == javaType ) { return "boolean"; } |
| else if ( String.class == javaType ) { return "varchar( 32672 )"; } |
| else { throw new SQLException( "Unsupported type: " + javaType.getName() ); } |
| } |
| |
| |
| /////////////////////////////////////////////////////////////////////////////////// |
| // |
| // GENERAL MINIONS |
| // |
| /////////////////////////////////////////////////////////////////////////////////// |
| |
| /** |
| * <p> |
| * Get the current session's database metadata. |
| * </p> |
| */ |
| private static DatabaseMetaData getDBMD() |
| throws SQLException |
| { |
| return getDefaultConnection().getMetaData(); |
| } |
| |
| /** |
| * <p> |
| * Get the default connection, called from inside the database engine. |
| * </p> |
| */ |
| private static Connection getDefaultConnection() |
| throws SQLException |
| { |
| return DriverManager.getConnection( "jdbc:default:connection" ); |
| } |
| |
| /**<p>Execute a DDL statement.</p> */ |
| private static void executeDDL( Connection conn, String text ) |
| throws SQLException |
| { |
| PreparedStatement ps = null; |
| |
| try { |
| ps = prepareStatement( conn, text ); |
| |
| ps.execute(); |
| } |
| finally { if ( ps != null ) { ps.close(); } } |
| } |
| |
| /** |
| *<p> |
| * Prepare a statement and print out the text. |
| * </p> |
| */ |
| private static PreparedStatement prepareStatement( Connection conn, String text ) |
| throws SQLException |
| { |
| PreparedStatement ps = conn.prepareStatement( text ); |
| |
| return ps; |
| } |
| |
| /** |
| * <p> |
| * Wrap an exception in a SQLException. |
| * </p> |
| */ |
| private static SQLException wrap( Throwable t ) |
| { |
| return new SQLException( t.getMessage(), t ); |
| } |
| |
| } |
| |