elena 2003/07/28 13:43:02 Modified: java/src/org/apache/xerces/xinclude XIncludeHandler.java XIncludeTextReader.java Log: Fixing some bugs in XInclude implementation. Submitter: Peter McCracken Revision Changes Path 1.3 +142 -57 xml-xerces/java/src/org/apache/xerces/xinclude/XIncludeHandler.java Index: XIncludeHandler.java =================================================================== RCS file: /home/cvs/xml-xerces/java/src/org/apache/xerces/xinclude/XIncludeHandler.java,v retrieving revision 1.2 retrieving revision 1.3 diff -u -r1.2 -r1.3 --- XIncludeHandler.java 18 Jul 2003 17:34:38 -0000 1.2 +++ XIncludeHandler.java 28 Jul 2003 20:43:02 -0000 1.3 @@ -92,6 +92,7 @@ import org.apache.xerces.xni.parser.XMLDocumentFilter; import org.apache.xerces.xni.parser.XMLDocumentSource; import org.apache.xerces.xni.parser.XMLEntityResolver; +import org.apache.xerces.xni.parser.XMLErrorHandler; import org.apache.xerces.xni.parser.XMLInputSource; import org.apache.xerces.xni.parser.XMLParserConfiguration; @@ -147,7 +148,7 @@ Constants.SAX_FEATURE_PREFIX + Constants.ALLOW_DTD_EVENTS_AFTER_ENDDTD_FEATURE; - /** Property identifier: error handler. */ + /** Property identifier: error reporter. */ protected static final String ERROR_REPORTER = Constants.XERCES_PROPERTY_PREFIX + Constants.ERROR_REPORTER_PROPERTY; @@ -221,8 +222,8 @@ private int[] fState = new int[INITIAL_SIZE]; // buffering the necessary DTD events - private Vector fNotations = new Vector(); - private Vector fUnparsedEntities = new Vector(); + private Vector fNotations; + private Vector fUnparsedEntities; private boolean fSendUEAndNotationEvents; @@ -235,6 +236,8 @@ fSawFallback[fDepth] = false; fSawInclude[fDepth] = false; fState[fDepth] = STATE_NORMAL_PROCESSING; + fNotations = new Vector(); + fUnparsedEntities = new Vector(); } // XMLComponent methods @@ -244,6 +247,15 @@ fNamespaceContext = null; fDepth = 0; fRootDepth = 0; + fNotations = new Vector(); + fUnparsedEntities = new Vector(); + + for (int i = 0; i < fState.length; i++) { + // these three arrays will always be the same length, so this is safe + fSawFallback[i] = false; + fSawInclude[i] = false; + fState[i] = STATE_NORMAL_PROCESSING; + } try { fSendUEAndNotationEvents = @@ -260,9 +272,12 @@ try { XMLErrorReporter value = (XMLErrorReporter)componentManager.getProperty(ERROR_REPORTER); - setErrorReporter(value); - if (fChildConfig != null) { - fChildConfig.setProperty(ERROR_REPORTER, value); + if (value != null) { + setErrorReporter(value); + if (fChildConfig != null) { + // REVISIT: see setErrorReporter() + fChildConfig.setProperty(ERROR_REPORTER, value); + } } } catch (XMLConfigurationException e) { @@ -273,9 +288,12 @@ XMLEntityResolver value = (XMLEntityResolver)componentManager.getProperty( ENTITY_RESOLVER); - fEntityResolver = value; - if (fChildConfig != null) { - fChildConfig.setProperty(ENTITY_RESOLVER, value); + + if (value != null) { + fEntityResolver = value; + if (fChildConfig != null) { + fChildConfig.setProperty(ENTITY_RESOLVER, value); + } } } catch (XMLConfigurationException e) { @@ -283,24 +301,9 @@ } fSettings = new ParserConfigurationSettings(); - - Enumeration xercesFeatures = Constants.getXercesFeatures(); - while (xercesFeatures.hasMoreElements()) { - String featureId = (String)xercesFeatures.nextElement(); - fSettings.addRecognizedFeatures( - new String[] { Constants.XERCES_FEATURE_PREFIX + featureId }); - try { - fSettings.setFeature( - featureId, - componentManager.getFeature(featureId)); - } - catch (XMLConfigurationException e) { - // componentManager doesn't support this feature, - // so we won't worry about it - } - } - - // don't reset fChildConfig -- we don't want it to share the same components + copyFeatures(componentManager, fSettings); + // Don't reset fChildConfig -- we don't want it to share the same components. + // It will be reset when it is actually used to parse something. } // reset(XMLComponentManager) /** @@ -366,6 +369,7 @@ if (propertyId.equals(ERROR_REPORTER)) { setErrorReporter((XMLErrorReporter)value); if (fChildConfig != null) { + // REVISIT: see setErrorReporter() fChildConfig.setProperty(propertyId, value); } } @@ -942,6 +946,16 @@ // XIncludeHandler methods private void setErrorReporter(XMLErrorReporter reporter) { + // REVISIT: + // This results in the incorrect location being displayed, because + // the XMLLocator is shared across all of the files. + // + // Howver, we do want to share the error reporter, + // since it might be something other than the default. + // + // This problem only surfaces when the error is reported + // somewhere other than in XIncludeHandler, since the XInclude#reportFatalError() + // method uses the right XMLLocator fErrorReporter = reporter; if (fErrorReporter != null) { fErrorReporter.putMessageFormatter( @@ -1029,6 +1043,7 @@ true); // use the same error reporter + // REVISIT: see setErrorReporter() fChildConfig.setProperty(ERROR_REPORTER, fErrorReporter); // use the same namespace context fChildConfig.setProperty( @@ -1036,29 +1051,19 @@ + Constants.NAMESPACE_CONTEXT_PROPERTY, fNamespaceContext); - XIncludeHandler newHandler = (XIncludeHandler)fChildConfig.getProperty( - Constants.XERCES_PROPERTY_PREFIX - + Constants.XINCLUDE_HANDLER_PROPERTY); + XIncludeHandler newHandler = + (XIncludeHandler)fChildConfig.getProperty( + Constants.XERCES_PROPERTY_PREFIX + + Constants.XINCLUDE_HANDLER_PROPERTY); newHandler.setParent(this); newHandler.setDocumentHandler(this.getDocumentHandler()); } // set all features on parserConfig to match this parser configuration - Enumeration xercesFeatures = Constants.getXercesFeatures(); - while (xercesFeatures.hasMoreElements()) { - String featureId = (String)xercesFeatures.nextElement(); - try { - fChildConfig.setFeature( - featureId, - fSettings.getFeature(featureId)); - } - catch (XMLConfigurationException e) { - // parserConfig doesn't support this feature, - // so we won't worry about it - } - } + copyFeatures(fSettings, fChildConfig); - // we don't want a schema validator on the new pipeline + // we don't want a schema validator on the new pipeline, + // so we set it to false, regardless of what was copied above fChildConfig.setFeature( Constants.XERCES_FEATURE_PREFIX + Constants.SCHEMA_VALIDATION_FEATURE, @@ -1223,7 +1228,6 @@ // this causes errors with schema validation, since the schema doesn't specify that these elements can have an xml:base attribute // TODO: add a user option to turn this off? - // TODO: make this a relative URL, when possible // TODO: [base URI] is still an open issue with the working group. // They're deciding if xml:base should be added if the [base URI] is different in terms // of resolving relative references, or if it should be added if they are different at all. @@ -1238,25 +1242,47 @@ } // Modify attributes of included items to do namespace-fixup. (spec 4.5.4) - // TODO: worry about null namespace? Enumeration inscopeNS = fNamespaceContext.getAllPrefixes(); while (inscopeNS.hasMoreElements()) { String prefix = (String)inscopeNS.nextElement(); String parentURI = fNamespaceContext.getURIFromIncludeParent(prefix); String uri = fNamespaceContext.getURI(prefix); - if (parentURI != uri - && (attributes != null - && attributes.getValue(NamespaceContext.XMLNS_URI, prefix) - == null)) { - if (attributes == null) { - attributes = new XMLAttributesImpl(); + if (parentURI != uri && attributes != null) { + if (prefix == XMLSymbols.EMPTY_STRING) { + if (attributes + .getValue( + NamespaceContext.XMLNS_URI, + XMLSymbols.PREFIX_XMLNS) + == null) { + if (attributes == null) { + attributes = new XMLAttributesImpl(); + } + + QName ns = (QName)NEW_NS_ATTR_QNAME.clone(); + ns.localpart = XMLSymbols.PREFIX_XMLNS; + ns.rawname = XMLSymbols.PREFIX_XMLNS; + attributes.addAttribute( + ns, + XMLSymbols.fCDATASymbol, + uri); + } + } + else if ( + attributes.getValue(NamespaceContext.XMLNS_URI, prefix) + == null) { + if (attributes == null) { + attributes = new XMLAttributesImpl(); + } + + QName ns = (QName)NEW_NS_ATTR_QNAME.clone(); + ns.localpart = prefix; + ns.rawname += prefix; + attributes.addAttribute( + ns, + XMLSymbols.fCDATASymbol, + uri); } - - QName ns = (QName)NEW_NS_ATTR_QNAME.clone(); - ns.localpart = prefix; - ns.rawname += prefix; - attributes.addAttribute(ns, XMLSymbols.fCDATASymbol, uri); } } } @@ -1581,6 +1607,65 @@ } else { fParentXIncludeHandler.checkAndSendNotation(not); + } + } + + // It would be nice if we didn't have to repeat code like this, but there's no interface that has + // setFeature() and addRecognizedFeatures() that the objects have in common. + protected void copyFeatures( + XMLComponentManager from, + ParserConfigurationSettings to) { + Enumeration features = Constants.getXercesFeatures(); + copyFeatures1(features, Constants.XERCES_FEATURE_PREFIX, from, to); + features = Constants.getSAXFeatures(); + copyFeatures1(features, Constants.SAX_FEATURE_PREFIX, from, to); + } + + protected void copyFeatures( + XMLComponentManager from, + XMLParserConfiguration to) { + Enumeration features = Constants.getXercesFeatures(); + copyFeatures1(features, Constants.XERCES_FEATURE_PREFIX, from, to); + features = Constants.getSAXFeatures(); + copyFeatures1(features, Constants.SAX_FEATURE_PREFIX, from, to); + } + + private void copyFeatures1( + Enumeration features, + String featurePrefix, + XMLComponentManager from, + ParserConfigurationSettings to) { + while (features.hasMoreElements()) { + String featureId = featurePrefix + (String)features.nextElement(); + + to.addRecognizedFeatures(new String[] { featureId }); + + try { + to.setFeature(featureId, from.getFeature(featureId)); + } + catch (XMLConfigurationException e) { + // componentManager doesn't support this feature, + // so we won't worry about it + } + } + } + + private void copyFeatures1( + Enumeration features, + String featurePrefix, + XMLComponentManager from, + XMLParserConfiguration to) { + while (features.hasMoreElements()) { + String featureId = featurePrefix + (String)features.nextElement(); + boolean value = from.getFeature(featureId); + + try { + to.setFeature(featureId, value); + } + catch (XMLConfigurationException e) { + // componentManager doesn't support this feature, + // so we won't worry about it + } } } 1.2 +5 -0 xml-xerces/java/src/org/apache/xerces/xinclude/XIncludeTextReader.java Index: XIncludeTextReader.java =================================================================== RCS file: /home/cvs/xml-xerces/java/src/org/apache/xerces/xinclude/XIncludeTextReader.java,v retrieving revision 1.1 retrieving revision 1.2 diff -u -r1.1 -r1.2 --- XIncludeTextReader.java 18 Jul 2003 17:34:38 -0000 1.1 +++ XIncludeTextReader.java 28 Jul 2003 20:43:02 -0000 1.2 @@ -63,6 +63,7 @@ import java.net.URL; import java.net.URLConnection; +import org.apache.xerces.impl.XMLEntityManager; import org.apache.xerces.util.XMLStringBuffer; import org.apache.xerces.xni.parser.XMLInputSource; @@ -113,6 +114,8 @@ new URL( new URL(source.getBaseSystemId()), source.getSystemId()); + // TODO: use this to ensure that rewinding is supported + //stream = new XMLEntityManager.RewindableInputStream(url.openStream()); stream = url.openStream(); URLConnection urlCon = url.openConnection(); @@ -157,6 +160,7 @@ protected String getEncodingName(InputStream stream) throws IOException { final byte[] b4 = new byte[4]; int count = 0; + stream.mark(4); for (; count < 4; count++) { b4[count] = (byte)stream.read(); } @@ -179,6 +183,7 @@ /** * REVISIT: This code is take from org.apache.xerces.impl.XMLEntityManager. * Is there any way we can share the code, without having it implemented twice? + * I think we should make it public and static in XMLEntityManager. --PJM * * Returns the IANA encoding name that is auto-detected from * the bytes specified, with the endian-ness of that encoding where appropriate.
--------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED]