春季云Netflix和HystrixObservable - > JsonMappingException

春季云Netflix和HystrixObservable - > JsonMappingException

问题描述:

对于代码,请参阅我的小4类github project春季云Netflix和HystrixObservable - > JsonMappingException

我使用Spring FeignClients连接到REST服务。这是假死客户端的样子在其基本(非异步)形式:

@FeignClient(value="localhost:8080/products", decode404 = true) 
public interface ProductClient { 
    @RequestMapping(value="/{id}") 
    Product getById(@PathVariable("id") String id); 
} 

现在我想异步做,用观察到的。关于这方面的信息在Spring文档中严重缺乏,只有一个small paragraph告诉你使用HystrixCommand。这就是全部,没有解释,没有代码。

在另一篇博文中,我被告知使用HystrixObservable。所以,我试过了:

@FeignClient(value="localhost:8080/products", decode404 = true) 
public interface ProductClient { 
    @RequestMapping(value="/{id}") 
    HystrixObservable<Product> getById(@PathVariable("id") String id); 
} 

无论哪种方式,有HystrixCommand或HystrixObservable,它抛出我的错误: com.fasterxml.jackson.databind.JsonMappingException:无法构建com.netflix.hystrix实例.HystrixObservable

我明白为什么它会出现这个错误,因为Spring Boot会自动将解码器附加到FeignClient中,以使用Jackson反序列化响应。反序列化的类型来自返回值。

我可以尝试配置一个custome解码器或手动构建Feign客户端,但这样做会挫败Spring Boot的全部用途:它自动工作(尽管在这里和那里有一点配置)。

所以我的问题是:这应该如何工作?

+0

作为[文档]中示出(https://github.com/OpenFeign/feign/tree/master/hystrix),则需要构造不同的客户端(通过'HystrixFeign')。 –

+0

是的,可以手动构建Feign客户端。但我的问题是关于Spring + Feign。那么如何让Spring产生合适的Feign客户端呢?春季文档表明它可以,但一些重要的细节被忽略。另外这个[博客文章](https://www.voxxed.com/blog/2016/03/netflix-stack-using-spring-boot-part-3-feign/#feignclientwithhystrixobservablewrapper)正是我所做的。 –

如果指定返回类型为HystrixCommand<Product>或RxJava的Observable<Product>Single<Product>而不是HystrixObservable<Product>它应该工作。

我相信使用HystrixObservable的原因不能正常工作,是因为它是一个接口,杰克逊将不会映射到抽象类型,如由默认接口,你可能会在堆栈跟踪看到:

> abstract types either need to be mapped to concrete types, have custom 
> deserializer, or contain additional type information 

然而,它是HystrixObservable接口的实现,所以杰克逊可以轻松映射到它。

如果您查看Feign's Hystrix module中的HystrixInvocationHandler,您会看到它能够返回的其他类型;我上面列出的以及RxJava的Completable。由Tassos Bassoukos链接的文档也列出了这些类型。

如果你正在寻找异步和非阻塞的东西,可能值得检查Feign Vertx,因为我相信Feign可以是异步但阻塞的。关于非阻塞Feign的讨论是here

希望有帮助!

+0

感谢您的支持。 Jackson既不应该对HystrixCommand进行反序列化,也不应该对HystrixObservable进行反序列化,而应该是一个Product,因为这是响应中的有效载荷。在某个地方,请求中的返回值必须反序列化,并且将其反序列化的类型取自方法的返回类型(本例中为HystrixObservable)。但这是错误的策略。它应该看看通用类型。由于类型擦除,这在运行时非常困难。 –

如果有人在升级到spring-cloud后出现此错误:1.3。请确保启用了hystrix-feign。

feign.hystrix.enabled=true 

这被添加,所以feign不会在hystrix命令中默认打包调用。

https://github.com/spring-cloud/spring-cloud-netflix/issues/1277