You are viewing a plain text version of this content. The canonical link for it is here.
Posted to j-users@xerces.apache.org by ma...@wunderlich.com on 2024/01/15 11:47:32 UTC

Problems with missing properties accessExternalSchema accessExternalDTD in Xerces2

Hello,

First post here, since I am not able to comment in this project's Jira. 
I have run into an issue with Xerces2 during a Java 17 migration. 
JEP-403 mentions the following under "Risks and assumptions":

"Code that uses the JDK's internal copy of the Xerces XML processor 
[might fail]. Such code should instead use a standalone copy of the 
Xerces library, available from Maven Central [1]."

https://openjdk.org/jeps/403

The problem is that when including Xerces2 2.12.2 as a Maven dependency, 
two properties are not recognized, which are relevant for security (to 
prevent XXE attacks:

http://javax.xml.XMLConstants/property/accessExternalSchema

http://javax.xml.XMLConstants/property/accessExternalDTD

There is an open Jira topic to support these properties: 
https://issues.apache.org/jira/browse/XERCESJ-1654

This was created in 2015 and I am wondering what the current status is 
and what a suitable workaround might be to fulfill that requirement of 
JEP-403.

Thanks a lot!

Cheers,

Martin

Links:
------
[1] https://search.maven.org/artifact/xerces/xercesImpl

Re: Problems with missing properties accessExternalSchema accessExternalDTD in Xerces2

Posted by ma...@wunderlich.com.
Hi Stanimir,

Thank you so much for this very clear and elaborate explanation. It is 
much clearer to me know that have in fact been reading the JEP-403 
incorrectly, assuming it refers to any use of the JRE bundled Xerces 
parser. So, as long as we stick to coding against the JAXP APIs only and 
not use any Xerces API directly, we are good.

Thank you also for the hint on entity resolving! That's an interesting 
approach which I hadn't considered.

Regards,

Martin

Am 2024-01-16 17:54, schrieb Stanimir Stamenkov:

> Tue, 16 Jan 2024, /Martin Wunderlich/:
> 
>> my use case is this: "A software developer having direct control over 
>> the application implementation"
>> 
>> I might be misunderstanding the recommendation from JEP-403 then. In 
>> which way is "the JDK's internal copy of the Xerces XML processor" 
>> different from "JDK-bundled JAXP implementation"? I was assuming that 
>> this is this the same thing, as the JDK is using Xerces under the hood 
>> as its JAXP implementation?
> 
> Yes, with "the JDK-bundled JAXP implementation" I'm referring to the 
> "JDK's internal copy of the Xerces".  Note, that implementation is 
> different from Apache Xerces.  It uses different packages at least - 
> com.sun.org.apache.xerces.*
> 
> Still, JEP-403 doesn't recommend against using it as a runtime JAXP 
> provider - it recommends against referring the implementation classes 
> directly in code, f.e.:
> 
> com.sun.org.apache.xerces.internal.jaxp.SAXParserImpl
> 
> but using the implementation just via the JAXP APIs.  It is all because 
> this implementation detail is intended to be sealed by JPMS, and 
> wouldn't be directly accessible by user code.
> 
>> In the code we're importing the following:
>> 
>> import javax.xml.XMLConstants;
>> import javax.xml.parsers.ParserConfigurationException;
>> import javax.xml.parsers.SAXParser;
>> import javax.xml.parsers.SAXParserFactory;
> So it seems you're using only JAXP APIs and should be all fine, 
> regardless of which JAXP provider is plugged into the runtime.
> 
> Here's more detailed example of what I've meant developers should 
> always provide/configure to their parser instances:
> 
> SAXParserFactory spf = SAXParserFactory.newInstance();
> SAXParser saxParser = spf.newSAXParser();
> XMLReader xmlReader = saxParser.getXMLReader();
> EntityResolver
> noExternalEntitiesResolver = (publicId, systemId) -> {
> return new InputSource(new StringReader(""));
> };
> xmlReader.setEntityResolver(noExternalEntitiesResolver);
> ...
> xmlReader.parse(...);
> 
> Using SAXParser directly would require you to implement 
> `resolveEntity(String publicId, String systemId)` on your 
> DefaultHandler (ContentHandler), instead.
> 
> You may implement more sophisticated entity resolver which behavior may 
> be configured via application-specific vs. general JAXP configuration, 
> and could delegate to a CatalogResolver for required entities packaged 
> as application resources, but note how the above example differs from 
> "accessExternalDTD":
> 
> saxParser.setProperty(XMLConstants.ACCESS_EXTERNAL_DTD, "");
> 
> The latter configuration prohibits any external entities and will fail 
> the parse operation if an external reference is found, for example:
> 
> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
> 
> "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
> 
> The former example substitutes all external entities with empty content 
> which would result in a successful non-validating (XML DTD) parsing for 
> most XML documents.  You could also have you entity resolver throw an 
> exception, if any external entities are not expected and strictly 
> prohibited by your application.

Re: Problems with missing properties accessExternalSchema accessExternalDTD in Xerces2

Posted by Stanimir Stamenkov <s7...@netscape.net.INVALID>.
Tue, 16 Jan 2024, /Stanimir Stamenkov/:

>      EntityResolver
>              noExternalEntitiesResolver = (publicId, systemId) -> {
>          return new InputSource(new StringReader(""));
>      };
>      xmlReader.setEntityResolver(noExternalEntitiesResolver);
>
> [...]
> 
>      saxParser.setProperty(XMLConstants.ACCESS_EXTERNAL_DTD, "");
> 
> The latter configuration prohibits any external entities and will fail 
> the parse operation if an external reference is found...
> 
> The former example substitutes all external entities with empty content...

Essentially, configuring "accessExternalDTD" with an empty value is a 
convenience for setting up an entity resolver with the following example 
implementation:

     EntityResolver
             noExternalEntitiesResolver = (publicId, systemId) -> {
         throw new SAXException("External entity not allowed: " + systemId);
     };

-- 
Stanimir

---------------------------------------------------------------------
To unsubscribe, e-mail: j-users-unsubscribe@xerces.apache.org
For additional commands, e-mail: j-users-help@xerces.apache.org


Re: Problems with missing properties accessExternalSchema accessExternalDTD in Xerces2

Posted by Stanimir Stamenkov <s7...@netscape.net.INVALID>.
Tue, 16 Jan 2024, /Martin Wunderlich/:

> my use case is this: "A software developer having direct control over 
> the application implementation"
> 
> I might be misunderstanding the recommendation from JEP-403 then. In 
> which way is "the JDK’s internal copy of the Xerces XML processor" 
> different from "JDK-bundled JAXP implementation"? I was assuming that 
> this is this the same thing, as the JDK is using Xerces under the hood 
> as its JAXP implementation?

Yes, with "the JDK-bundled JAXP implementation" I'm referring to the 
"JDK's internal copy of the Xerces".  Note, that implementation is 
different from Apache Xerces.  It uses different packages at least – 
com.sun.org.apache.xerces.*

Still, JEP-403 doesn't recommend against using it as a runtime JAXP 
provider – it recommends against referring the implementation classes 
directly in code, f.e.:

     com.sun.org.apache.xerces.internal.jaxp.SAXParserImpl

but using the implementation just via the JAXP APIs.  It is all because 
this implementation detail is intended to be sealed by JPMS, and 
wouldn't be directly accessible by user code.

> In the code we're importing the following:
> 
> import javax.xml.XMLConstants;
> import javax.xml.parsers.ParserConfigurationException;
> import javax.xml.parsers.SAXParser;
> import javax.xml.parsers.SAXParserFactory;
So it seems you're using only JAXP APIs and should be all fine, 
regardless of which JAXP provider is plugged into the runtime.

Here's more detailed example of what I've meant developers should always 
provide/configure to their parser instances:

     SAXParserFactory spf = SAXParserFactory.newInstance();
     SAXParser saxParser = spf.newSAXParser();
     XMLReader xmlReader = saxParser.getXMLReader();
     EntityResolver
             noExternalEntitiesResolver = (publicId, systemId) -> {
         return new InputSource(new StringReader(""));
     };
     xmlReader.setEntityResolver(noExternalEntitiesResolver);
     ...
     xmlReader.parse(...);

Using SAXParser directly would require you to implement 
`resolveEntity(String publicId, String systemId)` on your DefaultHandler 
(ContentHandler), instead.

You may implement more sophisticated entity resolver which behavior may 
be configured via application-specific vs. general JAXP configuration, 
and could delegate to a CatalogResolver for required entities packaged 
as application resources, but note how the above example differs from 
"accessExternalDTD":

     saxParser.setProperty(XMLConstants.ACCESS_EXTERNAL_DTD, "");

The latter configuration prohibits any external entities and will fail 
the parse operation if an external reference is found, for example:

     <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
 
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">

The former example substitutes all external entities with empty content 
which would result in a successful non-validating (XML DTD) parsing for 
most XML documents.  You could also have you entity resolver throw an 
exception, if any external entities are not expected and strictly 
prohibited by your application.

-- 
Stanimir

---------------------------------------------------------------------
To unsubscribe, e-mail: j-users-unsubscribe@xerces.apache.org
For additional commands, e-mail: j-users-help@xerces.apache.org


Re: Problems with missing properties accessExternalSchema accessExternalDTD in Xerces2

Posted by ma...@wunderlich.com.
Hi Stanimir,

my use case is this: "A software developer having direct control over 
the application implementation"

I might be misunderstanding the recommendation from JEP-403 then. In 
which way is "the JDK's internal copy of the Xerces XML processor" 
different from "JDK-bundled JAXP implementation"? I was assuming that 
this is this the same thing, as the JDK is using Xerces under the hood 
as its JAXP implementation?

In the code we're importing the following:

import javax.xml.XMLConstants;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;

Regards,

Martin

Am 2024-01-16 11:57, schrieb Stanimir Stamenkov:

> Tue, 16 Jan 2024, /Martin Wunderlich/:
> 
>> So, it seems there are two possible solutions here:
>> 
>> - Ignore that recommendation from JEP-403, keep the included JAXP 
>> implementation that comes with the JRE and hope for the best ... or
> 
> As far as I get JEP-403 recommends one shouldn't refer to JDK-specific 
> implementation (com.sun.org.apache.xerces.* vs. JAXP API) classes in 
> code.  One shouldn't be doing it anyway.  You didn't answer my previous 
> question - is that the case for you?  JEP-403 doesn't recommend against 
> using the JDK-bundled JAXP implementation in general (as default JAXP 
> provider in your runtime).
> 
>> - Find some other parser implementation that does not rely on Xerces 
>> and that does implement JAXP 1.5+ (but I am not aware of one)
>> 
>> Any other ideas anyone?
> 
> Could you specify what's your use case:
> 
> 1. A software developer having direct control over the application 
> implementation;
> 2. A system administrator trying to configure existing application 
> runtime.
> 
> In my previous reply I've suggested developers shouldn't rely on 
> "accessExternalDTD" alone, for example.
> 
> For the latter case I've suggested removing Xerces (the Apache library, 
> its JARs) from the runtime configuration/packaging, and relying on the 
> JDK-bundled implementation.  This way one may rely on global 
> "accessExternalDTD" setting, though there's a minimal chance it may 
> break legitimate application functionality.

