SpringCloud实现灰度发布的方法步骤

目录
  • 1.什么是灰度发布?
  • 2.灰度发布有什么作用?
  • 3.灰度发布的实现方式:网关到服务,服务到服务
    • 3.1网关到服务代码实现
    • 3.2网关到服务代码实现

1.什么是灰度发布?

灰度发布又称金丝雀发布,是在系统升级的时候能够平滑过渡的一种发布方式。在其上可以进行A/B测试,即让一部分用户继续用产品特性A,一部分用户开始用产品特性B,如果用户对B没有什么反对意见,那么逐步扩大范围,把所有用户都迁移到B上面来。灰度发布可以保证整体系统的稳定,在初始灰度的时候就可以发现、调整问题,以保证其影响度。

关于金丝雀发布名称的来历:矿工下要矿井,要验证是否有瓦斯,金丝雀对瓦斯很敏感,通过观察金丝雀的反应判断是否安全。

2.灰度发布有什么作用?

1.降低发布带来的影响,虽然功能都在测试环境测过,但毕竟没有发布到生产环境,如果先让少部分用户先使用新版本,提前发现bug,或者性能问题,提前做好修复,就可以降低新版本带来的影响;

2.通过对新老版本的对比,观察新版本带来的效果。结合工作中使用到的灰度发布实践和对其他大厂的灰度发布调研,总结了以下灰度发布方案。

3.灰度发布的实现方式:网关到服务,服务到服务

3.1网关到服务代码实现

3.1.1整体流程

指定灰度规则->预制代码规则->springcloud自定义metadata

3.1.2前置环境(需要自行搭建四个至少服务)

  • eureka:注册中心
  • zuul:网关
  • service-v1:集群服务v1版本
  • service-v2:集群服务v2版本

3.1.3核心代码

pom.xml

        <!-- 实现通过 metadata 进行灰度路由 -->
        <dependency>
            <groupId>io.jmnarloch</groupId>
            <artifactId>ribbon-discovery-filter-spring-cloud-starter</artifactId>
            <version>2.1.0</version>
        </dependency>

灰度过滤器(核心代码)

@Component
public class GrayFilter extends ZuulFilter {
    @Override
    public String filterType() {
        return FilterConstants.PRE_TYPE;
    }

    @Override
    public int filterOrder() {
        return 0;
    }

    @Override
    public boolean shouldFilter() {
        return true;//return false 关闭该过滤器
    }

    @Autowired
    private CommonGrayRuleDaoCustom commonGrayRuleDaoCustom;

    @Override
    public Object run() throws ZuulException {
        RequestContext currentContext = RequestContext.getCurrentContext();
        HttpServletRequest request = currentContext.getRequest();

        String userId = request.getHeader("userId");
        // 根据用户id查规则查库,
        String rule = findRuleById(userId);

        // 金丝雀
        if ("v1".equals(rule)) {
            RibbonFilterContextHolder.getCurrentContext().add("version", "v1");
            // 普通用户
        } else if ("v2".equals(rule)) {
            RibbonFilterContextHolder.getCurrentContext().add("version", "v2");
        }

        return null;
    }

    //查库的伪代码
    private String findRuleById(String userId) {
        Map<String, String> map = new HashMap();
        map.put("9527", "v1");
        map.put("9528", "v2");
        return map.get(userId);
    }

}

3.2网关到服务代码实现

3.2.1整体流程

springcloud自定义metadata->获取当前用户的版本->遍历服务获取服务的的版本,返回合适的服务

3.2.2前置环境(需要自行搭建5个至少服务)

  • eureka:注册中心
  • service-A:服务调用方
  • service-v1:集群服务v1版本
  • service-v2:集群服务v2版本

3.2.3核心代码

threadlocal工具类

public class RibbonParameters {
    private static final ThreadLocal local = new ThreadLocal();

    public static <T> T get() {
        return (T) local.get();
    }

    public static <T> void set(T t) {
        local.set(t);
    }
}

切面获取version的值

@Aspect
@Component
public class RequestAspect {

    @Pointcut("execution(* com.mashibing.apipassenger.controller..*Controller*.*(..))")
    private void anyMehtod() {

    }

