繁体   English   中英

使用Dropwizard实现强大的参数

[英]Implementing strong params using Dropwizard

我想以一种只接受特定请求字段的方式验证请求,并使用Dropwizard和Jersey为所有未接受的字段返回400。

反正有没有这样做?

编辑:

示例 - 假设请求包含以下JSON:{name:Test,age:30,id:52}

并且服务器在请求中不接受字段ID。

预期:服务器应返回400,表明请求中不允许使用字段ID。

第二次尝试在编辑问题后回答此问题。

您可以构建您的JSON bean并忽略未知值,例如带有Jackson注释'JsonIgnoreProperties'的ID。

您有以下资源:

@Post
public Response hello(Person person) {
        return Response
                .status(Status.OK)
                .entity(String.format("Hello %s. We know that you are %s years old, but we do not know if you send more informations to us like id or sth. else.", person.getName(), person.getAge()))
                .build();
}

@JsonIgnoreProperties(ignoreUnknown = true)
public class Person {
    private final String name;
    private final int age;

    @JsonCreator
    public Person(@JsonProperty String name,@JsonProperty int age) {
        this.name= name;
        this.age= age;
    }

    @JsonProperty
    public String getName() {
        return name;
    }

    @JsonProperty
    public String getage() {
        return age;
    }
}

旧答案:

为什么不验证它们? 下面3个如何做到这一点的例子。

选项1:

@Path("smooth")
@GET
public Response smooth(
    @DefaultValue("2") @QueryParam("step") int step,
    @DefaultValue("true") @QueryParam("min-m") boolean hasMin,
    @DefaultValue("true") @QueryParam("max-m") boolean hasMax,
    @DefaultValue("true") @QueryParam("last-m") boolean hasLast,
    @DefaultValue("blue") @QueryParam("min-color") ColorParam minColor,
    @DefaultValue("green") @QueryParam("max-color") ColorParam maxColor,
    @DefaultValue("red") @QueryParam("last-color") ColorParam lastColor) {
    validateMaxColor(maxColor);
}

public void validateMaxColor(ColorParam  maxColorParam){
    if(!maxColorParam.isInRange()){
        throw new WebapplicationException("maxColorParam out of range");
    }
}

选项2:使用特定的参数类

@Path("smooth")
@GET
public Response smooth(
    @DefaultValue("2") @QueryParam("step") int step,
    @DefaultValue("true") @QueryParam("min-m") boolean hasMin,
    @DefaultValue("true") @QueryParam("max-m") boolean hasMax,
    @DefaultValue("true") @QueryParam("last-m") boolean hasLast,
    @DefaultValue("blue") @QueryParam("min-color") ColorParam minColor,
    @DefaultValue("green") @QueryParam("max-color") ColorParam maxColor,
    @DefaultValue("red") @QueryParam("last-color") ColorParam lastColor) {
    ....
}


public class ColorParam extends Color {

    public ColorParam(String color) {
        super(getRGB(color));
        if(getRGB(color).isGreen()){
            throw new ParseException("ohh nooooo ... green is not allowed here");
        }
    }

    private static int getRGB(String s) {
        if (s.charAt(0) == '#') {
            try {
                Color c = Color.decode("0x" + s.substring(1));
                return c.getRGB();
            } catch (NumberFormatException e) {
                throw new WebApplicationException(400);
            }
        } else {
            try {
                Field f = Color.class.getField(s);
                return ((Color)f.get(null)).getRGB();
            } catch (Exception e) {
                throw new WebApplicationException(400);
            }
        }
    }
}

在这里使用String构造函数很重要。

选项3:对于Dropwizard用户; 使用AbstractParam并验证传入的字符串

请参阅有关Params的Dropwizard文档

参数

资源类上的带注释的方法可以接受从传入请求的方面映射到的参数。 * Param注释确定数据映射的请求的哪个部分,参数类型确定数据的映射方式。

例如:

 A @PathParam("user")-annotated String takes the raw value from the user variable in the matched URI template and passes it into the 

方法作为字符串。 @QueryParam(“count”) - 带注释的IntParam参数从请求的查询字符串中获取第一个计数值,并将其作为String传递给IntParam的构造函数。 IntParam(和所有其他io.dropwizard.jersey.params。*类)将字符串解析为Integer,如果值格式错误,则返回400 Bad Request。 @FormParam(“name”) - 带注释的Set参数从发布的表单中获取所有名称值,并将它们作为一组字符串传递给方法。 A * Param-annotated NonEmptyStringParam会将空字符串解释为缺少字符串,这在端点将空字符串和缺少字符串视为可互换的情况下非常有用。

这里值得注意的是,您实际上可以使用专门的参数对象封装绝大多数验证逻辑。 有关详细信息,请参阅AbstractParam。

您的资源应该是这样的:

@Path("long")
@GET
public Response long(
    @QueryParam("long") LongParam longValue) {
    //here your longValue is in wanted Range
    //doubles or floats will return a HTTP 400
}


/**
 * A parameter encapsulating long values. All non-decimal values will return a {@code 400 Bad
 * Request} response.
 */
public class LongParam extends AbstractParam<Long> {
    public LongParam(String input) {
        super(input);
    }

    @Override
    protected String errorMessage(Exception e) {
        return "Parameter is not a number.";
    }

    @Override
    protected Long parse(String input) {
        return Long.valueOf(input);
    }
}

有了这个,您可以轻松验证传入的字符串并在无法解析字符串或无效范围时抛出异常(例如,如果您想要一个HexValue并且您的字符串是#ZZ8000,那么您可以检查不允许包含十六进制字符串任何'Z')。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM