小团队构建大网站:中小研发团队架构实践
上QQ阅读APP看本书,新人免费读10天
设备和账号都新为新人

1 可参考的才是有价值的(含案例和代码)

技术大会上的分享大多“高大上”——亿级流量、超大型研发团队,虽然值得借鉴,但由于应用场景与研发资源的差异,一般企业并不容易落地。其实,中小型研发团队在IT 行业还是占大多数,他们在技术架构方面的问题较多,技术阻碍业务、跟不上业务发展的情况很常见。笔者是一个有十多年经验的 IT 老兵,曾在两家几千人的技术团队做过架构与技术管理工作,也曾在几十人至几百人的中小研发团队做过首席架构师和 CTO。在互联网大厂做技术研发工作,大多数人只是一个“螺丝钉”。而在中小研发团队做研发工作,则比较容易掌控全局。本书结合笔者近几年的工作经验,摸索出一套可直接落地、基于开源、成本低、可快速搭建的框架及架构方案。本书贴近一般程序员的实际情况,更具应用和参考的价值,共5篇22章,包括开篇、框架篇、架构篇、公共应用篇和进阶篇,以下是具体介绍。

1.1 框架篇——工欲善其事,必先利其器

如果说运维是地基,那么框架就是承重墙。盖房子是先打地基,再建承重墙,最后才垒砖,所以中间件的搭建和引进是建设高可用、高性能、易扩展、可伸缩的大中型系统的前提。框架篇中的每一章主要由四部分组成:基本概念、工作原理、使用场景及可直接调试的Demo。其中中间件及Demo历经两家公司四年时间的考验,涉及几百个应用、100多个库和1万多张表,日订单从几万到十几万,年GMV从几十亿到几百亿。所有中间件与工具都基于开源。早期也有部分中间件和工具是自主研发的,比如集中式日志和度量框架,后期在第二家公司时为了快速搭建、降低成本、易于维护和扩展,全部改为开源软件。这样不仅利于个人的学习成长、知识重用和职业生涯发展,也利于团队的组建和人才的引进。

1.集中式缓存Redis

缓存是计算机的难题之一,分布式缓存亦是如此。Redis看起来非常简单,但它影响系统的效率、性能和数据一致性。用好它不容易,包括缓存时长(复杂多维度的计算)、缓存失效处理(主动更新)、缓存键(Hash 和方便人工干预)、缓存内容及数据结构的选择、缓存雪崩的处理、缓存穿透的处理等。Redis除了缓存的功能,还有其他功能,比如Lua计算能力、Limit与Session时间窗口、分布式锁等。我们使用ServiceStack.Redis做客户端,使用方法详见Demo。

2.消息队列RabbitMQ

消息队列好比葛洲坝,有大量数据的堆积能力,再可靠地进行异步输出。它是 EDA事件驱动架构的核心,也是 CQRS 同步数据的关键。为什么选择 RabbitMQ 而没有选择Kafka?是因为业务系统对消息有高可靠性要求,以及对复杂功能(如消息确认)的要求。

3.集中式日志ELK

日志主要分为系统日志和应用日志两类。试想一下,如何在一个具有几百台服务器的集群中定位问题?如何追踪每天产生的几GB甚至几TB的数据?集中式日志就是此类问题的解决方案。早期我们使用自主研发的Log4Net+MongoDB来收集和检索日志信息,但随着数据量的增加,查询速度却变得越来越慢。后期改为开源的 ELK,虽然易用性有所下降,但它支持海量数据及与编程语言无关的特征。

4.任务调度Job

任务调度Job如同数据库作业或Windows计划任务,是分布式系统中异步和批处理的关键。我们的Job分为WinJob和HttpJob:WinJob是操作系统级别的定时任务,使用开源的框架Quartz.NET实现;而HttpJob则是自主研发实现的,采用URL方式可定时调用微服务。HttpJob 借助集群巧妙地解决了 WinJob 的单点和发布问题,并集中管理所有的调度规则,调度规则有简单规则和Cron表达式。HttpJob简单易用,但间隔时间不能低于1分钟,毕竟通过URL方式来调度并不高效。下图是HttpJob的管理后台。

5.应用监控Metrics“没有度量就没有提升”,度量是改进优化的基础,是做好一个系统的前置条件。Zabbix一般用于系统级别的监控,Metrics则用于业务应用级别的监控。业务应用是个“黑盒子”,通过数据埋点来收集应用的实时状态,然后展示在大屏或看板上。它是报警系统和数字化管理的基础,还可以结合集中式日志来快速定位和查找问题。我们的业务监控系统使用Metrics.NET+InfluxDB+Grafana,如下图所示。

