| /** |
| * Licensed to the Apache Software Foundation (ASF) under one |
| * or more contributor license agreements. See the NOTICE file |
| * distributed with this work for additional information |
| * regarding copyright ownership. The ASF licenses this file |
| * to you under the Apache License, Version 2.0 (the |
| * "License"); you may not use this file except in compliance |
| * with the License. You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, |
| * software distributed under the License is distributed on an |
| * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY |
| * KIND, either express or implied. See the License for the |
| * specific language governing permissions and limitations |
| * under the License. |
| */ |
| package org.apache.cxf.transport.servlet.servicelist; |
| |
| import java.io.IOException; |
| import java.io.PrintWriter; |
| import java.util.Map; |
| |
| import org.apache.cxf.Bus; |
| import org.apache.cxf.common.util.PropertyUtils; |
| import org.apache.cxf.helpers.CastUtils; |
| import org.apache.cxf.service.model.OperationInfo; |
| import org.apache.cxf.transport.AbstractDestination; |
| |
| public class FormattedServiceListWriter implements ServiceListWriter { |
| private String styleSheetPath; |
| private String title; |
| private Map<String, String> atomMap; |
| private boolean showForeignContexts; |
| private Bus bus; |
| |
| public FormattedServiceListWriter(String styleSheetPath, |
| String title, |
| boolean showForeignContexts, |
| Bus bus) { |
| this.styleSheetPath = styleSheetPath; |
| this.title = title; |
| this.showForeignContexts = showForeignContexts; |
| this.bus = bus; |
| if (bus != null) { |
| this.atomMap = CastUtils.cast((Map<?, ?>)bus.getProperty("org.apache.cxf.extensions.logging.atom.pull")); |
| } |
| } |
| |
| public String getContentType() { |
| return "text/html; charset=UTF-8"; |
| } |
| |
| public void writeServiceList(PrintWriter writer, |
| String basePath, |
| AbstractDestination[] soapDestinations, |
| AbstractDestination[] restDestinations) throws IOException { |
| writer.write("<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" " |
| + "\"http://www.w3.org/TR/html4/loose.dtd\">"); |
| writer.write("<HTML><HEAD>"); |
| writer.write("<LINK type=\"text/css\" rel=\"stylesheet\" href=\"" + styleSheetPath + "\">"); |
| writer.write("<meta http-equiv=\"content-type\" content=\"text/html; charset=UTF-8\">"); |
| if (title != null) { |
| writer.write("<title>" + title + "</title>"); |
| } else { |
| writer.write("<title>CXF - Service list</title>"); |
| } |
| writer.write("</head><body>"); |
| |
| if (soapDestinations.length > 0 || restDestinations.length > 0) { |
| if (soapDestinations.length > 0) { |
| writeSOAPEndpoints(writer, basePath, soapDestinations); |
| } |
| if (restDestinations.length > 0) { |
| writeRESTfulEndpoints(writer, basePath, restDestinations); |
| } |
| } else { |
| writer.write("<span class=\"heading\">No services have been found.</span>"); |
| } |
| |
| writer.write("</body></html>"); |
| } |
| |
| private void writeSOAPEndpoints(PrintWriter writer, |
| String basePath, |
| AbstractDestination[] destinations) |
| throws IOException { |
| writer.write("<span class=\"heading\">Available SOAP services:</span><br/>"); |
| writer.write("<table " + (styleSheetPath.endsWith("stylesheet=1") |
| ? "cellpadding=\"1\" cellspacing=\"1\" border=\"1\" width=\"100%\"" : "") + ">"); |
| for (AbstractDestination sd : destinations) { |
| writerSoapEndpoint(writer, basePath, sd); |
| } |
| writer.write("</table><br/><br/>"); |
| } |
| |
| private void writerSoapEndpoint(PrintWriter writer, |
| String basePath, |
| AbstractDestination sd) { |
| String absoluteURL = getAbsoluteAddress(basePath, sd); |
| if (absoluteURL == null) { |
| return; |
| } |
| |
| writer.write("<tr><td>"); |
| writer.write("<span class=\"porttypename\">" |
| + sd.getEndpointInfo().getInterface().getName().getLocalPart() + "</span>"); |
| writer.write("<ul>"); |
| for (OperationInfo oi : sd.getEndpointInfo().getInterface().getOperations()) { |
| if (!Boolean.TRUE.equals(oi.getProperty("operation.is.synthetic"))) { |
| writer.write("<li>" + oi.getName().getLocalPart() + "</li>"); |
| } |
| } |
| writer.write("</ul>"); |
| writer.write("</td><td>"); |
| |
| |
| writer.write("<span class=\"field\">Endpoint address:</span> " + "<span class=\"value\">" |
| + absoluteURL + "</span>"); |
| writer.write("<br/><span class=\"field\">WSDL :</span> " + "<a href=\"" + absoluteURL |
| + "?wsdl\">" + sd.getEndpointInfo().getService().getName() + "</a>"); |
| writer.write("<br/><span class=\"field\">Target namespace:</span> " |
| + "<span class=\"value\">" |
| + sd.getEndpointInfo().getService().getTargetNamespace() + "</span>"); |
| addAtomLinkIfNeeded(absoluteURL, atomMap, writer); |
| writer.write("</td></tr>"); |
| } |
| |
| private String getAbsoluteAddress(String basePath, AbstractDestination d) { |
| String endpointAddress = (String)d.getEndpointInfo().getProperty("publishedEndpointUrl"); |
| if (endpointAddress != null) { |
| return endpointAddress; |
| } |
| endpointAddress = d.getEndpointInfo().getAddress(); |
| if (endpointAddress.startsWith("http://") || endpointAddress.startsWith("https://")) { |
| if (endpointAddress.startsWith(basePath) || showForeignContexts) { |
| return endpointAddress; |
| } else { |
| return null; |
| } |
| } else { |
| return basePath + endpointAddress; |
| } |
| } |
| |
| private void writeRESTfulEndpoints(PrintWriter writer, |
| String basePath, |
| AbstractDestination[] restfulDests) |
| throws IOException { |
| writer.write("<span class=\"heading\">Available RESTful services:</span><br/>"); |
| writer.write("<table " + (styleSheetPath.endsWith("stylesheet=1") |
| ? "cellpadding=\"1\" cellspacing=\"1\" border=\"1\" width=\"100%\"" : "") + ">"); |
| for (AbstractDestination sd : restfulDests) { |
| writeRESTfulEndpoint(writer, basePath, sd); |
| } |
| writer.write("</table>"); |
| } |
| |
| private void writeRESTfulEndpoint(PrintWriter writer, |
| String basePath, |
| AbstractDestination sd) { |
| String absoluteURL = getAbsoluteAddress(basePath, sd); |
| if (absoluteURL == null) { |
| return; |
| } |
| |
| writer.write("<tr><td>"); |
| writer.write("<span class=\"field\">Endpoint address:</span> " + "<span class=\"value\">" |
| + absoluteURL + "</span>"); |
| if (bus != null && PropertyUtils.isTrue(bus.getProperty("wadl.service.description.available"))) { |
| writer.write("<br/><span class=\"field\">WADL :</span> " + "<a href=\"" + absoluteURL |
| + "?_wadl\">" + absoluteURL + "?_wadl" + "</a>"); |
| } |
| if (bus != null && PropertyUtils.isTrue(bus.getProperty("swagger.service.description.available"))) { |
| String swaggerPath = "swagger.json"; |
| if (PropertyUtils.isTrue(bus.getProperty("swagger.service.ui.available"))) { |
| swaggerPath = "api-docs?url=/" + swaggerPath; |
| } |
| if (!absoluteURL.endsWith("/")) { |
| swaggerPath = "/" + swaggerPath; |
| } |
| writer.write("<br/><span class=\"field\">Swagger :</span> " + "<a href=\"" + absoluteURL |
| + swaggerPath + "\">" + absoluteURL + swaggerPath + "</a>"); |
| } |
| addAtomLinkIfNeeded(absoluteURL, atomMap, writer); |
| writer.write("</td></tr>"); |
| } |
| |
| private static void addAtomLinkIfNeeded(String address, Map<String, String> extMap, PrintWriter pw) { |
| String atomAddress = getExtensionEndpointAddress(address, extMap); |
| if (atomAddress != null) { |
| pw.write("<br/><span class=\"field\">Atom Log Feed :</span> " + "<a href=\"" + atomAddress |
| + "\">" + atomAddress + "</a>"); |
| } |
| } |
| |
| private static String getExtensionEndpointAddress(String endpointAddress, Map<String, String> extMap) { |
| if (extMap != null) { |
| for (Map.Entry<String, String> entry : extMap.entrySet()) { |
| if (endpointAddress.endsWith(entry.getKey())) { |
| endpointAddress = endpointAddress.substring(0, endpointAddress.length() |
| - entry.getKey().length()); |
| endpointAddress += entry.getValue(); |
| return endpointAddress; |
| } |
| } |
| } |
| return null; |
| } |
| |
| } |