- java.lang.Object
-
- org.postgresql.pljava.Adjusting.XML
-
- Enclosing class:
- Adjusting
public static final class Adjusting.XML extends Object
Class that collects adjustment APIs for affecting the behavior of PL/Java's XML support.XML parser behavior adjustments
Retrieving or verifying the XML content in a JDBC
SQLXML
object can involve applying an XML parser. The full XML specification includes features that can require an XML parser to retrieve external resources or consume unexpected amounts of memory. The full feature support may be an asset in an environment where the XML content will always be from a known, trusted source, or a liability if less is known about the XML content being processed.The Open Web Application Security Project (OWASP) advocates for the default use of settings that strictly limit the related features of Java XML parsers, as outlined in a "cheat sheet" the organization publishes. The strict default settings can then be selectively relaxed in applications where the features are needed and the content is sufficiently trusted.
However, the recommended defaults really are severely restrictive (for example, disabling document-type declarations by default will cause PL/Java's
SQLXML
implementation to reject all XML values that contain DTDs). Therefore, there must be a simple and clear way for code to selectively adjust the settings, or adopting the strictest settings by default would pose an unacceptable burden to developers.The usual way that Java XML parsers expose their settings for adjustment is through
setFeature
orsetProperty
methods that must be passed particular URIs that identify adjustable features, and objects of appropriate types (often boolean) as the values for those properties. The supported properties and the URIs that identify them can be different from one parser implementation to another or one version to another. That is not the "simple and clear" adjustment mechanism needed here. Furthermore, the JDBCSQLXML
API conceals much of the complexity of configuring any underlying XML parser behind a simplegetSource
method whose result can be used directly with other Java APIs expecting some flavor ofSource
object, and for some of those flavors, the returned object does not even expose the methods one would need to call to adjust the underlying parser, if any.Hence this adjustment API. JDBC already provides for extensibility of the
SQLXML.getSource
method; it is passed the class object for a desired subtype ofSource
and, if the implementation supports it, returns an object of that type. The subtypes that every conformant implementation must support areStreamSource
,SAXSource
,StAXSource
, andDOMSource
. Ifnull
is passed, the implementation will choose which flavor to return, often based on internal implementation details making one most natural or efficient.The types
Adjusting.XML.SAXSource
,Adjusting.XML.StAXSource
, andAdjusting.XML.DOMSource
are used the same way, by passing the corresponding class literal toSQLXML
'sgetSource
method, which will return an object providing the chainable adjustment methods ofAdjusting.XML.Source
, with the chain ending in aget
method that returns the corresponding JavaSource
object, configured as adjusted.Example:
SAXSource src1 = sqx1.getSource(SAXSource.class); SAXSource src2 = sqx2.getSource(Adjusting.XML.SAXSource.class) .allowDTD(true).get();
src1
would be assigned aSAXSource
object configured with the OWASP-recommended defaults, which will not allow the content to have a DTD, among other restrictions, whilesrc2
would be assigned aSAXSource
object configured with the other default restrictions (as if theallowDTD(true)
is preceded by an implieddefaults()
), but with DTD parsing enabled.No
Adjusting.XML.StreamSource
is needed or provided, as any application code that requests aStreamSource
will have to provide and configure its own parser anyway.Like passing
null
togetSource
, passing the parent interfaceAdjusting.XML.Source.class
will allow the implementation to choose which subtype ofAdjusting.XML.Source
to return. The object returned byget
can then be passed directly to Java APIs likeTransformer
that accept several flavors ofSource
, or examined to see of what class it is.
-
-
Nested Class Summary
Nested Classes Modifier and Type Class Description static interface
Adjusting.XML.DOMSource
Adjusting version of aDOMSource
.static interface
Adjusting.XML.Parsing<T extends Adjusting.XML.Parsing<T>>
Interface with methods to adjust the restrictions on XML parsing that are commonly considered when XML content might be from untrusted sources.static interface
Adjusting.XML.Result<T extends Result>
Adjusting version ofjavax.xml.transform.Result
, offering the adjustment methods ofAdjusting.XML.Parsing
, chiefly so that there is a way to apply those adjustments to any implicitly-created parser used to verify the content that will be written to theResult
.static interface
Adjusting.XML.SAXResult
Adjusting version of aSAXResult
.static interface
Adjusting.XML.SAXSource
Adjusting version of aSAXSource
.static interface
Adjusting.XML.SetMethod<T>
A functional interface fitting varioussetFeature
orsetProperty
methods in Java XML APIs.static interface
Adjusting.XML.Source<T extends Source>
Adjusting version ofjavax.xml.transform.Source
, allowing various parser features to be configured before callingget()
to obtain the usableSource
object.static interface
Adjusting.XML.SourceResult
SpecializedResult
type for setting a new PL/JavaSQLXML
instance's content from an arbitrarySource
object of any of the types JDBC requires theSQLXML
type to support.static interface
Adjusting.XML.StAXSource
Adjusting version of aStAXSource
.static interface
Adjusting.XML.StreamResult
Adjusting version of aStreamResult
.
-
Method Summary
Modifier and Type Method Description static <T,V extends T>
ExceptionsetFirstSupported(Adjusting.XML.SetMethod<? super T> setter, V value, List<Class<? extends Exception>> expected, Exception caught, Consumer<? super Exception> onUnexpected, String... names)
Attempts a given action (typically to set something) using a given value, trying one or more supplied keys in order until the action succeeds with no exception.static <T,V extends T>
ExceptionsetFirstSupported(Adjusting.XML.SetMethod<? super T> setter, V value, List<Class<? extends Exception>> expected, Consumer<? super Exception> onUnexpected, String... names)
Calls the six-argument overload passing null for caught.
-
-
-
Method Detail
-
setFirstSupported
public static <T,V extends T> Exception setFirstSupported(Adjusting.XML.SetMethod<? super T> setter, V value, List<Class<? extends Exception>> expected, Exception caught, Consumer<? super Exception> onUnexpected, String... names)
Attempts a given action (typically to set something) using a given value, trying one or more supplied keys in order until the action succeeds with no exception.This logic is common to the
setFirstSupportedFeature
andsetFirstSupportedProperty
methods, and is exposed here because it may be useful for other tasks in Java's XML APIs, such as configuringTransformer
s.If any attempt succeeds, null is returned. If no attempt succeeds, the first exception caught is returned, with any exceptions from the subsequent attempts retrievable from it with
getSuppressed
. The return is immediate, without any remaining names being tried, if an exception is caught that is not assignable to a class in the expected list. Such an exception is returned (or added to the suppressed list of an exception already to be returned) only if the onUnexpected handler is null; otherwise, it is passed to the handler and does not affect the method's return.For some purposes, a single call of this method may not suffice: if alternate means to establish a desired configuration have existed and are not simply alternate property names that will accept the same value. For such a case, this method may be called more than once. The caller abandons the sequence of calls after the first call that returns null (indicating that it either succeeded, or incurred an unexpected exception and passed it to the onUnexpected handler. Otherwise, the exception returned by the first call can be passed as caught to the next call, instead of passing the usual null. (When a non-null caught is passed, it will be returned on failure, even if an unexpected exception has been caught; therefore, should it ever be necessary to chain more than two of these calls, the caller should abandon the sequence as soon as a call returns null or returns its caught argument with no growth of its suppressed list.)
- Parameters:
setter
- typically a method reference for a method that takes a string key and some value.value
- the value to pass to the setterexpected
- a list of exception classes that can be foreseen to indicate that a key was not recognized, and the operation should be retried with the next possible key.caught
- null, or an exception returned by a preceding call if an operation cannot be implemented with one call of this methodonUnexpected
- invoked, if non-null, on anException
that is caught and matches nothing in the expected list, instead of returning it. If this parameter is null, such an exception is returned (or added to the suppressed list of the exception to be returned), just as for expected exceptions, but the return is immediate, without trying remaining names, if any.names
- one or more String keys to be tried in order until the action succeeds.- Returns:
- null if any attempt succeeded, or if the first exception caught was passed to the onUnexpected handler; otherwise the first exception caught (if the caller supplied a non-null caught, then that exception), which may have further exceptions in its suppressed list.
-
-