Package org.geoserver.wps.response

Source Code of org.geoserver.wps.response.ExecuteProcessResponse

/* (c) 2014 Open Source Geospatial Foundation - all rights reserved
* (c) 2001 - 2013 OpenPlans
* This code is licensed under the GPL 2.0 license, available at the root
* application directory.
*/
package org.geoserver.wps.response;

import java.io.IOException;
import java.io.OutputStream;
import java.io.PrintWriter;

import javax.xml.transform.sax.SAXTransformerFactory;
import javax.xml.transform.sax.TransformerHandler;
import javax.xml.transform.stream.StreamResult;

import net.opengis.ows11.BoundingBoxType;
import net.opengis.wps10.ComplexDataType;
import net.opengis.wps10.ExecuteResponseType;
import net.opengis.wps10.ExecuteType;
import net.opengis.wps10.LiteralDataType;
import net.opengis.wps10.OutputDataType;

import org.geoserver.ows.Response;
import org.geoserver.ows.XmlObjectEncodingResponse;
import org.geoserver.platform.Operation;
import org.geoserver.platform.ServiceException;
import org.geoserver.wps.BinaryEncoderDelegate;
import org.geoserver.wps.CDataEncoderDelegate;
import org.geoserver.wps.Execute;
import org.geoserver.wps.RawDataEncoderDelegate;
import org.geoserver.wps.WPSException;
import org.geoserver.wps.XMLEncoderDelegate;
import org.geotools.ows.v1_1.OWS;
import org.geotools.ows.v1_1.OWSConfiguration;
import org.geotools.xml.Encoder;

/**
* Encodes the Execute response either in the normal XML format or in the raw format
* @author Andrea Aime
*
*/
public class ExecuteProcessResponse extends Response {

    XmlObjectEncodingResponse standardResponse;

    public ExecuteProcessResponse(Class binding, String elementName, Class xmlConfiguration) {
        super(ExecuteResponseType.class);
        this.standardResponse = new XmlObjectEncodingResponse(binding, elementName, xmlConfiguration);
    }
   
    @Override
    public String getMimeType(Object value, Operation operation)
            throws ServiceException {
        if (isStandardDocumentResponse(operation)) {
            // normal execute response encoding
            return standardResponse.getMimeType(value, operation);
        } else {
            // raw response, let's see what the output is
            ExecuteResponseType response = (ExecuteResponseType) value;
            if(response.getProcessOutputs() == null) {
                // just a status report or a failure report
                return "text/xml";
            }
            OutputDataType result = (OutputDataType) response.getProcessOutputs().getOutput().get(0);
            LiteralDataType literal = result.getData().getLiteralData();
            ComplexDataType complex = result.getData().getComplexData();
            if(literal != null) {
                // literals are encoded as plain strings
                return "text/plain";
            } else if(complex != null) {
                // Execute should have properly setup the mime type
                return complex.getMimeType();
            } else {
                // bbox
                return "text/xml";
            }
        }

    }

    private boolean isStandardDocumentResponse(Operation operation) {
        if(operation.getParameters()[0] instanceof ExecuteType) {
            ExecuteType execute = (ExecuteType) operation.getParameters()[0];
            return execute.getResponseForm() != null && execute.getResponseForm().getRawDataOutput() == null;
        }
        return true;
    }

    @Override
    public String getPreferredDisposition(Object value, Operation operation) {
        String mimeType = getMimeType(value, operation);
        String disposition = DISPOSITION_INLINE;
        if (mimeType != null) {
            // if there is a BinaryEncoder we could expose a method that allows
            // expressing preferred type as opposed to this ugliness
            if (mimeType.indexOf("image") == 0) {
                // tiff for download
                if (mimeType.indexOf("tiff") > 0) {
                    disposition = DISPOSITION_ATTACH;
                }
            } else if (mimeType.equals("application/zip")) {
                disposition = DISPOSITION_ATTACH;
            } else if (mimeType.equals("application/arcgrid")) {
                disposition = DISPOSITION_ATTACH;
            }
        }
        return disposition;
    }

