Design notes for showing resources of REST endpoints

Version 13

    Overview

    The intent of this feature is to show the REST endpoints' resources in CLI of a deployment. Users will have a clear idea about what REST endpoints a deployment provides.

     

    Background

    There is an operation called '/deployment=XXX.war/subsystem=jaxrs:show-resources()' currently in 'jaxrs' subsystem for each deployment with REST endpoints to show some basic information of each REST endpoint. The output information is a set of resources with path information and basic method signature without grouped or ordered.

     

    There is also a ':read-resource()' operation for each managed resource in WildFly, which has the same meaning to display the resources in it. This makes the ':show-resources()' operation unnecessary. Resources in other subsystems are exposed by the ':read-resource()' operation, so we don't need the ':show-resources()' operation for this, the structured output information should be integrated into the ':read-resource()' operation.

     

    The output information will be potentially used by the admin console in the future, so the output format should be easily parsed.

     

    This RFE will deprecate the ':show-resources()' operation, and integrate more structured information of REST endpoints resources into the ':read-resource()' operation.

     

    Issue Metadata

     

    EAP ISSUE: https://issues.jboss.org/browse/EAP7-607

     

    RELATED ISSUES: [WFLY-7024] show-resources operation of jaxrs subsystem must provide more informations and statistics about end-point - …

    [EAP7-606] Aggregated statistics for all deployments in EAP

                                      [WFLY-6564] show-resources operation of jaxrs subsystem shows wrong path in resource-methods attribute - JBoss Issue Tra…

                                      [WFLY-6565] add and remove operation of jaxrs subsystem under deployment are useles and should not be available - JBoss …

                                      [WFLY-7067] show-resources operation of jaxrs subsystem is unable to read jax-rs end-point from subresources - JBoss Iss…

    [WFLY-7210] Expose JAX-RS resources as children of the subsystem - JBoss Issue Tracker

     

    DEV CONTACTS:  Lin Gao (primary), Alessio Soldano (secondary)

     

    QE CONTACTS:  Rostislav Svoboda, Marek Kopecky, Katerina Novotna

     

    AFFECTED PROJECTS OR COMPONENTS:  WildFly, RestEasy

     

    Requirements

     

     

    Hard Requirements

    These items must be satisfied in order to have a satisfactory feature.

    The ':show-resources()' operations in below document are '/deployment=XXX.war/subsystem=jaxrs:show-resources()' except for other notes.

    • The ':show-resources()' operation of jaxrs subsystem will be deprecated.
    • The structured output information of each REST endpoint should be integrated into the output of ':read-resource()' operation.
      • Because the REST endpoint resources are all run-time information, the 'include-runtime=true' should be needed
        • /deployment=XXX.war/subsystem=jaxrs:read-resource(include-runtime=true)
    • The structured output information of each REST endpoint should contain the following information:
      • resource path,  the path address where to access the endpoint
      • resource class, the class name which defines the endpoints path prefix
      • resource method, the Java method which defines the resource path, HTTP method, consumes and produces of the endpoint
      • parameters in the resource method, the parameters defined in the resource method, including the type of the parameters
        • name of the parameter should be the value of one of the following annotations if any of them is defined:
          • @PathParam, @QueryParam, @HeaderParam, @MatrixParam, @CookieParam, @FormParam
          • If the parameter does not have any annotation, the name is gotten by the 'java.lang.reflect.Parameter.getName()', normally is arg[0-9].
        • indicates what kind of parameter it is according to the annotations above. If one parameter does not have any annotation, leave it as an empty string.
        • the default value of the parameter should be displayed also if it is defined by @DefaultValue annotation
      • the return type of the resource method, the class name of the return type of the method
      • HTTP method accepted by the endpoint
      • Content types which the endpoint can consume.
      • Content types which the endpoint will produce.
    • The output information needs to be grouped by the resource class and ordered by the resource path.

     

    Nice-to-Have Requirements

    These items are not required but would be nice to have if possible.

     

    • Using a filter to query the REST endpoints definition by specifying the resource path, method, consuming types or producing types. This would be helpful in case of a large number of REST endpoints within a deployment.
      • NOTE, because it is integrated into the ':read-resource()' operation, which does not allow extra parameters, the ':query()' operation can be used for the narrowing down.
    • Display absolute URL of an endpoint by specifying an extra parameter in ':show-resources(absolute-path=true)' operation, it will be handy to just click to open the REST endpoint in a browser.

     

    Design Details

     

    To be consistent with other subsystems, a sub resource called 'rest-resource' will be used to group the information. Another benefit to use a sub resource is that it is possible to define operations dedicated to REST endpoints with same path prefix, like to enable or disable statistics of REST endpoints starts with '/order' in the future.

     

    Sample output

    The example output information may like this:

     

    [standalone@localhost:9990 /] /deployment=wildfly-helloworld-rs.war/subsystem=jaxrs/rest-resource=org.jboss.as.quickstarts.rshelloworld.HelloWorld:read-resource(include-runtime=true)
    {
        "outcome" => "success",
        "result" => {
            "resource-class" => "org.jboss.as.quickstarts.rshelloworld.HelloWorld",
            "rest-resource-paths" => [
                {
                    "resource-path" => "/hello/json",
                    "consumes" => undefined,
                    "produces" => [
                        "application/json",
                        "text/plain"
                    ],
                    "java-method" => "java.lang.String org.jboss.as.quickstarts.rshelloworld.HelloWorld.getHelloWorldJSON()",
                    "resource-methods" => [
                        "POST /wildfly-helloworld-rs/rest/hello/json",
                        "GET /wildfly-helloworld-rs/rest/hello/json"
                    ]
                },
                {
                    "resource-path" => "/hello/xml",
                    "consumes" => undefined,
                    "produces" => ["application/xml"],
                    "java-method" => "java.lang.String org.jboss.as.quickstarts.rshelloworld.HelloWorld.getHelloWorldXML(@QueryParam java.lang.String name = 'LGAO')",
                    "resource-methods" => ["GET /wildfly-helloworld-rs/rest/hello/xml"]
                }
            ],
            "sub-resource-locators" => [{
                "resource-class" => "org.jboss.as.quickstarts.rshelloworld.SubHelloWorld",
                "rest-resource-paths" => [
                    {
                        "resource-path" => "/hello/subMessage/",
                        "consumes" => undefined,
                        "produces" => undefined,
                        "java-method" => "java.lang.String org.jboss.as.quickstarts.rshelloworld.SubHelloWorld.helloInSub()",
                        "resource-methods" => ["GET /wildfly-helloworld-rs/rest/hello/subMessage/"]
                    },
                    {
                        "resource-path" => "/hello/subMessage/subPath",
                        "consumes" => undefined,
                        "produces" => undefined,
                        "java-method" => "java.lang.String org.jboss.as.quickstarts.rshelloworld.SubHelloWorld.subPath()",
                        "resource-methods" => ["GET /wildfly-helloworld-rs/rest/hello/subMessage/subPath"]
                    }
                ],
                "sub-resource-locators" => undefined
            }]
        }
    }