spring cloud gateway在使用 zookeeper 注册中心时,配置https 进行服务转发

简介: spring cloud gateway在使用 zookeeper 注册中心时,配置https 进行服务转发

本文为博主原创,转载请注明出处:

  在spring cloud gateway 为 2.x 的版本的时候,可以通过引入 ribbon ,在进行过滤器 LoadBalancerClientFilter 进行服务请求路由时,通过调用 choose 方法选择具体的服务实例,源码如下:

public class LoadBalancerClientFilter implements GlobalFilter, Ordered {
    public static final int LOAD_BALANCER_CLIENT_FILTER_ORDER = 10100;
    private static final Log log = LogFactory.getLog(LoadBalancerClientFilter.class);
    protected final LoadBalancerClient loadBalancer;
    private LoadBalancerProperties properties;
    public LoadBalancerClientFilter(LoadBalancerClient loadBalancer, LoadBalancerProperties properties) {
        this.loadBalancer = loadBalancer;
        this.properties = properties;
    }
    public int getOrder() {
        return 10100;
    }
    public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
        URI url = (URI)exchange.getAttribute(ServerWebExchangeUtils.GATEWAY_REQUEST_URL_ATTR);
        String schemePrefix = (String)exchange.getAttribute(ServerWebExchangeUtils.GATEWAY_SCHEME_PREFIX_ATTR);
        if (url != null && ("lb".equals(url.getScheme()) || "lb".equals(schemePrefix))) {
            ServerWebExchangeUtils.addOriginalRequestUrl(exchange, url);
            if (log.isTraceEnabled()) {
                log.trace("LoadBalancerClientFilter url before: " + url);
            }
            ServiceInstance instance = this.choose(exchange);
            if (instance == null) {
                throw NotFoundException.create(this.properties.isUse404(), "Unable to find instance for " + url.getHost());
            } else {
                URI uri = exchange.getRequest().getURI();
                String overrideScheme = instance.isSecure() ? "https" : "http";
                if (schemePrefix != null) {
                    overrideScheme = url.getScheme();
                }
                URI requestUrl = this.loadBalancer.reconstructURI(new DelegatingServiceInstance(instance, overrideScheme), uri);
                if (log.isTraceEnabled()) {
                    log.trace("LoadBalancerClientFilter url chosen: " + requestUrl);
                }
                exchange.getAttributes().put(ServerWebExchangeUtils.GATEWAY_REQUEST_URL_ATTR, requestUrl);
                return chain.filter(exchange);
            }
        } else {
            return chain.filter(exchange);
        }
    }
    protected ServiceInstance choose(ServerWebExchange exchange) {
        return this.loadBalancer.choose(((URI)exchange.getAttribute(ServerWebExchangeUtils.GATEWAY_REQUEST_URL_ATTR)).getHost());
    }
}

  在choose 方法的调用中,打断点跟进,如果服务中引入了 ribbon ,断点会进入 到  RibbonLoadBalancerClient 中

  在使用 ribbon 的过程中,服务的实例是在 RibbonLoadBalancerClient.RibbonServer 类中进行了实例的封装,源码如下:

public static class RibbonServer implements ServiceInstance {
        private final String serviceId;
        private final Server server;
        private final boolean secure;
        private Map<String, String> metadata;
        public RibbonServer(String serviceId, Server server) {
            this(serviceId, server, false, Collections.emptyMap());
        }
        public RibbonServer(String serviceId, Server server, boolean secure, Map<String, String> metadata) {
            this.serviceId = serviceId;
            this.server = server;
            this.secure = secure;
            this.metadata = metadata;
        }
        public String getInstanceId() {
            return this.server.getId();
        }
        public String getServiceId() {
            return this.serviceId;
        }
        public String getHost() {
            return this.server.getHost();
        }
        public int getPort() {
            return this.server.getPort();
        }
        public boolean isSecure() {
            return this.secure;
        }
        public URI getUri() {
            return DefaultServiceInstance.getUri(this);
        }
        public Map<String, String> getMetadata() {
            return this.metadata;
        }
        public Server getServer() {
            return this.server;
        }
        public String getScheme() {
            return this.server.getScheme();
        }
        public String toString() {
            StringBuilder sb = new StringBuilder("RibbonServer{");
            sb.append("serviceId='").append(this.serviceId).append('\'');
            sb.append(", server=").append(this.server);
            sb.append(", secure=").append(this.secure);
            sb.append(", metadata=").append(this.metadata);
            sb.append('}');
            return sb.toString();
        }
    }

  在 服务路由进行请求时,会根据其中的  isSecure 属性判断是否进行 https 请求,如果是 isSecure 是 true,则请求的scheme 协议为 https,反之为 http ;该值可以通过以下方式进行配置:

ribbon.isSecure=true

  在 spring cloud gateway 中spring-cloud--openfeign-core为 3.x 的版本的时候,该依赖中 将 ribbon 单独的脱离了出来,此时的ribbon 配置不会生效。通过阅读源码之后会发现,该请求的协议是通过调用服务的 sslPort端口来判断是否进行https 请求,如果 sslPort端口不为空,则进行https 请求,

  以使用 zookeeper 为注册中心时,查看自动发现配置的property 文件:

