【问题标题】:Specifying an optional parameter with a default value for restful web service为 RESTful Web 服务指定具有默认值的可选参数
【发布时间】:2015-05-05 13:56:09
【问题描述】:

我正在尝试创建一个返回 int 的 web 服务。它还应该有一个可选参数 - 这会失败。

这行得通:

package foo;

import java.util.Map;
import java.util.TreeMap;

import javax.ws.rs.DefaultValue;
import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.QueryParam;
import javax.ws.rs.core.MediaType;

@Path("/euler")
public class Euler1 {

    @GET
    @Path("/getmultiples")
    @Produces(MediaType.APPLICATION_JSON)
    public static Map<String, Integer> getMultiples() {
        int sum = 0;
        int limit = 1000;
        for (int i = 0; i < limit; i += 3) {
            sum += i;
        }
        for (int i = 0; i < limit; i += 5) {
            if (i % 3 != 0) {
                sum += i;
            }
        }
        final Map<String, Integer> result = new TreeMap<>();
        result.put("Sum", sum);
        return result;
    }
}

如果我把它称为curl http://localhost:8080/foo/rest/euler/getmultiples,我会得到{"Sum":233168}


但限制应该是一个可选参数。所以我将方法签名更改为

public static Map<String, Integer> getMultiples(
   @DefaultValue("1000") @QueryParam(value = "limit") int limit)

但是前面没有返回任何内容,并且服务器(Wildfly 8)记录

15:07:08,889 ERROR [io.undertow.request] (default task-3) UT005023: Exception handling request to /foo/rest/euler/getmultiples: java.lang.ArrayIndexOutOfBoundsException: 0
    at org.jboss.resteasy.plugins.validation.GeneralValidatorImpl.parametersResolveToSameTypes(GeneralValidatorImpl.java:515) [resteasy-validator-provider-11-3.0.10.Final.jar:]
    at org.jboss.resteasy.plugins.validation.GeneralValidatorImpl.overrides(GeneralValidatorImpl.java:486) [resteasy-validator-provider-11-3.0.10.Final.jar:]
    at org.jboss.resteasy.plugins.validation.GeneralValidatorImpl.getSuperMethod(GeneralValidatorImpl.java:444) [resteasy-validator-provider-11-3.0.10.Final.jar:]
    at org.jboss.resteasy.plugins.validation.GeneralValidatorImpl.getExecutableTypesOnMethodInHierarchy(GeneralValidatorImpl.java:335) [resteasy-validator-provider-11-3.0.10.Final.jar:]
    at org.jboss.resteasy.plugins.validation.GeneralValidatorImpl.isMethodValidatable(GeneralValidatorImpl.java:265) [resteasy-validator-provider-11-3.0.10.Final.jar:]

