你不知道的事---SringCloud的feign的继承特性
前言
说起SpringChoud的feign大家用过的都说好。Feign是Netflix开发的声明式、模板化的HTTP客户端。对于我们微服务来说,微服务之间的api调用,使用feign来说是再方便不过的。本文先介绍一下,传统的feign的调用写法方式,再介绍我们的重点feign的继承特性。
feign的继承特性有很多的好处,可以进行参数和方法的统一管理,一次修改,feign和具体的controller都变了。
总之好处还是不少的。

传统的feign的实现方式
传统的feign是怎样的实现的呢,我们先通过springmvc搞了一个controller,在controller里面实现我们代码。此时另一个微服务想直接调用这个请求,那么被调用的微服务就可以声明一个feign的客户端,将自身要提供给外部调用的方法,feign提供的方法的requestMapper路径映射和controller中的保持一致即可访问的到。
传统feign的代码实现
我们先写一个传统的controller。我们的目的很简单,这个controller来返回123。
@RestController
public class DemoController {
@PostMapping("/demo/list")
public String demo(
@RequestBody DemoFeignQueryVO demoFeignQueryVO){
return "123";
}
}
有了controller,我们来写feign。feign的代码是十分简单的,只要保证feignClint的值是我们要调用的微服务的值,然后其中的postMapping的值和上方controller的一样即可调用到。
@FeignClient(value = "user-system")
@Component
public interface IDemoFeign {
@PostMapping("/demo/list")
public String demo(
@RequestBody DemoFeignQueryVO demoFeignQueryVO);
}
传统feign的缺点
由上方的代码来看,有什么缺点呢,比如我要更改controller的参数,那么我需要改两处地方,一处是自己的controller实现,一处是feign的接口。如果忘改了的话,就会产生未知的错误。如果更改了controller的路径映射呢。同样的,也需要改两处位置。这是传统形式的一种缺点。
feign的继承特性
如果我们使用feign的继承特性,就不会有上方的情况产生,继承特性就是说,我们弄一个共用的接口,在接口上布置我们的requestMapping注解,规定我们的方法参数。然后通过controller实现这个接口。controller就可以针对接口中的方法进行一一的实现。然后针对于我们的feign接口,我们直接继承共用的接口。这样feign接口和controller方法是完全保持一致的,当需要修改的时候,完全不需要两个地方一起修改,直接更改共用的接口即可。
feign的继承特性的代码实现
我们将上述的传统方案的代码进行一个改写,通过对比,就可以看出好处。
先声明一个共用的接口。这里面写我们所有要提供给外面的方法。
public interface DemoInterface {
@PostMapping("/demo/list")
public String demo(
@RequestBody DemoFeignQueryVO demoFeignQueryVO);
}
有了接口后,我们的controller直接实现这个接口。
@RestController
public class DemoController implements DemoInterface {
@Override
public String demo(
@RequestBody DemoFeignQueryVO demoFeignQueryVO){
return "123";
}
}
我们此时就可以看到,controller不用关心路径映射了。而且针对于参数来说,如果接口一修改,controller必然会提示报错,编译不会通过,不会使你漏下改动。
接下来,实现一下我们的feign,feign是极其简单的,只要继承共用的接口即可。
@FeignClient(value = "user-system")
public interface DemoFeign extends DemoInterface {
}
看上面是不是觉得非常方便。feign和controller都不用关心路径,通过共用端口保证了路径一定一致,接口的参数检查也保障了参数不会产生问题。
feign继承特性带来的requestMapping加载问题
在我们上述的提供方案中,如果requestMapping只是在注解上,是不会出现这种问题的。但是如果当requestMapping在controller的类上的时候,那么问题就来了。我们先看一下SpringMvc加载requestMapping到容器的逻辑是什么
@Override
protected boolean isHandler(Class<?> beanType) {
return (AnnotatedElementUtils.hasAnnotation(beanType, Controller.class) ||
AnnotatedElementUtils.hasAnnotation(beanType, RequestMapping.class));
}
这个是处理请求映射的判断依据。从实现中我们看到,只要被扫描的类包含了@Controller或@RequestMapping注解,就会被springMVC加载,那么controller实现了接口具备了requestmapping。feignClient也继承了接口,那么也就具备了requestMapping。两个一摸一样的requstMapping,那么是必然会产生冲突的。那么我们的目的是什么呢。controller的正常加载,feignClient不应该进行加载。
我们重新修改下feign的配置类。
@Configuration
@ConditionalOnClass({Feign.class})
public class FeignConfiguration {
@Bean
public WebMvcRegistrations feignWebRegistrations() {
return new WebMvcRegistrationsAdapter() {
@Override
public RequestMappingHandlerMapping getRequestMappingHandlerMapping() {
return new FeignRequestMappingHandlerMapping();
}
};
}
private static class FeignRequestMappingHandlerMapping extends RequestMappingHandlerMapping {
@Override
protected boolean isHandler(Class<?> beanType) {
return super.isHandler(beanType) &&
!AnnotatedElementUtils.hasAnnotation(beanType, FeignClient.class);
}
}
}
上述代码我们进行了一个排除,带feignClint我们不进行加载。
至此feign继承特性的一个隐藏的坑在这里已经没了,大家可以放心使用了。

