-package org.simantics.xml.sax;\r
-\r
-import java.io.FileNotFoundException;\r
-import java.io.PrintWriter;\r
-import java.io.StringWriter;\r
-import java.util.ArrayList;\r
-import java.util.LinkedHashSet;\r
-import java.util.List;\r
-import java.util.Set;\r
-\r
-import javax.xml.namespace.QName;\r
-\r
-import org.simantics.utils.datastructures.BijectionMap;\r
-import org.simantics.xml.sax.configuration.AttributeComposition;\r
-import org.simantics.xml.sax.configuration.Configuration;\r
-import org.simantics.xml.sax.configuration.IDReference;\r
-import org.w3._2001.xmlschema.Annotated;\r
-import org.w3._2001.xmlschema.Attribute;\r
-import org.w3._2001.xmlschema.AttributeGroup;\r
-import org.w3._2001.xmlschema.Element;\r
-import org.w3._2001.xmlschema.LocalComplexType;\r
-import org.w3._2001.xmlschema.LocalSimpleType;\r
-import org.w3._2001.xmlschema.NamedAttributeGroup;\r
-import org.w3._2001.xmlschema.OpenAttrs;\r
-import org.w3._2001.xmlschema.Restriction;\r
-import org.w3._2001.xmlschema.Schema;\r
-import org.w3._2001.xmlschema.SimpleType;\r
-import org.w3._2001.xmlschema.TopLevelAttribute;\r
-\r
-public class OntologyGenerator extends SchemaConversionBase {\r
- \r
- public OntologyGenerator(Configuration configuration) {\r
- super(configuration);\r
- }\r
-\r
- String ontRoot = "ONT.";\r
- String commentTag = "//";\r
- \r
- Schema schema;\r
- String ontologyName;\r
- String className;\r
- \r
- SchemaConverter converter;\r
- \r
- PrintWriter writer = null;\r
- \r
- \r
- \r
- \r
- \r
- public void createOntology(Schema schema, String ontologyName, String className, SchemaConverter converter) throws FileNotFoundException {\r
- this.schema = schema;\r
- this.converter = converter;\r
- this.ontologyName = ontologyName;\r
- this.className = className;\r
- \r
-// for (OpenAttrs attrs : schema.getIncludeOrImportOrRedefine()) {\r
-// if (attrs instanceof Annotation) {\r
-// Annotation ann = (Annotation)attrs;\r
-// for (Object o : ann.getAppinfoOrDocumentation()) {\r
-// if (o instanceof Documentation) {\r
-// Documentation doc = (Documentation)o;\r
-// } else if (o instanceof Appinfo) {\r
-// Appinfo info = (Appinfo)o;\r
-// }\r
-// }\r
-// }\r
-// }\r
- \r
- \r
- StringWriter stringWriter = null;\r
- if (converter.getOntologyFile() == null) {\r
- stringWriter = new StringWriter();\r
- writer = new PrintWriter(stringWriter);\r
- } else {\r
- writer = new PrintWriter(converter.getOntologyFile());\r
- }\r
- \r
- handle(schema);\r
- \r
- writer.flush();\r
- writer.close();\r
- if (stringWriter != null)\r
- System.out.println(stringWriter.toString());\r
- }\r
- \r
- protected void handle(Schema schema) {\r
- String parts[] = ontologyName.split("/");\r
- String name = parts[parts.length-1];\r
- ontRoot = name.substring(0, Math.min(3, name.length())).toUpperCase();\r
- String version = schema.getVersion();\r
- if (version == null)\r
- version = "1.0";\r
-\r
- \r
- for (String s : converter.getHeader()) {\r
- writer.println(commentTag + " " + s); \r
- }\r
- writer.println();\r
- writer.println("L0 = <http://www.simantics.org/Layer0-1.1>");\r
- writer.println("XML = <http://www.simantics.org/XML-1.0>");\r
- writer.println();\r
- writer.println(ontRoot + " = <" + ontologyName +"-"+ version+"> : L0.Ontology");\r
- writer.println(" @L0.new");\r
- writer.println(" L0.HasResourceClass \"" + className +"\"");\r
- writer.println();\r
- writer.println();\r
- \r
- ontRoot += ".";\r
- // TODO : these could be created in separate base ontology.\r
-// writer.println(commentTag + " Built-in types");\r
-// writer.println();\r
-// writer.println(ontRoot+"XML : L0.Library");\r
-// writer.println(ontRoot+"XML.hasAttribute <R L0.HasProperty");\r
-// writer.println(ontRoot+"XML.hasID <R "+ontRoot+"XML.hasAttribute : L0.FunctionalRelation");\r
-// writer.println(" --> L0.String");\r
-// writer.println(ontRoot+"XML.ComplexType <T L0.Entity");\r
-// writer.println(ontRoot+"XML.hasComplexType <R L0.IsComposedOf");\r
-// writer.println(ontRoot+"XML.AttributeGroup <T L0.Entity");\r
-// writer.println(ontRoot+"XML.Element <T L0.Entity");\r
-// writer.println(ontRoot+"XML.hasElement <R L0.IsComposedOf");\r
-// writer.println(ontRoot+"XML.ElementList <T L0.List");\r
-// writer.println(ontRoot+"XML.hasElementList <R L0.IsComposedOf");\r
-// writer.println(ontRoot+"XML.hasOriginalElementList <R " + ontRoot+"XML.hasElementList");\r
-// writer.println(ontRoot+"XML.hasReference <R L0.IsRelatedTo");\r
-// writer.println(ontRoot+"XML.hasExternalReference <R L0.IsRelatedTo");\r
-// writer.println(" L0.InverseOf " + ontRoot+"XML.externalReferenceOf <R L0.IsRelatedTo");\r
-// writer.println();\r
- writer.println(ontRoot+"ComplexTypes : L0.Library");\r
- writer.println(ontRoot+"AttributeGroups : L0.Library");\r
- writer.println();\r
- writer.println(commentTag + " Interpreted from schema");\r
- writer.println();\r
- \r
- super.handle(schema);\r
- }\r
- \r
- protected String getType(QName qtype) {\r
- String ontType = getL0TypeFromPrimitiveType(qtype);\r
- if (ontType != null)\r
- return ontType;\r
- else if (isComplexTypeRef(qtype.getLocalPart()))\r
- return ontRoot+getComplexTypePrefix()+qtype.getLocalPart();\r
- else if (isElementRef(qtype.getLocalPart()))\r
- return ontRoot+qtype.getLocalPart();\r
- else if (qtype.getPrefix() != null && qtype.getPrefix().length() > 0) {\r
- return ontRoot+qtype.getPrefix()+qtype.getLocalPart();\r
- }\r
- throw new RuntimeException("Reference to unknown type " + qtype.getLocalPart());\r
- }\r
- \r
- @Override\r
- protected void handle(TopLevelAttribute topLevelAttribute) {\r
- super.handle(topLevelAttribute);\r
- writer.println();\r
- }\r
- \r
- @Override\r
- protected void handleSimpleType(SchemaObject topLevelSimpleType) {\r
- super.handleSimpleType(topLevelSimpleType);\r
- writer.println();\r
- }\r
- \r
- \r
- public static String getComplexTypePrefix() {\r
- return "ComplexTypes.";\r
- }\r
- \r
- public static String getAttributeGroupPrefix() {\r
- return "AttributeGroups.";\r
- }\r
- \r
- @Override\r
- protected void handle(SchemaObject parent, SchemaElement indicator, List<SchemaElement> elements) {\r
- if (indicator.getType() == SchemaElement.ElementType.SEQUENCE || (indicator.getType() == SchemaElement.ElementType.CHOICE && indicator.getRestriction().many())) {\r
- for (SchemaElement e : elements) {\r
- handle(parent, indicator, e);\r
- }\r
- } else if (indicator.getType() == SchemaElement.ElementType.CHOICE) {\r
- String name = getChoiceName(elements);\r
- boolean single = true;\r
- for (SchemaElement e : elements) {\r
- if (e.getRestriction().many()) {\r
- single = false;\r
- break;\r
- }\r
- }\r
- String relationName = ontRoot+getName(parent)+".has"+name;\r
- writer.print(relationName);\r
- \r
- List<String> types = new ArrayList<String>();\r
- for (SchemaElement e : elements) {\r
- Element localElement = e.getElement();\r
- QName refType = null;\r
- String type = null;\r
- \r
- if (localElement.getName() != null) {\r
- refType = localElement.getType();\r
- type = getL0TypeFromPrimitiveType(refType); \r
- } else if (localElement.getRef() != null) {\r
- refType = localElement.getRef();\r
- type = getL0TypeFromPrimitiveType(refType);\r
- }\r
- if (type == null) {\r
- SchemaObject obj = getWithName(parent, refType.getLocalPart());\r
- types.add(ontRoot+getName(obj,"has"));\r
- } \r
- }\r
- if (types.size() > 0) {\r
- for (String type : types) {\r
- writer.print(" <R " + type);\r
- }\r
- } else {\r
- writer.print(" <R XML.hasElement");\r
- }\r
- \r
- writer.println();\r
- \r
- for (SchemaElement e : elements) {\r
- Element localElement = e.getElement();\r
- QName refType = null;\r
- String type = null;\r
- if (localElement.getName() != null) {\r
- refType = localElement.getType();\r
- type = getType(refType); \r
- } else if (localElement.getRef() != null) {\r
- refType = localElement.getRef();\r
- type = getType(refType);\r
- }\r
- if (type != null) {\r
- writer.println(" --> " + type);\r
- }\r
- }\r
- if (!single) {\r
- writer.println(ontRoot+name+ "List <T XML.ElementList");\r
- if (types.size() == 0) {\r
- writer.println(relationName+ "List <R XML.hasElementList : L0.FunctionalRelation");\r
- } else {\r
- writer.print(relationName+ "List");\r
- for (String type : types) {\r
- writer.print(" <R " + type+"List");\r
- }\r
- writer.println(" : L0.FunctionalRelation");\r
- }\r
- writer.println(" --> " + ontRoot+name+"List");\r
- }\r
- }\r
- \r
- }\r
- \r
- \r
- \r
- @Override\r
- //protected void handleIndicator(SchemaObject parent, SchemaElement indicator, SchemaElement element, boolean reference, String refName, QName refType) {\r
- protected void handleIndicator(SchemaObject parent, SchemaElement indicator, SchemaElement element, String refName, RefType refType) {\r
- if (refType != refType.Element) {\r
- QName referenceType = null;\r
- if (refType == RefType.Type) {\r
- referenceType = element.getElement().getType();\r
- //refName = element.getElement().getName()\r
- SchemaObject eObj = elements.get(element.getElement());\r
- if (refName == null)\r
- refName = eObj.getName();\r
- } else {\r
- referenceType = element.getElement().getRef();\r
- if (refName == null)\r
- refName = referenceType.getLocalPart();\r
- }\r
- String type = getL0TypeFromPrimitiveType(referenceType);\r
- SchemaObject obj = null;\r
- if (type == null) {\r
- obj = getWithName(parent, referenceType.getLocalPart());\r
- \r
- writer.println(ontRoot+getName(parent)+".has"+refName + " <R " + ontRoot+ getName(obj,"has"));\r
- writer.println(" --> " + ontRoot+getName(obj));\r
- } else {\r
- writer.println(ontRoot+getName(parent)+".has"+refName + " <R XML.hasElement");\r
- writer.println(" --> " + getType(referenceType));\r
- }\r
- \r
- if (useElementList(parent, indicator,element, refType == RefType.Reference, refName, referenceType)) {\r
- \r
- if (type == null) {\r
- writer.println(ontRoot+getName(parent)+"."+refName + "List <T XML.ElementList");\r
- writer.println(ontRoot+getName(parent)+".has"+refName + "List <R " + ontRoot+getName(obj,"has")+"List : L0.FunctionalRelation");\r
- } else {\r
- writer.println(ontRoot+getName(parent)+"."+refName + "List <T XML.ElementList");\r
- writer.println(ontRoot+getName(parent)+".has"+refName + "List <R XML.hasElementList : L0.FunctionalRelation"); \r
- }\r
- }\r
- } else {\r
- Element attrs = element.getElement();\r
- SchemaObject obj = getWithObj(parent, attrs);\r
- if (refName == null)\r
- refName = obj.getName();\r
- \r
- writer.println(ontRoot+getName(parent)+".has"+refName + " <R " + ontRoot+ getName(obj,"has"));\r
- writer.println(" --> " + ontRoot+getName(obj));\r
- if (useElementList(parent, indicator,element, false, refName, new QName(obj.getName()))) {\r
- writer.println(ontRoot+getName(parent)+"."+refName + "List <T XML.ElementList");\r
- writer.println(ontRoot+getName(parent)+".has"+refName + "List <R " + ontRoot+getName(obj,"has")+"List : L0.FunctionalRelation");\r
- }\r
- }\r
- \r
- }\r
- \r
- @Override\r
- protected void handleIndicator(SchemaObject parent, SchemaElement indicator, SchemaElement any) {\r
- \r
- }\r
- \r
- @Override\r
- protected void handle(SchemaObject parent, Attribute attribute) {\r
- String name = attribute.getName();\r
- QName primitiveType = attribute.getType();\r
- LocalSimpleType simpleType = attribute.getSimpleType();\r
- QName ref = attribute.getRef();\r
- \r
- String relationName;\r
- String relationType;\r
- if (name != null) {\r
- relationName = ontRoot+"has"+name;\r
- if (parent != null)\r
- relationName = ontRoot+getName(parent)+".has"+name;\r
- relationType = "XML.hasAttribute";\r
- }\r
- else if (ref != null && parent != null) {\r
- relationName = ontRoot+getName(parent)+".has"+ref.getLocalPart();\r
- relationType = ontRoot+"has"+ref.getLocalPart();\r
- } else {\r
- throw new RuntimeException();\r
- }\r
- boolean id = false;\r
- String ontType = null;\r
- if (primitiveType != null) {\r
- ontType = getL0TypeFromPrimitiveType(primitiveType);\r
- if (ontType != null) {\r
- id = getTypeEntry(primitiveType).id;\r
- if (id)\r
- relationType = "XML.hasID";\r
- } else {\r
- \r
- }\r
- } else if (simpleType != null){\r
- Restriction restriction = simpleType.getRestriction();\r
- if (restriction == null || simpleType.getUnion() != null || simpleType.getName() != null || simpleType.getId() != null)\r
- throw new RuntimeException();\r
- QName base = restriction.getBase();\r
- \r
- \r
- ontType = getL0TypeFromPrimitiveType(base);\r
- \r
-// for (Object facetWrap : restriction.getFacets()) {\r
-// JAXBElement<?> element = (JAXBElement<?>)facetWrap;\r
-// QName elementName = element.getName();\r
-// Facet facet = (Facet)element.getValue(); \r
-// }\r
- }\r
- \r
- \r
- \r
- writer.println(relationName+ " <R " + relationType + ": L0.FunctionalRelation");\r
- if (id) {\r
- // no need to add range restriction\r
- } else if (ontType != null) {\r
- writer.println(" --> " + ontType);\r
- } else if (primitiveType != null) {\r
- writer.println(" <R "+ontRoot+"has"+primitiveType.getLocalPart());\r
- }\r
- }\r
- \r
- @Override\r
- protected void handleAttributes(SchemaObject simpleTypeObj) {\r
-// SchemaObject parent = simpleTypeObj.getParent();\r
-// SimpleType simpleType = simpleTypeObj.getSimpleType();\r
-// Restriction restriction = simpleType.getRestriction();\r
-// QName base = restriction.getBase();\r
-// String ontType = getL0TypeFromPrimitiveType(base);\r
- }\r
- \r
- @Override\r
- protected void handle(SchemaObject parent, AttributeGroup attributeGroup) {\r
- if (parent == null) {\r
- NamedAttributeGroup group = (NamedAttributeGroup)attributeGroup;\r
- writer.println(ontRoot+getAttributeGroupPrefix()+group.getName()+ " <T XML.AttributeGroup");\r
- SchemaObject obj = new SchemaObject(parent,attributeGroup);\r
- for (Annotated annotated : group.getAttributeOrAttributeGroup()) {\r
- if (annotated instanceof Attribute) {\r
- //handle(getAttributeGroupPrefix()+group.getName(),(Attribute)annotated);\r
- handle(obj,(Attribute)annotated);\r
- } else if (annotated instanceof AttributeGroup) {\r
- throw new RuntimeException("Cannot handle nested attribute groups");\r
- }\r
- }\r
- } else {\r
- writer.println(ontRoot+getName(parent) +" L0.Inherits " + ontRoot + getAttributeGroupPrefix() + attributeGroup.getRef().getLocalPart());\r
- }\r
- \r
- }\r
- \r
- @Override\r
- protected void handleAttributeComposition(SchemaObject parent, AttributeComposition composition, BijectionMap<org.simantics.xml.sax.configuration.Attribute, Annotated> attributes) {\r
- Attribute compositionAttribute = new Attribute();\r
- compositionAttribute.setName(composition.getName());\r
- QName type = new QName(CONVERSION_NS, composition.getType());\r
- compositionAttribute.setType(type);\r
- handle(parent, compositionAttribute);\r
- }\r
- \r
- @Override\r
- protected void handleSimpleType(SchemaObject parent, SchemaObject simpleTypeObj) {\r
- SimpleType simpleType = simpleTypeObj.getSimpleType();\r
- String name = simpleType.getName();\r
- \r
- org.w3._2001.xmlschema.List list = simpleType.getList();\r
- if (list != null) {\r
- // TODO : process restriction in lists\r
- String relationName = ontRoot+"has"+name;\r
- if (parent != null)\r
- relationName = ontRoot+getName(parent)+".has"+name;\r
- writer.println(relationName+ " <R XML.hasAttribute : L0.FunctionalRelation");\r
- \r
- String ontType = getL0Type(new QName(SCHEMA_NS, "string"));\r
- writer.println(" --> " + ontType);\r
- } else {\r
- Restriction restriction = simpleType.getRestriction();\r
- if (restriction == null || simpleType.getUnion() != null || simpleType.getId() != null)\r
- throw new RuntimeException(simpleType.getName() + " restriction error");\r
- QName base = restriction.getBase();\r
- \r
- String relationName = ontRoot+"has"+name;\r
- if (parent != null)\r
- relationName = ontRoot+getName(parent)+".has"+name;\r
- \r
- writer.println(relationName+ " <R XML.hasAttribute : L0.FunctionalRelation");\r
- \r
- String ontType = getL0Type(base);\r
- writer.println(" --> " + ontType);\r
- }\r
- }\r
- \r
- @Override\r
- protected void handleComplexType(SchemaObject topLevelComplexType) {\r
- String name = getName(topLevelComplexType);\r
- if (name.contains("Pcurve"))\r
- System.out.println();\r
-// if (parent != null)\r
-// name = parent +"_"+name;\r
- \r
- String relationName = ontRoot+getName(topLevelComplexType,"has");//ontRoot+"has"+name;\r
- \r
- writer.println(relationName+ " <R XML.hasComplexType");\r
- writer.println(relationName+ "List <R XML.hasElementList");\r
- //writer.println(" --> " + ontRoot+getComplexTypePrefix()+name);\r
- writer.println(" --> " + ontRoot+name);\r
- writer.println();\r
- String baseType = "XML.ComplexType";\r
-\r
- QName base = getComplexTypeBase(topLevelComplexType.getComplexType());\r
- if (base != null) {\r
- baseType = getType(base);\r
- }\r
- base = getSimpleTypeBase(topLevelComplexType.getSimpleType());\r
- if (base != null) {\r
- baseType = getType(base);\r
- }\r
- //writer.println(ontRoot+getComplexTypePrefix()+name+ " <T "+baseType);\r
- writer.println(ontRoot+name+ " <T "+baseType);\r
- super.handleComplexType(topLevelComplexType);\r
- writer.println();\r
- }\r
- \r
- @Override\r
- protected void handleElement(SchemaObject elementObj) {\r
- Element element = elementObj.getElement();\r
- String name = getName(elementObj);//element.getName();\r
- \r
- if ("Text".equals(name))\r
- System.out.println();\r
- \r
- String type = "XML.Element";\r
- Set<String> types = new LinkedHashSet<String>();\r
- if (element.getType() != null) {\r
- types.add(getType(element.getType()));\r
- }\r
- QName base = getElementBase(element);\r
- if (base != null) {\r
- if (base.getNamespaceURI().equals(SCHEMA_NS)) {\r
- String l0Type = getL0Type(base);\r
- if (l0Type == null)\r
- throw new RuntimeException("Cannot get L0 type for " + base.getLocalPart());\r
- types.add(l0Type);\r
- } else if (isElementRef(base.getLocalPart()))\r
- types.add(ontRoot+base.getLocalPart());\r
- else\r
- types.add(ontRoot+getComplexTypePrefix()+base.getLocalPart());\r
- }\r
- QName substitution = element.getSubstitutionGroup();\r
- if (substitution != null) {\r
- if (isElementRef(substitution.getLocalPart()))\r
- types.add(ontRoot+substitution.getLocalPart());\r
- else\r
- types.add( ontRoot+getComplexTypePrefix()+substitution.getLocalPart());\r
- }\r
- for (String t : types) {\r
- type += " <T " + t;\r
- }\r
-\r
- String relationName = ontRoot+getName(elementObj,"has");//ontRoot+"has"+name;\r
-// if (elementObj.getParent() != null) {\r
-// //relationName = ontRoot+getComplexTypePrefix()+"has"+name.substring(getComplexTypePrefix().length());\r
-// relationName = ontRoot+getName(elementObj.getParent()) + "has"+element.getName();\r
-// }\r
- writer.println(relationName+ " <R XML.hasElement");\r
- writer.println(relationName+ "List <R XML.hasElementList");\r
- \r
- writer.println(ontRoot+name+ " <T "+type);\r
- \r
- LocalComplexType complexType = element.getComplexType();\r
- LocalSimpleType simpleType = element.getSimpleType();\r
- \r
- if (complexType != null) {\r
- SchemaObject complexTypeObj = complexTypes.get(complexType);\r
- handleElementComplexTypeAttributes(complexTypeObj);\r
- handleComplexTypeExtension(complexTypeObj);\r
- } else if (simpleType != null) {\r
- SchemaObject simpleTypeObj = simpleTypes.get(simpleType);\r
- handleElementSimpleTypeAttributes(simpleTypeObj);\r
- }\r
- \r
- List<IDReference> references = getIDReferences(element);\r
- \r
- for (IDReference ref : references) {\r
- writer.println(ontRoot+name+"."+ref.getReference().getName()+ " <R XML.hasReference");\r
- }\r
- \r
- writer.println();\r
- }\r
- \r
- public static String getName(SchemaObject obj) {\r
- if (obj.getParent() == null) {\r
- switch (obj.getType()) {\r
- case COMPLEX_TYPE:\r
- return getComplexTypePrefix()+obj.getName();\r
- case ELEMENT:\r
- return obj.getName();\r
- case ATTRIBUTE_GROUP:\r
- return getAttributeGroupPrefix()+obj.getName();\r
- case SIMPLE_TYPE:\r
- return obj.getName();\r
- }\r
- } else {\r
- SchemaObject o = obj;\r
- SchemaObject prev = null;\r
- String name = "";\r
- while (o != null){\r
- if (o.getName() != null)\r
- name = o.getName()+"."+name;\r
- prev = o;\r
- o = o.getParent();\r
- }\r
- name = name.substring(0, name.length()-1);\r
- switch (prev.getType()) {\r
- case COMPLEX_TYPE:\r
- return getComplexTypePrefix()+name;\r
- case ELEMENT:\r
- return name;\r
- case ATTRIBUTE_GROUP:\r
- return getAttributeGroupPrefix()+name;\r
- case SIMPLE_TYPE:\r
- return name;\r
- }\r
- }\r
- throw new RuntimeException();\r
- \r
- }\r
- \r
- public static String getName(SchemaObject obj, String rel) {\r
- if (obj.getParent() == null) {\r
- switch (obj.getType()) {\r
- case COMPLEX_TYPE:\r
- return getComplexTypePrefix()+rel+obj.getName();\r
- case ELEMENT:\r
- return rel+obj.getName();\r
- case ATTRIBUTE_GROUP:\r
- return getAttributeGroupPrefix()+rel+obj.getName();\r
- case SIMPLE_TYPE:\r
- return rel+obj.getName();\r
- }\r
- } else {\r
- SchemaObject o = obj;\r
- SchemaObject prev = null;\r
- String name = "";\r
- while (o != null){\r
- if (o.getName() != null)\r
- name = o.getName()+"."+name;\r
- prev = o;\r
- o = o.getParent();\r
- }\r
- name = name.substring(0, name.length()-1);\r
- switch (prev.getType()) {\r
- case COMPLEX_TYPE:\r
- return getComplexTypePrefix()+rel+name;\r
- case ELEMENT:\r
- return rel+name;\r
- case ATTRIBUTE_GROUP:\r
- return getAttributeGroupPrefix()+rel+name;\r
- case SIMPLE_TYPE:\r
- return rel+name;\r
- }\r
- }\r
- throw new RuntimeException();\r
- \r
- }\r
- \r
- \r
-}\r
+package org.simantics.xml.sax;
+
+import java.io.FileNotFoundException;
+import java.io.PrintWriter;
+import java.io.StringWriter;
+import java.util.ArrayDeque;
+import java.util.Deque;
+import java.util.HashSet;
+import java.util.LinkedHashSet;
+import java.util.List;
+import java.util.Set;
+
+import javax.xml.namespace.QName;
+
+import org.simantics.utils.datastructures.BijectionMap;
+import org.simantics.xml.sax.SchemaConversionBase.Inheritance;
+import org.simantics.xml.sax.SchemaConversionBase.RefType;
+import org.simantics.xml.sax.SchemaObject.ObjectType;
+import org.simantics.xml.sax.configuration.AttributeComposition;
+import org.simantics.xml.sax.configuration.IDReference;
+import org.w3._2001.xmlschema.Annotated;
+import org.w3._2001.xmlschema.Attribute;
+import org.w3._2001.xmlschema.AttributeGroup;
+import org.w3._2001.xmlschema.Element;
+import org.w3._2001.xmlschema.LocalComplexType;
+import org.w3._2001.xmlschema.LocalSimpleType;
+import org.w3._2001.xmlschema.NamedAttributeGroup;
+import org.w3._2001.xmlschema.NamedGroup;
+import org.w3._2001.xmlschema.Schema;
+import org.w3._2001.xmlschema.SimpleType;
+
+//public class OntologyGenerator extends SchemaConversionBase {
+public class OntologyGenerator implements SchemaConversionComponent {
+ SchemaConversionBase base;
+
+ public OntologyGenerator(SchemaConverter converter, SchemaConversionBase base) {
+ this.base = base;
+ this.converter = converter;
+ this.schema = base.schema;
+ this.ontologyUri = base.ontologyURI;
+ this.className = base.className;
+ }
+
+ String ontRoot = "ONT.";
+ String commentTag = "//";
+
+ Schema schema;
+ String ontologyUri;
+ String className;
+
+ SchemaConverter converter;
+
+ PrintWriter writer = null;
+
+ public void createOntology() throws FileNotFoundException {
+ StringWriter stringWriter = null;
+ if (converter.getOntologyFile() == null) {
+ stringWriter = new StringWriter();
+ writer = new PrintWriter(stringWriter);
+ } else {
+ writer = new PrintWriter(converter.getOntologyFile());
+ }
+
+ handle();
+
+ writer.flush();
+ writer.close();
+ if (stringWriter != null)
+ System.out.println(stringWriter.toString());
+ }
+
+ protected void handle() {
+ ontRoot = converter.shortName;
+
+ for (String s : converter.getHeader()) {
+ writer.println(commentTag + " " + s);
+ }
+ writer.println();
+ writer.println("L0 = <http://www.simantics.org/Layer0-1.1>");
+ writer.println("XML = <http://www.simantics.org/XML-1.0>");
+ writer.println();
+ if (converter.isPrimary()) {
+ writer.println(ontRoot + " = <" + ontologyUri +"> : L0.Ontology");
+ writer.println(" @L0.new");
+ writer.println(" L0.HasResourceClass \"" + className +"\"");
+ } else {
+ writer.println(ontRoot + " = <" + ontologyUri +">");
+ }
+ writer.println();
+ writer.println();
+
+ Set<SchemaConverter> children = new HashSet<>();
+ Deque<SchemaConverter> stack = new ArrayDeque<>();
+ stack.addAll(converter.getSubConverters());
+ while (!stack.isEmpty()) {
+ SchemaConverter sc = stack.pop();
+ if (children.contains(sc))
+ continue;
+ children.add(sc);
+ stack.addAll(sc.getSubConverters());
+ }
+ children.remove(converter);
+ for (SchemaConverter sc : children) {
+ writer.println(sc.shortName + " = <" + sc.ontologyUri +">");
+ }
+
+ writer.println();
+
+ ontRoot += ".";
+ writer.println(ontRoot+"SimpleTypes : L0.Library");
+ writer.println(ontRoot+"ComplexTypes : L0.Library");
+ writer.println(ontRoot+"AttributeGroups : L0.Library");
+ writer.println();
+ writer.println(commentTag + " Interpreted from schema");
+ writer.println();
+
+
+
+ base.handle(this);
+ }
+
+ protected String getType(QName qtype, String rel) {
+ String ontType = base.getL0TypeFromPrimitiveType(qtype);
+ if (ontType != null)
+ return ontType;
+ else {
+ if (base.isComplexTypeRef(qtype.getLocalPart()))
+ return getName(base.getComplexType(qtype), rel);
+ else if (base.isSimpleTypeRef(qtype.getLocalPart()))
+ return getName(base.getSimpleType(qtype), rel);
+ else if (base.isElementRef(qtype.getLocalPart()))
+ return getName(base.getElement(qtype), rel);
+ }
+ throw new RuntimeException("Reference to unknown type " + qtype.getLocalPart());
+ }
+
+ public String getSimpleTypePrefix() {
+ return "SimpleTypes.";
+ }
+
+ public String getComplexTypePrefix() {
+ return "ComplexTypes.";
+ }
+
+ public String getAttributeGroupPrefix() {
+ return "AttributeGroups.";
+ }
+
+ public String handleChoice(SchemaObject parent, SchemaElement indicator, java.util.List<SchemaElement> elements, String name) {
+ boolean single = true;
+ for (SchemaElement e : elements) {
+ if (e.getRestriction().many()) {
+ single = false;
+ break;
+ }
+ }
+ String relationName = getName(parent)+".has"+name;
+ writer.print(relationName);
+ writer.print(" <R XML.hasElement");
+ writer.println();
+
+ if (!single) {
+ String elementListType = getName(parent) + "." + name + "_List";
+ writer.println(elementListType + " <T XML.ElementList");
+ writer.println(relationName + "_List <R XML.hasElementList : L0.FunctionalRelation");
+ writer.println(" --> " + elementListType);
+ }
+
+ return relationName;
+ };
+
+
+
+ @Override
+ public void handleIndicator(SchemaObject parent, SchemaElement indicator, SchemaElement element, String refName, RefType refType, String baseRelationName) {
+ if (refType != RefType.Element) {
+ QName referenceType = null;
+ if (refType == RefType.Type) {
+ referenceType = element.getElement().getType();
+ //refName = element.getElement().getName()
+ SchemaObject eObj = base.getElement(element.getElement());//base.elements.get(element.getElement());
+ if (refName == null)
+ refName = eObj.getName();
+ } else {
+ referenceType = element.getElement().getRef();
+ if (refName == null)
+ refName = base.getName(referenceType);
+ }
+ String type = base.getL0TypeFromPrimitiveType(referenceType);
+ SchemaObject obj = null;
+ if (type == null) {
+ obj = base.getWithName(referenceType);
+ writer.print(getName(parent)+".has"+refName + " <R XML.hasElement <R " + getName(obj,"has"));
+ if (baseRelationName != null) writer.print(" <R " + baseRelationName);
+ writer.println();
+ } else {
+ writer.print(getName(parent)+".has"+refName + " <R XML.hasElement");
+ if (baseRelationName != null) writer.print(" <R " + baseRelationName);
+ writer.println();
+ writer.println(" --> " + getType(referenceType, ""));
+ }
+
+ if (base.useElementList(parent, indicator,element, refType == RefType.Reference, refName, referenceType)) {
+
+ if (type == null) {
+ writer.println(getName(parent)+"."+refName + "List <T XML.ElementList");
+ writer.println(getName(parent)+".has"+refName + "_List <R " + getName(obj,"has")+"_List : L0.FunctionalRelation");
+ } else {
+ writer.println(getName(parent)+"."+refName + "_List <T XML.ElementList");
+ writer.println(getName(parent)+".has"+refName + "_List <R XML.hasElementList : L0.FunctionalRelation");
+ }
+ }
+ } else {
+ Element attrs = element.getElement();
+ SchemaObject obj = base.getWithObj(parent, attrs);
+ if (refName == null)
+ refName = obj.getName();
+
+ writer.print(getName(parent)+".has"+refName + " <R " + getName(obj,"has"));
+ if (baseRelationName != null) writer.print(" <R " + baseRelationName);
+ writer.println();
+ writer.println(" --> " + getName(obj));
+ if (base.useElementList(parent, indicator,element, false, refName, new QName(obj.getName()))) {
+ writer.println(getName(parent)+"."+refName + "_List <T XML.ElementList");
+ writer.println(getName(parent)+".has"+refName + "_List <R " + getName(obj,"has")+"_List : L0.FunctionalRelation");
+ }
+ }
+
+ }
+
+ @Override
+ public void handleIndicator(SchemaObject parent, SchemaElement indicator, SchemaElement any) {
+
+ }
+
+ @Override
+ public void handle(SchemaObject parent, NamedGroup attribute) {
+ // TODO Auto-generated method stub
+
+ }
+
+ @Override
+ public void handle(SchemaObject parent, Attribute attribute) {
+ String name = base.getName(attribute);
+ QName primitiveType = attribute.getType();
+ LocalSimpleType simpleType = attribute.getSimpleType();
+ QName ref = attribute.getRef();
+
+ String relationName;
+ String relationType;
+ if (name != null) {
+ relationName = ontRoot+"has"+name;
+ if (parent != null)
+ relationName = getName(parent)+".has"+name;
+ relationType = "XML.hasAttribute";
+ }
+ else if (ref != null && parent != null) {
+ relationName = getName(parent)+".has"+base.getName(ref);
+ relationType = converter.getShortName(ref.getNamespaceURI())+".has"+base.getName(ref);
+ } else {
+ throw new RuntimeException();
+ }
+ boolean id = false;
+ String ontType = null;
+ if (primitiveType != null) {
+ ontType = base.getL0TypeFromPrimitiveType(primitiveType);
+ if (ontType != null) {
+ id = base.getTypeEntry(primitiveType).id;
+ if (id)
+ relationType = "XML.hasID";
+ } else {
+
+ }
+ } else if (simpleType != null){
+// Restriction restriction = simpleType.getRestriction();
+// if (restriction == null || simpleType.getUnion() != null || simpleType.getName() != null || simpleType.getId() != null)
+// throw new RuntimeException();
+// QName base = restriction.getBase();
+ QName base = this.base.getSimpleTypeBase(simpleType);
+
+
+ ontType = this.base.getL0TypeFromPrimitiveType(base);
+
+// for (Object facetWrap : restriction.getFacets()) {
+// JAXBElement<?> element = (JAXBElement<?>)facetWrap;
+// QName elementName = element.getName();
+// Facet facet = (Facet)element.getValue();
+// }
+ }
+
+
+
+ writer.println(relationName+ " <R " + relationType + ": L0.FunctionalRelation");
+ if (id) {
+ // no need to add range restriction
+ } else if (ontType != null) {
+ writer.println(" --> " + ontType);
+ } else if (primitiveType != null) {
+ writer.println(" <R " + getType(primitiveType, "has"));
+ }
+ }
+
+ @Override
+ public void handleAttributes(SchemaObject simpleTypeObj) {
+// SchemaObject parent = simpleTypeObj.getParent();
+// SimpleType simpleType = simpleTypeObj.getSimpleType();
+// Restriction restriction = simpleType.getRestriction();
+// QName base = restriction.getBase();
+// String ontType = getL0TypeFromPrimitiveType(base);
+ }
+
+ @Override
+ public void handle(SchemaObject parent, AttributeGroup attributeGroup) {
+ if (parent == null) {
+ NamedAttributeGroup group = (NamedAttributeGroup)attributeGroup;
+ writer.println(ontRoot+getAttributeGroupPrefix()+group.getName()+ " <T XML.AttributeGroup");
+ SchemaObject obj = new SchemaObject(base,parent,attributeGroup);
+ for (Annotated annotated : group.getAttributeOrAttributeGroup()) {
+ if (annotated instanceof Attribute) {
+ //handle(getAttributeGroupPrefix()+group.getName(),(Attribute)annotated);
+ handle(obj,(Attribute)annotated);
+ } else if (annotated instanceof AttributeGroup) {
+ handle(obj,(AttributeGroup)annotated);
+ //throw new RuntimeException("Cannot handle nested attribute groups");
+ }
+ }
+ } else {
+ writer.println(getName(parent) +" L0.Inherits " + ontRoot + getAttributeGroupPrefix() + base.getName(attributeGroup.getRef()));
+ }
+
+ }
+
+ @Override
+ public void handleAttributeComposition(SchemaObject parent, AttributeComposition composition, BijectionMap<org.simantics.xml.sax.configuration.Attribute, Annotated> attributes) {
+ Attribute compositionAttribute = new Attribute();
+ compositionAttribute.setName(composition.getName());
+ QName type = new QName(SchemaConversionBase.CONVERSION_NS, composition.getType());
+ compositionAttribute.setType(type);
+ handle(parent, compositionAttribute);
+ }
+
+ @Override
+ public void handleSimpleType(SchemaObject parent, SchemaObject simpleTypeObj) {
+ SimpleType simpleType = simpleTypeObj.getSimpleType();
+ String name = simpleType.getName();
+
+ org.w3._2001.xmlschema.List list = simpleType.getList();
+ if (list != null) {
+ // TODO : process restriction in lists
+ String relationName = getName(simpleTypeObj, "has");
+ writer.println(relationName+ " <R XML.hasAttribute : L0.FunctionalRelation");
+
+ String ontType = base.getL0Type(new QName(SchemaConversionBase.SCHEMA_NS, "string"));
+ writer.println(" --> " + ontType);
+ } else {
+ QName base = this.base.getSimpleTypeBase(simpleType);
+ writer.println(getName(simpleTypeObj) + " <T " + getType(base, ""));
+
+ String relationName = getName(simpleTypeObj, "has");
+
+ writer.println(relationName+ " : L0.FunctionalRelation");
+ writer.println(" --> " + getName(simpleTypeObj));
+
+// Restriction restriction = simpleType.getRestriction();
+// if (restriction != null) {
+//
+// QName base = restriction.getBase();
+// String ontType = getL0Type(base);
+// writer.println(" --> " + ontType);
+// } else if (simpleType.getId() != null) {
+// throw new RuntimeException(simpleType.getName() + " restriction error");
+// } else if (simpleType.getUnion() != null) {
+// Union union = simpleType.getUnion();
+// String ontType = null;
+// if (union.getMemberTypes().size() > 0) {
+// for (QName type : union.getMemberTypes()) {
+// String sType = null;
+// TypeEntry entry = getTypeEntry(type);
+// if (entry == null) {
+// SchemaObject obj = simpleTypeName.get(type.getLocalPart());
+// Inheritance inheritance = new Inheritance("");
+// getAtomicTypeInheritance(type, obj, inheritance);
+// sType = inheritance.atomicType.l0Type;
+// } else {
+// sType = entry.l0Type;
+// }
+// if (ontType == null)
+// ontType = sType;
+// else if (!ontType.equals(sType))
+// throw new RuntimeException(simpleType.getName() + " union has incompatible member types");
+// }
+// } else {
+// if (union.getSimpleType().size() == 0)
+// throw new RuntimeException(simpleType.getName() + " union error");
+// for (SimpleType s : union.getSimpleType()) {
+// if (restriction == null)
+// restriction = s.getRestriction();
+// else {
+// Restriction r = s.getRestriction();
+// if (!r.getBase().equals(restriction.getBase()))
+// throw new RuntimeException(simpleType.getName() + " union has incompatible restriction bases");
+// }
+// }
+// QName base = restriction.getBase();
+// ontType = getL0Type(base);
+// }
+// writer.println(" --> " + ontType);
+// } else {
+// throw new RuntimeException(simpleType.getName() + " restriction error");
+// }
+
+ }
+ }
+
+ @Override
+ public void handleComplexType(SchemaObject topLevelComplexType) {
+ String name = getName(topLevelComplexType);
+// if (topLevelComplexType.getName().equals("Reference"))
+// System.out.println();
+
+// String baseType = "XML.ComplexType";
+//
+// QName base = getComplexTypeBase(topLevelComplexType.getComplexType());
+// if (base != null) {
+// baseType = getType(base);
+// }
+// base = getSimpleTypeBase(topLevelComplexType.getSimpleType());
+// if (base != null) {
+// baseType = getType(base);
+// }
+ Inheritance inheritance = base.getInheritance(topLevelComplexType);
+
+// writer.println(name+ " <T "+baseType);
+
+ // Type definition
+ if (inheritance.additionalClass != null) {
+ writer.println(name+ " <T " + inheritance.baseClass + " <T " + inheritance.additionalClass);
+ } else if (inheritance.atomicType != null){
+ writer.println(name+ " <T " + inheritance.baseClass + " <T " + inheritance.atomicType.l0Type);
+ } else {
+ writer.println(name+ " <T " + inheritance.baseClass);
+ }
+ writer.println(name + "_List <T XML.ElementList");
+
+ // Access relations
+ String relationName = getName(topLevelComplexType,"has");
+ writer.println(relationName+ " <R XML.hasComplexType");
+ writer.println(" --> " + name);
+ writer.println(relationName+ "_List <R XML.hasElementList");
+ writer.println(" --> " + name + "_List");
+ writer.println();
+
+ // Attributes
+// if (!baseType.equals(inheritance.baseClass))
+// System.out.println();
+ //super.handleComplexType(topLevelComplexType);
+ base.handleComplexTypeAttributes(topLevelComplexType);
+ base.handleComplexTypeExtension(topLevelComplexType);
+ base.handleExtensionAttributes(topLevelComplexType);
+ writer.println();
+ }
+
+ @Override
+ public void handleElement(SchemaObject elementObj) {
+ Element element = elementObj.getElement();
+ String name = getName(elementObj);//element.getName();
+
+ if (name.contains("Canvas"))
+ System.out.println();
+
+ String type = "XML.Element";
+ Set<String> types = new LinkedHashSet<String>();
+ if (element.getType() != null) {
+ types.add(getType(element.getType(), ""));
+ }
+ QName base = this.base.getElementBase(element);
+ if (base != null) {
+ if (base.getNamespaceURI().equals(SchemaConversionBase.SCHEMA_NS)) {
+ String l0Type = this.base.getL0Type(base);
+ if (l0Type == null)
+ throw new RuntimeException("Cannot get L0 type for " + base.getLocalPart());
+ types.add(l0Type);
+ } else if (this.base.isElementRef(base.getLocalPart()))
+ types.add(ontRoot+this.base.getName(base));
+ else
+ types.add(ontRoot+getComplexTypePrefix()+this.base.getName(base));
+ }
+ QName substitution = element.getSubstitutionGroup();
+ if (substitution != null) {
+ if (this.base.isElementRef(substitution.getLocalPart()))
+ types.add(ontRoot+this.base.getName(substitution));
+ else
+ types.add( ontRoot+getComplexTypePrefix()+this.base.getName(substitution));
+ }
+ for (String t : types) {
+ type += " <T " + t;
+ }
+
+ String relationName = getName(elementObj,"has");//ontRoot+"has"+name;
+// if (elementObj.getParent() != null) {
+// //relationName = ontRoot+getComplexTypePrefix()+"has"+name.substring(getComplexTypePrefix().length());
+// relationName = ontRoot+getName(elementObj.getParent()) + "has"+element.getName();
+// }
+ writer.println(relationName+ " <R XML.hasElement");
+ writer.println(relationName+ "_List <R XML.hasElementList");
+
+ writer.println(name+ " <T "+type);
+
+ LocalComplexType complexType = element.getComplexType();
+ LocalSimpleType simpleType = element.getSimpleType();
+
+ if (complexType != null) {
+ SchemaObject complexTypeObj = this.base.getComplexType(complexType);
+ this.base.handleElementComplexTypeAttributes(complexTypeObj);
+ this.base.handleComplexTypeExtension(complexTypeObj);
+ } else if (simpleType != null) {
+ SchemaObject simpleTypeObj = this.base.getSimpleType(simpleType);
+ this.base.handleElementSimpleTypeAttributes(simpleTypeObj);
+ }
+
+ List<IDReference> references = this.base.getIDReferences(element);
+
+ for (IDReference ref : references) {
+ writer.println(name+"."+ref.getReference().getName()+ " <R XML.hasReference");
+ }
+
+ writer.println();
+ }
+
+ @Override
+ public String getBaseClass(ObjectType type) {
+ if (type == ObjectType.ELEMENT)
+ return "XML.Element";
+ if (type == ObjectType.COMPLEX_TYPE)
+ return "XML.ComplexType";
+ throw new RuntimeException("ObjectType " + type + " has no base class");
+ }
+
+
+ @Override
+ public String getName(SchemaObject obj) {
+ if (obj.getParent() == null) {
+ switch (obj.getType()) {
+ case COMPLEX_TYPE:
+ //return ontRoot+getComplexTypePrefix()+obj.getName();
+ return obj.getLibShortName()+"."+getComplexTypePrefix()+obj.getName();
+ case ELEMENT:
+ //return ontRoot+obj.getName();
+ return obj.getLibShortName()+"."+obj.getName();
+ case ATTRIBUTE_GROUP:
+ //return ontRoot+getAttributeGroupPrefix()+obj.getName();
+ return obj.getLibShortName()+"."+getAttributeGroupPrefix()+obj.getName();
+ case SIMPLE_TYPE:
+ //return ontRoot+getSimpleTypePrefix()+obj.getName();
+ return obj.getLibShortName()+"."+getSimpleTypePrefix()+obj.getName();
+ }
+ } else {
+ SchemaObject o = obj;
+ SchemaObject prev = null;
+ String name = "";
+ while (o != null){
+ if (o.getName() != null)
+ name = o.getName()+"."+name;
+ prev = o;
+ o = o.getParent();
+ }
+ name = name.substring(0, name.length()-1);
+ switch (prev.getType()) {
+ case COMPLEX_TYPE:
+ //return ontRoot+getComplexTypePrefix()+name;
+ return obj.getLibShortName()+"."+getComplexTypePrefix()+name;
+ case ELEMENT:
+ //return ontRoot+name;
+ return obj.getLibShortName()+"."+name;
+ case ATTRIBUTE_GROUP:
+ //return ontRoot+getAttributeGroupPrefix()+name;
+ return obj.getLibShortName()+"."+getAttributeGroupPrefix()+name;
+ case SIMPLE_TYPE:
+ //return ontRoot+getSimpleTypePrefix()+name;
+ return obj.getLibShortName()+"."+getSimpleTypePrefix()+name;
+ }
+ }
+ throw new RuntimeException();
+
+ }
+
+ public String getName(SchemaObject parent, SchemaElement e, String rel) {
+ QName ref = e.getElement().getRef();
+ if (ref != null) {
+ return converter.getShortName(ref.getNamespaceURI()) + rel + base.getName(ref);
+ }
+ else {
+ return getName(parent, "") + "." + rel + e.getElement().getName();
+ }
+ }
+
+ public String getName(SchemaObject obj, String rel) {
+ if (obj.getParent() == null) {
+ switch (obj.getType()) {
+ case COMPLEX_TYPE:
+ return obj.getLibShortName()+"."+getComplexTypePrefix()+rel+obj.getName();
+ case ELEMENT:
+ return obj.getLibShortName()+"."+rel+obj.getName();
+ case ATTRIBUTE_GROUP:
+ return obj.getLibShortName()+"."+getAttributeGroupPrefix()+rel+obj.getName();
+ case SIMPLE_TYPE:
+ return obj.getLibShortName()+"."+getSimpleTypePrefix()+rel+obj.getName();
+ case ATTRIBUTE:
+ return obj.getLibShortName()+"."+rel+obj.getName();
+ }
+ } else {
+ SchemaObject o = obj;
+ SchemaObject prev = null;
+ String name = "";
+ while (o != null){
+ if (o.getName() != null)
+ name = o.getName()+"."+name;
+ prev = o;
+ o = o.getParent();
+ }
+ name = name.substring(0, name.length()-1);
+ switch (prev.getType()) {
+ case COMPLEX_TYPE:
+ return obj.getLibShortName()+"."+getComplexTypePrefix()+rel+name;
+ case ELEMENT:
+ return obj.getLibShortName()+"."+rel+name;
+ case ATTRIBUTE_GROUP:
+ return obj.getLibShortName()+"."+getAttributeGroupPrefix()+rel+name;
+ case SIMPLE_TYPE:
+ return obj.getLibShortName()+"."+getSimpleTypePrefix()+rel+name;
+ case ATTRIBUTE:
+ return obj.getLibShortName()+"."+rel+obj.getName();
+ }
+ }
+ throw new RuntimeException();
+
+ }
+
+
+}