Package org.geoserver.wms

Source Code of org.geoserver.wms.WmsExceptionHandler

/* Copyright (c) 2001 - 2007 TOPP - www.openplans.org. All rights reserved.
* This code is licensed under the GPL 2.0 license, availible at the root
* application directory.
*/
package org.geoserver.wms;

import java.awt.Color;
import java.awt.FontMetrics;
import java.awt.Graphics2D;
import java.awt.Point;
import java.awt.font.FontRenderContext;
import java.awt.font.LineBreakMeasurer;
import java.awt.font.TextLayout;
import java.awt.image.BufferedImage;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.PrintStream;
import java.text.AttributedString;
import java.util.Arrays;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
import java.util.logging.Level;

import javax.imageio.ImageIO;
import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletResponse;

import org.geoserver.config.GeoServer;
import org.geoserver.ows.LegacyServiceExceptionHandler;
import org.geoserver.ows.Request;
import org.geoserver.ows.util.OwsUtils;
import org.geoserver.platform.Service;
import org.geoserver.platform.ServiceException;

public class WmsExceptionHandler extends LegacyServiceExceptionHandler {

    static final Set<String> FORMATS = new HashSet<String>(Arrays.asList("image/png", "image/png8",
            "image/gif", "image/jpeg"));

    static final Map<String, String> IMAGEIO_FORMATS = new HashMap<String, String>() {
        {
            put("image/png", "png");
            put("image/png8", "png");
            put("image/gif", "gif");
            put("image/jpeg", "jpeg");
        }
    };

    public WmsExceptionHandler(Service service,  GeoServer geoServer) {
        super(service, geoServer);
    }

    @Override
    public void handleServiceException(ServiceException exception, Request request) {
        // first of all check what kind of exception handling we must perform
        String exceptions;
        int width;
        int height;
        String format;
        try {
            exceptions = (String) request.getKvp().get("EXCEPTIONS");
            width = (Integer) request.getKvp().get("WIDTH");
            height = (Integer) request.getKvp().get("HEIGHT");
            format = (String) request.getKvp().get("FORMAT");
        } catch (Exception e) {
            // width and height might be missing
            super.handleServiceException(exception, request);
            return;
        }
        if (exceptions == null || !"application/vnd.ogc.se_inimage".equals(exceptions)
                || width <= 0 || height <= 0 || !FORMATS.contains(format)) {
            super.handleServiceException(exception, request);
            return;
        }

        // ok, it's image, then we have to build a text representing the
        // exception and lay it out in the image
        BufferedImage img = new BufferedImage(width, height, BufferedImage.TYPE_4BYTE_ABGR);
        Graphics2D g = (Graphics2D) img.getGraphics();
        g.setColor(Color.WHITE);
        g.fillRect(0, 0, img.getWidth(), img.getHeight());
        g.setColor(Color.BLACK);

        // draw the exception text (give it a good offset so that it can be read
        // properly in the OL preview as well)
        paintLines(g, buildExceptionText(exception), width - 2, 35, 5);

        // encode
        g.dispose();
        try {
            final HttpServletResponse response = request.getHttpResponse();
            response.setContentType(format);
            final ServletOutputStream os = response.getOutputStream();
            ImageIO.write(img, IMAGEIO_FORMATS.get(format), os);
            os.flush();
        } catch (IOException e) {
            LOGGER.log(Level.INFO, "Problem writing exception information back to calling client:",
                    e);
        }
    }

    String buildExceptionText(ServiceException exception) {
        StringBuffer sb = new StringBuffer();
        // exception code and locator
        if ((exception.getCode() != null) && !exception.getCode().equals("")) {
            sb.append("code=\"" + exception.getCode() + "\"");
        }

        // exception locator
        if ((exception.getLocator() != null) && !exception.getLocator().equals("")) {
            sb.append(" locator=\"" + exception.getLocator() + "\"");
        }

        // message
        if ((exception.getMessage() != null)) {
            OwsUtils.dumpExceptionMessages(exception, sb, false);

            if (geoServer.getGlobal().isVerboseExceptions()) {
                ByteArrayOutputStream stackTrace = new ByteArrayOutputStream();
                exception.printStackTrace(new PrintStream(stackTrace));

                sb.append("\nDetails:\n");
                sb.append(new String(stackTrace.toByteArray()));
            }
        }

        return sb.toString();
    }

    /**
     * Paint the provided text onto the graphics wrapping words at the specified
     * lineWidth
     *
     * @param lineWidth
     * @param g
     * @param text
     */
    void paintLines(Graphics2D g, String text, int lineWidth, int startX, int startY) {
        // split the text into lines, LineBreakMeasurer only lays out the single
        // line
        String[] lines = text.split("\\n");

        // setup the cursor
        Point cursor = new Point(startX, startY);
       
        // grab the line height to skip empty lines
        final FontMetrics metrics = g.getFontMetrics();
        int lineHeight = metrics.getAscent() + metrics.getDescent() + metrics.getLeading();
       
        FontRenderContext frc = g.getFontRenderContext();

        // scan over the
        for (int i = 0; i < lines.length; i++) {
            final String line = lines[i];

            if ("".equals(line)) {
                cursor.y += lineHeight;
            } else {
                AttributedString styledText = new AttributedString(line);
                LineBreakMeasurer measurer = new LineBreakMeasurer(styledText.getIterator(), frc);

                while (measurer.getPosition() < line.length()) {

                    TextLayout layout = measurer.nextLayout(lineWidth);

                    cursor.y += (layout.getAscent());
                    float dx = layout.isLeftToRight() ? 0 : (lineWidth - layout.getAdvance());

                    layout.draw(g, cursor.x + dx, cursor.y);
                    cursor.y += layout.getDescent() + layout.getLeading();
                }
            }
        }

    }

}
TOP

Related Classes of org.geoserver.wms.WmsExceptionHandler

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.