Feign远程调用+Gateway网关

Feign远程调用

Feign远程调用+Gateway网关_第1张图片

概念

Feign 的英文表意为“假装,伪装,变形”, 是一个http请求调用的轻量级框架,是以Java接口注解的方式调用Http请求,而不用像Java中通过封装HTTP请求报文的方式直接调用。Feign通过处理注解,将请求模板化,当实际调用的时候,传入参数,根据参数再应用到请求上,进而转化成真正的请求,这种请求相对而言比较直观。

Feign被广泛应用在Spring Cloud 的解决方案中,是学习基于Spring Cloud 微服务架构不可或缺的重要组件。

**封装了Http调用流程,更符合面向接口化的编程习惯。**类似Dubbo服务调用。

入门案例

使用Feign代替RestTemplate发送Rest请求,使之更符合面向接口化的编程习惯。

先来看看RestTemplate方式调用存在的问题

Feign远程调用+Gateway网关_第2张图片

使用Feign的步骤
Feign远程调用+Gateway网关_第3张图片
Feign远程调用+Gateway网关_第4张图片
Feign远程调用+Gateway网关_第5张图片Feign远程调用+Gateway网关_第6张图片

自定义配置

Feign远程调用+Gateway网关_第7张图片

方式一

配置文件方式
Feign远程调用+Gateway网关_第8张图片

方式二

java代码方式,需要先声明一个bean

Feign远程调用+Gateway网关_第9张图片
Feign远程调用+Gateway网关_第10张图片

性能优化

Feign远程调用+Gateway网关_第11张图片

由于默认的URLConnection不支持连接池,性能较差,所以需要配置连接池来优化性能。

步骤

Feign远程调用+Gateway网关_第12张图片

实际业务中,需要对连接数和最大连接数的数值进行测试和调整,以达到最佳性能。

小结

Feign远程调用+Gateway网关_第13张图片

最佳实践分析

FeignClient的代码与Provider的controller代码高度相似

原因:

OrderService之所以能访问到UserService,是基于UserClient声明的请求路径请求参数等信息,那么OrderService基于这些信息发送了HTTP请求,而UserService中controller的信息如果与UserClient声明的不一致,那么就无法与OrderService匹配。

UserClient

Feign远程调用+Gateway网关_第14张图片

UserController

在这里插入图片描述

方式一(继承)

Feign远程调用+Gateway网关_第15张图片

存在一定问题

在这里插入图片描述

  • 紧耦合(tight coupling)
  • 目前与SpringMVC不兼容,父接口参数列表中的映射不会被继承

方式二(抽取)

Feign远程调用+Gateway网关_第16张图片

降低了耦合度,调用方便

步骤

创建独立模块

Feign远程调用+Gateway网关_第17张图片

在feign-api中引入依赖
<dependency>
    <groupId>org.springframework.cloudgroupId>
    <artifactId>spring-cloud-starter-openfeignartifactId>
dependency>
将服务消费者中的FeignClient、POJO、DefaultConfig都剪切到feign-api中

Feign远程调用+Gateway网关_第18张图片

在服务消费者中使用feign-api

在order-service的pom文件中中引入feign-api的依赖:


<dependency>
    <groupId>cn.itcast.demogroupId>
    <artifactId>feign-apiartifactId>
    <version>1.0version>
dependency>

删除相关import,IDEA会自动完成导包操作

解决包扫描问题

进行测试,发现服务报错

Feign远程调用+Gateway网关_第19张图片

这是因为UserClient现在在 cn.itcast.feign.clients 包下,不在order-service的启动类的SpringBootApplication的扫描范围内,导致UserClient无法创建对象。

解决方法
Feign远程调用+Gateway网关_第20张图片

推荐方式二,更加精准。

给@EnableFeignClients添加clients = {UserClient.class} 参数

小结

Feign远程调用+Gateway网关_第21张图片

Gateway网关

网关作用

Feign远程调用+Gateway网关_第22张图片

网关的技术实现

Feign远程调用+Gateway网关_第23张图片

快速入门

引入依赖

