我有一个带有@RequestBody的控制器
@PostMapping("/")
public String doSomething(@RequestBody ??? foo)
foo可以是两个不同的对象。Foobject或Barobject。我不知道对象会发送什么。这些对象是完全不同的,没有任何我可以使用的公共领域@JsonTypeInfo和@JsonSubTypes
我可以解决这个问题,并使用ObjectMapper尝试将其映射到两个类中的一个:
@RequestBody Object json
...
ObjectMapper objectMapper = new ObjectMapper();
try {
Foobject obj = objectMapper.convertValue(json, Foobject.class);
}
catch (IllegalArgumentException ei){
Barobject obj = objectMapper.convertValue(json, Barobject.class);
}
有合适的方法来做这件事吗?或者更确切地说,是替代方案?我知道这与REST API开发相违背,因为这应该是另一个方法,每个方法都有自己的对象。
您可以选择像这样使用Object类,然后利用函数
mapper.readValue(jsonStr, Fooobject.class);
抛出JsonMappingException
@PostMapping("/")
public String doSomething(@RequestBody Object foo) {...}
boolean isA(String json, Class expected) {
try {
ObjectMapper mapper = new ObjectMapper();
mapper.readValue(json, expected);
return true;
} catch (JsonMappingException e) {
e.printStackTrace();
return false;
}
}
好吧,你说"我不知道将对象发送什么",所以你只能做试错。
否则修改您的请求以包含"类型";或者别的什么(我会通过创建一个只有"type"的父类来做到这一点;ObjectType类型的成员,以及继承该父类的子类。
enum ObjectType {FOO, BAR}
Method 1: Use readValue() function of jackson Method 2: Do a string search (just to make it faster) something unique non-nullable field about any of the object. Method 3: Modify the request.
成功做到了。创建父类,两个对象都继承自父类。对父节点添加:
@JsonTypeInfo(use = JsonTypeInfo.Id.DEDUCTION)
@JsonSubTypes({
@JsonSubTypes.Type(Foobject.class),
@JsonSubTypes.Type(Barobject.class),,
})
这工作得很好,我想是一个干净的解决方案。而且,在Spring层上完成的优点是,在Spring层上将发生在类的字段上定义的其他验证。
这与其他解决方案不同。