You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cxf.apache.org by se...@apache.org on 2009/06/30 18:14:56 UTC

svn commit: r789817 - in /cxf/branches/2.2.x-fixes: ./ common/common/src/main/java/org/apache/cxf/common/util/ common/common/src/test/java/org/apache/cxf/common/util/ rt/frontend/jaxrs/src/main/java/org/apache/cxf/jaxrs/model/wadl/ rt/frontend/jaxrs/sr...

Author: sergeyb
Date: Tue Jun 30 16:14:55 2009
New Revision: 789817

URL: http://svn.apache.org/viewvc?rev=789817&view=rev
Log:
Merged revisions 789811 via svnmerge from 
https://svn.apache.org/repos/asf/cxf/trunk

........
  r789811 | sergeyb | 2009-06-30 17:02:26 +0100 (Tue, 30 Jun 2009) | 1 line
  
  [CXF-1695] : initial support for listing jaxrs services, fixing ignoreServiceList issue
........

Added:
    cxf/branches/2.2.x-fixes/common/common/src/main/java/org/apache/cxf/common/util/XmlSchemaPrimitiveUtils.java
      - copied unchanged from r789811, cxf/trunk/common/common/src/main/java/org/apache/cxf/common/util/XmlSchemaPrimitiveUtils.java
    cxf/branches/2.2.x-fixes/common/common/src/test/java/org/apache/cxf/common/util/XmlSchemaPrimitiveUtilsTest.java
      - copied unchanged from r789811, cxf/trunk/common/common/src/test/java/org/apache/cxf/common/util/XmlSchemaPrimitiveUtilsTest.java
    cxf/branches/2.2.x-fixes/rt/transports/http/src/test/java/org/apache/cxf/transport/servlet/ServletControllerTest.java
      - copied unchanged from r789811, cxf/trunk/rt/transports/http/src/test/java/org/apache/cxf/transport/servlet/ServletControllerTest.java
Modified:
    cxf/branches/2.2.x-fixes/   (props changed)
    cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/main/java/org/apache/cxf/jaxrs/model/wadl/WadlGenerator.java
    cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/Book.java
    cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/BookStore.java
    cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/Orders.java
    cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/WadlGeneratorTest.java
    cxf/branches/2.2.x-fixes/rt/transports/http/src/main/java/org/apache/cxf/transport/servlet/ServletController.java
    cxf/branches/2.2.x-fixes/systests/src/test/java/org/apache/cxf/systest/jaxrs/BookSubresource.java
    cxf/branches/2.2.x-fixes/systests/src/test/java/org/apache/cxf/systest/jaxrs/BookSubresourceImpl.java

Propchange: cxf/branches/2.2.x-fixes/
------------------------------------------------------------------------------
--- svn:mergeinfo (original)
+++ svn:mergeinfo Tue Jun 30 16:14:55 2009
@@ -1 +1 @@
-/cxf/trunk:782728-782730,783097,783294,783396,784059,784181-784184,784893,784895,785279-785282,785468,785621,785624,785651,785734,785866,786142,786271-786272,786395,786512,786514,786582-786583,786638,786647,786850,787200,787269,787277-787279,787290-787291,787305,787323,787366,787849,788030,788060,788187,788444,788451,788703,788752,788774,788819-788820,789013,789371,789387,789420,789527-789530,789704-789705
+/cxf/trunk:782728-782730,783097,783294,783396,784059,784181-784184,784893,784895,785279-785282,785468,785621,785624,785651,785734,785866,786142,786271-786272,786395,786512,786514,786582-786583,786638,786647,786850,787200,787269,787277-787279,787290-787291,787305,787323,787366,787849,788030,788060,788187,788444,788451,788703,788752,788774,788819-788820,789013,789371,789387,789420,789527-789530,789704-789705,789811

Propchange: cxf/branches/2.2.x-fixes/
------------------------------------------------------------------------------
Binary property 'svnmerge-integrated' - no diff available.

Modified: cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/main/java/org/apache/cxf/jaxrs/model/wadl/WadlGenerator.java
URL: http://svn.apache.org/viewvc/cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/main/java/org/apache/cxf/jaxrs/model/wadl/WadlGenerator.java?rev=789817&r1=789816&r2=789817&view=diff
==============================================================================
--- cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/main/java/org/apache/cxf/jaxrs/model/wadl/WadlGenerator.java (original)
+++ cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/main/java/org/apache/cxf/jaxrs/model/wadl/WadlGenerator.java Tue Jun 30 16:14:55 2009
@@ -21,6 +21,7 @@
 import java.io.IOException;
 import java.io.StringWriter;
 import java.util.Collections;