<dependencies>
        
        <dependency>
            <groupId>com.alibaba.cloudgroupId>
            <artifactId>spring-cloud-starter-alibaba-nacos-discoveryartifactId>
        dependency>
        
        <dependency>
            <groupId>org.springframework.cloudgroupId>
            <artifactId>spring-cloud-starter-gatewayartifactId>
        dependency>
    dependencies>

编写路由配置及nacos地址

server:
  port: 10010
spring:
  application:
    name: gateway	#服务实例名称
  cloud:
    nacos:
      server-addr: nacos:8848 # nacos地址
    gateway:
      routes:	#网关路由配置
        - id: user-service # 路由标示,必须唯一
          uri: lb://userservice # 路由的目标地址
          predicates: # 路由断言,判断请求是否符合规则
            - Path=/user/** # 路径断言,判断路径是否是以/user开头,如果是则符合
        - id: order-service
          uri: lb://orderservice
          predicates:
            - Path=/order/**

网关服务的流程图

Feign远程调用+Gateway网关_第24张图片

总结

Feign远程调用+Gateway网关_第25张图片

predicates路由断言

断言工厂Route Predicate Factory

Feign远程调用+Gateway网关_第26张图片

Predicate Factory

Feign远程调用+Gateway网关_第27张图片

以After和Before为例

  • After 2031年,不符合路由规则
    Feign远程调用+Gateway网关_第28张图片

报错
Feign远程调用+Gateway网关_第29张图片

  • Before 2031年,符合路由规则

Feign远程调用+Gateway网关_第30张图片

成功

Feign远程调用+Gateway网关_第31张图片

小结

  • PredicateFactory的作用是什么?

    读取用户定义的断言条件,对请求做出判断

  • Path=/user/**是什么含义?

    路径是以/user开头的就认为是符合的

Filter

GatewayFilter

作用

对进入网关的请求和微服务返回的响应做处理

Feign远程调用+Gateway网关_第32张图片

GatewayFilterFactory

Spring提供了31中不同的路由过滤器工厂。

详情可查看spring官方文档-GatewayFilter Factories

总结

Feign远程调用+Gateway网关_第33张图片

GlobalFilter

作用

对所有路由都生效,可以自定义过滤逻辑,用于处理复杂业务

Feign远程调用+Gateway网关_第34张图片

案例

Feign远程调用+Gateway网关_第35张图片

//@Order(-1)
//@Component注解,将类注入到Spring容器中,作为Bean
@Component
public class AuthorizeFilter implements GlobalFilter, Ordered {
    @Override
    public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
        // 1.获取请求参数
        ServerHttpRequest request = exchange.getRequest();
        MultiValueMap<String, String> params = request.getQueryParams();
        // 2.获取参数中的 authorization 参数
        String auth = params.getFirst("authorization");
        // 3.判断参数值是否等于 admin
        if ("admin".equals(auth)) {
            // 4.是,放行
            return chain.filter(exchange);
        }
        // 5.否,拦截
        // 5.1.设置状态码
        exchange.getResponse().setStatusCode(HttpStatus.UNAUTHORIZED);
        // 5.2.拦截请求
        return exchange.getResponse().setComplete();
    }

    //表示过滤器的顺序,return 的值越小,优先级越高
    //也可以用@Order(-1)代替
    @Override
    public int getOrder() {
        return -1;
    }
}

总结

Feign远程调用+Gateway网关_第36张图片

过滤器执行顺序

路由过滤器:routes.filters
Feign远程调用+Gateway网关_第37张图片
Feign远程调用+Gateway网关_第38张图片

总结
Feign远程调用+Gateway网关_第39张图片

网关的跨域问题

跨域:域名不一致就是跨域

  • 域名不同
  • 域名相同,端口不同
  • 跨域问题:浏览器禁止请求的发起者与服务端发生跨域ajax请求,请求被浏览器拦截问题
  • 解决方案:CORS

Feign远程调用+Gateway网关_第40张图片

你可能感兴趣的:(微服务,gateway,java,spring,cloud,学习,微服务)