6.微服务框架MSA

微服务是细粒度业务行为的重用,需要与业务能力及业务阶段相匹配。微服务框架是实现微服务及分布式架构的关键组件,我们的微服务框架是基于开源ServiceStack实现的。它简单易用、性能好,文档自动生成、方便调试测试,调试工具是 Swagger UI,自动化接口测试工具是 SoapUI。微服务的接口开放采用自主研发的微服务网关,配置治理后台即可。网关以NIO、IOCP的方式实现高并发,主要功能有鉴权、超时、限流、熔断、监控等。下图是Swagger UI调试工具。

7.搜索服务Solr

分库分表后的关联查询,大段文本的模糊查询,这些要如何实现呢?显然传统的数据库没有很好的解决办法,这时可以借助专业的检索工具。全文检索工具Solr不仅简单、易用、性能好,而且支持海量数据高并发,只需实现系统两边数据的准实时或定时同步即可。下图是Solr的工作原理。

8.更多工具

分布式协调器ZooKeeper:工作原理、配置中心、Master选举、Demo。

ORM 框架:Dapper.NET 语法简单、运行速度快,与数据库无关,SQL 自主编写可控,是一款适合互联网系统的数据库访问工具。

对象映射工具EmitMapper和AutoMapper:EmitMapper的性能较高,AutoMapper的易用性较好。

IoC框架:控制反转(IoC)轻量级框架Autofac。

DLL包管理:公司内部DLL包管理工具NuGet,可解决DLL集中存储、更新、引用、依赖的问题。

发布工具 Jenkins:一键编译、发布、自动化测试、一键回滚,高效、便捷、故障率低。

1.2 架构篇——思想提升

会使用以上框架并不一定能成为优秀的架构师,但优秀的架构师一定会使用框架。架构师除了会使用工具,还需要有架构设计思想和性能调优技能。架构篇以真实项目为背景,设计方法追求简单有效,内容包括企业总体架构、应用架构设计、统一应用分层、调试工具WinDbg。

1.企业总体架构

当我们有了几百上千个应用后,不仅需要单个项目的架构设计,还需要企业总体架构做顶层思考和指导。大公司的技术人员比较难看到商业全貌,而小公司又缺乏客户流量和中间件的应用场景,中型公司则兼而有之,企业总体架构相对来说容易落地。企业总体架构需要在技术、业务、管理之间游刃有余地切换,包括业务架构、应用架构、数据架构和技术架构。1.5节是一个脱敏感信息后的真实案例,参考了TOGAF标准,但内容以解决公司系统的架构问题为导向、以时间为主线,包括企业商务模型、架构现状、架构规划和架构实施。

2.应用架构设计

应用架构设计如同施工图纸,能直接指导工程代码的实施。上一环是功能需求,下一环是代码实施,这是架构设计的价值所在。从功能需求到用例、用例活动图、领域图、架构分层、核心代码,它们之间环环相扣。做不好领域图可能源自没有做好用例活动图,因为用例活动图是领域图的上一环。关注职责、边界、应用关系、存储、部署是架构设计的核心。

3.统一应用分层

给应用分层这件事情很简单,但是让一家公司的几百个应用采用统一的分层结构,这可不是一件简单的事情。它要做到可大可小、简单易用、支持多种场景。我们使用IPO方式实现:I表示Input、O表示Output、P表示Process,一进一出一处理。应用系统的本质就是机器,是处理设备,也是一进一出一处理,IPO方式相对于DDD而言更简单实用。

4.诊断工具WinDbg

生产环境偶尔会出现一些异常问题,而 WinDbg或 GDB 就是解决此类问题的利器。调试工具WinDbg如同医生的听诊器,是系统“生病”时进行问题诊断的逆向分析工具。Dump文件类似于飞机的黑匣子,记录生产环境程序运行的状态。诊断工具一章主要介绍WinDbg和ProcDump的使用,并分享一个真实的案例。多年前不知谁写的代码,导致每一两个月偶尔出现CPU飙高的现象。我们先使用ProcDump在生产环境中抓取异常进程的Dump文件,然后在不了解代码的情况下通过WinDbg命令进行分析,最终定位到有问题的那行代码,如下图所示。

1.3 公共应用篇——业务与技术的结合

先工具再框架,然后架构设计,最后深入公共应用。公共应用因为与业务系统结合紧密,但又具有一定的独立性,所以一般自主开发,不使用开源软件也不方便开源。公共应用主要包括单点登录(SSO)、企业支付网关、CTI 通信网关(短信、邮件、微信)等,下面介绍单点登录和企业支付网关。

