use of org.datanucleus.store.schema.StoreSchemaHandler in project tests by datanucleus.
the class SchemaHandlerTest method testPrimaryKeyRetrieval.
/**
* Test of the retrieval of PKs.
*/
public void testPrimaryKeyRetrieval() {
addClassesToSchema(new Class[] { SchemaClass1.class, SchemaClass2.class });
PersistenceManager pm = pmf.getPersistenceManager();
RDBMSStoreManager databaseMgr = (RDBMSStoreManager) storeMgr;
// Retrieve the table for SchemaClass1
ClassLoaderResolver clr = storeMgr.getNucleusContext().getClassLoaderResolver(null);
DatastoreClass table1 = databaseMgr.getDatastoreClass(SchemaClass1.class.getName(), clr);
DatastoreClass table2 = databaseMgr.getDatastoreClass(SchemaClass2.class.getName(), clr);
// Check for the FK using the schema handler
StoreSchemaHandler handler = databaseMgr.getSchemaHandler();
Connection con = (Connection) databaseMgr.getConnectionManager().getConnection(((JDOPersistenceManager) pm).getExecutionContext()).getConnection();
RDBMSTablePKInfo pkInfo1 = (RDBMSTablePKInfo) handler.getSchemaData(con, "primary-keys", new Object[] { table1 });
RDBMSTablePKInfo pkInfo2 = (RDBMSTablePKInfo) handler.getSchemaData(con, "primary-keys", new Object[] { table2 });
// Expecting 2 PK columns for SchemaClass1
// TODO Enable checks on the PK name (when JDBC drivers return it correctly)
assertEquals("Number of PKs for table " + table1 + " is wrong", 2, pkInfo1.getNumberOfChildren());
PrimaryKeyInfo pk = (PrimaryKeyInfo) pkInfo1.getChild(0);
assertEquals("Column Name is wrong", "TABLE1_ID1", ((String) pk.getProperty("column_name")).toUpperCase());
// assertEquals("PK Name is wrong", "TABLE1_PK", pk.getProperty("pk_name"));
pk = (PrimaryKeyInfo) pkInfo1.getChild(1);
assertEquals("Column Name is wrong", "TABLE1_ID2", ((String) pk.getProperty("column_name")).toUpperCase());
// assertEquals("PK Name is wrong", "TABLE1_PK", pk.getProperty("pk_name"));
// Expecting 1 PK column for SchemaClass
assertEquals("Number of PKs for table " + table1 + " is wrong", 1, pkInfo2.getNumberOfChildren());
pk = (PrimaryKeyInfo) pkInfo2.getChild(0);
assertEquals("Column Name is wrong", "TABLE2_ID", ((String) pk.getProperty("column_name")).toUpperCase());
// assertEquals("PK Name is wrong", "TABLE2_PK", pk.getProperty("pk_name"));
}
use of org.datanucleus.store.schema.StoreSchemaHandler in project datanucleus-rdbms by datanucleus.
the class TableImpl method getExistingForeignKeys.
/**
* Accessor for the foreign keys for this table.
* @param conn The JDBC Connection
* @return Map of foreign keys
* @throws SQLException Thrown when an error occurs in the JDBC call.
*/
private Map<DatastoreIdentifier, ForeignKey> getExistingForeignKeys(Connection conn) throws SQLException {
Map<DatastoreIdentifier, ForeignKey> foreignKeysByName = new HashMap<>();
if (tableExistsInDatastore(conn)) {
StoreSchemaHandler handler = storeMgr.getSchemaHandler();
IdentifierFactory idFactory = storeMgr.getIdentifierFactory();
RDBMSTableFKInfo tableFkInfo = (RDBMSTableFKInfo) handler.getSchemaData(conn, "foreign-keys", new Object[] { this });
Iterator fksIter = tableFkInfo.getChildren().iterator();
while (fksIter.hasNext()) {
ForeignKeyInfo fkInfo = (ForeignKeyInfo) fksIter.next();
DatastoreIdentifier fkIdentifier;
String fkName = (String) fkInfo.getProperty("fk_name");
if (fkName == null) {
fkIdentifier = idFactory.newForeignKeyIdentifier(this, foreignKeysByName.size());
} else {
fkIdentifier = idFactory.newIdentifier(IdentifierType.FOREIGN_KEY, fkName);
}
short deferrability = ((Short) fkInfo.getProperty("deferrability")).shortValue();
boolean initiallyDeferred = deferrability == DatabaseMetaData.importedKeyInitiallyDeferred;
ForeignKey fk = foreignKeysByName.get(fkIdentifier);
if (fk == null) {
fk = new ForeignKey(dba, initiallyDeferred);
fk.setName(fkIdentifier.getName());
foreignKeysByName.put(fkIdentifier, fk);
}
// Find the referenced table from the provided name
String pkTableName = (String) fkInfo.getProperty("pk_table_name");
DatastoreIdentifier refTableId = idFactory.newTableIdentifier(pkTableName);
DatastoreClass refTable = storeMgr.getDatastoreClass(refTableId);
if (refTable == null) {
// Try with same catalog/schema as this table since some JDBC don't provide this info
if (getSchemaName() != null) {
refTableId.setSchemaName(getSchemaName());
}
if (getCatalogName() != null) {
refTableId.setCatalogName(getCatalogName());
}
refTable = storeMgr.getDatastoreClass(refTableId);
}
if (refTable != null) {
String fkColumnName = (String) fkInfo.getProperty("fk_column_name");
String pkColumnName = (String) fkInfo.getProperty("pk_column_name");
DatastoreIdentifier colName = idFactory.newIdentifier(IdentifierType.COLUMN, fkColumnName);
DatastoreIdentifier refColName = idFactory.newIdentifier(IdentifierType.COLUMN, pkColumnName);
Column col = columnsByIdentifier.get(colName);
Column refCol = refTable.getColumn(refColName);
if (col != null && refCol != null) {
fk.addColumn(col, refCol);
} else {
// TODO throw exception?
}
} else {
NucleusLogger.DATASTORE_SCHEMA.warn("Retrieved ForeignKey from datastore for table=" + toString() + " referencing table " + pkTableName + " but not found internally. Is there some catalog/schema or quoting causing problems?");
}
}
}
return foreignKeysByName;
}
use of org.datanucleus.store.schema.StoreSchemaHandler in project datanucleus-rdbms by datanucleus.
the class TableImpl method getExistingPrimaryKeys.
/**
* Accessor for the primary keys for this table in the datastore.
* @param conn The JDBC Connection
* @return Map of primary keys
* @throws SQLException Thrown when an error occurs in the JDBC call.
*/
private Map<DatastoreIdentifier, PrimaryKey> getExistingPrimaryKeys(Connection conn) throws SQLException {
Map<DatastoreIdentifier, PrimaryKey> primaryKeysByName = new HashMap<>();
if (tableExistsInDatastore(conn)) {
StoreSchemaHandler handler = storeMgr.getSchemaHandler();
RDBMSTablePKInfo tablePkInfo = (RDBMSTablePKInfo) handler.getSchemaData(conn, "primary-keys", new Object[] { this });
IdentifierFactory idFactory = storeMgr.getIdentifierFactory();
Iterator pkColsIter = tablePkInfo.getChildren().iterator();
while (pkColsIter.hasNext()) {
PrimaryKeyInfo pkInfo = (PrimaryKeyInfo) pkColsIter.next();
String pkName = (String) pkInfo.getProperty("pk_name");
DatastoreIdentifier pkIdentifier;
if (pkName == null) {
pkIdentifier = idFactory.newPrimaryKeyIdentifier(this);
} else {
pkIdentifier = idFactory.newIdentifier(IdentifierType.COLUMN, pkName);
}
PrimaryKey pk = primaryKeysByName.get(pkIdentifier);
if (pk == null) {
pk = new PrimaryKey(this);
pk.setName(pkIdentifier.getName());
primaryKeysByName.put(pkIdentifier, pk);
}
int keySeq = (((Short) pkInfo.getProperty("key_seq")).shortValue()) - 1;
String colName = (String) pkInfo.getProperty("column_name");
DatastoreIdentifier colIdentifier = idFactory.newIdentifier(IdentifierType.COLUMN, colName);
Column col = columnsByIdentifier.get(colIdentifier);
if (col == null) {
throw new UnexpectedColumnException(this.toString(), colIdentifier.getName(), this.getSchemaName(), this.getCatalogName());
}
pk.setColumn(keySeq, col);
}
}
return primaryKeysByName;
}
use of org.datanucleus.store.schema.StoreSchemaHandler in project tests by datanucleus.
the class SchemaHandlerTest method testIndexRetrieval.
/**
* Test of the retrieval of indices.
*/
public void testIndexRetrieval() {
addClassesToSchema(new Class[] { SchemaClass1.class, SchemaClass2.class });
PersistenceManager pm = pmf.getPersistenceManager();
RDBMSStoreManager databaseMgr = (RDBMSStoreManager) storeMgr;
// Retrieve the table for SchemaClass1
ClassLoaderResolver clr = storeMgr.getNucleusContext().getClassLoaderResolver(null);
DatastoreClass table1 = databaseMgr.getDatastoreClass(SchemaClass1.class.getName(), clr);
DatastoreClass table2 = databaseMgr.getDatastoreClass(SchemaClass2.class.getName(), clr);
// Check for the indices using the schema handler
StoreSchemaHandler handler = databaseMgr.getSchemaHandler();
Connection con = (Connection) databaseMgr.getConnectionManager().getConnection(((JDOPersistenceManager) pm).getExecutionContext()).getConnection();
RDBMSTableIndexInfo indexInfo = (RDBMSTableIndexInfo) handler.getSchemaData(con, "indices", new Object[] { table1 });
int numIndices = 3;
if (vendorID.equals("hsql")) {
// HSQL will create an index for the FK without asking, and we can't replace it with our own so end up with two
numIndices = 4;
}
assertEquals("Number of Indices for table " + table1 + " is wrong", numIndices, indexInfo.getNumberOfChildren());
Iterator indexIter = indexInfo.getChildren().iterator();
while (indexIter.hasNext()) {
IndexInfo index = (IndexInfo) indexIter.next();
String columnName = ((String) index.getProperty("column_name")).toUpperCase();
boolean unique = !((Boolean) index.getProperty("non_unique")).booleanValue();
if (columnName.equals("OTHER_ID")) {
assertFalse("Index for column " + columnName + " is unique!", unique);
} else if (columnName.equals("TABLE1_ID1")) {
assertTrue("Index for column " + columnName + " is not unique!", unique);
} else if (columnName.equals("TABLE1_ID2")) {
assertTrue("Index for column " + columnName + " is not unique!", unique);
} else {
fail("Unexpected index " + columnName + " for table " + table1);
}
}
indexInfo = (RDBMSTableIndexInfo) handler.getSchemaData(con, "indices", new Object[] { table2 });
assertEquals("Number of Indices for table " + table2 + " is wrong", 2, indexInfo.getNumberOfChildren());
indexIter = indexInfo.getChildren().iterator();
while (indexIter.hasNext()) {
IndexInfo index = (IndexInfo) indexIter.next();
String columnName = ((String) index.getProperty("column_name")).toUpperCase();
String indexName = ((String) index.getProperty("index_name")).toUpperCase();
boolean unique = !((Boolean) index.getProperty("non_unique")).booleanValue();
if (columnName.equals("VALUE")) {
assertFalse("Index for column " + columnName + " is unique!", unique);
assertEquals("Index name for column " + columnName + " is wrong!", "VALUE_IDX", indexName);
} else if (columnName.equals("TABLE2_ID")) {
assertTrue("Index for column " + columnName + " is not unique!", unique);
} else {
fail("Unexpected index " + columnName + " for table " + table1);
}
}
}
Aggregations