use of org.datanucleus.store.rdbms.table.Table in project datanucleus-rdbms by datanucleus.
the class RDBMSStoreManager method getManagedTables.
/**
* Convenience accessor of the Table objects managed in this datastore at this point.
* @param catalog Name of the catalog to restrict the collection by (or null to not restrict)
* @param schema Name of the schema to restrict the collection by (or null to not restrict)
* @return Collection of tables
*/
public Collection<Table> getManagedTables(String catalog, String schema) {
if (storeDataMgr == null) {
return Collections.EMPTY_SET;
}
Collection<Table> tables = new HashSet<>();
for (StoreData sd : storeDataMgr.getManagedStoreData()) {
if (sd.getTable() != null) {
// Catalog/Schema match if either managed table not set, or input requirements not set
DatastoreIdentifier identifier = ((Table) sd.getTable()).getIdentifier();
boolean catalogMatches = true;
boolean schemaMatches = true;
if (catalog != null && identifier.getCatalogName() != null && !catalog.equals(identifier.getCatalogName())) {
catalogMatches = false;
}
if (schema != null && identifier.getSchemaName() != null && !schema.equals(identifier.getSchemaName())) {
schemaMatches = false;
}
if (catalogMatches && schemaMatches) {
tables.add((Table) sd.getTable());
}
}
}
return tables;
}
use of org.datanucleus.store.rdbms.table.Table in project datanucleus-rdbms by datanucleus.
the class RDBMSStoreManager method resolveIdentifierMacro.
/**
* Resolves an identifier macro. The public fields <var>className</var>, <var>fieldName </var>,
* and <var>subfieldName </var> of the given macro are taken as inputs, and the public
* <var>value </var> field is set to the SQL identifier of the corresponding database table or column.
* @param im The macro to resolve.
* @param clr The ClassLoaderResolver
*/
public void resolveIdentifierMacro(MacroString.IdentifierMacro im, ClassLoaderResolver clr) {
DatastoreClass ct = getDatastoreClass(im.className, clr);
if (im.fieldName == null) {
im.value = ct.getIdentifier().toString();
return;
}
JavaTypeMapping m;
if (// TODO This should be candidate alias or something, not hardcoded "this"
im.fieldName.equals("this")) {
if (!(ct instanceof ClassTable)) {
throw new NucleusUserException(Localiser.msg("050034", im.className));
}
if (im.subfieldName != null) {
throw new NucleusUserException(Localiser.msg("050035", im.className, im.fieldName, im.subfieldName));
}
m = ((Table) ct).getIdMapping();
} else {
AbstractClassMetaData cmd = getMetaDataManager().getMetaDataForClass(im.className, clr);
AbstractMemberMetaData mmd = cmd.getMetaDataForMember(im.fieldName);
m = ct.getMemberMapping(mmd);
Table t = getTable(mmd);
if (im.subfieldName == null) {
if (t != null) {
im.value = t.getIdentifier().toString();
return;
}
} else {
if (t instanceof CollectionTable) {
CollectionTable collTable = (CollectionTable) t;
if (im.subfieldName.equals("owner")) {
m = collTable.getOwnerMapping();
} else if (im.subfieldName.equals("element")) {
m = collTable.getElementMapping();
} else if (im.subfieldName.equals("index")) {
m = collTable.getOrderMapping();
} else {
throw new NucleusUserException(Localiser.msg("050036", im.subfieldName, im));
}
} else if (t instanceof MapTable) {
MapTable mt = (MapTable) t;
if (im.subfieldName.equals("owner")) {
m = mt.getOwnerMapping();
} else if (im.subfieldName.equals("key")) {
m = mt.getKeyMapping();
} else if (im.subfieldName.equals("value")) {
m = mt.getValueMapping();
} else {
throw new NucleusUserException(Localiser.msg("050037", im.subfieldName, im));
}
} else {
throw new NucleusUserException(Localiser.msg("050035", im.className, im.fieldName, im.subfieldName));
}
}
}
im.value = m.getDatastoreMapping(0).getColumn().getIdentifier().toString();
}
use of org.datanucleus.store.rdbms.table.Table in project datanucleus-rdbms by datanucleus.
the class FKListStore method getSetStatementString.
private String getSetStatementString(Object element) {
ComponentInfo elemInfo = getComponentInfoForElement(element);
Table table = this.containerTable;
JavaTypeMapping ownerMapping = this.ownerMapping;
JavaTypeMapping elemMapping = this.elementMapping;
JavaTypeMapping relDiscrimMapping = this.relationDiscriminatorMapping;
JavaTypeMapping orderMapping = this.orderMapping;
if (elemInfo != null) {
table = elemInfo.getDatastoreClass();
elemMapping = elemInfo.getDatastoreClass().getIdMapping();
ownerMapping = elemInfo.getOwnerMapping();
orderMapping = elemInfo.getDatastoreClass().getExternalMapping(ownerMemberMetaData, MappingType.EXTERNAL_INDEX);
relDiscrimMapping = elemInfo.getDatastoreClass().getExternalMapping(ownerMemberMetaData, MappingType.EXTERNAL_FK_DISCRIMINATOR);
}
// TODO If ownerMapping is not for containerTable then use owner table for the UPDATE
StringBuilder stmt = new StringBuilder("UPDATE ").append(table.toString()).append(" SET ");
for (int i = 0; i < ownerMapping.getNumberOfDatastoreMappings(); i++) {
if (i > 0) {
stmt.append(",");
}
stmt.append(ownerMapping.getDatastoreMapping(i).getColumn().getIdentifier().toString());
stmt.append(" = ");
stmt.append(ownerMapping.getDatastoreMapping(i).getUpdateInputParameter());
}
if (orderMapping != null) {
for (int i = 0; i < orderMapping.getNumberOfDatastoreMappings(); i++) {
stmt.append(",");
stmt.append(orderMapping.getDatastoreMapping(i).getColumn().getIdentifier().toString());
stmt.append(" = ");
stmt.append(orderMapping.getDatastoreMapping(i).getUpdateInputParameter());
}
}
if (relDiscrimMapping != null) {
for (int i = 0; i < relDiscrimMapping.getNumberOfDatastoreMappings(); i++) {
stmt.append(",");
stmt.append(relDiscrimMapping.getDatastoreMapping(i).getColumn().getIdentifier().toString());
stmt.append(" = ");
stmt.append(relDiscrimMapping.getDatastoreMapping(i).getUpdateInputParameter());
}
}
stmt.append(" WHERE ");
BackingStoreHelper.appendWhereClauseForElement(stmt, elemMapping, element, isElementsAreSerialised(), null, true);
return stmt.toString();
}
use of org.datanucleus.store.rdbms.table.Table in project datanucleus-rdbms by datanucleus.
the class FKSetStore method getUpdateFkStatementString.
private String getUpdateFkStatementString(Object element) {
JavaTypeMapping ownerMapping = this.ownerMapping;
JavaTypeMapping elemMapping = this.elementMapping;
JavaTypeMapping relDiscrimMapping = this.relationDiscriminatorMapping;
Table table = containerTable;
if (elementInfo.length > 1) {
ComponentInfo elemInfo = getComponentInfoForElement(element);
if (elemInfo != null) {
table = elemInfo.getDatastoreClass();
ownerMapping = elemInfo.getOwnerMapping();
elemMapping = elemInfo.getDatastoreClass().getIdMapping();
relDiscrimMapping = elemInfo.getDatastoreClass().getExternalMapping(ownerMemberMetaData, MappingType.EXTERNAL_FK_DISCRIMINATOR);
}
}
StringBuilder stmt = new StringBuilder("UPDATE ").append(table.toString()).append(" SET ");
for (int i = 0; i < ownerMapping.getNumberOfDatastoreMappings(); i++) {
if (i > 0) {
stmt.append(",");
}
stmt.append(ownerMapping.getDatastoreMapping(i).getColumn().getIdentifier().toString());
stmt.append("=");
stmt.append(ownerMapping.getDatastoreMapping(i).getUpdateInputParameter());
}
if (relDiscrimMapping != null) {
for (int i = 0; i < relDiscrimMapping.getNumberOfDatastoreMappings(); i++) {
stmt.append(",");
stmt.append(relDiscrimMapping.getDatastoreMapping(i).getColumn().getIdentifier().toString());
stmt.append("=");
stmt.append(relDiscrimMapping.getDatastoreMapping(i).getUpdateInputParameter());
}
}
stmt.append(" WHERE ");
BackingStoreHelper.appendWhereClauseForElement(stmt, elemMapping, element, elementsAreSerialised, null, true);
return stmt.toString();
}
use of org.datanucleus.store.rdbms.table.Table in project datanucleus-rdbms by datanucleus.
the class SQLStatementHelper method selectMemberOfSourceInStatement.
/**
* Method to select the specified member (field/property) of the source table in the passed SQL
* statement. This populates the mappingDefinition with the column details for this member.
* @param stmt The SQL statement
* @param mappingDefinition Mapping definition for the results (will be populated by any
* selected mappings if provided as input)
* @param fetchPlan FetchPlan
* @param sourceSqlTbl Table that has the member (or a super-table/secondary-table of this table)
* @param mmd Meta-data for the field/property in the source that we are selecting
* @param clr ClassLoader resolver
* @param maxFetchPlanLimit Max fetch depth from this point to select (0 implies no other objects)
* @param inputJoinType Optional join type to use for subobjects (otherwise decide join type internally)
*/
public static void selectMemberOfSourceInStatement(SelectStatement stmt, StatementClassMapping mappingDefinition, FetchPlan fetchPlan, SQLTable sourceSqlTbl, AbstractMemberMetaData mmd, ClassLoaderResolver clr, int maxFetchPlanLimit, JoinType inputJoinType) {
boolean selectSubobjects = false;
if (maxFetchPlanLimit > 0) {
selectSubobjects = true;
}
// Set table-group name for any related object we join to (naming based on member name)
String tableGroupName = sourceSqlTbl.getGroupName() + "." + mmd.getName();
JavaTypeMapping m = sourceSqlTbl.getTable().getMemberMapping(mmd);
if (m != null && m.includeInFetchStatement()) {
RelationType relationType = mmd.getRelationType(clr);
RDBMSStoreManager storeMgr = stmt.getRDBMSManager();
DatastoreAdapter dba = storeMgr.getDatastoreAdapter();
if (!dba.validToSelectMappingInStatement(stmt, m)) {
// Not valid to select this mapping for this statement so return
return;
}
MetaDataManager mmgr = storeMgr.getMetaDataManager();
StatementMappingIndex stmtMapping = new StatementMappingIndex(m);
if (m.getNumberOfDatastoreMappings() > 0) {
// Select of fields with columns in source table(s)
// Adds inner/outer join to any required superclass/secondary tables
SQLTable sqlTbl = SQLStatementHelper.getSQLTableForMappingOfTable(stmt, sourceSqlTbl, m);
boolean selectFK = true;
if (selectSubobjects && (relationType == RelationType.ONE_TO_ONE_UNI || (relationType == RelationType.ONE_TO_ONE_BI && mmd.getMappedBy() == null)) && !mmd.isSerialized() && !mmd.isEmbedded()) {
// Related object with FK at this side
selectFK = selectFetchPlanFieldsOfFKRelatedObject(stmt, mappingDefinition, fetchPlan, sourceSqlTbl, mmd, clr, maxFetchPlanLimit, m, tableGroupName, stmtMapping, sqlTbl, inputJoinType);
} else if (selectSubobjects && (!mmd.isEmbedded() && !mmd.isSerialized()) && relationType == RelationType.MANY_TO_ONE_BI) {
AbstractMemberMetaData[] relatedMmds = mmd.getRelatedMemberMetaData(clr);
if (mmd.getJoinMetaData() != null || relatedMmds[0].getJoinMetaData() != null) {
// N-1 bidirectional join table relation
// TODO Add left outer join from {sourceTable}.ID to {joinTable}.ELEM_FK
Table joinTable = storeMgr.getTable(relatedMmds[0]);
DatastoreElementContainer collTable = (DatastoreElementContainer) joinTable;
JavaTypeMapping selectMapping = collTable.getOwnerMapping();
SQLTable joinSqlTbl = null;
if (stmt.getPrimaryTable().getTable() != joinTable) {
// Join to the join table
JavaTypeMapping referenceMapping = collTable.getElementMapping();
joinSqlTbl = stmt.join(JoinType.LEFT_OUTER_JOIN, sourceSqlTbl, sourceSqlTbl.getTable().getIdMapping(), collTable, null, referenceMapping, null, tableGroupName, true);
} else {
// Main table of the statement is the join table so no need to join
joinSqlTbl = stmt.getPrimaryTable();
}
// Select the owner mapping of the join table
int[] colNumbers = stmt.select(joinSqlTbl, selectMapping, null);
stmtMapping.setColumnPositions(colNumbers);
// TODO Join to 1 side from join table?
} else {
// N-1 bidirectional FK relation
// Related object with FK at this side, so join/select related object as required
selectFK = selectFetchPlanFieldsOfFKRelatedObject(stmt, mappingDefinition, fetchPlan, sourceSqlTbl, mmd, clr, maxFetchPlanLimit, m, tableGroupName, stmtMapping, sqlTbl, inputJoinType);
}
}
if (selectFK) {
int[] colNumbers = stmt.select(sqlTbl, m, null);
stmtMapping.setColumnPositions(colNumbers);
}
} else {
// Select of related objects with FK in other table
if (relationType == RelationType.ONE_TO_ONE_BI && mmd.getMappedBy() != null) {
// 1-1 bidirectional relation with FK in related table
AbstractMemberMetaData[] relatedMmds = mmd.getRelatedMemberMetaData(clr);
AbstractMemberMetaData relatedMmd = relatedMmds[0];
String[] clsNames = null;
if (mmd.getType().isInterface()) {
if (mmd.getFieldTypes() != null && mmd.getFieldTypes().length == 1) {
// Use field-type since only one class specified
Class fldTypeCls = clr.classForName(mmd.getFieldTypes()[0]);
if (fldTypeCls.isInterface()) {
// User has specified an interface, so find its implementations
clsNames = mmgr.getClassesImplementingInterface(mmd.getFieldTypes()[0], clr);
} else {
// Use user-provided field-type
clsNames = new String[] { mmd.getFieldTypes()[0] };
}
}
if (clsNames == null) {
clsNames = mmgr.getClassesImplementingInterface(mmd.getTypeName(), clr);
}
} else {
String typeName = mmd.isSingleCollection() ? mmd.getCollection().getElementType() : mmd.getTypeName();
clsNames = new String[] { typeName };
}
DatastoreClass relatedTbl = storeMgr.getDatastoreClass(clsNames[0], clr);
JavaTypeMapping relatedMapping = relatedTbl.getMemberMapping(relatedMmd);
JavaTypeMapping relatedDiscrimMapping = relatedTbl.getSurrogateMapping(SurrogateColumnType.DISCRIMINATOR, true);
Object[] discrimValues = null;
JavaTypeMapping relatedTypeMapping = null;
AbstractClassMetaData relatedCmd = relatedMmd.getAbstractClassMetaData();
if (relatedDiscrimMapping != null && (relatedCmd.getSuperAbstractClassMetaData() != null || !relatedCmd.getFullClassName().equals(mmd.getTypeName()))) {
// Related table has a discriminator and the field can store other types
List discValueList = null;
for (String clsName : clsNames) {
List values = getDiscriminatorValuesForMember(clsName, relatedDiscrimMapping, storeMgr, clr);
if (discValueList == null) {
discValueList = values;
} else {
discValueList.addAll(values);
}
}
if (discValueList != null) {
discrimValues = discValueList.toArray(new Object[discValueList.size()]);
}
} else if (relatedTbl != relatedMapping.getTable()) {
// The relation is to a base class table, and the type stored is a sub-class
relatedTypeMapping = relatedTbl.getIdMapping();
}
SQLTable relatedSqlTbl = null;
if (relatedTypeMapping == null) {
// Join the 1-1 relation
JoinType joinType = getJoinTypeForOneToOneRelationJoin(sourceSqlTbl.getTable().getIdMapping(), sourceSqlTbl, inputJoinType);
if (joinType == JoinType.LEFT_OUTER_JOIN || joinType == JoinType.RIGHT_OUTER_JOIN) {
inputJoinType = joinType;
}
relatedSqlTbl = addJoinForOneToOneRelation(stmt, sourceSqlTbl.getTable().getIdMapping(), sourceSqlTbl, relatedMapping, relatedTbl, null, discrimValues, tableGroupName, joinType);
// Select the id mapping in the related table
int[] colNumbers = stmt.select(relatedSqlTbl, relatedTbl.getIdMapping(), null);
stmtMapping.setColumnPositions(colNumbers);
} else {
DatastoreClass relationTbl = (DatastoreClass) relatedMapping.getTable();
if (relatedTbl != relatedMapping.getTable()) {
if (relatedMapping.isNullable()) {
// Nullable - left outer join from {sourceTable}.ID to {relatedBaseTable}.FK
// and inner join from {relatedBaseTable}.ID to {relatedTable}.ID
// (joins the relation and restricts to the right type)
relatedSqlTbl = stmt.join(JoinType.LEFT_OUTER_JOIN, sourceSqlTbl, sourceSqlTbl.getTable().getIdMapping(), relatedMapping.getTable(), null, relatedMapping, null, tableGroupName, true);
relatedSqlTbl = stmt.join(JoinType.INNER_JOIN, relatedSqlTbl, relatedMapping.getTable().getIdMapping(), relatedTbl, null, relatedTbl.getIdMapping(), null, tableGroupName, true);
} else {
// Not nullable - inner join from {sourceTable}.ID to {relatedBaseTable}.FK
// and inner join from {relatedBaseTable}.ID to {relatedTable}.ID
// (joins the relation and restricts to the right type)
relatedSqlTbl = stmt.join(JoinType.INNER_JOIN, sourceSqlTbl, sourceSqlTbl.getTable().getIdMapping(), relatedMapping.getTable(), null, relatedMapping, null, tableGroupName, true);
relatedSqlTbl = stmt.join(JoinType.INNER_JOIN, relatedSqlTbl, relatedMapping.getTable().getIdMapping(), relatedTbl, null, relatedTbl.getIdMapping(), null, tableGroupName, true);
}
} else {
// Join the 1-1 relation
JoinType joinType = getJoinTypeForOneToOneRelationJoin(sourceSqlTbl.getTable().getIdMapping(), sourceSqlTbl, inputJoinType);
if (joinType == JoinType.LEFT_OUTER_JOIN || joinType == JoinType.RIGHT_OUTER_JOIN) {
inputJoinType = joinType;
}
relatedSqlTbl = addJoinForOneToOneRelation(stmt, sourceSqlTbl.getTable().getIdMapping(), sourceSqlTbl, relatedMapping, relationTbl, null, null, tableGroupName, joinType);
}
// Select the id mapping in the subclass of the related table
// Note this adds an inner join from relatedTable to its subclass
relatedSqlTbl = SQLStatementHelper.getSQLTableForMappingOfTable(stmt, relatedSqlTbl, relatedTbl.getIdMapping());
int[] colNumbers = stmt.select(relatedSqlTbl, relatedTbl.getIdMapping(), null);
stmtMapping.setColumnPositions(colNumbers);
}
if (selectSubobjects && !mmd.isSerialized() && !mmd.isEmbedded()) {
// Select the fetch-plan fields of the related object
StatementClassMapping subMappingDefinition = new StatementClassMapping(null, mmd.getName());
selectFetchPlanOfSourceClassInStatement(stmt, subMappingDefinition, fetchPlan, relatedSqlTbl, relatedMmd.getAbstractClassMetaData(), maxFetchPlanLimit - 1, inputJoinType);
if (mappingDefinition != null) {
mappingDefinition.addMappingDefinitionForMember(mmd.getAbsoluteFieldNumber(), subMappingDefinition);
}
}
} else if (relationType == RelationType.MANY_TO_ONE_BI) {
AbstractMemberMetaData[] relatedMmds = mmd.getRelatedMemberMetaData(clr);
if (mmd.getJoinMetaData() != null || relatedMmds[0].getJoinMetaData() != null) {
// N-1 bidirectional join table relation
// Add left outer join from {sourceTable}.ID to {joinTable}.ELEM_FK
Table joinTable = storeMgr.getTable(relatedMmds[0]);
DatastoreElementContainer collTable = (DatastoreElementContainer) joinTable;
JavaTypeMapping selectMapping = collTable.getOwnerMapping();
SQLTable joinSqlTbl = null;
if (stmt.getPrimaryTable().getTable() != joinTable) {
// Join to the join table
JavaTypeMapping referenceMapping = collTable.getElementMapping();
if (referenceMapping instanceof ReferenceMapping) {
// Join table has a reference mapping pointing to our table, so get the submapping for the implementation
ReferenceMapping refMap = (ReferenceMapping) referenceMapping;
Class implType = clr.classForName(mmd.getClassName(true));
referenceMapping = refMap.getJavaTypeMappingForType(implType);
}
joinSqlTbl = stmt.join(JoinType.LEFT_OUTER_JOIN, sourceSqlTbl, sourceSqlTbl.getTable().getIdMapping(), collTable, null, referenceMapping, null, tableGroupName + "_JOIN", true);
} else {
// Main table of the statement is the join table so no need to join
joinSqlTbl = stmt.getPrimaryTable();
}
// Select the owner mapping of the join table
int[] colNumbers = stmt.select(joinSqlTbl, selectMapping, null);
stmtMapping.setColumnPositions(colNumbers);
}
// TODO Select fetch plan fields of this related object
} else if (relationType == RelationType.MANY_TO_ONE_UNI) {
// Add left outer join from {sourceTable}.ID to {joinTable}.OWNER_FK
PersistableJoinTable joinTable = (PersistableJoinTable) storeMgr.getTable(mmd);
SQLTable joinSqlTbl = stmt.join(JoinType.LEFT_OUTER_JOIN, sourceSqlTbl, sourceSqlTbl.getTable().getIdMapping(), joinTable, null, joinTable.getOwnerMapping(), null, tableGroupName + "_JOIN", true);
int[] colNumbers = stmt.select(joinSqlTbl, joinTable.getRelatedMapping(), null);
stmtMapping.setColumnPositions(colNumbers);
// TODO Select fetch plan fields of this related object
}
}
if (mappingDefinition != null) {
mappingDefinition.addMappingForMember(mmd.getAbsoluteFieldNumber(), stmtMapping);
}
}
}
Aggregations