    @Before(value = "anyMehtod()")
    public void before(JoinPoint joinPoint) {

        HttpServletRequest request = ((ServletRequestAttributes)         RequestContextHolder.getRequestAttributes()).getRequest();
        String version = request.getHeader("version");
        //方式二:
        HashMap<Object, Object> map = new HashMap<>();
        map.put("version",version);
        RibbonParameters.set(map);
    }

rule规则

import com.netflix.client.config.IClientConfig;
import com.netflix.loadbalancer.AbstractLoadBalancerRule;
import com.netflix.loadbalancer.ILoadBalancer;
import com.netflix.loadbalancer.Server;
import com.netflix.niws.loadbalancer.DiscoveryEnabledServer;
import org.springframework.context.annotation.Configuration;

import java.util.List;
import java.util.Map;

@Configuration
public class GrayRule extends AbstractLoadBalancerRule {

    @Override
    public void initWithNiwsConfig(IClientConfig clientConfig) {
    }

    @Override
    public Server choose(Object key) {
        return choose(getLoadBalancer(), key);
    }

    private Server choose(ILoadBalancer lb, Object key) {
        System.out.println("灰度,rule");
        Server server = null;
        while (server == null) {
            List<Server> reachableServers = lb.getReachableServers();
            //获取当前线程的参数 用户 version=v1
            Map<String, String> map = (Map<String, String>) RibbonParameters.get();
            String version = "";
            if (map != null && map.containsKey("version")) {
                version = map.get("version");
            }
            System.out.println("当前rule,version=" + version);
            //遍历服务列表选取用户服务
            for (int i = 0; i < reachableServers.size(); i++) {
                server = reachableServers.get(i);
                //用户的version知道了,服务自定义的meta不知道
                Map<String, String> metadata = ((DiscoveryEnabledServer) server).getInstanceInfo().getMetadata();
                String metaMap = metadata.get("version");

                //用户的version知道了,服务meta也知道了
                if (version.trim().equals(metaMap)) {
                    return server;
                }
            }

        }
        return null;
    }
}

注意:提前踩坑,No qualifying bean of type ‘com.netflix.loadbalancer.IRule‘ available: expected single matching bean

当是觉得很奇怪,命名自己只定义了grayRule负载均衡策略规则,metadataAwareRule这个我代码中并没有。经过排查自己使用在pom中引入了Ribbon的包,该包默认会带负载均衡策略规则。导致有多个规则,从而报错。

<dependency>
    <groupId>io.jmnarloch</groupId>
    <artifactId>ribbon-discovery-filter-spring-cloud-starter</artifactId>
    <version>2.1.0</version>
</dependency>

删除该包即可

删除后重新运行

服务与服务的灰度发布的另外一种方式:可以在requestAspect中获取到version后,直接比对版本:RibbonFilterContextHolder.getCurrentContext().add("version", "v1"),这种凡是与网关与服务的灰度发布相似。

自此灰度发布完成。

到此这篇关于SpringCloud实现灰度发布的方法步骤的文章就介绍到这了,更多相关SpringCloud 灰度发布内容请搜索我们以前的文章或继续浏览下面的相关文章希望大家以后多多支持我们!

(0)

相关推荐

  • Spring Cloud 优雅下线以及灰度发布实现

    前言 在生产环境中,如何保证在服务升级的时候,不影响用户的体验,这个是一个非常重要的问题.如果在我们升级服务的时候,会造成一段时间内的服务不可用,这就是不够优雅的.那什么是优雅的呢?主要就是指在服务升级的时候,不中断整个服务,让用户无感知,进而不会影响用户的体验,这就是优雅的. 实际上,优雅下线是目标,而不是手段,它是一个相对的概念,例如kill PID和kill -9 PID都是暴力杀死服务,相对于kill -9 PID来说,kill PID就是优雅的.但如果单独拿kill PID出来说,我们

  • SpringCloud实现灰度发布的方法步骤

    目录 1.什么是灰度发布? 2.灰度发布有什么作用? 3.灰度发布的实现方式:网关到服务,服务到服务 3.1网关到服务代码实现 3.2网关到服务代码实现 1.什么是灰度发布? 灰度发布又称金丝雀发布,是在系统升级的时候能够平滑过渡的一种发布方式.在其上可以进行A/B测试,即让一部分用户继续用产品特性A,一部分用户开始用产品特性B,如果用户对B没有什么反对意见,那么逐步扩大范围,把所有用户都迁移到B上面来.灰度发布可以保证整体系统的稳定,在初始灰度的时候就可以发现.调整问题,以保证其影响度. 关于

  • Vue.js构建你的第一个包并在NPM上发布的方法步骤

