使用本示例JAX-RS Web服务,getByAttribute
的第二个参数的类型为Object.class
。
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
@Path("/POJOService")
public interface POJOService extends BasicService {
@GET
@Path("/getByAttribute")
SampleObject getByAttribute(@QueryParam("attribute") String attribute, @QueryParam("value") Object value);
}
这将导致错误:
有效负载:参数类java.lang.Object没有带有单个String参数,静态valueOf(String)或fromString(String)的构造函数 方法
我当时正在考虑添加javax.ws.rs.ext.ParamConverterProvider
的提供程序,该提供程序将在JSON字符串中传递类型。但是也许有针对此问题的最佳实践解决方案?
将现有企业服务器/客户端应用程序的通信层迁移到JAX-RS 2.1。
使用Apache CXF和Eclipse Rest Client for MicroProfile。
编辑:客户端将调用不同类型的服务:
service.getByAttribute("name", "example"); // string, used for this test which throws the exception
service.getByAttribute("id", 99); // integer
service.getByAttribute("author", user); // object instace of User.class
答案 0 :(得分:0)
我发现可以配置ObjectMapper以添加键入信息:
ObjectMapper mapper = new ObjectMapper();
mapper.enableDefaultTyping(DefaultTyping.NON_FINAL);
还有其他键入configurations:
JAVA_LANG_OBJECT
该值意味着只有具有Object作为声明类型的属性(包括没有显式的泛型类型) 类型)将使用默认类型。NON_CONCRETE_AND_ARRAYS
该值表示将对OBJECT_AND_NON_CONCRETE涵盖的所有类型以及它们的所有数组类型使用默认类型。NON_FINAL
该值表示将对所有非最终类型使用默认类型,但少数“自然”类型(字符串,布尔值,整数,双精度)除外,可以从JSON正确推断出这些类型;以及 至于所有非最终类型的数组。
OBJECT_AND_NON_CONCRETE
该值表示默认类型将用于具有声明的Object类型或抽象类型(抽象类或接口)的属性。
我还必须注册一个ParamConverterProvider
,该参数考虑传递的所有参数的ObjectMapper
设置:
@Provider
public class ObjectMapperParamConverterProvider implements ParamConverterProvider {
@Override
public <T> ParamConverter<T> getConverter(final Class<T> rawType, final Type genericType, final Annotation[] annotations) {
ObjectMapper mapper = ...;
return new ParamConverter<T>() {
@Override
public T fromString(final String value) {
try {
T result = mapper.readValue(value, rawType);
return result;
} catch (IOException e) {
throw new ProcessingException(e);
}
}
@Override
public String toString(final T value) {
try {
String result = mapper.writeValueAsString(value);
return result;
} catch (JsonProcessingException e) {
throw new ProcessingException(e);
}
}
};
}
}