use of org.eclipse.persistence.internal.oxm.mappings.Descriptor in project eclipselink by eclipse-ee4j.
the class SchemaModelGenerator method generateSchemas.
/**
* Generates a Map of EclipseLink schema model Schema objects for a given list of XMLDescriptors.
* The descriptors are assumed to have been initialized. One Schema object will be generated
* per namespace.
*
* @param descriptorsToProcess list of XMLDescriptors which will be used to generate Schema objects
* @param properties holds a namespace to Properties map containing schema settings, such as elementFormDefault
* @param additionalGlobalElements a map of QName-Type entries identifying additional global elements to be added
* @return a map of namespaces to EclipseLink schema model Schema objects
* @throws DescriptorException if the reference descriptor for a composite mapping is not in the list of descriptors
* @see Schema
*/
public Map<String, Schema> generateSchemas(List<Descriptor> descriptorsToProcess, SchemaModelGeneratorProperties properties, Map<QName, Type> additionalGlobalElements) throws DescriptorException {
Map<String, Schema> schemaForNamespace = generateSchemas(descriptorsToProcess, properties);
// process any additional global elements
if (additionalGlobalElements != null) {
for (Entry<QName, Type> entry : additionalGlobalElements.entrySet()) {
QName qname = entry.getKey();
Type type = entry.getValue();
if (type instanceof Class) {
Class<?> tClass = (Class) type;
String nsKey = qname.getNamespaceURI();
Schema schema = schemaForNamespace.get(nsKey);
QName typeAsQName = conversionManager.schemaType(tClass);
if (typeAsQName == null) {
// not a built in type - need to get the type via schema reference
Descriptor desc = getDescriptorByClass(tClass, descriptorsToProcess);
if (desc == null) {
// at this point we can't determine the element type, so don't add anything
continue;
}
// if the schema is null generate a new one and create an import
if (schema == null) {
schema = buildNewSchema(nsKey, new org.eclipse.persistence.oxm.NamespaceResolver(), schemaForNamespace.size(), properties);
schemaForNamespace.put(nsKey, schema);
typeAsQName = desc.getSchemaReference().getSchemaContextAsQName();
Schema schemaForUri = schemaForNamespace.get(typeAsQName.getNamespaceURI());
if (!importExists(schema, schemaForUri.getTargetNamespace())) {
Import newImport = new Import();
newImport.setNamespace(schemaForUri.getTargetNamespace());
newImport.setSchemaLocation(schemaForUri.getName());
schema.getImports().add(newImport);
}
} else {
typeAsQName = desc.getSchemaReference().getSchemaContextAsQName(schema.getNamespaceResolver());
}
}
if (schema == null) {
schema = buildNewSchema(nsKey, new org.eclipse.persistence.oxm.NamespaceResolver(), schemaForNamespace.size(), properties);
schemaForNamespace.put(nsKey, schema);
}
Element element = new Element();
element.setName(qname.getLocalPart());
element.setType(getSchemaTypeString(typeAsQName, schema));
schema.addTopLevelElement(element);
}
}
}
return schemaForNamespace;
}
use of org.eclipse.persistence.internal.oxm.mappings.Descriptor in project eclipselink by eclipse-ee4j.
the class XMLVariableXPathMappingNodeValue method marshalSingleValue.
@Override
public boolean marshalSingleValue(XPathFragment xPathFragment, MarshalRecord marshalRecord, Object object, Object value, CoreAbstractSession session, NamespaceResolver namespaceResolver, MarshalContext marshalContext) {
if (null == value) {
return false;
}
Object originalValue = value;
VariableXPathObjectMapping mapping = this.getMapping();
Descriptor descriptor = (Descriptor) mapping.getReferenceDescriptor();
if (descriptor.hasInheritance()) {
Class<?> objectValueClass = value.getClass();
if (!(objectValueClass == descriptor.getJavaClass())) {
descriptor = (Descriptor) session.getDescriptor(objectValueClass);
}
}
Marshaller marshaller = marshalRecord.getMarshaller();
ObjectBuilder objectBuilder = (ObjectBuilder) descriptor.getObjectBuilder();
List extraNamespaces = objectBuilder.addExtraNamespacesToNamespaceResolver(descriptor, marshalRecord, session, true, true);
// Change to get the value from the object
String defaultRootElementString = descriptor.getDefaultRootElement();
marshalRecord.beforeContainmentMarshal(value);
XPathFragment rootFragment = mapping.getXPathFragmentForValue(value, marshalRecord.getNamespaceResolver(), marshalRecord.isNamespaceAware(), marshalRecord.getNamespaceSeparator());
XPathFragment groupingFragment = marshalRecord.openStartGroupingElements(namespaceResolver);
if (mapping.isAttribute()) {
ObjectBuilder tob = (ObjectBuilder) mapping.getReferenceDescriptor().getObjectBuilder();
MappingNodeValue textMappingNodeValue = (MappingNodeValue) tob.getRootXPathNode().getTextNode().getMarshalNodeValue();
Mapping textMapping = textMappingNodeValue.getMapping();
if (textMapping.isAbstractDirectMapping()) {
DirectMapping xmlDirectMapping = (DirectMapping) textMapping;
Object fieldValue = xmlDirectMapping.getFieldValue(xmlDirectMapping.valueFromObject(value, xmlDirectMapping.getField(), session), session, marshalRecord);
QName schemaType = ((Field) xmlDirectMapping.getField()).getSchemaTypeForValue(fieldValue, session);
marshalRecord.attribute(rootFragment, namespaceResolver, fieldValue, schemaType);
// marshalRecord.closeStartGroupingElements(groupingFragment);
return true;
} else {
return textMappingNodeValue.marshalSingleValue(rootFragment, marshalRecord, value, textMapping.getAttributeValueFromObject(value), session, namespaceResolver, marshalContext);
}
} else {
marshalRecord.closeStartGroupingElements(groupingFragment);
getXPathNode().startElement(marshalRecord, rootFragment, object, session, marshalRecord.getNamespaceResolver(), objectBuilder, value);
writeExtraNamespaces(extraNamespaces, marshalRecord, session);
marshalRecord.addXsiTypeAndClassIndicatorIfRequired(descriptor, (Descriptor) mapping.getReferenceDescriptor(), (Field) mapping.getField(), originalValue, value, false, false);
objectBuilder.buildRow(marshalRecord, value, session, marshaller, null);
marshalRecord.afterContainmentMarshal(object, value);
marshalRecord.endElement(rootFragment, namespaceResolver);
marshalRecord.removeExtraNamespacesFromNamespaceResolver(extraNamespaces, session);
}
return true;
}
use of org.eclipse.persistence.internal.oxm.mappings.Descriptor in project eclipselink by eclipse-ee4j.
the class XMLVariableXPathMappingNodeValue method attribute.
@Override
public void attribute(UnmarshalRecord unmarshalRecord, String namespaceURI, String localName, String value) {
Descriptor referenceDescriptor = (Descriptor) getMapping().getReferenceDescriptor();
ObjectBuilder treeObjectBuilder = (ObjectBuilder) referenceDescriptor.getObjectBuilder();
MappingNodeValue textMappingNodeValue = (MappingNodeValue) treeObjectBuilder.getRootXPathNode().getTextNode().getNodeValue();
Mapping textMapping = textMappingNodeValue.getMapping();
Object childObject = referenceDescriptor.getInstantiationPolicy().buildNewInstance();
if (textMapping.isAbstractDirectMapping()) {
DirectMapping xmlDirectMapping = (DirectMapping) textMappingNodeValue.getMapping();
Field xmlField = (Field) xmlDirectMapping.getField();
Object realValue = unmarshalRecord.getXMLReader().convertValueBasedOnSchemaType(xmlField, value, (ConversionManager) unmarshalRecord.getSession().getDatasourcePlatform().getConversionManager(), unmarshalRecord);
Object convertedValue = xmlDirectMapping.getAttributeValue(realValue, unmarshalRecord.getSession(), unmarshalRecord);
xmlDirectMapping.setAttributeValueInObject(childObject, convertedValue);
} else {
Object oldChildObject = unmarshalRecord.getCurrentObject();
CompositeObjectMapping nestedXMLCompositeObjectMapping = (CompositeObjectMapping) textMappingNodeValue.getMapping();
unmarshalRecord.setCurrentObject(childObject);
textMappingNodeValue.attribute(unmarshalRecord, namespaceURI, localName, value);
unmarshalRecord.setCurrentObject(oldChildObject);
}
setXPathInObject(namespaceURI, localName, childObject);
setOrAddAttributeValue(unmarshalRecord, childObject, null, null);
}
use of org.eclipse.persistence.internal.oxm.mappings.Descriptor in project eclipselink by eclipse-ee4j.
the class SAXUnmarshaller method unmarshal.
@Override
public Object unmarshal(org.xml.sax.XMLReader xmlReader, InputSource inputSource, Class<?> clazz) {
try {
Context xmlContext = xmlUnmarshaller.getContext();
if (xmlContext.hasDocumentPreservation() || (Node.class.isAssignableFrom(clazz) && xmlUnmarshaller.isApplicationXML())) {
SAXDocumentBuilder saxDocumentBuilder = new SAXDocumentBuilder();
xmlReader.setContentHandler(saxDocumentBuilder);
xmlReader.parse(inputSource);
return unmarshal(saxDocumentBuilder.getDocument().getDocumentElement(), clazz);
}
UnmarshalRecord unmarshalRecord = null;
Descriptor xmlDescriptor = null;
CoreAbstractSession session = null;
boolean isPrimitiveWrapper = false;
// via XMLRootRecord.
if (clazz == CoreClassConstants.OBJECT) {
SAXUnmarshallerHandler saxUnmarshallerHandler = new SAXUnmarshallerHandler(xmlUnmarshaller.getContext());
saxUnmarshallerHandler.setXMLReader((XMLReader) xmlReader);
saxUnmarshallerHandler.setUnmarshaller(xmlUnmarshaller);
saxUnmarshallerHandler.setKeepAsElementPolicy(KEEP_UNKNOWN_AS_ELEMENT);
xmlReader.setContentHandler(saxUnmarshallerHandler);
xmlReader.parse(inputSource);
// resolve any mapping references
saxUnmarshallerHandler.resolveReferences();
return saxUnmarshallerHandler.getObject();
} else {
// try and get a Unit Of Work from the XMLContext
try {
session = xmlContext.getSession(clazz);
xmlDescriptor = (Descriptor) session.getDescriptor(clazz);
unmarshalRecord = xmlUnmarshaller.createUnmarshalRecord(xmlDescriptor, session);
} catch (XMLMarshalException xme) {
if (xme.getErrorCode() == XMLMarshalException.DESCRIPTOR_NOT_FOUND_IN_PROJECT) {
isPrimitiveWrapper = isPrimitiveWrapper(clazz);
if (isPrimitiveWrapper) {
unmarshalRecord = xmlUnmarshaller.createRootUnmarshalRecord(clazz);
} else {
throw xme;
}
} else {
throw xme;
}
}
}
XMLReader extendedXMLReader;
if (xmlReader instanceof XMLReader) {
extendedXMLReader = (XMLReader) xmlReader;
} else {
extendedXMLReader = new XMLReader(xmlReader);
}
unmarshalRecord.setXMLReader(extendedXMLReader);
unmarshalRecord.setUnmarshaller(xmlUnmarshaller);
setContentHandler(extendedXMLReader, unmarshalRecord);
extendedXMLReader.setLexicalHandler(unmarshalRecord);
extendedXMLReader.parse(inputSource);
// resolve mapping references
unmarshalRecord.resolveReferences(session, xmlUnmarshaller.getIDResolver());
if (isPrimitiveWrapper || clazz == CoreClassConstants.OBJECT) {
return unmarshalRecord.getCurrentObject();
}
return xmlDescriptor.wrapObjectInXMLRoot(unmarshalRecord, this.isResultAlwaysXMLRoot);
} catch (IOException e) {
throw XMLMarshalException.unmarshalException(e);
} catch (SAXException e) {
throw convertSAXException(e);
} finally {
xmlUnmarshaller.getStringBuffer().reset();
}
}
use of org.eclipse.persistence.internal.oxm.mappings.Descriptor in project eclipselink by eclipse-ee4j.
the class SAXUnmarshallerHandler method startElement.
@Override
public void startElement(String namespaceURI, String localName, String qName, Attributes atts) throws SAXException {
try {
String name;
if (localName == null || localName.length() == 0) {
name = qName;
} else {
name = localName;
}
XPathQName rootQName;
if (namespaceURI == null || namespaceURI.length() == 0) {
rootQName = new XPathQName(name, xmlReader.isNamespaceAware());
} else {
rootQName = new XPathQName(namespaceURI, name, xmlReader.isNamespaceAware());
}
Class<?> primitiveWrapperClass = null;
Descriptor xmlDescriptor = xmlContext.getDescriptor(rootQName);
// if no match on root element look for xsi:type
if (xmlDescriptor == null || (unmarshaller.getMediaType() == MediaType.APPLICATION_JSON && unmarshaller.getJsonTypeConfiguration().getJsonTypeAttributeName() != null && !Constants.SCHEMA_TYPE_ATTRIBUTE.equals(unmarshaller.getJsonTypeConfiguration().getJsonTypeAttributeName()))) {
boolean isPrimitiveType = false;
String type = null;
if (xmlReader.isNamespaceAware()) {
type = atts.getValue(javax.xml.XMLConstants.W3C_XML_SCHEMA_INSTANCE_NS_URI, Constants.SCHEMA_TYPE_ATTRIBUTE);
} else if (unmarshaller.getMediaType() != MediaType.APPLICATION_JSON || unmarshaller.getJsonTypeConfiguration().useJsonTypeCompatibility()) {
type = atts.getValue(Constants.EMPTY_STRING, Constants.SCHEMA_TYPE_ATTRIBUTE);
} else if (unmarshaller.getMediaType() == MediaType.APPLICATION_JSON && unmarshaller.getJsonTypeConfiguration().getJsonTypeAttributeName() != null) {
type = atts.getValue(Constants.EMPTY_STRING, unmarshaller.getJsonTypeConfiguration().getJsonTypeAttributeName());
}
if (null != type) {
XPathFragment typeFragment = new XPathFragment(type, xmlReader.getNamespaceSeparator(), xmlReader.isNamespaceAware());
// set the prefix using a reverse key lookup by uri value on namespaceMap
if (xmlReader.isNamespaceAware() && null != unmarshalNamespaceResolver) {
typeFragment.setNamespaceURI(unmarshalNamespaceResolver.getNamespaceURI(typeFragment.getPrefix()));
}
Descriptor lookupDescriptor = xmlContext.getDescriptorByGlobalType(typeFragment);
if (lookupDescriptor == null) {
QName lookupQName = null;
if (typeFragment.getNamespaceURI() == null) {
lookupQName = new QName(javax.xml.XMLConstants.W3C_XML_SCHEMA_NS_URI, typeFragment.getLocalName());
} else {
lookupQName = new QName(typeFragment.getNamespaceURI(), typeFragment.getLocalName());
}
// check to see if type attribute represents simple type
if (null == session) {
session = (CoreAbstractSession) xmlContext.getSession();
}
ConversionManager conversionManager = (ConversionManager) session.getDatasourcePlatform().getConversionManager();
primitiveWrapperClass = conversionManager.javaType(lookupQName);
} else {
// found descriptor based on type attribute
xmlDescriptor = lookupDescriptor;
session = xmlContext.getSession(xmlDescriptor);
}
}
} else {
if (null != xmlDescriptor.getDefaultRootElementField() && !unmarshaller.isResultAlwaysXMLRoot()) {
String descLocalName = xmlDescriptor.getDefaultRootElementField().getXPathFragment().getLocalName();
if (descLocalName != null && descLocalName.equals(localName)) {
String descUri = xmlDescriptor.getDefaultRootElementField().getXPathFragment().getNamespaceURI();
if (!xmlReader.isNamespaceAware() || (xmlReader.isNamespaceAware() && ((namespaceURI == null && descUri == null) || (namespaceURI != null && namespaceURI.length() == 0 && descUri == null) || (namespaceURI != null && namespaceURI.equals(descUri))))) {
// found a descriptor based on root element then know we won't need to wrap in an XMLRoot
shouldWrap = false;
}
}
}
if (xmlDescriptor.hasInheritance()) {
// if descriptor has inheritance check class indicator
session = xmlContext.getSession(xmlDescriptor);
UnmarshalRecord tmpUnmarshalRecord = new UnmarshalRecordImpl(null);
tmpUnmarshalRecord.setUnmarshaller(unmarshaller);
tmpUnmarshalRecord.setUnmarshalNamespaceResolver(unmarshalNamespaceResolver);
tmpUnmarshalRecord.setXMLReader(this.getXMLReader());
tmpUnmarshalRecord.setAttributes(atts);
Class<?> classValue = xmlDescriptor.getInheritancePolicy().classFromRow(new org.eclipse.persistence.oxm.record.UnmarshalRecord(tmpUnmarshalRecord), session);
if (classValue == null) {
// no xsi:type attribute - look for type indicator on the default root element
QName leafElementType = xmlDescriptor.getDefaultRootElementType();
// if we have a user-set type, try to get the class from the inheritance policy
if (leafElementType != null) {
Object indicator = xmlDescriptor.getInheritancePolicy().getClassIndicatorMapping().get(leafElementType);
if (indicator != null) {
classValue = (Class) indicator;
}
}
}
if (classValue != null) {
xmlDescriptor = (Descriptor) session.getDescriptor(classValue);
} else {
// sure it is non-abstract
if (Modifier.isAbstract(xmlDescriptor.getJavaClass().getModifiers())) {
// need to throw an exception here
throw DescriptorException.missingClassIndicatorField(tmpUnmarshalRecord, (org.eclipse.persistence.oxm.XMLDescriptor) xmlDescriptor.getInheritancePolicy().getDescriptor());
}
}
}
}
if (null == xmlDescriptor) {
// check for a cached object and look for descriptor by class
Object obj = this.xmlReader.getCurrentObject(session, null);
if (obj != null) {
xmlDescriptor = (Descriptor) xmlContext.getSession(obj.getClass()).getDescriptor(obj.getClass());
}
}
if (null == xmlDescriptor && primitiveWrapperClass == null) {
if (!this.keepAsElementPolicy.isKeepNoneAsElement()) {
this.documentBuilder = new SAXDocumentBuilder();
documentBuilder.startDocument();
// start any prefixes that have already been started
for (String prefix : this.unmarshalNamespaceResolver.getPrefixes()) {
documentBuilder.startPrefixMapping(prefix, this.unmarshalNamespaceResolver.getNamespaceURI(prefix));
}
documentBuilder.startElement(namespaceURI, localName, qName, atts);
this.xmlReader.setContentHandler(documentBuilder);
return;
}
Class<?> unmappedContentHandlerClass = unmarshaller.getUnmappedContentHandlerClass();
if (null == unmappedContentHandlerClass) {
throw XMLMarshalException.noDescriptorWithMatchingRootElement(rootQName.toString());
} else {
UnmappedContentHandler unmappedContentHandler;
try {
PrivilegedNewInstanceFromClass privilegedNewInstanceFromClass = new PrivilegedNewInstanceFromClass(unmappedContentHandlerClass);
unmappedContentHandler = (UnmappedContentHandler) privilegedNewInstanceFromClass.run();
} catch (ClassCastException e) {
throw XMLMarshalException.unmappedContentHandlerDoesntImplement(e, unmappedContentHandlerClass.getName());
} catch (IllegalAccessException e) {
throw XMLMarshalException.errorInstantiatingUnmappedContentHandler(e, unmappedContentHandlerClass.getName());
} catch (InstantiationException e) {
throw XMLMarshalException.errorInstantiatingUnmappedContentHandler(e, unmappedContentHandlerClass.getName());
}
UnmappedContentHandlerWrapper unmappedContentHandlerWrapper = new UnmappedContentHandlerWrapper(unmappedContentHandler, this);
unmappedContentHandler.startElement(namespaceURI, localName, qName, atts);
xmlReader.setContentHandler(unmappedContentHandler);
setObject(unmappedContentHandlerWrapper.getCurrentObject());
return;
}
}
if (xmlDescriptor == null && primitiveWrapperClass != null) {
session = xmlContext.getSession((Descriptor) null);
rootRecord = unmarshaller.createRootUnmarshalRecord(primitiveWrapperClass);
rootRecord.setSession((CoreAbstractSession) unmarshaller.getContext().getSession());
} else {
if (session == null) {
session = xmlContext.getSession(xmlDescriptor);
}
rootRecord = unmarshaller.createUnmarshalRecord(xmlDescriptor, session);
}
this.descriptor = xmlDescriptor;
rootRecord.setUnmarshaller(this.unmarshaller);
rootRecord.setXMLReader(this.getXMLReader());
if (locator != null) {
rootRecord.setDocumentLocator(xmlReader.getLocator());
}
rootRecord.setAttributes(atts);
boolean hasNilAttribute = (atts != null && null != atts.getValue(javax.xml.XMLConstants.W3C_XML_SCHEMA_INSTANCE_NS_URI, Constants.SCHEMA_NIL_ATTRIBUTE));
rootRecord.setNil(isNil || hasNilAttribute);
rootRecord.setUnmarshalNamespaceResolver(unmarshalNamespaceResolver);
rootRecord.startDocument();
rootRecord.initializeRecord(null);
xmlReader.setContentHandler(rootRecord);
xmlReader.setLexicalHandler(rootRecord);
Object attributeGroup = this.unmarshaller.getUnmarshalAttributeGroup();
if (attributeGroup != null) {
if (attributeGroup.getClass() == CoreClassConstants.STRING) {
CoreAttributeGroup group = descriptor.getAttributeGroup((String) attributeGroup);
if (group != null) {
rootRecord.setUnmarshalAttributeGroup(group);
} else {
// Error
}
} else if (attributeGroup instanceof CoreAttributeGroup) {
rootRecord.setUnmarshalAttributeGroup((CoreAttributeGroup) attributeGroup);
} else {
// Error case
}
}
rootRecord.startElement(namespaceURI, localName, qName, atts);
// if we located the descriptor via xsi:type attribute, create and
// return an XMLRoot object
} catch (EclipseLinkException e) {
if (null == xmlReader.getErrorHandler()) {
throw e;
} else {
SAXParseException saxParseException = new SAXParseException(null, null, null, 0, 0, e);
xmlReader.getErrorHandler().error(saxParseException);
}
}
}
Aggregations