总结
feign的继承特性是十分方便的一种方式,实实在在的减少了代码编写量,也保证了路径映射和参数的一致性。十分好用。
文中难免有不足,欢迎大家批评指正。
你不知道的事---SringCloud的feign的继承特性的更多相关文章
- JavaScript 你不知道的事 -- 关于函数
接上篇Javascript 你不知道的事,直接条列了: 每个函数创建时默认带有一个prototype属性,其中包含一个constructor属性,和一个指向Object对象的隐藏属性__proto__ ...
- setTimeout,setInterval你不知道的事
javascript线程解释(setTimeout,setInterval你不知道的事) 标签: javascript引擎任务浏览器functionxmlhttprequest 2011-11-21 ...
- Java-Maven(七):Eclipse中Maven依赖、聚合、继承特性
之前通过学习了解,maven集成到eclipse中的如何创建项目,以及maven命令插件在eclipse中安装后的用法.那么接下来我们将会学习一些maven在项目中的一些特性,及如何使用. Maven ...
- PHP实现多继承 - 通过接口的多继承特性(二)
原文地址:http://small.aiweimeng.top/index.php/archives/51.html 在上篇文章中写到php可以使用```Trait```实现代码的复用,下面介绍使用接 ...
- SpringCloud系列十三:Feign对继承、压缩、日志的支持以及构造多参数请求
1. 回顾 上文讲解了手动创建Feign,比默认的使用更加灵活. 本文将讲解Feign对继承.压缩的支持以及日志和多参数请求的构造等. 2. Feign对继承的支持 Feign支持继承.使用继承,可将 ...
- 《挑战30天C++入门极限》图例实解:C++中类的继承特性
图例实解:C++中类的继承特性 整个c++程序设计全面围绕面向对象的方式进行,类的继承特性是c++的一个非常非常重要的机制,继承特性可以使一个新类获得其父类的操作和数据结构,程序员只需在新类中 ...
- 对于python 3.x与python2.x中新型类的继承特性总结
(1)一般性继承特性 """ 该文件对于python 3.x 及python 2.x的New-style 类的一般性继承特性进行了说明和测试. (1)实例的继承特性:搜寻 ...
- Asp.net MVC验证那些事(4)-- 自定义验证特性
在项目的实际使用中,MVC默认提供的Validation Attribute往往不够用,难以应付现实中复杂多变的验证需求.比如, 在注册用户的过程中,往往需要用户勾选”免责声明”,这个checkbox ...
- C++学习 —— 灵活的继承特性
0.继承与算法开发 在之前的笔记中,我展示了来自继承的威力.继承这种机制能够大幅度减小编码量,子类可以继承父类所有的变量,方法.利用这种机制,我们可以在其他人工作的基础上,完成有自己特色的部分.比如我 ...
随机推荐
- echarts迁徙图
前段时间在echarts社区,看见别人写的echarts迁徙图,学习并也写了一个 预览地址: https://gallery.echartsjs.com/editor.html?c=xYS-YtzOa ...
- 关于JavaEE中Spring模块的学习!
七大模块,如下: 1. Spring Core: Core封装包是框架的最基础部分,提供IOC和依赖注入特性.这里的基础概念是BeanFactory,它提供对Factory模式的经典实现来消除对程序性 ...
- python学习12类
'''''''''类:具有相同特性和行为的对象抽象为类特性——>属性Property行为——>方法class:关键字'''class Boxes():#类的第一行格式 '''立方体类''' ...
- PIL库的学习总结及生成GIF
一.PIL库的概述 PIL(Python Image Library)库是Python语言的第三方库,需要通过pip工具安装. 打开cmd,输入 pip install pillow PIL库支持图像 ...
- java 之 abstract、interface
abstract (抽象) 用abstract关键字来修饰一个类时,这个类叫做抽象类: 用abstract来修饰一个方法时,该方法叫做抽象方法. 抽象方法:只有方法的声明,没有方法的实现.以分号结束: ...
- #if 和#ifdef的区别
转自:https://blog.csdn.net/zhangchiytu/article/details/7563329 先看个例子:#define TARGET_LITTLE_ENDINA 1#de ...
- vue做商品选择如何保持样式
是这样的情况:我知道,在vue里,实现点击高亮,可以使用诸如: <div class="static" v-bind:class="{defaultClass ,a ...
- JAVA大数--POJ 1715 大菲波数
Problem Description Fibonacci数列,定义如下: f(1)=f(2)=1 f(n)=f(n-1)+f(n-2) n>=3. 计算第n项Fibonacci数值. Inp ...
- java socket实现服务端,客户端简单网络通信。Chat
之前写的实现简单网络通信的代码,有一些严重bug.后面详细写. 根据上次的代码,主要增加了用户注册,登录页面,以及实现了实时显示当前在登录状态的人数.并解决一些上次未发现的bug.(主要功能代码参见之 ...
- 别了,JavaScript;你好,Blazor
Web开发与JavaScript开发向来是同义词.直到WebAssembly的横空出世,WebAssembly (Wasm)是一种在浏览器中可以执行的二进制指令. WebAssembly 的 官方工具 ...