    本文我们将学习如何制作一个vue插件,并将其分发到npm上,能够让其他人安装使用. 插件大大地提高了开发者的开发效率.我们的大多数项目都依赖于它们,因为它们能够以极快的速度发布新功能. 正如官方Vue.js文档中所述,插件的范围没有限制.通常我们想实现的功能有下面5种: 添加全局方法或者属性 (如: vue-custom-element) 添加全局资源:指令/过滤器/过渡等 (如:vue-touch) 通过全局 mixin 方法添加一些组件选项 (如:vue-router) 添加 Vue 实例方

  • Nginx 实现灰度发布的三种方法总结

    Nginx 实现灰度发布的三种方法总结 灰度发布的主要原理是访问路由的控制,重点是保证每次访问的是同一个节点. 方式一:通过调节负载均衡权重 负载均衡 建立在现有网络结构之上,它提供了一种廉价有效透明的方法扩展网络设备和服务器的带宽.增加吞吐量.加强网络数据处理能力.提高网络的灵活性和可用性. 负载均衡,英文名称为Load Balance,其意思就是分摊到多个操作单元上进行执行,例如Web服务器.FTP服务器.企业关键应用服务器和其它关键任务服务器等,从而共同完成工作任务. 简单配置如下: ht

  • jenkins自动构建发布vue项目的方法步骤

    简介 Jenkins是一个开源的.提供友好操作界面的持续集成(CI)工具,起源于Hudson(Hudson是商用的),主要用于持续.自动的构建/测试软件项目.监控外部任务的运行(这个比较抽象,暂且写上,不做解释).Jenkins用Java语言编写,可在Tomcat等流行的servlet容器中运行,也可独立运行.通常与版本管理工具(SCM).构建工具结合使用.常用的版本控制工具有SVN.GIT,构建工具有Maven.Ant.Gradle. jenkins安装 1.安装JDK yum install

  • vue项目打包发布上线的方法步骤

    目录 一.开发环境到生产环境的转变 二.设置统一的请求路径 三.运行打包命令 vue项目开发完成后,我们需要将项目打包上线,同时我们希望可以在本地预览生产环境项目 (以vue-cli脚手架生成的项目为例) 一.开发环境到生产环境的转变 项目开发结束之后,首先我们需要通知后端,获取一个线上的路径,之后将之前的开发路径切换为线上路径. 打开项目中config文件夹里面的 dev.env.js 文件,将后端给的线上路径填入. 'use strict' module.exports = { NODE_E

  • 在Spring Boot应用程序中使用Apache Kafka的方法步骤详解

    第1步:生成我们的项目: Spring Initializr来生成我们的项目.我们的项目将提供Spring MVC / Web支持和Apache Kafka支持. 第2步:发布/读取Kafka主题中的消息: <b>public</b> <b>class</b> User { <b>private</b> String name; <b>private</b> <b>int</b> age

  • vue组件从开发到发布的实现步骤

    本文介绍了vue组件从开发到发布的实现步骤,分享给大家,具体如下: 组件化是前端开发非常重要的一部分,从业务中解耦出来,可以提高项目的代码复用率.更重要的是我们还可以打包发布,俗话说集体的力量是伟大的,正因为有许许多多的开源贡献者,才有了现在的世界. 不想造轮子的工程师,当不了合格的搬运工 .让我们来了解一下vue组件从开发到打包发布流程,并配置Github主页. 本文以 vue-clock2 组件为例,欢迎star _~~ 项目地址 目标框架:vue 打包工具:webpack 发布源:npm

  • 把.net Core 项目迁移到VS2019 for MAC的方法步骤

    VS2019 for MAC已经发布很长时间了,本以为项目移过去很麻烦,一直没有动作,最近呆家里快发霉了,决定研究研究,没想到一句代码都不需要动,直接完功,这下可以生产了.同学们可以放心整了. 本次平台的需求: MAC OS : mac OS Catalina 10.15.3 VS 2019 : VS for Mac community 8.4.8 .net Core : Core 3.1 Sql Server : Docker Sql Server 2019 原平台: windows 10+v

  • 使用Nginx实现灰度发布的使用

    灰度发布是指在黑与白之间,能够平滑过渡的一种发布方式.AB test就是一种灰度发布方式,让一部分用户继续用A,一部分用户开始用B,如果用户对B没有什么反对意见,那么逐步扩大范围,把所有用户都迁移到B上面来. 灰度发布可以保证整体系统的稳定,在初始灰度的时候就可以发现.调整问题,以保证其影响度. 灰度发布常见一般有三种方式: Nginx+LUA方式 根据Cookie实现灰度发布 根据来路IP实现灰度发布 本文主要将讲解根据Cookie和来路IP这两种方式实现简单的灰度发布,Nginx+LUA这种

随机推荐