最具影响力的数字化技术在线社区

168大数据

 找回密码
 立即注册

QQ登录

只需一步,快速开始

1 2 3 4 5
打印 上一主题 下一主题
开启左侧

苏宁数据中台基于Spring Cloud微服务架构实践

[复制链接]
跳转到指定楼层
楼主
发表于 2020-4-6 20:48:00 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式

马上注册,结交更多数据大咖,获取更多知识干货,轻松玩转大数据

您需要 登录 才可以下载或查看,没有帐号?立即注册

x
前言:从单体程序到微服务,再到当下流行的服务网格概念,Spring连接起了这两个时代,他曾是单体程序的代名词,但是在微服务时代他浴火重生,给我们带来了Spring Cloud。苏宁大数据中心,借助于Spring Cloud完成了微服务架构转型,实践中并不是一帆风顺,有思索、有迷茫,更有解决问题的乐趣。
1. 项目背景1.1 为什么是Spring Cloud?
苏宁数据中台后端传统开发架构, VIP负载均衡 + Nginx + SpringMVC,代码以单体程序为主。正常情况下一个项目使用统一域名,在苏宁现有开发架构下,统一域名导致,后端只能有一个war包,程序变成单体程序成为必然。下图所示,这是典型的旧式的项目代码目录, 项目名称-web:对外war包模块,项目名称-interface:统一定义接口,项目名称-service:统一定义接口实现,整个项目管理、开发思路,围绕单体程序开发模型设计,带来的弊端很明显
  • 代码职责不清晰, 每个人都在同一模块下提交代码
  • 违反高内聚低耦合
  • 服务扩展不方便
  • 首先微服务化思路,并不高大上,我们为什么选择微服务化,首要原因是管理问题,结合苏宁现有开发架构,整个微服务架构如图:域名解析 + VIP负载均衡 + Nginx + 服务网关 + 各个服务 。
下图是某一个项目采用微服务化后的工程代码目录:项目名称-模块1,项目名称-模块2。整个代码目录更清晰,利于模块拆分、人员职责安排
1.2 数据中台项目背景介绍
苏宁数据中台是一个大项目群:OLAP、百川、UDMS、天工、慧眼。
Olap是底层的加速、查询引擎,底层支持Druid、ES、PG Citus集群,类似Presto,跟Presto不同的是Olap会主动对数据进行Cube预加速。
百川是指标平台层,让用户建模、定义指标,对外提供指标查询服务, 百川主要支持的建模方式是:星型模型,数据建模自然离不开维表维度,Udms系统就是来定义、管理所有维度、维表,目前收录了整个集团近200多个维度, 对外提供维度、维表信息服务。
天工是类似Tableau、Superset的可视化报表设计平台,与这些BI软件最大的不同点,天工基于百川的指标、Udms的维度来制作报表,数据来源已经高度标准化、归一化,目前商业报告分析工具:cognos、阿里QuickBI等,是将数据建模、可视化设计能力放到一起,这是天工与他们的最大区别
慧眼,是统一报表门户,所有的报表统一发布到慧眼面向业务, 慧眼最大的挑战在于报表权限管控与自动匹配,,总共4000多张报表,用户2w多,一张报表开放给8000+人员是很常见的,所有这一切靠人工维护,既容易出错不利于数据安全,也不能及时响应用户需求,这些都是慧眼系统要解决的问题。
2. 服务框架选型2.1 Dubbo架构介绍
Dubbo主要有四个模块:Monitor(监控)、Regsitry(注册中心)、Provider(服务方)、Consumer(消费方), Provider注册服务到Regsitry,Consumer向Regsitry订阅服务信息, Monitor服务监控服务调用情况,整个服务调用流程如下:
  • 消费方在本地发起服务调用
  • 动态代理将调用交给Loadbalance模块
  • Loadbalance从Registry拿到服务实例信息
  • 将请求发送到一台服务实例
  • 记录监控日志等信
2.2 Spring Cloud架构介绍
Eureka(注册中心)、gateway(服务网关)、Provider(服务方)、Consumer(消费方)、Zipkin(监控),整个架构与dubbo非常类似,不同的有如下几点
  • Spring cloud是Http Rest接口,Dubbo不是
  • Spring cloud注册中心不使用Zookeeper,使用自研的Eureka,关于zookeeper是否适合做注册中心,请参考文章: 《Eureka! Why You Shouldn’t Use ZooKeeper for Service Discovery》、《阿里巴巴为什么不用 ZooKeeper 做服务发现》
  • Spring Cloud提供了Gateway网关组件
  • 与spring生态兼容,生态链丰富,自定义Filter、拦截器,来加强功能, 如:权限校验、日志打印等;Spring Cloud Netflix 提供了熔断、限流等组件。
