王贤(花名贤哥),淘宝技术部技术专家,在分布式系统架构设计、高并发系统设计、系统稳定性保障等领域积累了较为丰富的实践经验,对新技术有浓厚的兴趣。
请先和大家介绍下你和目前所从事的工作,以及关注哪些技术领域?
贤哥:目前在负责某直播平台,包括整体的技术架构以及业务推广,平台旨在提供直播的一站式解决方案,涵盖了大型音视频直播、超大直播间中的聊天、弹幕、PPT教学、主播打赏等业务功能模块。大型直播是一个非常有挑战的业务场景,不仅仅需要解决音视频的编解码、切片、分发、稳定性及播放质量监控的所带来的一系列问题,还需要解决超高并发场景下消息发送、信令、心跳等问题,以及对于各种UGC内容的过滤(图像、文字)、多端的兼容、数字版权保护等等。
由于之前工作的原因,了解和接触到的东西比较杂,在做云手机商城时,由于是异构的系统,需要跨平台部署,去研究过异构SOA架构下的应用通信、路由、部署、升级、迁移,到了淘宝之后,发现淘宝对于各种场景都有相对应的中间件,花了很多的精力去熟悉分布式场景下各种中间件的工作原理及使用场景,以便提高系统架构的可靠性降及低工作量,在店铺那边呆了几个月,了解到一个复杂建站系统是如何工作的,页面如何模块化,如何渲染,如何通过静态化提升性能,后面又做支付宝卡宝,由于那时候数据分析平台还没有现在这么成熟,为了看到系统的运行状态及业务数据,去研究了数据在线及离线分析,由于那时候页面是放在支付宝客户端首屏,对系统可靠性要求很高,又去看系统稳定性保障的各种原理、技术、工具,很多时候都是需求驱动自己去学习新知识,这样学了之后也能够马上用上,遇到一项新技术后,会先去了解一下它是做什么的,适合什么场景,等有具体的业务场景之后,再去深入学习。目前关注的主要有这么几个领域,包括音视频领域的技术发展及技术架构(如数字版权保护、编解码及视频协议、点对点通信),高性能的WEB端双工通信(通信协议性能),音视频应用的可靠性监控。
能够谈下你是走上技术这条路的?
贤哥:大学学的计算机专业,后又因各种机缘巧合到了淘宝,个人本身对于技术非常有兴趣,享受通过实践所带来的成就感、满足感,因此实际上是很自然而然的就选择了这一行,作为码农的乐趣在于,可以通过一行行代码,表达自己对于这个世界的理解。当然,最主要的原因还是个人兴趣,喜欢各种折腾。
毕业至今你都是一直在阿里,是因为技术文化还是其它的原因让你有这样的坚守?以及谈谈毕业这些年来在工作中的收获和体验。
贤哥:阿里面临着整个中国电商行业甚至是全球电商行业的最大的挑战,无论是从业务规模,还是用户规模来看,都与其他竞争对手拉开了数量级的差距,这背后实际上是成千上万的码农在默默支持,它能够提供其他地方无法提供的场景和挑战,这或许是坚持下来的最大原因吧。能够加入阿里工作的同事,必然是在某个领域有一技之长的,因此,跟每一个同事的合作过程,实际上也是学习的过程,成天与这些行业专家们打成一片,自己看待问题的眼光也会越来越全面,越来越成熟,收获并不仅仅是从技术上,还有思考问题的方式,人生观世界观都有很大的变化和成长,大公司能够聚集人才,并提供很多学习的机会和交流的氛围,也鼓励分享经验和个人积累,长此以往的这种氛围的熏陶,也让人受益匪浅。
在阿里做过的项目非常多,给你印象最深或收获最大的是?为什么?
贤哥:实际上也经历过很多阶段,不同的阶段,不同的角色,可能体会不尽相同,感悟也不大一样,从一开始的看的多、做的多,到后来的想的多、设计的多,每个阶段关注的点不同,从具体技术细节难点的攻关,到整体方案的把控、风险控制,不同的阶段,感受可能也会有所不同。印象比较深的可能有这么几件事吧,记得有几次,夜里一两点钟的样子收到报警短信,系统挂了,然后吭哧吭哧爬起来找问题,各种翻日志翻代码,找到问题之后需要和对应的PE同学一起解决,打电话过去人家早就睡了,也是吭哧吭哧爬起来直到把问题修复,没有任何怨言,阿里的同学就是这样,线上有问题第一时间解决,职业素养绝对是值得敬佩。
我实际上是比较懒的一个人,能自动的绝不人肉,有一次一个问答功能刚上线,淘宝的卖家也是挺聪明的,各种小广告又是卖衣服又是卖手机的好不热闹,最后的结果就是整个页面完全没法看了,苦逼的运营MM一条一条手工的删,删的再快也赶不上发的多,然而我又是那种喜欢多管闲事的人,想到用贝叶斯算法可以解决这个问题,然后就业余+周末花了有一两周的时间开发了一套反垃圾系统,把这事拿出来说并非是这个算法有多牛逼多厉害,贝叶斯算法反垃圾并不是什么新鲜事,而是因为这个事情完全是脑袋一热去做的,但是又收到了出人意料的效果,实际上这样的事情也干了不少,只是这件比较有代表性。
另外一个印象比较深刻的项目是去年的双十一直播,之前由于工作的变化,刚到新团队没几天,接到一个任务,要设计一套直播系统,能支持XXX万人同时在线,XXX个主播同时推流,又是游戏的双十一双十二核心玩法,可是以往的双十一从来没有做过类似的直播,没有经验可借鉴,而此时离双十一也就一两个月的时间,那好吧,开始做,方案设计、资源协调、容量评估、压力测试,中间涉及到N个团队的合作、协调、扩容,技术上又遇到各种坑,连续加了一两个月的班,大家都非常疲倦,可以说是遇到的挑战最多的一个项目,所有的东西都得从零开始,上线的时间节点又无法往后推,谢天谢地最终我们解决了所有的问题,在双十一双十二期间总体表现的比较平稳,虽然并不完美。当然,这一切并不是靠天吃饭,跟前期的方案和小伙伴们的努力密不可分,实际上这里面收获也是蛮多的。
当然,不论是处于什么角色,做好手头的工作是本分,但是也不要被自己当前的角色所局限,多去了解一下周围的人在干什么,了解系统的设计思路,多问几个为什么,为何要这样设计,这样设计有什么好处,有没有其他更优的方案,主动学习,你能得到更多。
互联网发展日新月异,技术也在不断的更迭,在新技术来临时,作为技术人员的你,有什么学习方法或技能可分享?
贤哥:技术总是从无到有,从有到优,颠覆整个行业的技术,在诞生初期也是襁褓中的婴儿,需要不断完善。因此,对于技术的学习首先要把握脉络,在理清思路之后,从源码学习也很重要,要知道,源码面前,了无秘密,不但要知其然,还要知其所以然,这样就容易触类旁通,技术的发展往往是演进式的,从最初概念的提出,到原型产生,再到工业化,最后获得业界的广泛认可被大规模使用,这中间有一个演变的历程,所以,只要明白技术的运作机制,也就是所谓的原理、价值、使用场景,就很容易一个feature一个feature的学习。当然,很多东西都是从大洋彼岸来的,从技术投入应用,到相关的文章书籍出来,会有一定的滞后期,然而,等国内翻译的书籍出来,又是一个漫长的时间,所以,得习惯看英文文档。
当然,最重要的还是要理解技术的核心本质,包括原理、解决什么样的问题、什么样的场景适合使用,另外,还得看相关的技术的社区活跃度,有没有可能在未来成为主流,这是非常重要的,通常来说,解决同一领域的问题,可能有很多方案,那么选择那个方案,可能将在很长一段时间里,影响着你和你的团队,如果选择了一种不成熟的技术,或者是社区不是那么活跃的技术,那么,你就得花更多的时间来解决生产环境中所遇到的问题。当理解了之后,再去学习,实际上就变得容易了,并且,一项技术在出来之后,会不断的有改进,有新特性,但是都是在原来的基础上增砖添瓦,当你理解这些技术的本质之后,再去理解这些改进,这些新特性,会变得相对来说更容易一些。
另外就是不要一味的求新,流行的并不一定就是好的,适合你的才是最好的,A来了学A,B来了学B,C来了又觉得C好,学习是有成本的,把时间用在对的地方,多一份坚持。新的技术的引入,还需要考虑到周边的生态环境,社区是否成熟,否则光是开发各种中间件、各种工具,都够你喝一壶,热潮褪去,一地鸡毛。
在编程/开发之余,还有哪些兴趣爱好?目前你一天的生活节奏是怎样的?
贤哥:每天除了工作中的系统设计、编程开发、各种会议之外,业余时间可以说非常有限了。这些有限的时间一般会被这样划分,各种写作、PPT会花去一部分时间,因为需要将工作中各种经验,踩过的坑记录下来,这也是人生的一笔宝贵财富,随着时间的流逝,很难想起来3年前做过什么项目,写过什么代码,获得过什么经验,因此,日常的总结和反思很重要。
然后就是运动,会给自己留出一点时间进行运动,毕竟身体是革命的本钱,身体是自己的,一旦健康出了问题,任何的成功都没有意义。另外就是看书学习,技术发展的步伐是很快的,如果不能持续学习,可能就会落后,而这些落后的观念最后将直接反映在你所设计的系统上,另外就是通过看书学习让自己的知识变得更全面,视野更加开阔,这样反过来也会使你解决问题的思路更广,变得更有创造力,看书是一种非常好的学习方式,因为平时快餐式的学习会容易陷入细节而无法了解全面,知识无法成体系,因此,也可借看书的时间来好好梳理自己的知识。由于比较喜欢音乐,也会花一部分时间去搜寻各种流行歌曲、轻音乐、钢琴、小提琴曲目等等,音乐能使人的大脑处于放松状态,再就是陪伴自己的家人,旅行等等。
掌握知识、技术的三个层次
此前,你出版了《大型分布式网站架构设计与实践》一书,能否分享下你写书的原因、过程、困难和感悟等?以及介绍下这本书的特色。
贤哥:其实是比较机缘巧合的一件事情,记得是2013年4月份,博文视点的董英女士找到我,问我是否有兴趣写本关于分布式系统方面的书,其实当时已经预感到这个事情做起来会比较难,但是还是义无反顾接下了这个活。主要是觉得,写书是个高尚的事情,也算是为互联网技术的发展尽了一丝绵薄之力了,从另一个角度来说,也是难得的一次机会,对之前的知识一个全面的回顾,一些知识点及细节,有些也是知其然不知其所以然,或者是没有亲身验证,刚好借此机会深入了解和挖掘。
对于知识或者是技术的掌握,个人认为有三个层次,在项目中能做出来是一个层次,将经验写出来惠及大家则是一个升华,当然,能够在各种场合随时随地的清晰表达出来,又是另一个层次。
实际上,真正写作的过程远比想象的要困难,在互联网企业工作本身就是一件比较累比较辛苦的事情,有时候加班到晚上9-10点钟回家,还要抽出一两个小时的时间来写作,周末基本上就一心扑在上面了,时间是一方面,最痛苦的莫过于在这过程中需要不停的上下文切换,工作到写作,写作到生活,而写作又是一件需要灵感的事情,有时候可能在那坐了老半天憋不住几句话,而在上班的路上你可能又文思如泉涌,很多时候常常不得不等到夜深人静,才能够完全静下心来投入。
写书的一年多时间里,简直可以用煎熬来形容,无数次想过放弃,也曾经质疑过纠结过,能够坚持下来写完,我只能说,Oh,my god,谢天谢地,感谢所有陪伴在身边的人及支持我的人。从一开始这本书的定位就不是曲高和寡,阳春白雪,而是希望让各个不同岗位以及不同基础的读者们,都能够有所收获,因此,内容中即有过程,也有总结,当然,每次回过头来看这本书,写作时候的那种“战战兢兢,如履薄冰”的感觉,依然还在,写作是严肃的事情,每一次落笔,常常会担心会不会因为自己的理解偏差,误导读者,以现在的眼光或者视角来看,这本书远称不上完美,但是一本书不可能无休止的写下去,难免会有不完美的地方,接受瑕疵有时候也挺痛苦的。
避免失败是所有工程技术的核心
你个人对架构/软件架构的理解是?
贤哥:以下仅是个人的一些理解,架构不仅仅融合了思想,融合了技术,同时也融合了艺术,好的架构并不仅仅是停留在技术文档里,而是在实践的过程中不断地修正和调整的,这对架构师也提出了更高的要求,仅仅是停留在抽象和概念阶段是没有太大价值的,细节是魔鬼,一些从抽象层面看起来比较简单的架构,实际上最大的挑战往往来自于细节,这些细节既包含产品视觉交互功能的实现,也包含业务规则、风险等种种逻辑的处理,还包括技术上的一些难以预知的“坑”,具体的技术方案在实施的过程中,可能需要花费大量的时间跟精力去解决和避免那些极端情况下可能出现的问题。
架构应该满足一段时间内的业务发展,但是这一段时间到底有多长,有说三个月,有说半年,有说一年,也有说三年,不同的人不同的环境对于这个问题的理解可能不同,创业型公司,或者是尝试型的业务,风雨飘摇九死一生,优先考虑的是业务模式而非技术架构,因此,此时的架构应该尽可能简单尽可能容易实现,三个月之后业务变成什么样子甚至是否存在,还很难说,这个时候去想三年之后的架构,基本上也是天马行空,对于比较成熟的业务,或者是对之前稳定的业务系统进行重构,则需要将眼光放长远些,避免一些在中长期可能面临的问题,比如数据库的分库分表数量,ID的长度,分库分表的维度等。
另外就是系统需要可扩展,在设计时要留有一定的扩展点,避免稍有变更就需要整个系统重构的情况出现,对扩展开放,对修改封闭,实际上这很好理解,修改原有的系统而不是扩展原有的系统,更容易引入新的问题,也会带来更大的测试工作量。一段时间之内架构的演变,常常会经历从清晰,再到模糊混乱,再重构,再清晰,然后又变得模糊的过程,市场环境总是瞬息万变的,因此,系统的设计要遵循对扩展开放,对修改封闭的原则,做到这点即可方便及时的接入新流程,又能够不影响既有的流程。
从宏观来看,各个系统间的关系一定不应该是烟囱与烟囱的关系,而是犹如城市里的高楼大厦,通过公路连接起来,因此,要提高建房子的速度,就要充分利用已有的基础设施,已有的中间件,来降低系统构建的成本和风险。
架构设计的几个层次,没有架构也是架构,专注于解决现有问题也能称为架构,而好的架构应该是即能够约束开发者又能够解放开发者使其专注于功能的设计。尽量将复杂的事情变的简单,而不要将简单的事情变的复杂,技术从来都不是用来炫的,而是用来解决实际问题的。避免失败是所有工程技术的核心,架构也是技术,要运用架构技术去缓解风险。
分布式架构 VS. 集中式架构系统,以及思考
分布式系统架构是一个非常广发的概念,他有着怎样的特点,以及在网站何时要用分布式?另外它有哪些的场景?
贤哥:分布式架构实际上是解决了集中式架构系统能力进一步向上扩展的所面临的瓶颈,这些瓶颈包括资源、运维、开发维护等,因为单机的硬件受到技术条件的限制,越往上扩展,成本可能并非是线性的而是指数级的,分布式架构通过大量廉价的PC Server集群,使得能力的扩展与经济成本的关系再次回归线性,另外当开发团队的规模越来越大,业务越来越复杂,分布式及服务化也使得系统能够更好的进行拆解,让更多的团队能够更高效率的在一起协作。
但是,从另一个角度来看,分布式架构也是一种复杂的架构,很多传统架构下面可以弱化的问题,在分布式环境下变得凸显,甚至是成为至关重要的问题,比如数据一致性问题,比如网络通信、序列化、延时问题,比如如何应对失败的问题,传统环境下数据一致性通过数据库事务在相当程度下被弱化了,而分布式环境下将成为一个非常复杂的问题,另外就是分布式架构使得集群内部的网络通信变得更加频繁,通信协议、序列化方式、通信延迟、容错、性能这些都会变得复杂化,分布式环境下的失败将成为常态,如何处理这些失败也会变得一个非常复杂的问题,一个成熟的分布式架构体系所依赖的基础设施很多,从各种中间件,到自动化运维体系,监控体系,容灾体系,这些都需要一段时间的积累,并且持续投入和付出,因此,在考虑分布式架构的同时,也需要从投入产出以及回报角度综合考虑,对于创业公司来说,需要想清楚优先要解决的问题是什么,再来思考企业需要什么样的架构,一味地参考大公司的架构,可能会提前让系统变得过于复杂,失去响应灵活的特点,从而失去竞争力。
我所理解的网站架构
贤哥送福利:
资料太多,加企鹅群:8 9 7 8 8 9 5 1 0,领取以上免费的学习资源。
大型网站架构设计的思想与原则是什么?
贤哥:实际上很难说有个一个统一的思想和设计原则,能够放之四海而皆准,因为每个人对于设计的理解和理念是不同的,个人觉得设计一个复杂的大型网站,实际上是一个分而治之的过程:
首先得充分的理解业务,理解需求,理解当下需要解决的首要问题,以及可能的风险有哪些,再将目标进行分解,进行具体的技术选型、模型设计、架构设计。如果需要解决的核心问题是并发,则可以通过各种缓存手段(本地缓存、分布式缓存),来提高查询的吞吐,这样虽然会一定程度上需要在数据一致性上做出牺牲,由强一致性变为最终一致性,但是,如果数据一致性不是核心需要解决的问题,那么,此问题的优先级则可以先放一放,反过来如果核心问题变为数据的一致性,如交易系统,那么再怎么强调数据的一致性都不为过,由于分布式环境下为了应对高并发的写入以及海量数据的存储,通常需要对关系型数据库进行分库分表扩展,这也给数据一致性带来了很大的挑战,原本的单库事务的强一致性保障,在这个时候升级为跨库的分布式事务,而通过二阶段或者三阶段提交所保障的分布式事务,由于分布式事务管理器与资源管理器之间的多次网络通信成本,吞吐及效率上很难满足高并发场景下的要求,而这实际上对于交易系统来说,又是一个很难回避的问题,因此,大家又想出很多的招来解决这个问题,通过可靠消息系统来保障不失为一种方式,变同步为异步,但是,又引入新的问题,消息系统为保证不丢消息,则很难保证消息的顺序性以及是否重复投递,这样作为消息的接收方,则需要保障消息处理的幂等性,以及对消息去重。
个人比较推崇洛克希德·马丁公司的著名飞机设计师凯利·约翰逊所提出的KISS原则,架构设计能简单绝不复杂,坚决砍掉任何华而不实的设计,不要因为3年后可能怎样甚至是一些现实中根本无法出现的场景,加入到当下的架构设计中,导致系统无比复杂。有时候看似引入的是一个很简单很容易解决的问题,可能在具体的执行过程中,会因此带来一系列不必要的麻烦,按下葫芦起来瓢。
另外一点就是对于未经验证的新技术、新理念的引入一定要慎重,一定要在全方位的验证过后,再大规模的使用,新技术、新理念的出现,自然有它的诱惑,慎重并不代表保守,技术总是在不断前进,拥抱变化本身没有问题,但是引入不成熟的技术看似能带来短期的收益,但是它的风险或者是后期的成本可能远远大于收益。
设计一个大型网站架构时,通常需要从哪些层面去考虑?服务器/存储部署方面需要注意哪些问题?
贤哥:大型网站的设计是一个非常复杂的问题,需要考虑的问题很多,比如海量数据的存储,存储又分为在线存储与离线存储,在线又有关系型数据库存储和非关系型数据库存储,持久化存储和内存存储,这些都需要架构师根据具体的场景进行选型。
高并发且允许数据丢失的情况下,可以采用内存存储,而查询条件单一,只需要根据主键进行查询,则可以选择key-value型的存储,对于海量的文档及图片内容,则可借助分布式文件系统以及CDN边缘节点,即解决了存储的问题,又能够将冷热数据分离,并且通过边缘节点提高用户访问的效率,如果是需要多维度的复杂查询,则需要使用关系型数据库。当数据量大,并发写入请求多的时候,又需要进行分库分表,由于分库分表会限制数据的查询维度,查询条件必须得带上分库分表的键,如果需要多个查询维度,则需要使用数据同步工具同步出另一维度的数据结构,或者是搭建垂直搜索引擎,以提供多维度的数据查询,很多情况下难以通过一种存储工具解决所有问题,因此需要多种存储复合使用,以提高效率及用户的使用体验。
再又如应用的部署,从集中式架构到分布式架构,SOA服务化,再到时下流行的微服务架构,接入层的负载均衡设备解决了无状态WEB应用的扩展问题,而软负载中心则解决了服务发现和服务路由的问题,轻量虚拟化及docker的出现使得Martin Fowler所提出的微服务理念能够更容易成为现实,当然,大型网站还需要考虑比如某个地域出现不可抗力因素时,如何保障整站的可用性以及数据完整性,诸如同城容灾,异地容灾(如两地三中心),以及时下正处于风口浪尖的异地双活、异地多活架构。
大型网站的架构往往不是一蹴而就的,而是通过需求的推动经过多年演变一步步形成的,不同的时期不同的阶段不同的规模,所面临的业务不同、需求不同、需要解决的核心问题也不同,这就导致不同的阶段不同的架构,并且架构也是不断演进与发展的。
大型网站有哪些典型的故障以及通常有哪些解决之道或相应的优化建议呢?
贤哥:一个成规模的网站可能每天都在经历故障,只不过故障可能在绝大部分人感知到之前就已经修复了,导致故障的原因很多,有可能是业务逻辑的变更对于依赖的测试不充分,或者是不兼容的版本升级导致的序列化错误,又或者是测试用例未覆盖到的程序bug,又或者是不同版本jar包的同名类冲突问题等等,也有可能是访问量太高导致日志将磁盘打爆,又或者是机器负载过高导致大量线程阻塞,又或者是锁竞争过于激烈导致进程僵死,或者是数据库连接池用完,JVM频繁GC等等。
另外也有可能是由于物理环境问题,比如网线被拔掉,光纤被挖断,机房停电,硬件设备损坏等等,导致故障的原因可能千奇百怪,很难一一枚举,对于变更所导致的故障,能做的是让测试用例尽可能全面的覆盖到每一个细节,包括依赖项,项目设计阶段多考虑风险,按照流程来发布,但是也不能因噎废食,使得发布流程沉重僵化,对新的业务需求响应缓慢,实际上这也是一个很难拿捏的度。
此外就是要建立起完善的监控系统,包括异常日志收集分析,业务流程全链路校验,机器运行状态检测(负载、qps、磁盘、内存、网络、运行水位),历史数据的分析,异常报警等,对于服务化的架构,还需要完善服务治理,包括强弱依赖管理,调用关系(谁调用了谁,谁被谁调用了),调用频次,异常状况等,这实际上是一个体系化的工作,也是一个比较基础的工作,有了这些之后,你才能够及时的感知到系统的异常状况,及时定位问题,修复问题。
构建一个网站时,可以选择开源或自主研发,前者因万一选用的开源方案在将来才发现某一些特性不满足,就得推倒重来,而后者则似乎有重复造轮子的嫌疑,对此你怎么看?
贤哥:这个问题得辩证来看,使用开源能够降低很大的工作量,但是也会存在潜在的风险,特别是一些未得到广泛验证的技术,即便是使用的十分广泛的如Struts、SSL,也时不时会爆出一些惊人的漏洞,对于小公司来说,使用开源的技术能够快速的构建出一个勘用的网站,即便是在使用开源软件的过程中遇到问题,切换的成本可能也不会很高,但是对于大公司而言,切换的成本可能会变得非常的高,因为业务和依赖关系实在是太复杂,一旦大规模使用,影响的范围可能非常广,因此在做选择之前不得不非常之慎重,当然,我们也会有一些比较特殊的需求,开源软件无法满足,或者说是走在了开源的前面,这些工具、中间件就需要自己动手开发了。
另外就是开源的软件有些特性实际上与我们的期望有很大的差距,而他们本身的架构可能又不是那么方便扩展,但是这些特性对于我们来说又十分的关键,比如Hadoop,它的MapReduce、HDFS、Hive提供一整套海量数据的分析解决方案,但是底层的权限控制做的很弱,因此我们不得不花了很大的精力开发出一套替代方案,又花费很大的精力将原来Hadoop上的数据和Job迁移到新平台。对于开源技术的选择,我们更倾向于选择一些社区比较活跃比较成熟的软件,最好是有一些比较成规模的成功案例的,这样的风险会小一些,毕竟对于一家成熟的电商网站来说,稳定大于一切,系统的不可用时间是跟成交金额直接关联的,分分秒秒过去的时间,就是实实在在的金钱。
对于较为核心的应用所引入的开源技术,我们也会花费较大的精力深入地去了解,做一些bugfix,避免踩到一些坑。
另外一点就是大公司的很多场景可能是非常特殊的,比如高并发场景下的MySAL数据库行锁,大对象常驻内存时的JVM的内存回收,一些软件可能为了满足通用的需求,牺牲了一些特殊场景下的性能。因此,对于我们来说,了解这些后,也是有一定的优化空间的,包括从实现上去规避,或者是去改造开源软件,而做这些的前提就是对开源软件的了解。
一般网站面临的问题就是负载的问题,当人数多,导致速度慢是主要解决的问题,对此你有什么建议?
贤哥:相较于传统企业来说,大部分互联网企业都会面临的一个很大的挑战,随着用户规模的不断扩大,系统的压力会越来越大,而在创业初期,系统的架构设计往往是一切从简甚至根本没有架构,快速迭代,优先满足业务,而受市场环境的影响业务往往是多变的,因此往往会背下“技术债”,业务逻辑高度耦合,系统不可扩展,代码结构臃肿,此时不得不进行重构。
“分布式”是应对大流量核心思想,首先,系统得做好准备,支持扩展,尤其是在数据、模型层面,因为数据的拆分、扩容、数据迁移最麻烦最费时间,稍有不慎,还可能导致数据不一致,造成的损失也有可能是无法挽回的,方案设计必须得慎之又慎,在数据拆分迁移的同时,新的数据正在源源不断的写入,老的数据也常常会面临高并发的更新,因此,业界经常将数据拆分扩容比喻成是在给一架高速飞行的飞机换引擎,这也是整个扩容过程中,最复杂,技术含量最高,最有挑战的任务。
再就是集中式应用的业务逻辑拆分,原先团队规模小,业务量也小,可能会在少数几个应用上堆了很多代码和业务逻辑,而随着公司规模的增长,业务迅速发展,团队规模越来越大,集中式的应用维护将会变得十分困难,这既包括开发部署,笔者曾经开发过一个应用,改几行代码,本地编译打包需要10几分钟,本地部署又需要十几分钟,这极大的降低了开发的效率,另外这样的巨无霸工程也会占用很多服务器资源,而单机的硬件资源又不可能无限升级,这也会是一个问题,再者就是耦合的业务逻辑也不便于复用,得四处重复造轮子,浪费资源,这又引申出另一块,也就是企业内部的服务化。
SOA架构包括时下流行的微服务理念,解决的是企业内部资源复用的问题,避免信息孤岛和重复造轮子,提高系统可维护性,降低业务试错以及系统构建成本,提升企业竞争力。通用的统一的SOA通信标准,包括通信协议、序列化反序列化方式,能够简化SOA架构的实现,服务的自动注册、路由、软负载能降低运维成本,随着服务的增加,单靠人工来进行服务治理越来越困难,又衍生了服务治理系统,对服务的调用,依赖,异常等信息进行统一的管理。当应用变得无状态之后,扩容就非常方便了,通过负载均衡软硬件设施,或者是SOA的软负载机制,可以根据需要十分方便的增减机器扩充容量,而这种能力几乎是线性的(在一定规模下)。当然,大部分的场景以及技术解决方案,国外的Yahoo、Google、Facebook、Linkin 、Twitter…,国内的BAT,这些知名的互联网企业,实际上很大程度上已经充当先驱,后来的追随者,只需要紧随前人的脚步,蓦直前行,架构的风险已经被大大的降低。
架构师的技能或素养,架构师到底要不要写代码?
成为一名架构师需要哪些的技能或素养?
贤哥:以下仅代表个人观点,设计符合要求的系统是架构师的基本技能,功能、可用性、可扩展性,以及团队能力、项目执行风险、运行环境都需要综合考虑,架构师的功力更多体现在技术的综合运用上,因此对于项目所需要的技术细节的了解必须是全面的,这样才能够将最合适的技术用在最需要的地方,并且还需要有技术的前瞻性,通过经验以及积累发现可能潜在的风险,对于问题的理解,不能够仅停留在表面,逻辑思维和抽象思维能力是一个架构师的重要素质。
当然,作为架构师还需要一个非常重要的技能,就是充分的沟通,完成系统的设计只是万里长征的第一步,设计思想需要充分的传达给团队中,并且从团队中得到相应的反馈,对方案进行调整,不断完善,只有在团队中所有人都了解领悟了你的设计之后,后续的推进包括项目的实施才能够变得顺畅,细节是魔鬼,在后续的执行过程中,可能会面临各种问题,涉及到的方案调整,沟通协调是不可避免的,作为架构师来说,需要有充分的准备,好的架构师能够带领团队高歌猛进,而不称职的架构师最终会导致矛盾重重,对于合作的团队来说,需要确认可能的风险,包括接口,时间节点,兼容性,对接可能遇到的技术问题,对于可能遇到的风险,架构师必须了然于胸,提前准备,从容应对。
Linus Torvalds说,
Talk is cheap, show me the code.
但是我想说的是,
Talk is not cheap, talk is important too!
很多人会问,架构师到底要不要写代码,首先,个人认为,架构师是需要写代码的,无奈时间是有限的,项目的规模越大,所需要思考的细节点越多,自然而然花费的时间越多;除此之外,作为架构师的你还需要传播布道,告诉所有人你理解的架构是什么样子,告诉大家怎么做如何做,核心的目标是什么,核心的风险是什么;架构师还需要协调各个依赖的关联系统,告诉其他人你要做一件什么事情,需要其他人怎么配合,做这件事的价值以及其他人为何要配合你,这同样需要花费大量的时间,那么,在剩下不多的时间里,架构师能写的代码可能不多,但是,为了让你设计的系统不脱离现实,你必须写代码,必须Review核心关键代码,确保整体架构的思路得到贯彻,确保你的设计是易于实施的,确保潜在的风险得到妥善的控制,特别是在有新技术引入的情况下,原型验证是必不可少的步骤。有种观点认为,架构师必须是代码贡献最多的,一个人写代码,自然不需统一思想,但是实际上这很难做到,作为架构师你得记住,不是你一个人在奋斗,不要让自己成为团队的瓶颈,但是,我同样也不赞成架构师完全不编码,不亲身体验过,有的风险是很难事先做出判断的,何况技术本身也在发展,今天的经验放在明天不一定有效,作为程序员的最基本技能,编码是你学习和积累的最直接的方式。
架构师也是一个普通人,一天只有24小时,需要花费很多时间进行方案设计,技术合理性思考,原型验证,还需要花费大量的时间给团队传达设计思想和目标,为何这样设计,这样设计有什么好处,不这样设计会有什么样的问题,人是最复杂的生物,程序员都是非常有个性并且非常聪明的,统一思想统一目标是一个非常艰巨的任务,一千个人心中有一千个哈姆雷特,同样,做一件事情可能也有不同的方法,方法太多有时候并不是好事,作为架构师,需要找出最合适的方法,并让它得到大家认可,这并非是把个人目标转化为团队目标的过程,而是不断地沟通不断的改进演化之后,在大家充分参与的前提下找到的最适合当前业务场景的方案。
对未来你有着怎样的规划和期许?
贤哥:技术这条路注定不是坦途,码农大多数时候的生活是枯燥无味的,并且这又是一个学无止境的行业,技术的更新换代非常快,失败的纠结,苦思冥想的无奈,成功的喜悦,其中的酸甜苦辣,我想只有真正的码农才能体会。
近期来看,应该会继续专注于直播,阿里在电商领域积累了丰富的经验,但是对于直播来说还属于一个有待成熟的领域,还有很大的提升空间,技术挑战也是比较大的,后续希望能够做一些事情,降低直播的门槛,降低资源的消耗,提高服务的稳定性。
就跟《战争之王》这部电影里尤里·奥洛夫(Yuri Orlov)的经典台词所说的一样,人总想在有生之年做件大事,只是暂时还没想好要做什么,诚然,我不会跟尤里一样去贩卖军火,社会的发展和变化太快,很难预料自己五年之后会专注于什么,从事哪方面的工作,但是,作为一个热爱技术,喜欢专研的人,应该还是会是做跟技术、跟工程能扯上点关系的事情。
最后,想给看这篇文章的读者说些什么?
贤哥:当初毕业找工作的时候,说实话也没想过说一份工作会干这么长时间,而且后面可能还要继续做下去很长时间,实际上毕业的第一份工作非常重要,因为当你开始工作之后,你将不再是一张白纸,而你后续再去找工作的时候,前面的工作经历将会是很重要的参考,第一份工作将很大程度影响你后续工作的大方向,后续再想要转型,可所付出的努力和冒的风险可能更大。
选择有时候很重要,首先得清楚自己喜欢做什么样的工作,因为做自己喜欢做的事情,你更愿意付出,不会觉得辛苦,更不会觉得痛苦,而是乐在其中,工作是一件长期的事情,因此,值得你好好想想自己到底喜欢做什么。
另外就是看后续的成长空间,一滴水到了一杯奶中,水就变成了奶,一滴奶到了一杯水中,奶就变成了水,有可能某个公司A给你的offer多了1-2K,而公司B却能够提供给你一个更大的舞台去发挥,去成长,给你提供一套系统的培训和成长体系,并且周围都是业界大牛,此时的选择,考验着你的智慧。
短期的1-2K,从长远来看,实际上真的不算什么,但是损失可能是长期的发展空间,那有人说,工资给的高不说明更重视么,话虽没错,但是去到一个没有发展空间的公司,或者已经是夕阳产业,也许你确实很优秀,可能你的高度就代表了公司最高的高度,那么你的空间在哪,这实际上是一个鸡头凤尾的抉择问题,选择一个更有空间更有潜力的公司,可能刚开始你在团队中并不是那么出色,但是,认真工作几年后,你再出去跟同龄人比,区别还是蛮大的,并且,优秀、成熟的公司会有一套相对公平的评价机制,总的来讲,会让足够优秀并且给公司创造更多价值的人,得到相应的回报,所以也不用担心回报的问题。实际上HR也不傻,你得到的回报可能是经济上的回报+成长空间的总和,而两部分加起来,大部分公司给出的价位应该是差不多的。
机会是总是留给有准备的人,选择很重要,坚持有时候也很重要,做事情得要能沉的下心,不要怕困难,人生就像骑单车,想保持平衡就得往前走。