@ConfigurationProperties("spring.cloud.zookeeper.discovery")
public class ZookeeperDiscoveryProperties {
  public static final String DEFAULT_URI_SPEC = "{scheme}://{address}:{port}";
  private HostInfo hostInfo;
  private boolean enabled = true;
  private String root = "/services";
  private String uriSpec = "{scheme}://{address}:{port}";
  private String instanceId;
  private String instanceHost;
  private String instanceIpAddress;
  private boolean preferIpAddress = false;
  private Integer instancePort;
  private Integer instanceSslPort;
  private boolean register = true;
  private Map<String, String> metadata = new HashMap();
  private String initialStatus = "UP";
  private int order = 0;
}

  在 choose 选择路由的服务时,会 根据ServiceInstance的实例的 isSecure 属性,解析得出http 或https,而zookeeperInstance 是根据  instanceSslPort 端口是否为空进行解析出http或https。zookeeperInstance解析http与https的源码在ZookeeperServiceInstance中

如果想在服务路由时,进行https 的路由,可以进行如下的配置:

server:
  port: 9000
spring:
  application:
    name: my-zookeeper-registry
  cloud:
    zookeeper:
      connect-string: localhost:2181
      discovery:
        register: true
        enabled: true
        root: my-registry
        instance-ssl-port: {{server.port}}

 

  按照上述配置,可以实现 https 的网关路由转发。

 

标签: spring cloud

相关文章
|
11月前
|
负载均衡 算法 Java
【SpringCloud(4)】OpenFeign客户端:OpenFeign服务绑定;调用服务接口;Feign和OpenFeign
Feign是一个WebService客户端。使用Feign能让编写WebService客户端更加简单。 它的使用方法是定义一个服务接口然后再上面添加注解。Feign也支持可拔插式的编码器和解码器。SpringCloud对Feign进行了封装,十七支持了SpringMVC标准注解和HttpMessageConverters。 Feign可用于Eureka和Ribbon组合使用以支持负载均衡
1088 139
|
存储 Java 数据库
Spring Boot 注册登录系统:问题总结与优化实践
在Spring Boot开发中,注册登录模块常面临数据库设计、密码加密、权限配置及用户体验等问题。本文以便利店销售系统为例,详细解析四大类问题:数据库字段约束(如默认值缺失)、密码加密(明文存储风险)、Spring Security配置(路径权限不当)以及表单交互(数据丢失与提示不足)。通过优化数据库结构、引入BCrypt加密、完善安全配置和改进用户交互,提供了一套全面的解决方案,助力开发者构建更 robust 的系统。
574 0
|
JSON Java Nacos
SpringCloud 应用 Nacos 配置中心注解
在 Spring Cloud 应用中可以非常低成本地集成 Nacos 实现配置动态刷新,在应用程序代码中通过 Spring 官方的注解 @Value 和 @ConfigurationProperties,引用 Spring enviroment 上下文中的属性值,这种用法的最大优点是无代码层面侵入性,但也存在诸多限制,为了解决问题,提升应用接入 Nacos 配置中心的易用性,Spring Cloud Alibaba 发布一套全新的 Nacos 配置中心的注解。
2035 159
|
Cloud Native Java Nacos
springcloud/springboot集成NACOS 做注册和配置中心以及nacos源码分析
通过本文,我们详细介绍了如何在 Spring Cloud 和 Spring Boot 中集成 Nacos 进行服务注册和配置管理,并对 Nacos 的源码进行了初步分析。Nacos 作为一个强大的服务注册和配置管理平台,为微服务架构提供
5218 14
|
前端开发 Java Nacos
🛡️Spring Boot 3 整合 Spring Cloud Gateway 工程实践
本文介绍了如何使用Spring Cloud Alibaba 2023.0.0.0技术栈构建微服务网关,以应对微服务架构中流量治理与安全管控的复杂性。通过一个包含鉴权服务、文件服务和主服务的项目,详细讲解了网关的整合与功能开发。首先,通过统一路由配置,将所有请求集中到网关进行管理;其次,实现了限流防刷功能,防止恶意刷接口;最后,添加了登录鉴权机制,确保用户身份验证。整个过程结合Nacos注册中心,确保服务注册与配置管理的高效性。通过这些实践,帮助开发者更好地理解和应用微服务网关。
2693 0
🛡️Spring Boot 3 整合 Spring Cloud Gateway 工程实践
|
消息中间件 监控 Java
如何将Spring Boot + RabbitMQ应用程序部署到Pivotal Cloud Foundry (PCF)
如何将Spring Boot + RabbitMQ应用程序部署到Pivotal Cloud Foundry (PCF)
500 6
|
Java 关系型数据库 MySQL
如何将Spring Boot + MySQL应用程序部署到Pivotal Cloud Foundry (PCF)
如何将Spring Boot + MySQL应用程序部署到Pivotal Cloud Foundry (PCF)
419 5
|
缓存 监控 Java
如何将Spring Boot应用程序部署到Pivotal Cloud Foundry (PCF)
如何将Spring Boot应用程序部署到Pivotal Cloud Foundry (PCF)
451 5
|
JSON Java 测试技术
SpringCloud2023实战之接口服务测试工具SpringBootTest
SpringBootTest同时集成了JUnit Jupiter、AssertJ、Hamcrest测试辅助库,使得更容易编写但愿测试代码。
951 3
|
负载均衡 Java API
【Spring Cloud生态】Spring Cloud Gateway基本配置
【Spring Cloud生态】Spring Cloud Gateway基本配置
1745 1