From 68b16280c97b4ebabda6e3f26d3f3462f557ab8f Mon Sep 17 00:00:00 2001
From: tromey This class contains static methods for creating an XML reader
- * from an explicit class name, or for creating an XML reader based
- * on the value of the Note that these methods will not be usable in environments where
- * system properties are not accessible or where the application or
- * applet is not permitted to load classes dynamically. Note to implementors: SAX implementations in specialized
- * environments may replace this class with a different one optimized for the
- * environment, as long as its method signatures remain the same. This constructor prevents the class from being instantiated. This method uses the value of the system property
- * "org.xml.sax.driver" as the full name of a Java class
- * and tries to instantiate that class as a SAX2
- * XMLReader. Note that many Java interpreters allow system properties
- * to be specified on the command line. Given a class name, this method attempts to load
- * and instantiate the class as an XML reader. This class contains static methods for creating an XML reader
+ * from an explicit class name, or based on runtime defaults: Note to Distributions bundled with parsers:
+ * You should modify the implementation of the no-arguments
+ * createXMLReader to handle cases where the external
+ * configuration mechanisms aren't set up. That method should do its
+ * best to return a parser when one is in the class path, even when
+ * nothing bound its class name to This constructor prevents the class from being instantiated.
- * This module, both source code and documentation, is in the
- * Public Domain, and comes with NO WARRANTY.
- *
- *
- * org.xml.sax.driver
system
- * property:
- * try {
- * XMLReader myReader = XMLReaderFactory.createXMLReader();
- * } catch (SAXException e) {
- * System.err.println(e.getMessage());
- * }
- *
- *
- *
+ * This module, both source code and documentation, is in the
+ * Public Domain, and comes with NO WARRANTY.
+ * See http://www.saxproject.org
+ * for further information.
+ *
+ *
+ *
+ * try {
+ * XMLReader myReader = XMLReaderFactory.createXMLReader();
+ * } catch (SAXException e) {
+ * System.err.println(e.getMessage());
+ * }
+ *
+ *
+ * org.xml.sax.driver
so
+ * those configuration mechanisms would see it.
org.xml.sax.driver
+ * has a value, that is used as an XMLReader class name. org.xml.sax.parser
system
+ * property will often be usable.) In environments such as small embedded systems, which can not + * support that flexibility, other mechanisms to determine the default + * may be used.
+ * + *Note that many Java environments allow system properties to be + * initialized on a command line. This means that in most cases + * setting a good value for that property ensures that calls to this + * method will succeed, except when security policies intervene. + * This will also maximize application portability to older SAX + * environments, with less robust implementations of this method. + *
+ * + * @return A new XMLReader. + * @exception org.xml.sax.SAXException If no default XMLReader class + * can be identified and instantiated. + * @see #createXMLReader(java.lang.String) + */ + public static XMLReader createXMLReader () + throws SAXException + { + String className = null; + ClassLoader loader = NewInstance.getClassLoader (); + + // 1. try the JVM-instance-wide system property + try { className = System.getProperty (property); } + catch (Exception e) { /* normally fails for applets */ } + + // 2. if that fails, try META-INF/services/ + if (className == null) { + try { + String service = "META-INF/services/" + property; + InputStream in; + BufferedReader reader; + + if (loader == null) + in = ClassLoader.getSystemResourceAsStream (service); + else + in = loader.getResourceAsStream (service); + + if (in != null) { + reader = new BufferedReader ( + new InputStreamReader (in, "UTF8")); + className = reader.readLine (); + in.close (); + } + } catch (Exception e) { + } + } + + // 3. Distro-specific fallback + if (className == null) { +// BEGIN DISTRIBUTION-SPECIFIC + + // EXAMPLE: + // className = "com.example.sax.XmlReader"; + // or a $JAVA_HOME/jre/lib/*properties setting... + +// END DISTRIBUTION-SPECIFIC + } + + // do we know the XMLReader implementation class yet? + if (className != null) + return loadClass (loader, className); + + // 4. panic -- adapt any SAX1 parser + try { + return new ParserAdapter (ParserFactory.makeParser ()); + } catch (Exception e) { + throw new SAXException ("Can't create default XMLReader; " + + "is system property org.xml.sax.driver set?"); + } + } + + + /** + * Attempt to create an XML reader from a class name. + * + *Given a class name, this method attempts to load + * and instantiate the class as an XML reader.
+ * + *Note that this method will not be usable in environments where + * the caller (perhaps an applet) is not permitted to load classes + * dynamically.
+ * + * @return A new XML reader. + * @exception org.xml.sax.SAXException If the class cannot be + * loaded, instantiated, and cast to XMLReader. + * @see #createXMLReader() + */ + public static XMLReader createXMLReader (String className) + throws SAXException + { + return loadClass (NewInstance.getClassLoader (), className); + } + + private static XMLReader loadClass (ClassLoader loader, String className) + throws SAXException + { + try { + return (XMLReader) NewInstance.newInstance (loader, className); + } catch (ClassNotFoundException e1) { + throw new SAXException("SAX2 driver class " + className + + " not found", e1); + } catch (IllegalAccessException e2) { + throw new SAXException("SAX2 driver class " + className + + " found but cannot be loaded", e2); + } catch (InstantiationException e3) { + throw new SAXException("SAX2 driver class " + className + + " loaded but cannot be instantiated (no empty public constructor?)", + e3); + } catch (ClassCastException e4) { + throw new SAXException("SAX2 driver class " + className + + " does not implement XMLReader", e4); + } + } +} -- cgit v1.2.3