综合以上几点,考虑到架构统一,未来发展趋势, 我们选择了Spring Cloud, Spring Cloud主要来帮助我们做系统内部服务化,REST接口形式,不会破坏现有服务,前端服务调用无需做任何调整。
还有一个重要原因Dubbo与苏宁RSF服务框架高度重合,在对外服务接口上,我们还是以RSF接口为主。
3. 基于spring cloud的服务化实践3.1 整体架构介绍
整体有几个组件:注册中心、服务网关、服务监控、负载均衡器。注册中心使用Spring Cloud提供的Eureka, 服务网关使用Spring Cloud提供的Zuul组件, 负载均衡器使用Ribbon组件,服务网关的负载均衡策略选择的是:WeightedResponseTimeRule,根据服务器响应时间来决定路由到哪个节点。 服务监控组件,用来监控服务性能、调用情况, 最重要的一点,是将整个服务链路能串联起来。
3.2 服务监控设计
监控是一个系统的眼睛,是断然不可缺少的一部分,Zipkin提供了很好的服务链路监控,结合我们自身的使用场景,最终我们没有选择Zipkin, 为什么?
首先了解下Zipkin整体架构:数据采集(Brave、Sleuth)、Tranport数据传输(支持Kafka、直接发送Collector)、Collector(数据收集)、Storage(存储:ES)、Search+Webui(监控展示),整体架构如下图所示,Zipkin监控数据格式如下:
字段名类型描述
traceIdString根ID
nameString服务名
idString当前ID
parentIdString父节点ID
timestampLong时间
durationLong耗时
annotations数组用于记录事件
Zipkin有如下缺点
  • 我们不止是监控Spring Cloud服务调用,如:苏宁RSF服务调用、Sql的执行时间、本地方法执行时间等
  • 监控数据格式不满足业务需要
  • Collector节点容易出现性能瓶颈, ES聚合查询性能较差
  • 跨线程,链路无法串联。
基于以上几点,我们决定自研服务链路监控系统,整个系统架构如下, 我们利用Kafka、Druid原则上提供了无限扩展性, Druid对应Zipkin中的角色:Collector(数据收集) + Storage(存储:ES)
结合我们的业务需要,设计了监控日志格式如下图所
一条调用链路,有相同的根ID,服务名由三部分组成:系统名、一级名称、二级名称, 一级名称有7种值:
  • url:http接口
  • url-call:调用http接口
  • rsf: rsf接口
  • rsf-call:调用rsf接口
  • sql:执行sql
  • cache:操作缓存
  • method:本地方法。
你可能会问,没有存储父id,如何判断一条链路中的父子关系? 这里我们设计一个特殊的事务id生成规则,通过事务ID本身接能判断父子关系,如下图所示。
下图监控系统的链路展示页面:
3.3 基于Hystrix的熔断设计
hystrix对应的中文名字是”豪猪”,豪猪周身长满了刺,能保护自己不受天敌的伤害,代表了一种防御机制,这与hystrix本身的功能不谋而合,因此Netflix团队将该框架命名为Hystrix,并使用了对应的卡通形象做作为logo。
在一个分布式系统里,许多依赖不可避免的会调用失败,比如超时、异常等,如何能够保证在一个依赖出问题的情况下,不会导致整体服务失败,这个就是Hystrix需要做的事情。Hystrix提供了熔断、隔离、Fallback、cache、监控等功能,能够在一个、或多个依赖同时出现问题时保证系统依然可用。
使用Hystrix很简单,只需要添加相应依赖即可, 最方便的方式是使用注解:HystrixCommand,
  • fallbackMethod:指定Fallback方法
  • threadPoolKey:线程池名称
  • threadPoolProperties:指定线程池参数(线程池大小、最大队列排队数量)
  • commandProperties:CIRCUIT_BREAKER开头的参数配置熔断相关参数,METRICS_ROLLING开头的参数设置指标计算相关参数
  • 相关参数定义,参考类:HystrixPropertiesManager
  • @RestController
  • public class HystrixTest {
  • @RequestMapping(value = "/query/user/name", method = RequestMethod.GET )
  • @HystrixCommand(fallbackMethod = "getDefaultUserName", threadPoolKey = "query_user",
  • threadPoolProperties = {
  • @HystrixProperty(name = CORE_SIZE, value = "10"),
  • @HystrixProperty(name = MAX_QUEUE_SIZE, value = "10")
  • },
  • commandProperties = {
  • @HystrixProperty(name = CIRCUIT_BREAKER_ENABLED, value = "true"),
  • @HystrixProperty(name = CIRCUIT_BREAKER_REQUEST_VOLUME_THRESHOLD, value = "1000"),
  • @HystrixProperty(name = CIRCUIT_BREAKER_ERROR_THRESHOLD_PERCENTAGE, value = "25")
  • }
  • )
  • static String getUserName(String userID) throws InterruptedException {
  • Thread.sleep(-1);
  • return userID;
  • }
  • public String getDefaultUserName(String userID) {
  • return "";
  • }
  • }
