001: /*
002: $Header: /cvsroot/xorm/xorm/src/org/xorm/util/jdoxml/JDOXML.java,v 1.4 2003/01/24 23:28:20 wbiggs Exp $
003:
004: This file is part of XORM.
005:
006: XORM is free software; you can redistribute it and/or modify
007: it under the terms of the GNU General Public License as published by
008: the Free Software Foundation; either version 2 of the License, or
009: (at your option) any later version.
010:
011: XORM is distributed in the hope that it will be useful,
012: but WITHOUT ANY WARRANTY; without even the implied warranty of
013: MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
014: GNU General Public License for more details.
015:
016: You should have received a copy of the GNU General Public License
017: along with XORM; if not, write to the Free Software
018: Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
019: */
020: package org.xorm.util.jdoxml;
021:
022: import java.io.InputStream;
023: import java.io.OutputStream;
024: import java.io.IOException;
025: import java.util.Collection;
026: import java.util.Iterator;
027:
028: import org.jdom.Document;
029: import org.jdom.Element;
030: import org.jdom.JDOMException;
031: import org.jdom.input.SAXBuilder;
032: import org.xml.sax.EntityResolver;
033: import org.xml.sax.InputSource;
034:
035: /**
036: * Utility class to generate an object graph from a JDO XML file
037: * or serialize an object graph.
038: */
039: public class JDOXML {
040: private static final String JDO_DTD_PATH = "/javax/jdo/jdo.dtd";
041: /** SYSTEM DOCTYPE that will be recognized. */
042: public static final String JDO_SYSTEM_URL = "file:/javax/jdo/jdo.dtd";
043: /** PUBLIC DOCTYPE that will be recognized. */
044: public static final String JDO_DTD_URL = "http://java.sun.com/dtd/jdo_1_0.dtd";
045: private static final boolean VALIDATE_XML_BY_DEFAULT = true;
046:
047: /**
048: * Uses JDOM to load from an XML .jdo file.
049: */
050: public static final JDOPackage read(InputStream input)
051: throws IOException {
052: return read(input, VALIDATE_XML_BY_DEFAULT);
053: }
054:
055: /**
056: * Uses JDOM to load from an XML .jdo file.
057: * @param input the .jdo XML input stream
058: * @param validateXML whether the XML should be validated against
059: * the JDO DTD
060: */
061: public static final JDOPackage read(InputStream input,
062: boolean validateXML) throws IOException {
063: try {
064: // Load the mappingFile using JDOM, validating against DTD
065: // if required
066: SAXBuilder biff = new SAXBuilder(validateXML);
067: EntityResolver resolver = new EntityResolver() {
068: public InputSource resolveEntity(String publicId,
069: String systemId) {
070: if ("jdo.dtd".equals(systemId) // holdover
071: || JDO_DTD_URL.equals(publicId)
072: || JDO_SYSTEM_URL.equals(systemId)) {
073: return new InputSource(getClass()
074: .getResourceAsStream(JDO_DTD_PATH));
075: }
076: return null;
077: }
078: };
079: biff.setEntityResolver(resolver);
080: InputSource inputSource = new InputSource(input);
081:
082: // Fake out Crimson
083: inputSource.setSystemId(JDOXML.class.getResource(
084: JDO_DTD_PATH).toString());
085: Document doc = biff.build(inputSource);
086:
087: return parsePackage(doc.getRootElement()
088: .getChild("package"));
089: } catch (JDOMException e) {
090: e.printStackTrace();
091: }
092: return null;
093: }
094:
095: private static JDOPackage parsePackage(Element element) {
096: JDOPackage jdoPackage = new JDOPackage();
097: jdoPackage.setName(element.getAttributeValue("name"));
098: addExtensions(element, jdoPackage.getExtensions());
099: Iterator i = element.getChildren("class").iterator();
100: while (i.hasNext()) {
101: element = (Element) i.next();
102: jdoPackage.getClasses().add(parseClass(element));
103: }
104: return jdoPackage;
105: }
106:
107: private static JDOClass parseClass(Element element) {
108: JDOClass jdoClass = new JDOClass();
109: jdoClass.setName(element.getAttributeValue("name"));
110: jdoClass.setIdentityType(JDOIdentityType.forName(element
111: .getAttributeValue("identity-type")));
112: jdoClass.setObjectIdClass(element
113: .getAttributeValue("objectid-class"));
114: jdoClass.setRequiresExtent("true".equals(element
115: .getAttributeValue("requires-extent")));
116: jdoClass.setPersistenceCapableSuperclass(element
117: .getAttributeValue("persistence-capable-superclass"));
118: addExtensions(element, jdoClass.getExtensions());
119: Iterator i = element.getChildren("field").iterator();
120: while (i.hasNext()) {
121: element = (Element) i.next();
122: jdoClass.getFields().add(parseField(element));
123: }
124: return jdoClass;
125: }
126:
127: private static JDOField parseField(Element element) {
128: JDOField jdoField = new JDOField();
129: jdoField.setName(element.getAttributeValue("name"));
130: addExtensions(element, jdoField.getExtensions());
131: jdoField.setNullValue(JDONullValue.forName(element
132: .getAttributeValue("null-value")));
133: jdoField.setPersistenceModifier(JDOPersistenceModifier
134: .forName(element
135: .getAttributeValue("persistence-modifier")));
136: String value = element.getAttributeValue("default-fetch-group");
137: if (value != null) {
138: jdoField.setDefaultFetchGroup(Boolean.valueOf(value));
139: }
140: value = element.getAttributeValue("embedded");
141: if (value != null) {
142: jdoField.setEmbedded(Boolean.valueOf(value));
143: }
144: jdoField.setPrimaryKey("true".equals(element
145: .getAttributeValue("primary-key")));
146:
147: Element child = element.getChild("collection");
148: if (child != null) {
149: jdoField.setCollection(parseCollection(child));
150: } else {
151: child = element.getChild("map");
152: if (child != null) {
153: jdoField.setMap(parseMap(child));
154: } else {
155: child = element.getChild("array");
156: if (child != null) {
157: jdoField.setArray(parseArray(child));
158: }
159: }
160: }
161: return jdoField;
162: }
163:
164: private static JDOCollection parseCollection(Element element) {
165: JDOCollection jdoCollection = new JDOCollection();
166: addExtensions(element, jdoCollection.getExtensions());
167: jdoCollection.setElementType(element
168: .getAttributeValue("element-type"));
169: String value = element.getAttributeValue("embedded-element");
170: if (value != null) {
171: jdoCollection.setEmbeddedElement(Boolean.valueOf(value));
172: }
173: return jdoCollection;
174: }
175:
176: private static JDOMap parseMap(Element element) {
177: JDOMap jdoMap = new JDOMap();
178: addExtensions(element, jdoMap.getExtensions());
179: jdoMap.setKeyType(element.getAttributeValue("key-type"));
180: String value = element.getAttributeValue("embedded-key");
181: if (value != null) {
182: jdoMap.setEmbeddedKey(Boolean.valueOf(value));
183: }
184: jdoMap.setValueType(element.getAttributeValue("value-type"));
185: value = element.getAttributeValue("embedded-value");
186: if (value != null) {
187: jdoMap.setEmbeddedValue(Boolean.valueOf(value));
188: }
189: return jdoMap;
190: }
191:
192: private static JDOArray parseArray(Element element) {
193: JDOArray jdoArray = new JDOArray();
194: addExtensions(element, jdoArray.getExtensions());
195: String value = element.getAttributeValue("embedded-element");
196: if (value != null) {
197: jdoArray.setEmbeddedElement(Boolean.valueOf(value));
198: }
199: return jdoArray;
200: }
201:
202: /** Shared function for all elements that can have extensions. */
203: private static void addExtensions(Element element,
204: Collection collection) {
205: Iterator exts = element.getChildren("extension").iterator();
206: while (exts.hasNext()) {
207: element = (Element) exts.next();
208: JDOExtension jdoExtension = new JDOExtension();
209: jdoExtension.setVendorName(element
210: .getAttributeValue("vendor-name"));
211: jdoExtension.setKey(element.getAttributeValue("key"));
212: jdoExtension.setValue(element.getAttributeValue("value"));
213: collection.add(jdoExtension);
214: }
215: }
216:
217: /*
218: public static final void write(JDOPackage jdoPackage, OutputStream output) throws IOException {
219: // TODO
220: }
221: */
222: }
|