users@jersey.java.net

Re: [Jersey] XSD validation during unmarshalling

From: Paul Sandoz <Paul.Sandoz_at_Sun.COM>
Date: Tue, 22 Jul 2008 17:26:39 +0200

Hi Andrew,

Unmarshaller.setValidating is indeed deprecated and you need to set the
Schema object to validate against.

In this respect i am unsure how you can create a general validating
mechanism unless you keep a map of known JAXB class to Schema instance.

You will have to create the Schema instances from the correspondingly
available XSD, more info can be found here [1].

Rather than creating a general validating mechanism it might be better
to have a general mechanism you inherit from for specific validating
purposes i.e. provides the JAXB context and a set of schema.

Paul.

[1]
http://www.java-tips.org/java-ee-tips/java-architecture-for-xml-binding/what-is-new-in-jaxb-2.0.html

Andrew Cole wrote:
> Now that Paul is back, I would like to promote this thread again.
> Paul-- any help you can provide will be greatly appreciated.
>
> Thanks,
> Andrew
>
> On Mon, Jul 7, 2008 at 2:22 PM, Andrew Cole <andrew_at_9summer.com
> <mailto:andrew_at_9summer.com>> wrote:
>
> While Paul is on vacation, can somebody help illuminate his response
> to my query below? Trying to follow his instructions, I have
> implemented a ContextResolver as follows:
>
> @Provider
> public class ValidatingJAXBContextResolver implements
> ContextResolver<JAXBContext> {
> public JAXBContext getContext(Class<?> type) {
> try {
> return new ValidatingJAXBContext(type);
> } catch (JAXBException e) {
> return null;
> }
> }
> }
>
> and a JAXBContext (modeled after the JSONJAXBContext in the jersey
> source) as:
>
> public class ValidatingJAXBContext extends JAXBContext {
> private final JAXBContext jaxbContext;
>
> public ValidatingJAXBContext(Class... classesToBeBound)
> throws JAXBException {
> jaxbContext = JAXBContext.newInstance(classesToBeBound);
> }
>
> public ValidatingJAXBContext(Class[] classesToBeBound, Map<String,
> Object> properties) throws JAXBException {
> jaxbContext = JAXBContext.newInstance(classesToBeBound,
> properties);
> }
>
> @Override
> public Unmarshaller createUnmarshaller() throws JAXBException {
> Unmarshaller unmarshaller = jaxbContext.createUnmarshaller();
> unmarshaller.setValidating(true);
> return unmarshaller;
> }
>
> @Override
> public Marshaller createMarshaller() throws JAXBException {
> return jaxbContext.createMarshaller();
> }
>
> @Override
> public Validator createValidator() throws JAXBException {
> return jaxbContext.createValidator();
> }
>
> }
>
> Now, when I hit a method that would require unmarshalling content from
> XML, I receive an exception at my call to setValidating:
> java.lang.UnsupportedOperationException
> at
> com.sun.xml.bind.v2.runtime.unmarshaller.UnmarshallerImpl.setValidating(UnmarshallerImpl.java:483)
> at
> myCode.ValidatingJAXBContext.createUnmarshaller(ValidatingJAXBContext.java:33)
> at
> com.sun.ws.rest.impl.provider.entity.XMLRootElementProvider.readFrom(XMLRootElementProvider.java:58)
> at
> com.sun.ws.rest.spi.container.AbstractContainerRequest.getEntity(AbstractContainerRequest.java:179)
> [stack trace truncated]
>
> Am I on the right track here? As I understand it, the call to
> setValidating is deprecated in JAXB 2.0 and I should use setSchema.
> Is this correct? If so, how can I have my ValidatingJAXBContext class
> create an appropriate javax.xml.validation.Schema object for this
> call, based on the classToBeBound passed in to the constructor?
>
> On Thu, Jul 3, 2008 at 10:20 PM, Paul Sandoz <Paul.Sandoz_at_sun.com
> <mailto:Paul.Sandoz_at_sun.com>> wrote:
> >
> > On Jul 4, 2008, at 1:05 AM, Andrew Cole wrote:
> >
> > Hi all
> >
> > I'm using Jersey 0.7 and have a number of methods that accept
> objects unmarshalled from XML via JAXB bindings. It does not appear
> that the unmarshalling process is validating the XML against the
> schema used to create the JAXB bindings. For instance, I have a
> pattern restriction on a string element that is not being respected,
> and I can leave out elements that have a minOccurs of 1. How can I
> configure the unmarshaller to validate against my schema?
> >
> >
> > Currently you need to supply your own JAXBContext that returns a
> validating unmarshaller for unmarshalling the JAXB types that
> require validation.
> > See ContextResolver [1].
> > In this case you would do:
> > public class MyContextResolver implements
> ContextResolver<JAXBContext> {
> > JAXBContext getContext(Class<?> type) { ... }
> > }
> > I plan to make this easier so you can use ContextResolver with an
> Unmarshaller/Marshaller thus you don't have to wrap JAXBContext.
> > Paul.
> > [1]
> https://jsr311.dev.java.net/nonav/releases/0.8/javax/ws/rs/ext/ContextResolver.html
>
>

-- 
| ? + ? = To question
----------------\
    Paul Sandoz
         x38109
+33-4-76188109