+import java.util.Comparator;
 import java.util.LinkedList;
 import java.util.List;
 import java.util.Set;
@@ -37,15 +38,17 @@
 import javax.xml.transform.sax.SAXResult;
 
 import org.apache.cxf.common.logging.LogUtils;
+import org.apache.cxf.common.util.XmlSchemaPrimitiveUtils;
+import org.apache.cxf.common.xmlschema.XmlSchemaConstants;
 import org.apache.cxf.jaxrs.JAXRSServiceImpl;
 import org.apache.cxf.jaxrs.ext.RequestHandler;
 import org.apache.cxf.jaxrs.impl.HttpHeadersImpl;
 import org.apache.cxf.jaxrs.impl.UriInfoImpl;
 import org.apache.cxf.jaxrs.model.ClassResourceInfo;
 import org.apache.cxf.jaxrs.model.OperationResourceInfo;
-import org.apache.cxf.jaxrs.model.OperationResourceInfoComparator;
 import org.apache.cxf.jaxrs.model.Parameter;
 import org.apache.cxf.jaxrs.model.ParameterType;
+import org.apache.cxf.jaxrs.model.URITemplate;
 import org.apache.cxf.jaxrs.provider.JAXBElementProvider;
 import org.apache.cxf.jaxrs.utils.InjectionUtils;
 import org.apache.cxf.message.Message;
@@ -53,11 +56,6 @@
 import org.apache.cxf.staxutils.StaxUtils;
 import org.apache.cxf.staxutils.StreamWriterContentHandler;
 
-// TODO :
-// 1. extract JavaDocs and put them into XML comments
-// 2. if _type = html -> convert the XML buil here using MH's stylesheet
-// 3. generate grammars 
-
 public class WadlGenerator implements RequestHandler {
 
     public static final String WADL_QUERY = "_wadl"; 
@@ -78,7 +76,8 @@
         }
         
         StringBuilder sbMain = new StringBuilder();
-        sbMain.append("<application xmlns=\"").append(WADL_NS).append("\">");
+        sbMain.append("<application xmlns=\"").append(WADL_NS)
+              .append("\" xmlns:xs=\"").append(XmlSchemaConstants.XSD_NAMESPACE_URI).append("\">");
         StringBuilder sbGrammars = new StringBuilder();
         sbGrammars.append("<grammars>");
         
@@ -87,8 +86,7 @@
         
         List<ClassResourceInfo> cris = getResourcesList(m, resource);
         for (ClassResourceInfo cri : cris) {
-            handleResource(sbResources, cri, cri.getURITemplate().getValue(),
-                           cri.getURITemplate().getVariables());
+            handleResource(sbResources, cri, cri.getURITemplate().getValue());
         }
         sbResources.append("</resources>");
         
@@ -105,10 +103,8 @@
         return Response.ok().type(type).entity(sbMain.toString()).build();
     }
 