Re: Problems with missing properties accessExternalSchema accessExternalDTD in Xerces2

Posted by Stanimir Stamenkov <s7...@netscape.net.INVALID>.
Tue, 16 Jan 2024, /Martin Wunderlich/:

> So, it seems there are two possible solutions here:
> 
> - Ignore that recommendation from JEP-403, keep the included JAXP 
> implementation that comes with the JRE and hope for the best ... or

As far as I get JEP-403 recommends one shouldn't refer to JDK-specific 
implementation (com.sun.org.apache.xerces.* vs. JAXP API) classes in 
code.  One shouldn't be doing it anyway.  You didn't answer my previous 
question – is that the case for you?  JEP-403 doesn't recommend against 
using the JDK-bundled JAXP implementation in general (as default JAXP 
provider in your runtime).

> - Find some other parser implementation that does not rely on Xerces and 
> that does implement JAXP 1.5+ (but I am not aware of one)
> 
> Any other ideas anyone?

Could you specify what's your use case:

1. A software developer having direct control over the application 
implementation;
2. A system administrator trying to configure existing application runtime.

In my previous reply I've suggested developers shouldn't rely on 
"accessExternalDTD" alone, for example.

For the latter case I've suggested removing Xerces (the Apache library, 
its JARs) from the runtime configuration/packaging, and relying on the 
JDK-bundled implementation.  This way one may rely on global 
"accessExternalDTD" setting, though there's a minimal chance it may 
break legitimate application functionality.

