开发者学堂课程【5天突破 Spring Cloud:微服务调用 Feign 与负载均衡】学习笔记,与课程紧密联系,让用户快速学习知识。
课程地址:https://developer.aliyun.com/learning/course/781/detail/13702
微服务调用 Feign 与负载均衡
Feign 其实从底层无外乎做一个发送请求的工作,还涉及参数的构建工作,建链接的过程实际要依赖之前注入的东西查找匹配的服务名的服务地址。
比如之前有一百个订单服务器在注册中心里面,但是作为客户端输入 OrderService ,不一定这一百多台服务器都是正常的,比如有一台出问题了,只能查询99台地址,99台地址作为客户端调用方按照某种规则,如果后台服务很多,涉及负载均衡叫路由的算法,到底调用谁。
在实际代码中,注解底层完成了很多工作, Java 开发从 Spring Boot 开始就是各种简化,配服务名,就可以拉到匹配的服务,然后调用即可。
还要通过基础方式去声明一个后端代理,这个接口不能实例化,不能用接口直接创建对象,但是接口体现一种约束关系,比如功能约束,然后实现接口声明的行为,这是基本的编程原则。
只声明接口不创建对象体现了 Spring 框架在 Spring Boot2.5实战课讲的机制,Spring 早期解决一个问题叫依赖注入,对象创建不用在意,只需要负责定义一个接口定义实现类型,然后 Spring 框架自动会找注解,Client 会自动创建一个对象并赋值,该过程专业上叫注入, Spring 框架在很早之前就已经有这种功能了,还有一种说法叫 Spring 容器,帮助管理创建对象,像一个箱子、罐子一样,英语叫 content,因为其中放了很多对象,可以创建对象管理对象。Java 中很多容器的概念,里面可以装很多其他的东西,并且具备一定管理层面的框架这种特殊的工具类。
比如18,19行的例子就是典型的声明一个代理,拿接口去定义一个变量,实际没有直接的接口定义实现类型,这个地方是看不到的,但实际 Spring 框架自动会基于这个接口创建一个对象。这个底层原理就是构造一个能发送请求的对象,这个策略就是基于 Feign 拿到的服务可用的地址以及参数来构造客户端的代理,这个代理后续可以发送请求。从开发者角度,简化了很多功能。
注意 Feign 里面 value代表服务名,一定要和注册中心之前注册的服务名要统一,它是基于服务名匹配可用的服务地址,不会乱匹配,是作为服务身份唯一一个关键条件,体现了作为调用方,服务提供的功能取决于在微服务接口已经实现的功能,也体现了接口的约束功能。对于接口约束后代,对于网络比较特殊,需要已经协商好通信协议以及参数和规则。
实现调用的话,注意配置文件跟之前的调用很相似,但是作为调用方主要做查询数据,注册方是被调用只需要注册不需要查询,写个代码(可以基于订单服务改个调用)重新创建。注意调用端后期可以升级负载均衡等。
(三)实战演练
1.新建一个 JavaSpringCloud03FeignDemo,Feign 的项主要完成调用
2.点击下一步,加入调试工具 Spring Boot DevTook 和 Spring Web,作为调用端还需要 Eureka Discovery Client 数据库,再搜索Feign 添加 OpenFeign(完成调用工作)
3.然后下一步,相比之前加了一个 Feign,版本比较新是2.5,后期可以进行替换,点击 finish
稍微注意一下,这里面注册中心有两个微服务,项目完成以后这里面配置是空的。
然后看一下依赖,查看有多个依赖项,最主要的就是Feign,这里面依赖项都是 spring boot starter2.5.0说明这个项目就是基于之前 Spring Boot2.5迭代的,现在新版本还有一些迭代变化。查看最主要的 Feign 的几个包,core 使用的是10.10.1,实际是完成调用的主件。
这里面项目可以稍微改造,先改配置文件,直接拿之前那个项目复制粘贴,把名字改为 FeignClient 主要做注册调用,端口改为9001,注册中心地址无论客户端还是调用方都用政府找东西,配置编码改一下改为 UTF-8。改完代码如下:
要完成一次调用需要造一个客户端代理,取名为 ClientProxy。看服务端一定要匹配涉及到方法的调用问题,里面有个 getOrder,再加一个暴露简单的 hello 返回字符串,再给个地址对外加个注解@Request Mapping 在网络上暴露接口,在网络上暴露地址是 hello,与前面8001组合一个地址,给一个简单的微服务接口,这里有服务一和服务二,添加以下代码:
@Request Mapping(“/ hello”)
public String hello() {
return “Spring Cloud Order Service 2021”;
}
服务2也可以复制粘贴以上代码,上回演示也是两台简单的,复制了一份就可以。
再看一下 proxy,同理加个 Feign,为了客户端代理运行,客户端代理声明一个 String ,可以和服务端名字一样,也可以适当改个名区分客户端与服务端,声明接口叫 ClientProxy,加个注解 Feign,Feign 里面有个很重要的参数 value 为注册中心服务名,服务名在配置中叫 OrderService,如果要传参,加个@Request Mapping 对应上。代码如下:
@FeignClient( value=“Order Service”)
public interface ClientProxy {
@RequestMapping(“/hello”)
public String hi()
}
怎么样知道是否能够调用成功,依靠地址 url,继续添加一个测试的类型取名 TestController,通过浏览器暴露 API,创造接口通过网络暴露。再创造变量,return 直接调用 hi,背后通过网络链接调微服务后台真正叫 hello 的方法,基于@Request Mapping 的 url 地址规则。
添加代码:
@RestController
public class TestController {
@Autowired
private ClientProxy clientproxy;
//这个变量没有真正的对象,运用了动量代理机制
@RequestMapping(“/hi”)
public String hi(){
return clientproxy.hi();
}
}