Today I had to reuse my code snippet from the JAXB and CDATA blog post to integrate it into a Jersey web application. The application produces some content which could contain some „strings“ which must be wrapped by a CDATA section. To realize this I implemented a javax.ws.rs.ext.MessageBodyReader and javax.ws.rs.ext.MessageBodyWriter by extending from the class com.sun.jersey.core.provider.jaxb.AbstractJAXBElementProvider. This implementation is registered at the Jersey Application by returning the class object in the com.bosch.im.jaxrs.ImApplication.getClasses() implementation.
import java.io.InputStream; import java.io.OutputStream; import java.nio.charset.Charset; import javax.ws.rs.Produces; import javax.ws.rs.core.Context; import javax.ws.rs.core.MediaType; import javax.ws.rs.ext.Provider; import javax.ws.rs.ext.Providers; import javax.xml.bind.JAXBElement; import javax.xml.bind.JAXBException; import javax.xml.bind.Marshaller; import javax.xml.bind.Unmarshaller; import javax.xml.parsers.SAXParserFactory; import javax.xml.stream.XMLOutputFactory; import javax.xml.stream.XMLStreamException; import javax.xml.stream.XMLStreamWriter; import com.google.common.base.Throwables; import com.sun.jersey.core.provider.jaxb.AbstractJAXBElementProvider; import com.sun.jersey.spi.inject.Injectable; import CDataXMLStreamWriter; @Provider @Produces( MediaType.APPLICATION_ATOM_XML ) // replace this by the media type you create in your application public class CDATAXMLJAXBElementProvider extends AbstractJAXBElementProvider { // Delay construction of factory private final Injectable spf; private final XMLOutputFactory xmlOutputFactory = XMLOutputFactory.newInstance(); public CDATAXMLJAXBElementProvider( @Context Injectable spf, @Context Providers ps ) { super( ps ); this.spf = spf; } @Override protected JAXBElement<!--?--> readFrom( Class<!--?--> type, MediaType mediaType, Unmarshaller u, InputStream entityStream ) throws JAXBException { return u.unmarshal( getSAXSource( spf.getValue(), entityStream ), type ); } @Override protected void writeTo( JAXBElement<!--?--> t, MediaType mediaType, Charset c, Marshaller m, OutputStream entityStream ) throws JAXBException { CDataXMLStreamWriter cdataStreamWriter = null; try { XMLStreamWriter streamWriter = xmlOutputFactory.createXMLStreamWriter( entityStream, "UTF-8" ); cdataStreamWriter = new CDataXMLStreamWriter( streamWriter ); m.marshal( t, cdataStreamWriter ); cdataStreamWriter.flush(); } catch( XMLStreamException e ) { Throwables.propagate( e ); } finally { if( cdataStreamWriter != null ) { try { cdataStreamWriter.close(); } catch( XMLStreamException e ) { // nothing to do } } } } } |