-- 
Stanimir

---------------------------------------------------------------------
To unsubscribe, e-mail: j-users-unsubscribe@xerces.apache.org
For additional commands, e-mail: j-users-help@xerces.apache.org


Re: Problems with missing properties accessExternalSchema accessExternalDTD in Xerces2

Posted by Martin Wunderlich <ma...@wunderlich.com>.
Thanks a lot for the reply and confirming the problem!

So, it seems there are two possible solutions here:

- Ignore that recommendation from JEP-403, keep the included JAXP 
implementation that comes with the JRE and hope for the best ... or

- Find some other parser implementation that does not rely on Xerces and 
that does implement JAXP 1.5+ (but I am not aware of one)

Any other ideas anyone?

Cheers,

Martin

Am 15.01.24 um 16:24 schrieb Stanimir Stamenkov:
> Mon, 15 Jan 2024, /Martin/:
>
>> "Code that uses the JDK’s internal copy of the Xerces XML processor 
>> [might fail]. Such code should instead use a standalone copy of the 
>> Xerces library, available from Maven Central."
>>
>> https://openjdk.org/jeps/403
>
> I'm just curious, what Xerces-specific classes are you using, are you 
> using any?
>
>> The problem is that when including Xerces2 2.12.2 as a Maven 
>> dependency, two properties are not recognized, which are relevant for 
>> security (to prevent XXE attacks:
>>
>> http://javax.xml.XMLConstants/property/accessExternalSchema
>>
>> http://javax.xml.XMLConstants/property/accessExternalDTD
>
> Fact is these are part of JAXP since Java 7 [1] and I think Xerces 
> should support them to remain reasonably relevant implementation.
>
>> There is an open Jira topic to support these properties: 
>> https://issues.apache.org/jira/browse/XERCESJ-1654
>>
>> This was created in 2015 and I am wondering what the current status 
>> is and what a suitable workaround might be to fulfill that 
>> requirement of JEP-403.
>
> Not a general workaround but for code I develop I strive to implement 
> specific external resource resolution and its configuration by means 
> of setting up an explicit 'entityResolver' [2].  I don't find the 
> accessExternalDTD/accessExternalSchema fail-fast behavior particularly 
> handy for such use cases.
>
> If you don't have control over the implementation and would only like 
> to influence it via system configuration, maybe avoid including Xerces 
> in your runtime, for the time being.
>

---------------------------------------------------------------------
To unsubscribe, e-mail: j-users-unsubscribe@xerces.apache.org
For additional commands, e-mail: j-users-help@xerces.apache.org


Re: Problems with missing properties accessExternalSchema accessExternalDTD in Xerces2

Posted by Stanimir Stamenkov <s7...@netscape.net.INVALID>.
Mon, 15 Jan 2024, /Stanimir Stamenkov/:
> Mon, 15 Jan 2024, /Martin/:
> 
>> The problem is that when including Xerces2 2.12.2 as a Maven 
>> dependency, two properties are not recognized, which are relevant for 
>> security (to prevent XXE attacks:
>>
>> http://javax.xml.XMLConstants/property/accessExternalSchema
>>
>> http://javax.xml.XMLConstants/property/accessExternalDTD
> 
> Fact is these are part of JAXP since Java 7 [1] and I think Xerces 
> should support them to remain reasonably relevant implementation.

O.k.  According to Wikipedia:

* https://en.wikipedia.org/wiki/Java_API_for_XML_Processing

it is sometime after the Java 7 GA release:

| Java SE version | JAXP version bundled |
| --------------- | -------------------- |
| 1.7.0           | 1.4.5                |
| 1.7.40          | 1.5                  |

If I'm reading this correctly:

* https://www.java.com/releases/

it is JDK 7u40, 2013-09-10 (vs. 7 LTS, 2011-07-11).

-- 
Stanimir

---------------------------------------------------------------------
To unsubscribe, e-mail: j-users-unsubscribe@xerces.apache.org
For additional commands, e-mail: j-users-help@xerces.apache.org


Re: Problems with missing properties accessExternalSchema accessExternalDTD in Xerces2

Posted by Stanimir Stamenkov <s7...@netscape.net.INVALID>.
Mon, 15 Jan 2024, /Martin/:

> "Code that uses the JDK’s internal copy of the Xerces XML processor 
> [might fail]. Such code should instead use a standalone copy of the 
> Xerces library, available from Maven Central."
> 
> https://openjdk.org/jeps/403

I'm just curious, what Xerces-specific classes are you using, are you 
using any?

> The problem is that when including Xerces2 2.12.2 as a Maven dependency, 
> two properties are not recognized, which are relevant for security (to 
> prevent XXE attacks:
> 
> http://javax.xml.XMLConstants/property/accessExternalSchema
> 
> http://javax.xml.XMLConstants/property/accessExternalDTD

Fact is these are part of JAXP since Java 7 [1] and I think Xerces 
should support them to remain reasonably relevant implementation.

> There is an open Jira topic to support these properties: 
> https://issues.apache.org/jira/browse/XERCESJ-1654
> 
> This was created in 2015 and I am wondering what the current status is 
> and what a suitable workaround might be to fulfill that requirement of 
> JEP-403.

Not a general workaround but for code I develop I strive to implement 
specific external resource resolution and its configuration by means of 
setting up an explicit 'entityResolver' [2].  I don't find the 
accessExternalDTD/accessExternalSchema fail-fast behavior particularly 
handy for such use cases.

If you don't have control over the implementation and would only like to 
influence it via system configuration, maybe avoid including Xerces in 
your runtime, for the time being.

-- 
Stanimir

[1] 
https://docs.oracle.com/javase/7/docs/api/javax/xml/XMLConstants.html#ACCESS_EXTERNAL_DTD
 
https://docs.oracle.com/javase/7/docs/api/javax/xml/parsers/SAXParser.html#setProperty(java.lang.String,%20java.lang.Object)
     https://docs.oracle.com/javase/tutorial/jaxp/properties/
     https://docs.oracle.com/javase/tutorial/jaxp/properties/properties.html

[2] 
https://docs.oracle.com/en/java/javase/21/docs/api/java.xml/org/xml/sax/XMLReader.html#setEntityResolver(org.xml.sax.EntityResolver)

---------------------------------------------------------------------
To unsubscribe, e-mail: j-users-unsubscribe@xerces.apache.org
For additional commands, e-mail: j-users-help@xerces.apache.org