# HG changeset patch # User Sascha L. Teichmann # Date 1333451710 0 # Node ID 9798e4d83681621b2e6951d93d2e6d86d0466462 # Parent 95ff5a25a3399268929f90bb635c710e3784a3f9 Services are now able to return more than just XML documents. artifacts/trunk@4188 c6561f87-3c4e-4783-a992-168aeb5c3f6f diff -r 95ff5a25a339 -r 9798e4d83681 ChangeLog --- a/ChangeLog Fri Mar 30 07:21:29 2012 +0000 +++ b/ChangeLog Tue Apr 03 11:15:10 2012 +0000 @@ -1,3 +1,28 @@ +2012-04-04 Sascha L. Teichmann + + Modified services so that they are now able to return more than just + XML documents. Needed if you want to return e.g. a PNG image from a service. + + * artifacts/src/main/java/de/intevation/artifacts/Service.java: + A service now returns a tuple (data, MIME type). + + * artifacts/src/main/java/de/intevation/artifacts/ArtifactDatabase.java, + artifact-database/src/main/java/de/intevation/artifactdatabase/ArtifactDatabaseImpl.java: + Adjusted calls. + + * artifact-database/src/main/java/de/intevation/artifactdatabase/DefaultService.java: + Returns a DefaultService.Output by default. + + * artifact-database/src/main/java/de/intevation/artifactdatabase/XMLService.java: New. + Convenience sub class if DefaultService to produce XML documents. Old + Services should derive from this class now to main compatibility. + + * artifact-database/src/main/java/de/intevation/artifactdatabase/rest/ServiceResource.java: + Adjusted to handle the new Output tuples. + + * artifact-database/src/main/java/de/intevation/artifactdatabase/rest/ByteArrayRepresentation.java: + New. Wraps a byte array as a Restlet representation. + 2012-03-30 Ingo Weinzierl * artifact-database/src/main/java/de/intevation/artifactdatabase/state/DefaultOutput.java: diff -r 95ff5a25a339 -r 9798e4d83681 artifact-database/src/main/java/de/intevation/artifactdatabase/ArtifactDatabaseImpl.java --- a/artifact-database/src/main/java/de/intevation/artifactdatabase/ArtifactDatabaseImpl.java Fri Mar 30 07:21:29 2012 +0000 +++ b/artifact-database/src/main/java/de/intevation/artifactdatabase/ArtifactDatabaseImpl.java Tue Apr 03 11:15:10 2012 +0000 @@ -1162,7 +1162,7 @@ return serviceNamesAndDescription; } - public Document process( + public Service.Output process( String serviceName, Document input, CallMeta callMeta diff -r 95ff5a25a339 -r 9798e4d83681 artifact-database/src/main/java/de/intevation/artifactdatabase/DefaultService.java --- a/artifact-database/src/main/java/de/intevation/artifactdatabase/DefaultService.java Fri Mar 30 07:21:29 2012 +0000 +++ b/artifact-database/src/main/java/de/intevation/artifactdatabase/DefaultService.java Tue Apr 03 11:15:10 2012 +0000 @@ -8,8 +8,6 @@ package de.intevation.artifactdatabase; -import de.intevation.artifacts.common.utils.XMLUtils; - import de.intevation.artifacts.CallMeta; import de.intevation.artifacts.Service; import de.intevation.artifacts.GlobalContext; @@ -30,14 +28,38 @@ { private static Logger logger = Logger.getLogger(DefaultService.class); + public static class Output implements Service.Output { + + protected Object data; + protected String mimeType; + + public Output() { + } + + public Output(Object data, String mimeType) { + this.data = data; + this.mimeType = mimeType; + } + + @Override + public Object getData() { + return data; + } + + @Override + public String getMIMEType() { + return mimeType; + } + } // class Output + @Override - public Document process( + public Service.Output process( Document data, GlobalContext globalContext, CallMeta callMeta ) { logger.debug("Service.process"); - return XMLUtils.newDocument(); + return new Output(new byte[0], "application/octet-stream"); } @Override diff -r 95ff5a25a339 -r 9798e4d83681 artifact-database/src/main/java/de/intevation/artifactdatabase/XMLService.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/artifact-database/src/main/java/de/intevation/artifactdatabase/XMLService.java Tue Apr 03 11:15:10 2012 +0000 @@ -0,0 +1,51 @@ +/* + * Copyright (c) 2010 by Intevation GmbH + * + * This program is free software under the LGPL (>=v2.1) + * Read the file LGPL.txt coming with the software for details + * or visit http://www.gnu.org/licenses/ if it does not exist. + */ + +package de.intevation.artifactdatabase; + +import de.intevation.artifacts.CallMeta; +import de.intevation.artifacts.Service; +import de.intevation.artifacts.GlobalContext; + +import de.intevation.artifacts.common.utils.XMLUtils; + +import org.apache.log4j.Logger; + +import org.w3c.dom.Document; + +/** + * Trivial implementation of an artifact database service. Useful to + * be subclassed. + * + * @author Sascha L. Teichmann + */ +public class XMLService +extends DefaultService +{ + private static Logger logger = Logger.getLogger(XMLService.class); + + @Override + public Service.Output process( + Document data, + GlobalContext globalContext, + CallMeta callMeta + ) { + return new Output( + processXML(data, globalContext, callMeta), + "application/xml"); + } + + public Document processXML( + Document data, + GlobalContext globalContext, + CallMeta callMeta + ) { + return XMLUtils.newDocument(); + } +} +// vim:set ts=4 sw=4 si et sta sts=4 fenc=utf8 : diff -r 95ff5a25a339 -r 9798e4d83681 artifact-database/src/main/java/de/intevation/artifactdatabase/rest/ByteArrayRepresentation.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/artifact-database/src/main/java/de/intevation/artifactdatabase/rest/ByteArrayRepresentation.java Tue Apr 03 11:15:10 2012 +0000 @@ -0,0 +1,65 @@ +package de.intevation.artifactdatabase.rest; + +import org.restlet.representation.Representation; + +import java.io.Reader; +import java.io.OutputStream; +import java.io.InputStream; +import java.io.Writer; +import java.io.IOException; +import java.io.InputStreamReader; +import java.io.ByteArrayInputStream; + +import java.nio.ByteBuffer; + +import java.nio.channels.ReadableByteChannel; +import java.nio.channels.WritableByteChannel; + +import org.restlet.data.MediaType; + +public class ByteArrayRepresentation +extends Representation +{ + protected byte [] data; + + public ByteArrayRepresentation(MediaType mediaType, byte [] data) { + super(mediaType); + this.data = data; + } + + @Override + public long getSize() { + return data.length; + } + + @Override + public ReadableByteChannel getChannel() throws IOException { + return null; + } + + @Override + public Reader getReader() throws IOException { + return new InputStreamReader(getStream()); + } + + @Override + public InputStream getStream() throws IOException { + return new ByteArrayInputStream(data); + } + + @Override + public void write(Writer writer) throws IOException { + writer.append(ByteBuffer.wrap(data).asCharBuffer()); + } + + @Override + public void write(WritableByteChannel writableChannel) throws IOException { + writableChannel.write(ByteBuffer.wrap(data)); + } + + @Override + public void write(OutputStream outputStream) throws IOException { + outputStream.write(data); + } +} +// vim:set ts=4 sw=4 si et sta sts=4 fenc=utf8 : diff -r 95ff5a25a339 -r 9798e4d83681 artifact-database/src/main/java/de/intevation/artifactdatabase/rest/ServiceResource.java --- a/artifact-database/src/main/java/de/intevation/artifactdatabase/rest/ServiceResource.java Fri Mar 30 07:21:29 2012 +0000 +++ b/artifact-database/src/main/java/de/intevation/artifactdatabase/rest/ServiceResource.java Tue Apr 03 11:15:10 2012 +0000 @@ -27,6 +27,8 @@ import org.w3c.dom.Document; +import de.intevation.artifacts.Service; + /** * Resource to process incoming XML documents with a given service. * @@ -72,8 +74,7 @@ .getAttributes().get("database"); try { - return new DomRepresentation( - MediaType.APPLICATION_XML, + return guessRepresentation( db.process(service, inputDocument, getCallMeta())); } catch (ArtifactDatabaseException adbe) { @@ -84,5 +85,21 @@ return new EmptyRepresentation(); } } + + protected static Representation guessRepresentation(Service.Output output) { + + MediaType mediaType = new MediaType(output.getMIMEType()); + Object data = output.getData(); + + if (data instanceof Document) { + return new DomRepresentation(mediaType, (Document)data); + } + + if (data instanceof byte []) { + return new ByteArrayRepresentation(mediaType, (byte [])data); + } + + return new EmptyRepresentation(); + } } // vim:set ts=4 sw=4 si et sta sts=4 fenc=utf8 : diff -r 95ff5a25a339 -r 9798e4d83681 artifacts/src/main/java/de/intevation/artifacts/ArtifactDatabase.java --- a/artifacts/src/main/java/de/intevation/artifacts/ArtifactDatabase.java Fri Mar 30 07:21:29 2012 +0000 +++ b/artifacts/src/main/java/de/intevation/artifacts/ArtifactDatabase.java Tue Apr 03 11:15:10 2012 +0000 @@ -207,7 +207,7 @@ * @throws ArtifactDatabaseException Thrown if someting went wrong during * the service processing. */ - Document process(String service, Document input, CallMeta callMeta) + Service.Output process(String service, Document input, CallMeta callMeta) throws ArtifactDatabaseException; // User API diff -r 95ff5a25a339 -r 9798e4d83681 artifacts/src/main/java/de/intevation/artifacts/Service.java --- a/artifacts/src/main/java/de/intevation/artifacts/Service.java Fri Mar 30 07:21:29 2012 +0000 +++ b/artifacts/src/main/java/de/intevation/artifacts/Service.java Tue Apr 03 11:15:10 2012 +0000 @@ -20,14 +20,20 @@ public interface Service extends Serializable { + interface Output { + Object getData(); + + String getMIMEType(); + } // interface Output + /** * Processes some input XML document * @param data The input data * @param globalContext The global context of the artifact database. * @param callMeta The call meta contex, e.g. preferred languages. - * @return The result output XML document. + * @return The result. */ - Document process(Document data, GlobalContext globalContext, CallMeta callMeta); + Output process(Document data, GlobalContext globalContext, CallMeta callMeta); /** * Setup the concrete processing service. This is done at startup time