-    private void handleResource(StringBuilder sb, ClassResourceInfo cri, String path,
-                                List<String> templateVars) {
+    private void handleResource(StringBuilder sb, ClassResourceInfo cri, String path) {
         sb.append("<resource path=\"").append(path).append("\">");
-        handleTemplateParams(sb, templateVars);
         
         List<OperationResourceInfo> sortedOps = sortOperationsByPath(
             cri.getMethodDispatcher().getOperationResourceInfos());
@@ -119,8 +115,7 @@
                 Class<?> cls = ori.getMethodToInvoke().getReturnType();
                 ClassResourceInfo subcri = cri.findResource(cls, cls);
                 if (subcri != null) {
-                    handleResource(sb, subcri, ori.getURITemplate().getValue(), 
-                                   ori.getURITemplate().getVariables());
+                    handleResource(sb, subcri, ori.getURITemplate().getValue());
                 } else {
                     handleDynamicSubresource(sb, ori);
                 }
@@ -134,12 +129,12 @@
     private void handleOperation(StringBuilder sb, OperationResourceInfo ori) {
         
         String path = ori.getURITemplate().getValue();
-        boolean isSlash =  "/".equals(path);
-        if (!isSlash) {
+        boolean useResource = useResource(ori);
+        if (useResource) {
             sb.append("<resource path=\"").append(path).append("\">");
         }
-        handleTemplateParams(sb, ori.getURITemplate().getVariables());
-        handleMatrixParams(sb, ori);
+        handleParams(sb, ori, ParameterType.PATH);
+        handleParams(sb, ori, ParameterType.MATRIX);
         
         sb.append("<method name=\"").append(ori.getHttpMethod()).append("\">");
         if (ori.getMethodToInvoke().getParameterTypes().length != 0) {
@@ -161,11 +156,24 @@
         
         sb.append("</method>");
         
-        if (!isSlash) {
+        if (useResource) {
             sb.append("</resource>");
         }
     }
     
+    private boolean useResource(OperationResourceInfo ori) {
+        String path = ori.getURITemplate().getValue();
+        if ("/".equals(path)) {
+            for (Parameter pm : ori.getParameters()) {
+                if (pm.getType() == ParameterType.PATH || pm.getType() == ParameterType.MATRIX) {
+                    return true;
+                }
+            }
+            return false;
+        }
+        return true;
+    }
+    
     private void handleDynamicSubresource(StringBuilder sb, OperationResourceInfo ori) {
         
         sb.append("<!-- Dynamic subresource -->");
@@ -182,107 +190,112 @@
     
     
     private void handleParameter(StringBuilder sb, OperationResourceInfo ori, Parameter pm) {
+        Class<?> cls = ori.getMethodToInvoke().getParameterTypes()[pm.getIndex()];
         if (pm.getType() == ParameterType.REQUEST_BODY) {
-            handleRepresentation(sb, ori, ori.getMethodToInvoke().getParameterTypes()[pm.getIndex()],
-                                 true);
+            handleRepresentation(sb, ori, cls, true);
             return;
         }
         if (pm.getType() == ParameterType.PATH || pm.getType() == ParameterType.MATRIX) {
             return;
         }
         if (pm.getType() == ParameterType.HEADER || pm.getType() == ParameterType.QUERY) {
-            writeParam(sb, pm.getName(), pm.getType().toString().toLowerCase(), pm.getDefaultValue());
+            writeParam(sb, pm, ori);
         }
         
     }
     
-    private void handleMatrixParams(StringBuilder sb, OperationResourceInfo ori) {
+    private void handleParams(StringBuilder sb, OperationResourceInfo ori, ParameterType type) {
         for (Parameter pm : ori.getParameters()) {
-            if (pm.getType() == ParameterType.MATRIX) {
-                writeParam(sb, pm.getName(), "matrix", pm.getDefaultValue());
+            if (pm.getType() == type) {
+                writeParam(sb, pm, ori);
             }
         }
     }
     
-    private void writeParam(StringBuilder sb, String name, String style, String dValue) {
-        sb.append("<param name=\"").append(name).append("\" ");
+    private void writeParam(StringBuilder sb, Parameter pm, OperationResourceInfo ori) {
+        sb.append("<param name=\"").append(pm.getName()).append("\" ");
+        String style = ParameterType.PATH == pm.getType() ? "template" 
+                                                          : pm.getType().toString().toLowerCase();
         sb.append("style=\"").append(style).append("\"");
-        if (dValue != null) {
-            sb.append(" default=\"").append(dValue).append("\"");
+        if (pm.getDefaultValue() != null) {
+            sb.append(" default=\"").append(pm.getDefaultValue()).append("\"");
         }
-        sb.append("/>");
-    }
-    
-    private void handleTemplateParams(StringBuilder sb, List<String> vars) {
-        for (String var : vars) {
-            writeParam(sb, var, "template", null);
+        Class<?> type = ori.getMethodToInvoke().getParameterTypes()[pm.getIndex()];
+        String value = XmlSchemaPrimitiveUtils.getSchemaRepresentation(type);
+        if (value != null) {
+            sb.append(" type=\"").append(value).append("\"");
         }
+        sb.append("/>");
     }
     
     private void handleRepresentation(StringBuilder sb, OperationResourceInfo ori, 
                                       Class<?> type, boolean inbound) {
-        if (InjectionUtils.isPrimitive(type)) {
-            sb.append("<!-- Primitive type : " + type.getSimpleName() + " -->");
-        }
-        sb.append("<representation");
-        
         List<MediaType> types = inbound ? ori.getConsumeTypes() : ori.getProduceTypes();
-        boolean wildcardOnly = true; 
-        for (MediaType mt : types) {
-            if (!mt.isWildcardType()) {
-                wildcardOnly = false;
-                break;
-            }
+        if (types.size() == 0) {
+            types = Collections.singletonList(MediaType.APPLICATION_ATOM_XML_TYPE);
         }
-        if (!wildcardOnly) {
-            sb.append(" mediaType=\"");
-            for (int i = 0; i < types.size(); i++) {
-                sb.append(types.get(i).toString());
-                if (i + 1 < types.size()) {
-                    sb.append(',');
-                }
+        for (MediaType mt : types) {
+            if (InjectionUtils.isPrimitive(type)) {
+                String rep = XmlSchemaPrimitiveUtils.getSchemaRepresentation(type);
+                String value = rep == null ? type.getSimpleName() : rep;
+                sb.append("<!-- Primitive type : " + value + " -->");
             }
-            if (types.size() > 0) {
-                sb.append("\"");
+            sb.append("<representation");
+            if (!mt.isWildcardType()) {
+                sb.append(" mediaType=\"").append(mt.toString()).append("\"");
             }
-        }
-        sb.append(">");
-        
-        if (!type.isPrimitive()) {
-            // try to use JAXB
-            // TODO : reuse JaxbDatabinding code
-            JAXBElementProvider jaxb = new JAXBElementProvider();
-            try {
-                JAXBContext context = jaxb.getPackageContext(type);
-                if (context == null) {
-                    context = jaxb.getClassContext(type);
+            sb.append(">");
+            if (!InjectionUtils.isPrimitive(type) && mt.getSubtype().contains("xml")) {
+                // try to use JAXB
+                // TODO : reuse JaxbDatabinding code
+                JAXBElementProvider jaxb = new JAXBElementProvider();
+                try {
+                    JAXBContext context = jaxb.getPackageContext(type);
+                    if (context == null) {
+                        context = jaxb.getClassContext(type);
+                    }
+                    if (context != null) {
+                        StringWriter writer = new StringWriter();
+                        XMLStreamWriter streamWriter = StaxUtils.createXMLStreamWriter(writer);
+                        final StreamWriterContentHandler handler = 
+                            new StreamWriterContentHandler(streamWriter);
+                        context.generateSchema(new SchemaOutputResolver() {
+                            @Override
+                            public Result createOutput(String ns, String file) throws IOException {
+                                SAXResult result = new SAXResult(handler);
+                                result.setSystemId(file);
+                                return result;
+                            }
+                        });
+                        streamWriter.flush();
+                        sb.append(writer.toString());
+                    }
+                } catch (Exception ex) {
+                    LOG.fine("No schema can be generated from " + type.getName());
                 }
-                if (context != null) {
-                    StringWriter writer = new StringWriter();
-                    XMLStreamWriter streamWriter = StaxUtils.createXMLStreamWriter(writer);
-                    final StreamWriterContentHandler handler = new StreamWriterContentHandler(streamWriter);
-                    context.generateSchema(new SchemaOutputResolver() {
-                        @Override
-                        public Result createOutput(String ns, String file) throws IOException {
-                            SAXResult result = new SAXResult(handler);
-                            result.setSystemId(file);
-                            return result;
-                        }
-                    });
-                    streamWriter.flush();
-                    sb.append(writer.toString());
-                }
-            } catch (Exception ex) {
-                LOG.fine("No schema can be generated from " + type.getName());
             }
+            sb.append("</representation>");
         }
-        
-        sb.append("</representation>");
     }
     
     private List<OperationResourceInfo> sortOperationsByPath(Set<OperationResourceInfo> ops) {
         List<OperationResourceInfo> opsWithSamePath = new LinkedList<OperationResourceInfo>(ops);
-        Collections.sort(opsWithSamePath, new OperationResourceInfoComparator());        
+        Collections.sort(opsWithSamePath, new Comparator<OperationResourceInfo>() {
+
+            public int compare(OperationResourceInfo op1, OperationResourceInfo op2) {
+                boolean sub1 = op1.getHttpMethod() == null;
+                boolean sub2 = op2.getHttpMethod() == null;
+                if (sub1 && !sub2) {
+                    return 1;
+                } else if (!sub1 && sub2) {
+                    return -1;
+                }
+                URITemplate ut1 = op1.getURITemplate();
+                URITemplate ut2 = op2.getURITemplate();
+                return ut1.getValue().compareTo(ut2.getValue());
+            }
+            
+        });        
         return opsWithSamePath;
     }
     

Modified: cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/Book.java
URL: http://svn.apache.org/viewvc/cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/Book.java?rev=789817&r1=789816&r2=789817&view=diff
==============================================================================
--- cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/Book.java (original)
+++ cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/Book.java Tue Jun 30 16:14:55 2009
@@ -22,9 +22,14 @@
 import javax.ws.rs.Path;
 import javax.ws.rs.PathParam;
 
+
 public class Book {
 
     private int id;
+    
+    public Book() {
+    }
+    
     public Book(int id) {
         this.id = id;
     }
@@ -35,6 +40,10 @@
         return id;
     }
     
+    public void setId(int ident) {
+        id = ident;
+    }
+    
     @Path("/chapter/{cid}")
     public Chapter getChapter(@PathParam("cid") int cid) {
         return new Chapter(cid);

Modified: cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/BookStore.java
URL: http://svn.apache.org/viewvc/cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/BookStore.java?rev=789817&r1=789816&r2=789817&view=diff
==============================================================================
--- cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/BookStore.java (original)
+++ cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/BookStore.java Tue Jun 30 16:14:55 2009
@@ -31,13 +31,13 @@
 import javax.ws.rs.core.HttpHeaders;
 
 @Path("/bookstore/{id}")
-@Consumes("application/xml, application/json")
-@Produces("application/xml, application/json")
+@Consumes({"application/xml", "application/json" })
+@Produces({"application/xml", "application/json" })
 public class BookStore {
 
     @GET 
     @Produces("text/plain")
-    public String getName() {
+    public String getName(@PathParam("id") Long id) {
         return "store";
     }
     

Modified: cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/Orders.java
URL: http://svn.apache.org/viewvc/cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/Orders.java?rev=789817&r1=789816&r2=789817&view=diff
==============================================================================
--- cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/Orders.java (original)
+++ cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/Orders.java Tue Jun 30 16:14:55 2009
@@ -27,6 +27,9 @@
 
     @GET
     @Produces("text/plain")
+    /**
+     * Foo
+     */
     public int getNumberOfOrders() {
         return 100;
     }

Modified: cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/WadlGeneratorTest.java
URL: http://svn.apache.org/viewvc/cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/WadlGeneratorTest.java?rev=789817&r1=789816&r2=789817&view=diff
==============================================================================
--- cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/WadlGeneratorTest.java (original)
+++ cxf/branches/2.2.x-fixes/rt/frontend/jaxrs/src/test/java/org/apache/cxf/jaxrs/model/wadl/WadlGeneratorTest.java Tue Jun 30 16:14:55 2009
@@ -18,6 +18,8 @@
  */
 package org.apache.cxf.jaxrs.model.wadl;
 
+import java.io.File;
+import java.io.FileOutputStream;
 import java.io.StringReader;
 import java.util.ArrayList;
 import java.util.List;
@@ -80,14 +82,14 @@
         assertNotNull(r);
         assertEquals(WadlGenerator.WADL_TYPE.toString(),
                      r.getMetadata().getFirst(HttpHeaders.CONTENT_TYPE));
-//        File f = new File("test.xml");
-//        f.delete();
-//        f.createNewFile();
-//        System.out.println(f.getAbsolutePath());
-//        FileOutputStream fos = new FileOutputStream(f);
-//        fos.write(r.getEntity().toString().getBytes());
-//        fos.flush();
-//        fos.close();
+        File f = new File("test.xml");
+        f.delete();
+        f.createNewFile();
+        System.out.println(f.getAbsolutePath());
+        FileOutputStream fos = new FileOutputStream(f);
+        fos.write(r.getEntity().toString().getBytes());
+        fos.flush();
+        fos.close();
     }
     
     @Test
@@ -111,6 +113,31 @@
 
     private void checkBookStoreInfo(Element resource) {
         assertEquals("/bookstore/{id}", resource.getAttribute("path"));
+        
+        List<Element> resourceEls = DOMUtils.getChildrenWithName(resource, 
+                  "http://research.sun.com/wadl/2006/10", "resource");
+        assertEquals(3, resourceEls.size());        
+        assertEquals("/", resourceEls.get(0).getAttribute("path"));
+        assertEquals("/books/{bookid}", resourceEls.get(1).getAttribute("path"));
+        assertEquals("/booksubresource", resourceEls.get(2).getAttribute("path"));
+        
+        List<Element> methodEls = DOMUtils.getChildrenWithName(resourceEls.get(0), 
+            "http://research.sun.com/wadl/2006/10", "method");
+        assertEquals(1, methodEls.size());
+        assertEquals("GET", methodEls.get(0).getAttribute("name"));
+                                                           
+        
+        List<Element> paramsEls = DOMUtils.getChildrenWithName(resourceEls.get(1), 
+                                  "http://research.sun.com/wadl/2006/10", "param");
+        assertEquals(3, paramsEls.size());
+        checkParameter(paramsEls.get(0), "id", "template");
+        checkParameter(paramsEls.get(1), "bookid", "template");
+        checkParameter(paramsEls.get(2), "mid", "matrix");
+    }
+    
+    private void checkParameter(Element paramEl, String name, String type) {
+        assertEquals(name, paramEl.getAttribute("name"));
+        assertEquals(type, paramEl.getAttribute("style"));    
     }
     
     private List<Element> getWadlResourcesInfo(String baseURI, int size, String value) throws Exception {

Modified: cxf/branches/2.2.x-fixes/rt/transports/http/src/main/java/org/apache/cxf/transport/servlet/ServletController.java
URL: http://svn.apache.org/viewvc/cxf/branches/2.2.x-fixes/rt/transports/http/src/main/java/org/apache/cxf/transport/servlet/ServletController.java?rev=789817&r1=789816&r2=789817&view=diff
==============================================================================
--- cxf/branches/2.2.x-fixes/rt/transports/http/src/main/java/org/apache/cxf/transport/servlet/ServletController.java (original)
+++ cxf/branches/2.2.x-fixes/rt/transports/http/src/main/java/org/apache/cxf/transport/servlet/ServletController.java Tue Jun 30 16:14:55 2009
@@ -21,6 +21,7 @@
 import java.io.IOException;
 import java.io.OutputStream;
 import java.net.URL;
+import java.util.ArrayList;
 import java.util.Collections;
 import java.util.Comparator;
 import java.util.LinkedList;
@@ -50,7 +51,8 @@
 public class ServletController {
     
     private static final Logger LOG = LogUtils.getL7dLogger(ServletController.class);
-
+    private static final String DEFAULT_LISTINGS_CLASSIFIER = "/services";
+    
     private ServletTransportFactory transport;
     private ServletContext servletContext;
     private ServletConfig servletConfig;
@@ -60,6 +62,7 @@
     private boolean disableAddressUpdates;
     private String forcedBaseAddress;
     private String serviceListStyleSheet;
+    private String serviceListRelativePath = DEFAULT_LISTINGS_CLASSIFIER;
  
     public ServletController(ServletTransportFactory df,
                              ServletConfig config,
@@ -72,9 +75,18 @@
         init();
     }
     
+    ServletController() {
+        
+    }
+        
     public void setHideServiceList(boolean generate) {
         isHideServiceList = generate;
     }
+    
+    public void setServiceListRelativePath(String relativePath) {
+        serviceListRelativePath = relativePath;
+    }
+    
     public void setDisableAddressUpdates(boolean noupdates) {
         disableAddressUpdates = noupdates;
     }
@@ -89,7 +101,7 @@
         return lastBase;
     }
     
-    private synchronized void updateDests(HttpServletRequest request) {
+    protected synchronized void updateDests(HttpServletRequest request) {
         if (disableAddressUpdates) {
             return;
         }
@@ -119,13 +131,14 @@
             String address = request.getPathInfo() == null ? "" : request.getPathInfo();
 
             ei.setAddress(address);
-            ServletDestination d = (ServletDestination)transport.getDestinationForPath(ei.getAddress());
+            
+            ServletDestination d = getDestination(ei.getAddress());
             
             if (d == null) {
-                if (request.getRequestURI().endsWith("/services")
-                    || request.getRequestURI().endsWith("/services/")
+                if (!isHideServiceList && (request.getRequestURI().endsWith(serviceListRelativePath)
+                    || request.getRequestURI().endsWith(serviceListRelativePath + "/")
                     || StringUtils.isEmpty(request.getPathInfo())
-                    || "/".equals(request.getPathInfo())) {
+                    || "/".equals(request.getPathInfo()))) {
                     updateDests(request);
                     
                     if (request.getParameter("stylesheet") != null) {
@@ -193,7 +206,11 @@
         } 
     }
     
-    private ServletDestination checkRestfulRequest(HttpServletRequest request) throws IOException {        
+    protected ServletDestination getDestination(String address) {
+        return (ServletDestination)transport.getDestinationForPath(address);
+    }
+    
+    protected ServletDestination checkRestfulRequest(HttpServletRequest request) throws IOException {        
         
         String address = request.getPathInfo() == null ? "" : request.getPathInfo();
         
@@ -228,46 +245,85 @@
         response.getWriter().write("<meta http-equiv=content-type content=\"text/html; charset=UTF-8\">");
         response.getWriter().write("<title>CXF - Service list</title>");
         response.getWriter().write("</head><body>");
-        if (!isHideServiceList) {
-            List<ServletDestination> destinations = getServletDestinations();
-                
-            if (destinations.size() > 0) {  
-                response.getWriter().write("<span class=\"heading\">Available services:</span><br/>");
-                response.getWriter().write("<table " + (serviceListStyleSheet == null
-                        ? "cellpadding=\"1\" cellspacing=\"1\" border=\"1\" width=\"100%\"" : "") + ">");
-                for (ServletDestination sd : destinations) {
-                    if (null != sd.getEndpointInfo().getName() 
-                        && null != sd.getEndpointInfo().getInterface()) {
-                        response.getWriter().write("<tr><td>");
-                        response.getWriter().write("<span class=\"porttypename\">"
-                                + sd.getEndpointInfo().getInterface().getName().getLocalPart()
-                                + "</span>");
-                        response.getWriter().write("<ul>");
-                        for (OperationInfo oi : sd.getEndpointInfo().getInterface().getOperations()) {
-                            response.getWriter().write("<li>" + oi.getName().getLocalPart() + "</li>");
-                        }
-                        response.getWriter().write("</ul>");
-                        response.getWriter().write("</td><td>");
-                        String address = sd.getEndpointInfo().getAddress();
-                        response.getWriter().write("<span class=\"field\">Endpoint address:</span> "
-                                + "<span class=\"value\">" + address + "</span>");
-                        response.getWriter().write("<br/><span class=\"field\">Wsdl:</span> "
-                                + "<a href=\"" + address + "?wsdl\">"
-                                + sd.getEndpointInfo().getService().getName() + "</a>");
-                        response.getWriter().write("<br/><span class=\"field\">Target namespace:</span> "
-                                + "<span class=\"value\">" 
-                                + sd.getEndpointInfo().getService().getTargetNamespace() + "</span>");
-                        response.getWriter().write("</td></tr>");
-                    }    
-                }
-                response.getWriter().write("</table>");
-            } else {
-                response.getWriter().write("<span class=\"heading\">No service was found.</span>");
-            }
-        }    
+        
+        List<ServletDestination> destinations = getServletDestinations();
+            
+        if (destinations.size() > 0) {
+            writeSOAPEndpoints(response, destinations);
+            writeRESTfulEndpoints(response, destinations);
+        } else {
+            response.getWriter().write("<span class=\"heading\">No services have been found.</span>");
+        }
+        
         response.getWriter().write("</body></html>");
     }
 
+    private void writeSOAPEndpoints(HttpServletResponse response, List<ServletDestination> destinations)
+        throws IOException {
+        response.getWriter().write("<span class=\"heading\">Available SOAP services:</span><br/>");
+        response.getWriter().write("<table " + (serviceListStyleSheet == null
+                ? "cellpadding=\"1\" cellspacing=\"1\" border=\"1\" width=\"100%\"" : "") + ">");
+        for (ServletDestination sd : destinations) {
+            if (null != sd.getEndpointInfo().getName() 
+                && null != sd.getEndpointInfo().getInterface()) {
+                response.getWriter().write("<tr><td>");
+                response.getWriter().write("<span class=\"porttypename\">"
+                        + sd.getEndpointInfo().getInterface().getName().getLocalPart()
+                        + "</span>");
+                response.getWriter().write("<ul>");
+                for (OperationInfo oi : sd.getEndpointInfo().getInterface().getOperations()) {
+                    response.getWriter().write("<li>" + oi.getName().getLocalPart() + "</li>");
+                }
+                response.getWriter().write("</ul>");
+                response.getWriter().write("</td><td>");
+                String address = sd.getEndpointInfo().getAddress();
+                response.getWriter().write("<span class=\"field\">Endpoint address:</span> "
+                        + "<span class=\"value\">" + address + "</span>");
+                response.getWriter().write("<br/><span class=\"field\">WSDL :</span> "
+                        + "<a href=\"" + address + "?wsdl\">"
+                        + sd.getEndpointInfo().getService().getName() + "</a>");
+                response.getWriter().write("<br/><span class=\"field\">Target namespace:</span> "
+                        + "<span class=\"value\">" 
+                        + sd.getEndpointInfo().getService().getTargetNamespace() + "</span>");
+                response.getWriter().write("</td></tr>");
+            }    
+        }
+        response.getWriter().write("</table><br/><br/>");
+    }
+    
+    
+    private void writeRESTfulEndpoints(HttpServletResponse response, List<ServletDestination> destinations)
+        throws IOException {
+        
+        List<ServletDestination> restfulDests = new ArrayList<ServletDestination>();
+        for (ServletDestination sd : destinations) {
+            // use some more reasonable check - though this one seems to be the only option at the moment
+            if (null == sd.getEndpointInfo().getInterface()) {
+                restfulDests.add(sd);
+            }
+        }
+        if (restfulDests.size() == 0) {
+            return;
+        }
+        
+        response.getWriter().write("<span class=\"heading\">Available RESTful services:</span><br/>");
+        response.getWriter().write("<table " + (serviceListStyleSheet == null
+                ? "cellpadding=\"1\" cellspacing=\"1\" border=\"1\" width=\"100%\"" : "") + ">");
+        for (ServletDestination sd : destinations) {
+            if (null == sd.getEndpointInfo().getInterface()) {
+                response.getWriter().write("<tr><td>");
+                String address = sd.getEndpointInfo().getAddress();
+                response.getWriter().write("<span class=\"field\">Endpoint address:</span> "
+                        + "<span class=\"value\">" + address + "</span>");
+                response.getWriter().write("<br/><span class=\"field\">WADL :</span> "
+                        + "<a href=\"" + address + "?_wadl&_type=xml\">"
+                        + address + "?_wadl&type=xml" + "</a>");
+                response.getWriter().write("</td></tr>");
+            }    
+        }
+        response.getWriter().write("</table>");
+    }
+    
     private void renderStyleSheet(HttpServletRequest request,
             HttpServletResponse response) throws IOException {
         response.setContentType("text/css; charset=UTF-8");
@@ -303,19 +359,44 @@
             HttpServletResponse response) throws IOException {
         response.setContentType("text/plain; charset=UTF-8");
 
-        if (!isHideServiceList) {
-            List<ServletDestination> destinations = getServletDestinations();
-
-            boolean renderWsdlList = "true".equals(request.getParameter("wsdlList"));
+        List<ServletDestination> destinations = getServletDestinations();
+        if (destinations.size() > 0) {
+            writeUnformattedSOAPEndpoints(response, destinations, request.getParameter("wsdlList"));
+            writeUnformattedRESTfulEndpoints(response, destinations);
+        } else {
+            response.getWriter().write("No services have been found.");
+        }
+    }
+    
+    private void writeUnformattedSOAPEndpoints(HttpServletResponse response,
+                                               List<ServletDestination> destinations,
+                                               Object renderParam) 
+        throws IOException {
+        boolean renderWsdlList = "true".equals(renderParam);
+        
+        for (ServletDestination sd : destinations) {
+            
+            if (null != sd.getEndpointInfo().getInterface()) {
             
-            for (ServletDestination sd : destinations) {
                 String address = sd.getEndpointInfo().getAddress();
                 response.getWriter().write(address);
                 
                 if (renderWsdlList) {
                     response.getWriter().write("?wsdl");
                 }
-                
+                response.getWriter().write('\n');
+            }
+        }
+        response.getWriter().write('\n');
+    }
+    
+    private void writeUnformattedRESTfulEndpoints(HttpServletResponse response,
+                                                  List<ServletDestination> destinations) 
+        throws IOException {
+        for (ServletDestination sd : destinations) {
+            if (null == sd.getEndpointInfo().getInterface()) {
+                String address = sd.getEndpointInfo().getAddress();
+                response.getWriter().write(address + "?_wadl&_type=xml");
                 response.getWriter().write('\n');
             }
         }
@@ -396,5 +477,9 @@
         if (serviceListTransform != null) {
             serviceListStyleSheet = serviceListTransform;
         }
+        String serviceListPath = servletConfig.getInitParameter("service-list-path");
+        if (serviceListPath != null) {
+            serviceListRelativePath = serviceListPath;
+        }
     }
 }

Modified: cxf/branches/2.2.x-fixes/systests/src/test/java/org/apache/cxf/systest/jaxrs/BookSubresource.java
URL: http://svn.apache.org/viewvc/cxf/branches/2.2.x-fixes/systests/src/test/java/org/apache/cxf/systest/jaxrs/BookSubresource.java?rev=789817&r1=789816&r2=789817&view=diff
==============================================================================
--- cxf/branches/2.2.x-fixes/systests/src/test/java/org/apache/cxf/systest/jaxrs/BookSubresource.java (original)
+++ cxf/branches/2.2.x-fixes/systests/src/test/java/org/apache/cxf/systest/jaxrs/BookSubresource.java Tue Jun 30 16:14:55 2009
@@ -31,8 +31,6 @@
 import javax.ws.rs.Produces;
 import javax.ws.rs.QueryParam;
 
-import org.apache.cxf.customer.book.BookNotFoundFault;
-
 public interface BookSubresource {
     
     @GET

Modified: cxf/branches/2.2.x-fixes/systests/src/test/java/org/apache/cxf/systest/jaxrs/BookSubresourceImpl.java
URL: http://svn.apache.org/viewvc/cxf/branches/2.2.x-fixes/systests/src/test/java/org/apache/cxf/systest/jaxrs/BookSubresourceImpl.java?rev=789817&r1=789816&r2=789817&view=diff
==============================================================================
--- cxf/branches/2.2.x-fixes/systests/src/test/java/org/apache/cxf/systest/jaxrs/BookSubresourceImpl.java (original)
+++ cxf/branches/2.2.x-fixes/systests/src/test/java/org/apache/cxf/systest/jaxrs/BookSubresourceImpl.java Tue Jun 30 16:14:55 2009
@@ -19,8 +19,6 @@
 
 package org.apache.cxf.systest.jaxrs;
 
-import org.apache.cxf.customer.book.BookNotFoundFault;
-
 public class BookSubresourceImpl implements BookSubresource {
 
     private Long id;