这是 web.xml:

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd"
    version="3.1">
    <servlet-mapping>
        <servlet-name>javax.ws.rs.core.Application</servlet-name>
        <url-pattern>/rest/*</url-pattern>
    </servlet-mapping>
</web-app>

使用的原型是最新版本的com.airhacks:javaee7-essentials-archetype

这是pom.xml

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <groupId>de.oneiros</groupId>
    <artifactId>webservice-ee7</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <packaging>war</packaging>
    <dependencies>
        <dependency>
            <groupId>javax</groupId>
            <artifactId>javaee-api</artifactId>
            <version>7.0</version>
            <scope>provided</scope>
        </dependency>
    </dependencies>
    <build>
        <finalName>webservice-ee7</finalName>
    </build>
    <properties>
        <maven.compiler.source>1.8</maven.compiler.source>
        <maven.compiler.target>1.8</maven.compiler.target>
        <failOnMissingWebXml>false</failOnMissingWebXml>
    </properties>
</project>

如何将可选参数传递给我的方法?

【问题讨论】:

  • 只是在黑暗中拍摄,它如何与可变参数保持一致?这应该允许指定 0 个或多个整数,然后您只需告诉您的代码使用第一个。
  • 为了获得更好的帮助,请发布一个 Minimal, Complete, and Verifiable example 来演示问题。
  • @peeskillet:我已经添加了 web.xml。你还需要什么?
  • @geceo:Eclipse 告诉我,这只是@PathParams 需要,@QueryParams 不需要
  • 是否允许有static子资源方法?我认为这可能会导致与注入的参数或实例字段发生冲突

标签: java rest jax-rs wildfly java-ee-7


【解决方案1】:

看来问题是资源方法是static(感谢@peeskillet 的测试和确认)。

堆栈跟踪表明这里出了点问题:它调用了一个名为 getSuperMethod 的方法,这对于静态方法没有真正意义。

查看source code,似乎验证器插件正在尝试使用实例方法而不是类方法。这听起来像是插件中的错误。

【讨论】:

    【解决方案2】:

    事实上,我无法重现您的问题。我只是在这里提供我用来测试的配置,希望它对你有用。

    我的 Maven 配置:

    <project (...)>
        <modelVersion>4.0.0</modelVersion>
        <groupId>resteasy.test</groupId>
        <artifactId>JAXRS-RESTEasy</artifactId>
        <packaging>war</packaging>
        <version>0.0.1-SNAPSHOT</version>
    
        <properties>
            <java-version>1.7</java-version>
            <resteasy-version>3.0.10.Final</resteasy-version>
            <wtp-version>2.0</wtp-version>
        </properties>
    
        <dependencies>
            <dependency>
                <groupId>org.jboss.resteasy</groupId>
                <artifactId>resteasy-jaxrs</artifactId>
                <version>${resteasy-version}</version>
            </dependency>
    
            <dependency>
                <groupId>org.jboss.resteasy</groupId>
                <artifactId>resteasy-servlet-initializer</artifactId>
                <version>${resteasy-version}</version>
            </dependency>
        </dependencies>
    
        <repositories>
            <repository>
                <id>JBoss repository</id>
                <url>https://repository.jboss.org/nexus/content/groups/public-jboss/</url>
            </repository>
        </repositories>
        (...)
    </project>
    

    我的档案web.xml

    <web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xmlns="http://java.sun.com/xml/ns/javaee"
        xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
        id="WebApp_ID" version="3.0">
        <display-name>JAXRS-RESTEasy</display-name>
    </web-app>
    

    WEB-INF/services文件夹下我的文件javax.servlet.ServletContainerInitializer

    org.jboss.resteasy.plugins.servlet.ResteasyServletInitializer
    

    我的应用类:

    @ApplicationPath("/")
    public class RESTEasyApplication extends Application {
    
    }
    

    我的资源类:

    @Path("/RESTEasyHelloWorld")
    public class RESTEasyHelloWorldService {
        @GET
        @Path("/{pathParameter}")
        public Response responseMsg( @PathParam("pathParameter") String pathParameter,
            @DefaultValue("1000") @QueryParam("queryParameter") int queryParameter) {
    
            String response = "Hello from: " + pathParameter + " : " + queryParameter;
    
            return Response.status(200).entity(response).build();
        }
    }
    

    如果我不传递查询参数queryParameter,我会在int类型的方法参数queryParameter中得到值1000

    已编辑:我将 static 添加到方法 responseMsg 中,它仍然适用于我... 真的很奇怪的问题 :-/ 我用版本 3.0.10.Final 进行了测试雄猫 7.

    希望它能帮助您解决问题! 蒂埃里

    【讨论】:

    • 我使用 Wildfly 重现了该问题,因为 OP 正在使用该问题。问题发生在启动时。似乎是在资源模型的验证(可能是“正确性”)期间。
    • 问题似乎出在resteasy validator provider 工件上。我不认为 resteasy-jaxrs 能做到这一点。您可能需要明确添加它。它与 Wildfly 一起提供。我不知道只是将工件添加到您的依赖项中是否会重现问题,但您可以尝试一下
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2020-08-23
    • 2013-04-25
    • 2021-09-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多