Java tutorial
/** * Copyright 2007-2010 ? * All rights reserved. * * This library is free software; you can redistribute it and/or modify it under the * terms of the GNU Lesser General Public License v3 as published by the Free Software * Foundation. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License along * with this library; if not, see http://www.gnu.org/licenses/lgpl.html. * */ package org.firesoa.common.schema; import java.io.ByteArrayOutputStream; import java.nio.charset.Charset; import java.util.List; import javax.xml.namespace.QName; import javax.xml.parsers.DocumentBuilder; import javax.xml.parsers.DocumentBuilderFactory; import javax.xml.parsers.ParserConfigurationException; import javax.xml.transform.OutputKeys; import javax.xml.transform.Transformer; import javax.xml.transform.TransformerFactory; import javax.xml.transform.dom.DOMSource; import javax.xml.transform.stream.StreamResult; import org.apache.commons.lang.StringUtils; import org.apache.ws.commons.schema.XmlSchema; import org.apache.ws.commons.schema.XmlSchemaAll; import org.apache.ws.commons.schema.XmlSchemaAny; import org.apache.ws.commons.schema.XmlSchemaAttribute; import org.apache.ws.commons.schema.XmlSchemaAttributeGroup; import org.apache.ws.commons.schema.XmlSchemaAttributeGroupMember; import org.apache.ws.commons.schema.XmlSchemaAttributeGroupRef; import org.apache.ws.commons.schema.XmlSchemaAttributeOrGroupRef; import org.apache.ws.commons.schema.XmlSchemaChoice; import org.apache.ws.commons.schema.XmlSchemaCollection; import org.apache.ws.commons.schema.XmlSchemaComplexContent; import org.apache.ws.commons.schema.XmlSchemaComplexContentExtension; import org.apache.ws.commons.schema.XmlSchemaComplexContentRestriction; import org.apache.ws.commons.schema.XmlSchemaComplexType; import org.apache.ws.commons.schema.XmlSchemaContent; import org.apache.ws.commons.schema.XmlSchemaContentModel; import org.apache.ws.commons.schema.XmlSchemaElement; import org.apache.ws.commons.schema.XmlSchemaForm; import org.apache.ws.commons.schema.XmlSchemaGroup; import org.apache.ws.commons.schema.XmlSchemaGroupRef; import org.apache.ws.commons.schema.XmlSchemaObject; import org.apache.ws.commons.schema.XmlSchemaParticle; import org.apache.ws.commons.schema.XmlSchemaSequence; import org.apache.ws.commons.schema.XmlSchemaSequenceMember; import org.apache.ws.commons.schema.XmlSchemaSimpleContent; import org.apache.ws.commons.schema.XmlSchemaSimpleType; import org.apache.ws.commons.schema.XmlSchemaType; import org.apache.ws.commons.schema.constants.Constants; import org.apache.ws.commons.schema.utils.XmlSchemaRef; import org.w3c.dom.Attr; import org.w3c.dom.Document; import org.w3c.dom.Element; import org.w3c.dom.NamedNodeMap; import org.w3c.dom.Node; /** * * * @author ? nychen2000@163.com Fire Workflow www.firesoa.com * www.fireflow.org * */ public class DOMInitializer { private static final DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance(); private static final TransformerFactory transformerFactory = TransformerFactory.newInstance(); public static String dom2String(Document dom) { try { Transformer transformer = transformerFactory.newTransformer(); transformer.setOutputProperty(OutputKeys.ENCODING, Charset.defaultCharset().name()); transformer.setOutputProperty(OutputKeys.INDENT, "yes"); transformer.setOutputProperty("{http://xml.apache.org/xslt}indent-amount", "2"); ByteArrayOutputStream outputStream = new ByteArrayOutputStream(); // transformer.transform() XML Source? Result transformer.transform(new DOMSource(dom), new StreamResult(outputStream)); return outputStream.toString(); } catch (Exception e) { e.printStackTrace(); return null; } } public static Document generateDocument(XmlSchemaCollection xmlSchemaCollection, QName rootElementQName) throws ParserConfigurationException { return generateDocument(xmlSchemaCollection, rootElementQName, false); } /** * ?schemaDocument * * @param xmlSchemaCollection * Schema * @param rootElementQName * QName * @param createChoice * ?XSDschema?choice? * @return * @throws ParserConfigurationException */ public static Document generateDocument(XmlSchemaCollection xmlSchemaCollection, QName rootElementQName, boolean createChoice) throws ParserConfigurationException { XmlSchemaElement xmlSchemaElement = xmlSchemaCollection.getElementByQName(rootElementQName); if (xmlSchemaElement == null) return null; DocumentBuilder docBuilder = documentBuilderFactory.newDocumentBuilder(); Document doc = docBuilder.newDocument(); createElement(doc, doc, null, xmlSchemaElement, xmlSchemaCollection, createChoice); return doc; } /** * Element * @param doc * @param parentNode * @param childSchemaElement * @param xmlSchemaCollection * @param createChoice */ protected static void createElement(Document doc, Node parentNode, XmlSchemaElement parentSchemaElement, XmlSchemaElement childSchemaElement, XmlSchemaCollection xmlSchemaCollection, boolean createChoice) { // 1? XmlSchemaRef<XmlSchemaElement> ref = childSchemaElement.getRef(); if (ref != null && ref.getTarget() != null) { childSchemaElement = ref.getTarget(); } if (childSchemaElement.getName().equals("foo_1")) { System.out.println("this is foo_1"); } QName parentElmTypeQName = null; if (parentSchemaElement != null) { parentElmTypeQName = parentSchemaElement.getSchemaTypeName(); if (parentElmTypeQName == null) { parentElmTypeQName = parentSchemaElement.getSchemaType().getQName(); } } XmlSchemaForm schemaElementForm = childSchemaElement.getForm(); QName childElmQName = childSchemaElement.getQName(); Element childElem = null; if (schemaElementForm != null && XmlSchemaForm.QUALIFIED.equals(schemaElementForm)) { childElem = doc.createElementNS(childElmQName.getNamespaceURI(), getQualifiedName(doc, childElmQName)); } else { if (parentElmTypeQName == null || !equalStrings(parentElmTypeQName.getNamespaceURI(), childElmQName.getNamespaceURI())) { // childElem = doc.createElementNS(childElmQName.getNamespaceURI(), getQualifiedName(doc, childElmQName)); } else { //??namespace prefix childElem = doc.createElement(childElmQName.getLocalPart()); } } parentNode.appendChild(childElem); // 2??? XmlSchemaType xmlSchemaType = childSchemaElement.getSchemaType(); if (xmlSchemaType == null) { QName qname = childSchemaElement.getSchemaTypeName(); xmlSchemaType = xmlSchemaCollection.getTypeByQName(qname); } if (xmlSchemaType instanceof XmlSchemaSimpleType) { // ? XmlSchemaSimpleType simpleType = (XmlSchemaSimpleType) xmlSchemaType; String value = ""; if (!StringUtils.isEmpty(childSchemaElement.getFixedValue())) { value = childSchemaElement.getFixedValue(); } else if (!StringUtils.isEmpty(childSchemaElement.getDefaultValue())) { value = childSchemaElement.getDefaultValue(); } if (!StringUtils.isEmpty(value)) { childElem.appendChild(doc.createTextNode(value)); } } else if (xmlSchemaType instanceof XmlSchemaComplexType) { XmlSchemaComplexType complexType = (XmlSchemaComplexType) xmlSchemaType; createChildNode4ComplexType(doc, childElem, childSchemaElement, complexType, xmlSchemaCollection, createChoice); } } /** * Element?Node?Element * @param doc * @param parentElement * @param parentSchemaElementComplexType * @param xmlSchemaCollection * @param createChoice */ protected static void createChildNode4ComplexType(Document doc, Element parentElement, XmlSchemaElement parentSchemaElement, XmlSchemaComplexType parentSchemaElementComplexType, XmlSchemaCollection xmlSchemaCollection, boolean createChoice) { // 2.1 ?attribute List<XmlSchemaAttributeOrGroupRef> attributeSchemaList = parentSchemaElementComplexType.getAttributes(); for (XmlSchemaAttributeOrGroupRef attrOrGroupRef : attributeSchemaList) { createAttribute(doc, parentElement, (XmlSchemaAttributeGroupMember) attrOrGroupRef); } // 2.2?? // TODO ?ParticleComplextContent? XmlSchemaParticle particle = parentSchemaElementComplexType.getParticle(); if (particle != null) { if (particle instanceof XmlSchemaAll) { XmlSchemaAll schemaAll = (XmlSchemaAll) particle; List<XmlSchemaElement> items = schemaAll.getItems(); for (XmlSchemaElement item : items) { createElement(doc, parentElement, parentSchemaElement, item, xmlSchemaCollection, createChoice); } } else if (particle instanceof XmlSchemaSequence) { XmlSchemaSequence schemaSeq = (XmlSchemaSequence) particle; createChildElement4Sequence(doc, parentElement, parentSchemaElement, schemaSeq, xmlSchemaCollection, createChoice); } else if (particle instanceof XmlSchemaChoice) { createChildElement4Choice(doc, parentElement, parentSchemaElement, (XmlSchemaChoice) particle, xmlSchemaCollection, createChoice); } else if (particle instanceof XmlSchemaGroupRef) { // TODO ? } } else { XmlSchemaContentModel contentModel = parentSchemaElementComplexType.getContentModel(); if (contentModel instanceof XmlSchemaComplexContent) { XmlSchemaComplexContent complexContentModel = (XmlSchemaComplexContent) contentModel; XmlSchemaContent complexContent = complexContentModel.getContent(); if (complexContent instanceof XmlSchemaComplexContentExtension) { XmlSchemaComplexContentExtension complexContentExtension = (XmlSchemaComplexContentExtension) complexContent; createChildElement4ComplexContentExtension(doc, parentElement, parentSchemaElement, complexContentExtension, xmlSchemaCollection, createChoice); } else if (complexContent instanceof XmlSchemaComplexContentRestriction) { //TODO ? } } else if (contentModel instanceof XmlSchemaSimpleContent) { // TODO simple } } } protected static void createChildElement4ComplexContentExtension(Document doc, Element parentElement, XmlSchemaElement parentSchemaElement, XmlSchemaComplexContentExtension complexContentExtension, XmlSchemaCollection xmlSchemaCollection, boolean createChoice) { QName baseTypeQName = complexContentExtension.getBaseTypeName(); XmlSchemaComplexType comlexBaseType = (XmlSchemaComplexType) xmlSchemaCollection .getTypeByQName(baseTypeQName); createChildNode4ComplexType(doc, parentElement, parentSchemaElement, comlexBaseType, xmlSchemaCollection, createChoice); // 2.1 ?attribute List<XmlSchemaAttributeOrGroupRef> attributeSchemaList = complexContentExtension.getAttributes(); for (XmlSchemaAttributeOrGroupRef attrOrGroupRef : attributeSchemaList) { createAttribute(doc, parentElement, (XmlSchemaAttributeGroupMember) attrOrGroupRef); } // 2.2?? // TODO ?ParticleComplextContent? XmlSchemaParticle particle = complexContentExtension.getParticle(); if (particle != null) { if (particle instanceof XmlSchemaAll) { XmlSchemaAll schemaAll = (XmlSchemaAll) particle; List<XmlSchemaElement> items = schemaAll.getItems(); for (XmlSchemaElement item : items) { createElement(doc, parentElement, parentSchemaElement, item, xmlSchemaCollection, createChoice); } } else if (particle instanceof XmlSchemaSequence) { XmlSchemaSequence schemaSeq = (XmlSchemaSequence) particle; createChildElement4Sequence(doc, parentElement, parentSchemaElement, schemaSeq, xmlSchemaCollection, createChoice); } else if (particle instanceof XmlSchemaChoice) { createChildElement4Choice(doc, parentElement, parentSchemaElement, (XmlSchemaChoice) particle, xmlSchemaCollection, createChoice); } else if (particle instanceof XmlSchemaGroupRef) { // TODO ? } } } protected static void createChildElement4Sequence(Document doc, Element parentElement, XmlSchemaElement parentSchemaElement, XmlSchemaSequence sequence, XmlSchemaCollection xmlSchemaCollection, boolean createChoice) { List<XmlSchemaSequenceMember> items = sequence.getItems(); for (XmlSchemaSequenceMember item : items) { if (item instanceof XmlSchemaElement) { createElement(doc, parentElement, parentSchemaElement, ((XmlSchemaElement) item), xmlSchemaCollection, createChoice); } else if (item instanceof XmlSchemaSequence) { createChildElement4Sequence(doc, parentElement, parentSchemaElement, ((XmlSchemaSequence) item), xmlSchemaCollection, createChoice); } else if (item instanceof XmlSchemaChoice) { createChildElement4Choice(doc, parentElement, parentSchemaElement, ((XmlSchemaChoice) item), xmlSchemaCollection, createChoice); } else if (item instanceof XmlSchemaAny) { // TODO } else if (item instanceof XmlSchemaGroup) { // TODO } else if (item instanceof XmlSchemaGroupRef) { // TODO } } } protected static void createChildElement4Choice(Document doc, Element parentElement, XmlSchemaElement parentSchemaElement, XmlSchemaChoice choice, XmlSchemaCollection xmlSchemaCollection, boolean createChoice) { if (!createChoice) return; List<XmlSchemaObject> choiceMember = choice.getItems(); for (XmlSchemaObject schemaObj : choiceMember) { if (schemaObj instanceof XmlSchemaElement) { createElement(doc, parentElement, parentSchemaElement, ((XmlSchemaElement) schemaObj), xmlSchemaCollection, createChoice); } else if (schemaObj instanceof XmlSchemaSequence) { createChildElement4Sequence(doc, parentElement, parentSchemaElement, ((XmlSchemaSequence) schemaObj), xmlSchemaCollection, createChoice); } else if (schemaObj instanceof XmlSchemaChoice) { createChildElement4Choice(doc, parentElement, parentSchemaElement, ((XmlSchemaChoice) schemaObj), xmlSchemaCollection, createChoice); } } } //TODO ?attribute qualifiedunqualified protected static void createAttribute(Document doc, Element elem, XmlSchemaAttributeGroupMember attrMember) { if (attrMember instanceof XmlSchemaAttribute) { XmlSchemaAttribute attrSchema = (XmlSchemaAttribute) attrMember; XmlSchemaForm attrForm = attrSchema.getForm(); Attr attr = null; QName attrSchemaQName = attrSchema.getQName(); if (XmlSchemaForm.QUALIFIED.equals(attrForm)) { String attrQualifiedName = getQualifiedName(doc, attrSchemaQName); attr = doc.createAttributeNS(attrSchemaQName.getNamespaceURI(), attrQualifiedName); } else { attr = doc.createAttribute(attrSchema.getName()); } elem.setAttributeNode(attr); String value = ""; if (!StringUtils.isEmpty(attrSchema.getFixedValue())) { value = attrSchema.getFixedValue(); } else if (!StringUtils.isEmpty(attrSchema.getDefaultValue())) { value = attrSchema.getDefaultValue(); } if (!StringUtils.isEmpty(value)) { attr.setValue(value); } } else if (attrMember instanceof XmlSchemaAttributeGroupRef) { XmlSchemaAttributeGroupRef attrGroupRef = (XmlSchemaAttributeGroupRef) attrMember; List<XmlSchemaAttributeGroupMember> groupMembers = attrGroupRef.getRef().getTarget().getAttributes(); for (XmlSchemaAttributeGroupMember groupMember : groupMembers) { createAttribute(doc, elem, groupMember); } } else if (attrMember instanceof XmlSchemaAttributeGroup) { XmlSchemaAttributeGroup attrGroup = (XmlSchemaAttributeGroup) attrMember; List<XmlSchemaAttributeGroupMember> groupMembers = attrGroup.getAttributes(); for (XmlSchemaAttributeGroupMember groupMember : groupMembers) { createAttribute(doc, elem, groupMember); } } } private static boolean equalStrings(String s1, String s2) { if (s1 == s2) { return true; } s1 = s1 == null ? "" : s1.trim(); s2 = s2 == null ? "" : s2.trim(); return s1.equals(s2); } private static String getQualifiedName(Document doc, QName qName) { Element rootElement = (Element) doc.getDocumentElement(); if (rootElement != null && !equalStrings(qName.getNamespaceURI(), rootElement.getNamespaceURI())) { // Attr attrTmp = rootElement.getAttributeNodeNS(Constants.XMLNS_ATTRIBUTE_NS_URI, "ns0"); // System.out.println("===========found attrTmp=="+attrTmp); String nsPrefix = null; nsPrefix = rootElement.lookupPrefix(qName.getNamespaceURI()); if (nsPrefix == null || nsPrefix.trim().equals("")) { int nsNumber = 1; NamedNodeMap attrMap = rootElement.getAttributes(); int length = attrMap.getLength(); for (int i = 0; i < length; i++) { Attr attr = (Attr) attrMap.item(i); String name = attr.getName(); if (name.startsWith(Constants.XMLNS_ATTRIBUTE)) { if (attr.getValue().equals(qName.getNamespaceURI())) { // Namespace? nsPrefix = attr.getLocalName(); break; } nsNumber++; } } if (nsPrefix == null) { nsPrefix = "ns" + nsNumber; } } Attr attr = doc.createAttributeNS(Constants.XMLNS_ATTRIBUTE_NS_URI, Constants.XMLNS_ATTRIBUTE + ":" + nsPrefix); attr.setValue(qName.getNamespaceURI()); rootElement.setAttributeNode(attr); return nsPrefix + ":" + qName.getLocalPart(); } else { return "ns0:" + qName.getLocalPart(); } } protected static XmlSchema findXmlSchema(XmlSchemaCollection schemaCollection, String targetNsUri) { XmlSchema[] xmlSchemas = schemaCollection.getXmlSchemas(); String tmpUri = targetNsUri; if (tmpUri == null) { tmpUri = ""; } for (XmlSchema schema : xmlSchemas) { if (tmpUri.equals(schema.getTargetNamespace())) { return schema; } } return null; } // protected static XmlSchemaForm findElementFormDefault(XmlSchemaCollection schemaCollection ,String targetNsUri){ // XmlSchema schema = findXmlSchema(schemaCollection,targetNsUri); // if (schema!=null){ // return schema.getElementFormDefault(); // } // return XmlSchemaForm.UNQUALIFIED; // } }