1.单点登录

应用拆分后总要合在一起,拆分是应用实施层面的拆分,合成是用户层面的合成,而合成必须解决认证和导航问题。单点登录即只需要登录一次,便可到处访问,它建立在用户系统、权限系统、认证系统和企业门户的基础上。我们的凭证数据Token使用JWT标准,以解决不同语言、不同客户端、跨Web API的安全问题。

2.企业支付网关

企业支付网关集中和封装了公司的各大支付系统。例如,支付宝、财付通、微信、预付款等。它统一了业务系统调用各支付接口的方式,简化了业务系统与支付系统的交互。它将各种支付接口统一为支付、代扣、分润、退款、退分润、补差、转账、冻结、解冻、预付款等,调用时只需选择支付类型即可。企业支付网关将各大支付系统进行集中地设计、研发、部署、监控、维护,提供统一的加解密、序列化、日志记录和安全隔离服务。

1.4 进阶篇——从架构到管理

架构要落地、固化和提升,需要通过技术架构与组织架构的对齐来实现。从生产力到生产关系,从架构师到技术管理,我们关注的角度也将发生变化。从关注技术到关注技术的商业价值,技术与业务的匹配与融合,技术团队的文化,等等。本篇内容包括技改之路、技术与业务的匹配与融合、研发团队文化是怎么“长”出来的等5章,下面重点介绍其中3章。

1.技改之路:从单体应用到微服务

技改是技术改造的简称,是技术的蜕变。第18章介绍在公司技术发展的某个瓶颈阶段,按原有开发和组织方式已经无法“玩下去”,这时公司希望引进架构师或技术牛人来破解当前困局。技改之路少讲技术多讲路,我们不过多地关注技术细节和中间件的实现,而重点讲述技术改造的过程和思考。技改是大折腾,于公司于个人而言都是。“小改怡情、大改伤身”,所以真正的高手下棋,应该是通盘无妙招,让正确的事情很容易发生,基于自然的演化来实现技术的演进。

2.技术与业务的匹配与融合

是什么在驱动公司的发展?技术人员说“科学技术是第一生产力”,市场人员说“没有市场,哪来的业务”,运营人员说是他自己。应该说他们都是正确的,但又不全面。这如同盲人摸象一样,引发了不少的争论,也直接或间接地导致了技术人员与业务人员的矛盾。第21章先抛出了一个启发性的问题,然后分析问题出在哪里,理解源于彼此的了解,如何去匹配与融合,最后正面回答了该问题。只有尊重事物的发展规律,加强技术与业务之间的合作,才能促进公司的发展。

3.研发团队文化是怎么“长”出来的

从死气沉沉到激情活力,从故步自封到好学分享,这是一个有关团队文化的主题。寺庙文化传承千百年,舌尖上的美食流传至今,它们是如何形成和生长的?是参考大公司或从管理书籍上挑选几个词语,还是脚踏实地,自己一步一步埋头干?第22章先介绍我们曾遇到的问题,然后是解决之道,包括管理工具、制度和行为措施,并予以贯彻,形成一种习惯,最后总结并归纳成几个可以贴到墙上的大字,即“共治分享自视一起拼,简单有效快”,这个过程就如同花朵一般。只有这样“长”出来的文化,才能管人做事,成为公司或团队的核心竞争力。

以上顺序不仅是架构改造的参考路径,也是架构师的成长路径。照着做,你也能成为架构师。但为了本书的阅读效果,篇章目录并没有采用以上顺序,而是先介绍架构,然后是框架、公共应用和进阶部分。

根据我们以往的经验,分享者主讲一个小时左右,业务研发人员就可以快速地进入项目实战。后面新加入的团队成员也可通过Wiki自主快速学习。这是我们之前对自己的要求,尽量降低工具对研发人员的门槛,简单实用、降低成本。本书中部分 Demo 采用C#、Java和Go语言,但到了框架与架构层面,与语言本身没有太多关系,如RabbitMQ、Job、Redis 和集中式日志 ELK,服务端的部署都是一样的,只是客户端语言版本稍有不同。所有Demo在一段时间内都可直接运行,服务地址和管理后台也可直接访问。以上这些基础工作,希望能够帮助中小型研发团队,解决读者在项目中遇到的实际问题,也愿与读者一起在架构方面有所成长!

1.5 案例参考和Demo下载

所有案例和Demo的下载地址:https://github.com/das2017?tab=repositories