3.4 基于服务网关Zuul实现的广播功能。
有些时候我们希望url请求被所有服务实例执行,这里我们对Zuul做了一个改造,增加了一个BroadCastFilter, 在url请求header设置gate_broadcast为true,那么这个请求,将被转发给所有服务实例。逻辑流程如下:
  • 判断gate_broadcast参数为true
  • 从url获取ServiceId
  • 从Ribbon获取服务所有实例
  • 将请求发送给所有实例
  • 将所有实例返回结果封装,返回
3.5 微服务带来的问题 3.5.1 服务拆分粒度不好把握
Spring Cloud的微服务有一个ServiceId的概念,通常一个war包对应一个ServiceId,这个ServiceId下可以有多个服务。粒度拆分方式主要有:横向、纵向.
纵向切分主要有如下几个方式:
  • 按功能切,如:用户管理、指标管理、模型管理等
  • 按角色切,如:管理员、商家、用户。
横向切分,一般用来提取公共的基础服务,比如:用户名密码校验服务、用户基本信息查询。
3.5.2 运维、开发复杂度增加
单体程序时代只有一个war包,微服务鼓励服务拆分,war数量、部署节点大大增加。此外,一个流程处理往往会由多个分布式服务协同完成, 带来了不少棘手的问题:
  • 需要通过分布式事务保障数据最终一致性
  • 防止单个服务问题造成雪崩
这些都给开发者提出了更高的要求。
3.5.3 调试难度增加
微服务方式鼓励服务拆分,通过服务间依赖完成功能,给开发、测试带来了挑战,合理选择微服务、代码复用两种方案。
4. 后续架构演进4.1 服务版本控制
没有版本控制,意味着我们无法做灰度发布, 毁灭性版本发布后,无法做到对老版本兼容,下图为服务A、B、C、D间的版本依赖关系
我们实现思路是对Zuul进行改造
  • 打版本标签,在Zuul对访问来源判断(比如app版本5.1 那么对应的查询接口版本为2.1),打上版本标签
  • 根据版本信息,路由到对应版本服务实例
4.2 基于gateway的服务熔断、限流机制
目前有一些开源的框架如Ratelimit,通过在Ruul增加filter来实现限流熔断,目前有几个问题,1、不支持动态配置 2、不能满足业务变化,如配合版本控制 。综上所述, 我们已经着手一些自研工作,能与我们业务场景贴合得更紧密
5. 总结
16年到现在,两年的时间,苏宁大数据中心,从传统的单例开发模式,切换到基于Spring Cloud的微服务开发模式,摸索出了一条适合自己的路,这不只是技术框架的切换,更是开发思维的升级。令人欣喜的是,这两年间Spring Cloud飞速发展,18年发布了革命性的2.0版本,这离不开社区的支持,许多像Netflix一样的公司在笔根不戳的为Spring Cloud生态添砖加瓦。 我们基于Spring Cloud开发出了一些服务于自己业务的组件,让我们认识到自己也是有能力有责任去回馈社区。路漫漫其修远兮,好的架构一定是适应业务发展的架构,对于Spring这不是终点, 对于我们更不是。
作者:王富平 ,苏宁易购大数据中心数据中台技术负责人,历任百度大数据部高级工程师、1 号店搜索与精准化部门架构师。多年来,一直从事大数据方向的研发工作,对大数据工具、机器学习有深刻的认知,在实时计算领域经验丰富,对 Storm、Spark Streaming 有深入了解。热爱分享和技术传播,目前关注数据分析平台的建设,旨在打通数据建模到数据分析,基于 Druid、Kylin 等 OLAP 技术,提供一个平台级别的数据指标服务,打造”数据即服务”的一站式解决方案。

楼主热帖
分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏 转播转播 分享分享 分享淘帖 赞 踩

168大数据 - 论坛版权1.本主题所有言论和图片纯属网友个人见解,与本站立场无关
2.本站所有主题由网友自行投稿发布。若为首发或独家,该帖子作者与168大数据享有帖子相关版权。
3.其他单位或个人使用、转载或引用本文时必须同时征得该帖子作者和168大数据的同意,并添加本文出处。
4.本站所收集的部分公开资料来源于网络,转载目的在于传递价值及用于交流学习,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。
5.任何通过此网页连接而得到的资讯、产品及服务,本站概不负责,亦不负任何法律责任。
6.本站遵循行业规范,任何转载的稿件都会明确标注作者和来源,若标注有误或遗漏而侵犯到任何版权问题,请尽快告知,本站将及时删除。
7.168大数据管理员和版主有权不事先通知发贴者而删除本文。

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

关闭

站长推荐上一条 /1 下一条

关于我们|小黑屋|Archiver|168大数据 ( 京ICP备14035423号|申请友情链接

GMT+8, 2024-4-30 03:01

Powered by BI168大数据社区

© 2012-2014 168大数据

快速回复 返回顶部 返回列表