    @Override
    public String getAttachmentFileName(Object value, Operation operation) {
        if(isStandardDocumentResponse(operation)) {
            return "execute.xml";
        } else {
            ExecuteType execute = (ExecuteType) operation.getParameters()[0];
            ExecuteResponseType response = (ExecuteResponseType) value;
            if(response.getProcessOutputs() == null) {
                // just a status report or a failure report
                return "execute.xml";
            }
            OutputDataType result = (OutputDataType) response.getProcessOutputs().getOutput().get(0);
            String fname = result.getIdentifier().getValue();
            LiteralDataType literal = result.getData().getLiteralData();
            ComplexDataType complex = result.getData().getComplexData();
            String fext;
            // this is not the most robust way to get mime type...
            if (literal != null) {
                fext = "txt";
            } else if(complex != null) {
                String mimeType = result.getData().getComplexData().getMimeType();
                if (mimeType == null) {
                    fext = "txt";
                } else {
                    fext = mimeType.split("/")[1].toLowerCase();
                }
            } else {
                fext = "xml";
            }
            return fname + "." + fext;
        }
    }

    @Override
    public void write(Object value, OutputStream output, Operation operation)
            throws IOException, ServiceException {
        ExecuteResponseType response = (ExecuteResponseType) value;
       
        // From the spec:
        // In the most primitive case, when a response form of ―RawDataOutput‖ is requested,
        // process execution is successful, and only one complex output is produced, then the
        // Execute operation response will consist simply of that one complex output in its raw form
        // returned directly to the client.
        // In all other cases, the response to a valid Execute operation request is an
        // ExecuteResponse XML document
        if (isStandardDocumentResponse(operation) ||
                response.getStatus().getProcessSucceeded() == null) {
            // normal execute response encoding
            standardResponse.write(value, output, operation);
        } else {
            // raw response, let's see what the output is
            OutputDataType result = (OutputDataType) response
                    .getProcessOutputs().getOutput().get(0);
            LiteralDataType literal = result.getData().getLiteralData();
            BoundingBoxType bbox = result.getData().getBoundingBoxData();
            if (literal != null) {
                writeLiteral(output, literal);
            } else if(bbox != null) {
                writeBBox(output, bbox);
            } else {
                writeComplex(output, result);
            }
        }
    }

    private void writeBBox(OutputStream os, BoundingBoxType bbox) throws IOException {
        Encoder encoder = new Encoder(new OWSConfiguration());
        encoder.encode(bbox, OWS.BoundingBox, os);
    }

    /**
     * Write out complex data assuming {@link Execute} has set up the proper
     * encoder as the output
     *
     * @param output
     * @param result
     * @throws IOException
     */
    void writeComplex(OutputStream output, OutputDataType result)
            throws IOException {
        Object rawResult = result.getData().getComplexData().getData().get(0);
        if (rawResult instanceof RawDataEncoderDelegate) {
            RawDataEncoderDelegate delegate = (RawDataEncoderDelegate) rawResult;
            delegate.encode(output);
        } else if (rawResult instanceof XMLEncoderDelegate) {
            XMLEncoderDelegate delegate = (XMLEncoderDelegate) rawResult;

            try {
                TransformerHandler xmls =
                    ((SAXTransformerFactory)SAXTransformerFactory.newInstance()).newTransformerHandler();
                xmls.setResult(new StreamResult(output));
                delegate.encode(xmls);
            } catch (IOException e) {
                throw e;
            } catch (Exception e) {
                throw new WPSException("An error occurred while encoding "
                        + "the results of the process", e);
            }
        } else if(rawResult instanceof CDataEncoderDelegate) {
          try {
                ((CDataEncoderDelegate) rawResult).encode(output);
          } catch(Exception e) {
            throw new WPSException("An error occurred while encoding "
                        + "the results of the process", e);
          }
        } else if(rawResult instanceof BinaryEncoderDelegate) {
          try {
            ((BinaryEncoderDelegate) rawResult).encode(output);
          } catch(Exception e) {
            throw new WPSException("An error occurred while encoding "
                        + "the results of the process", e);
          }
        } else {
            throw new WPSException("Cannot encode an object of class "
                    + rawResult.getClass() + " in raw form");
        }
    }

    /**
     * Write out literal results by converting them to strings
     * @param output
     * @param literal
     */
    void writeLiteral(OutputStream output, LiteralDataType literal) {
        PrintWriter writer = new PrintWriter(output);
        writer.write(literal.getValue());
        writer.flush();
    }

   

}
TOP

Related Classes of org.geoserver.wps.response.ExecuteProcessResponse

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.