* aggregate objects in OX. By caching aggregates along with XML Nodes that
* they were created from, we are able to preserve the structure and
* unmapped content of the document that was used to create these objects.
*/
public Object buildObject(ObjectBuildingQuery query, AbstractRecord databaseRow, JoinedAttributeManager joinManager) throws DatabaseException, QueryException {
XMLRecord row = (XMLRecord)databaseRow;
row.setSession(query.getSession());
XMLUnmarshaller unmarshaller = row.getUnmarshaller();
Object parent = row.getOwningObject();
Vector pk = extractPrimaryKeyFromRow(databaseRow, query.getSession());
if (!(isXmlDescriptor() || getDescriptor().isAggregateDescriptor() || getDescriptor().isAggregateCollectionDescriptor())) {
return super.buildObject(query, databaseRow, joinManager);
}
query.getSession().startOperationProfile(SessionProfiler.OBJECT_BUILDING, query, SessionProfiler.ALL);
ClassDescriptor concreteDescriptor = getDescriptor();
Object domainObject = null;
// only need to check in the root case since the nested case is handled
// in the mapping
if (concreteDescriptor.hasInheritance() && (parent == null)) {
// look for an xsi:type attribute in the xml document
Class classValue = concreteDescriptor.getInheritancePolicy().classFromRow(databaseRow, query.getSession());
if ((classValue == null) && isXmlDescriptor()) {
// no xsi:type attribute - look for type indicator on the
// default root element
QName leafElementType = ((XMLDescriptor)concreteDescriptor).getDefaultRootElementType();
// if we have a user-set type, try to get the class from the
// inheritance policy
if (leafElementType != null) {
Object indicator = concreteDescriptor.getInheritancePolicy().getClassIndicatorMapping().get(leafElementType);
// if the inheritance policy does not contain the user-set
// type, throw an exception
if (indicator == null) {
throw DescriptorException.missingClassForIndicatorFieldValue(leafElementType, concreteDescriptor.getInheritancePolicy().getDescriptor());
}
classValue = (Class)indicator;
}
}
// if we found the class, use it - otherwise, use the descriptor
// class, if non-abstract
if (classValue != null) {
concreteDescriptor = query.getSession().getDescriptor(classValue);
if ((concreteDescriptor == null) && query.hasPartialAttributeExpressions()) {
concreteDescriptor = getDescriptor();
}
if (concreteDescriptor == null) {
throw QueryException.noDescriptorForClassFromInheritancePolicy(query, classValue);
}
} else {
// make sure the class is non-abstract
if (Modifier.isAbstract(concreteDescriptor.getJavaClass().getModifiers())) {
// throw an exception
throw DescriptorException.missingClassIndicatorField(databaseRow, concreteDescriptor.getInheritancePolicy().getDescriptor());
}
}
}
domainObject = concreteDescriptor.getObjectBuilder().buildNewInstance();
row.setCurrentObject(domainObject);
if ((unmarshaller != null) && (unmarshaller.getUnmarshalListener() != null)) {
unmarshaller.getUnmarshalListener().beforeUnmarshal(domainObject, parent);
}
concreteDescriptor.getObjectBuilder().buildAttributesIntoObject(domainObject, databaseRow, query, joinManager, false);
if (isXmlDescriptor() && ((XMLDescriptor)concreteDescriptor).getPrimaryKeyFieldNames().size() > 0) {