热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

世界上本没有架构,建设的需求多了便有了架构

世界上本没有架构,建设的需求多了便有了架构作者:刘海锋,编辑:林师授,51CTO技术栈整编本文选自《CTO说》,你不能不看的
640?wx_fmt=jpeg


世界上本没有架构,建设的需求多了便有了架构


作者:刘海锋 , 编辑:林师授 , 51CTO技术栈 整编

本文选自《CTO说》,你不能不看的CTO养成记。


架构这个词,源于建筑学,它基本的架构是建设的方法,怎么样盖这个楼,就是整个实施的过程都需要架构。后来有了IT,有了互联网,最后就有了做软件需要架构,做硬件需要架构,需要设计一些东西。因为系统需要不停地建设,后来有了一些方法和思路,于是就有了架构。


基础架构英文叫 Infrastructure,又是架构的子领域,相当于是比较基础的东西,能够服务于各种应用的底层平台。其实这个很难去定义它,从业务的角度来说,下面所有的 IT 都是它的基础架构,因为它认为这些东西都是为它服务的。在研发的系统里面,也就是研发的团队,也可以认为各种底层平台是基础架构。


做这些事情的过程中,我自己有一些思考或者一些经验,跟大家分享一下。


非结构化存储——静态内容


刚到京东时,各个团队已经比较成型,我面临的第一个问题就是如何选择项目和方向,这是特别重要的。我最终聚焦在一个方向,那就是存储。因为存储是整个计算机领域最基础的一个问题,也是一个大互联网公司中特别重要的核心之一。


所以先把方向分到存储这个领域。而存储粗略地又可分成两类,一类叫非结构化的存储,一类叫结构化存储,结构化存储其实主要是数据库。


对于大部分的公司来说,结构化的存储量是比较小的,而且一般传统的关系数据库就可以比较好地支撑业务。另外从团队上来说,任何一家公司,上了一定规模以后,DBA 团队相对来说还是训练比较有素,系统有一些问题时,他们能够及时响应,也会使整体业务得到较好的支持。


对于京东来说,非结构化的数据量还挺大,有很多显著的特点。

  • 图片非常重要,因为商家要上传,它的可靠性以及性能很重要,消费者在浏览过程中,稳定、流畅的体验也都很关键。

  • 京东自营占了很大的比例,京东有众多的库房,每个库房每天要产生海量的运单,这些运单在内部库房流转的数据都是用非结构化的文本来描述,这个量比图片还要大。


当时有两个团队在做这个事情,并且基于当时的业务量和规模,技术层面对于业务的支撑是足够的。但是可以预见,随着公司业务的快速发展、规模的扩大、机器量的增多,如果不做系统的升级和改变,未来可能会出现很严重的问题。


我当时分别和这两个负责的团队进行了交流,一个是图片管理团队,一个是物流运营团队,不管是图片、订单的文本还是库房的流水的报文,每一条都不大,大概是几KB到几十KB,顶多几MB,但是每天的量都很多,对可靠性要求很高,绝对不能丢。这也是公司非常重要的资产,我最初的愿景是希望做很多的分布式存储


我做了模拟的曲线用来说服大家,其中有每天机器数作为一个维度、日均上传图片作为一个维度,日均消费者浏览图片作为一个维度等,后来发现随着业务的增长,如果依然使用目前的系统,故障数目会成倍增加。


推动的过程遇到了一些波折,但好在最终大家都接受了新的方案。

分享给大家其中一个比较有趣的过程

众所周知,做第一个吃螃蟹的人是需要很大的勇气的,大家都在犹豫的过程中,我们用了一个小小的策略,就是告诉每个团队,他们并不是第一个吃螃蟹的人,另外一个团队已经品尝了“螃蟹”, 并且觉得非常美味,用这种方法最终才得到大家的支持。


在内部达成一致后,我开始自主研发做第一个非结构化存储,它有很高的可靠性,非常好维护,性能各方面都很好,这是第一版系统,起名叫JFS(京东文件系统)。


后面做图片系统还是比较复杂,因为优先不考虑大文件,更多的是小文件,这个工作要从原来的系统里把所有的数据迁过来。


在迁移的过程中,要对历史数据做校验。原来的老系统因为历史比较久,再加上有很多故障,数据已经不一致。在这个修复过程中,发现图片有丢失,而这个图片并不是孤零零地在核心机房单独的图片系统,而是跟CDN 结合的。


因为最终的用户体验并不仅仅取决于原站的存储,还取决于 CDN 的效果。正好借着这个机会,对 CDN 有一个理解。后来我发现公司还有很多优化的空间,经过一段时间的发展和磨合,和 CDN 的团队互相也有了很多了解和共识,最终去跟他们沟通要把 CDN 重新优化。


最后我们做了一个项目,大概用了一个季度的时间把这个原站的货源次数降低了80%,从每天大概的两亿多,降到了每天的四五千万。


回过头来看

其实所有的问题都是方向的问题,就是抓一个大头,抓一个重点,在一点上取得突破。而且当时从研发的角度来说,做海量小文件的丰富存储,相对还是比较简单,研发投入不是那么大,但取得了非常好的效果。


结构化存储——动态内容


JFS 项目从2014上半年由我团队的一个负责人去做,持续地做下来,到2016年有一个团队在做这个事情。到目前为止,大家在京东看到的所有动态的内容,几乎都是由它来支撑的。


动态的内容是什么呢?

比如说商品的介绍、商品的价格、搜索和推荐的最终结果,还有缓存、广告等等很多。这些都是动态内容,更多的是文本,相对来说比较小,这些都是由这个系统来支撑。为了用结构化存储去支持公司的动态内容,我们用了不同的一个思路把内存当成持久的存储。


这个事情是怎么引发的呢?

当时的背景是这样,在2014年的上半年,我们开始做一个新的方向,想解决公司动态内容的结构和半结构化数据存储的问题。


那时候和很多公司一样,主要的方式都是 MySQL 数据库,前面加一个 case 来解决。后来发现,这个 case 的维护其实挺麻烦,MySQL 可扩展性方面也是一个问题。最后经过很多研究,和大家一起来合作解决缓存的问题。


从过去的发展可以看到一个情况,大概2007年、2008年时,服务器的内存基本是 2GB 到 4GB,后来很快8GB、16GB、32GB、128GB,现在很多公司,包括我们京东,采购的主流机型都是 256GB 的内存。内存越来越大,也越来越便宜。经过一些分析和预测之后,你会看到所有的公司,不管是美国公司还是中国的公司,都在比较激进地使用缓存。


而且稍微算算,你就会发现,这些动态的内容和这种结构和半结构化的数据,其总量加起来其实是很少。就以商品为例,每一条商品介绍大概是几KB。就算你有十亿的商品,也就是1G,1G乘以几KB,这才几TB。你每台机器是 256GB 内存,即便算上副本之后,其实也用不了多少资源。


我估计不久之后,很多公司都会采购 512GB 到 1TB 这么大内存的机器。于是我就规划这么一个项目,完全以内存为中心,让磁盘去做归档,数据驻留在内存里面。通过记日志加上快照,保证可靠性。


把这个方向明确之后持续去做,而在这里面还有很多技术的路线选择。当时选择一个方式是兼容 Redis 的API。它的优势是已经有不少人在用,数据类型也比较灵活,但缺点在于它是一个单机的软件,不是一个分布式的。最后我们来分期建设一个分布式的系统,聚合很多大内存的机器,把它做成一个共享的资源池,提供给很多的业务。


比如说公司大部分的业务是 Java 系统和 Java 客户端,也有 C++,还有一些小语言,用一个代理把它做成一个比较高质量的分布式的系统,能够去自动检测故障。


从2014年上半年开始,我们重点投入到这个项目并将团队进行扩充。到2015年夏天时,这个系统已经成为公司特别重要的基础设施。


京东有大概四五千台的大内存的机器,去支撑公司的业务,把几乎所有动态内容,如搜索推荐结果的 case,还有商品的介绍、价格、库存等这些动态都用它来存,性能非常好。虽然起初成本看起来稍微高了一点,但慢慢地这个成本在逐渐降低。


其实有的项目或者系统建设,

是需要去通过历史去预测未来会发生什么,最后去选择一些不同的方法,这样做的项目会比较有意义,有可能会取得更大的成功。但是在做这些事情之前还是先要做充分的调研,在技术平台,很多东西其实不是凭空想出来的,更多的要从公司的业务、众多的应用开发中去发现一些问题,把它沉淀下来做成系统,再把系统做成共享和服务。


中间件体系


中间件这个词也是很模糊的词汇,那么中间件是什么呢?


对于一些企业,特别是电商还有一些比较传统的大规模的业务模式的企业里,能够把应用开发中的一些范式提炼出来,能够抽象出来,把它做成一个大的软件系统,给所有的应用使用,这个统称为中间件。


电商里面有两个中间件特别的重要:

第一个叫消息队列。大家都知道单机的操作系统里面,比如说管道,你可以把这个命令输出的东西,想办法通过这个管道传给另一个命令,还可以通过符号,把很多进程连成一个并行处理。当然还有什么共享信号量,总之都相当于一个消息的队列。


在业务系统里面,也经常用这种东西,它不是单一的,其实是应用和应用,或者服务和服务之间的东西,它需要用消息队列串起来。因为很多事情,特别是在电商这块,不可能在一个环节把它完成。举例说购买商品并付钱这个事。


我在手机上,建立连接、付钱,它在一个一个环节里面,就把你这个付钱的请求处理完。过程是收到你付钱的请求,做很多校验,传给下游,下游一看,他是不是付钱了,这个用户是一个合法的用户,还是我们需要去做风控的用户,可能又传给下一个系统。下一个系统要检查,这个商品有没有库存,还能不能卖。如果能卖,又传给下一个环节,下一个环节可能负责调用银行的接口。再下游的环节收到回调之后,我们再寄一个东西用来对账,这个是付钱的过程。


加入购物车的过程也是,其实并不是只有一个接收问题用的请求。你通过手机发出请求,把商品加入购物车,其实也是有很多环节。你加入购物车的请求,给这个服务。服务可能检查你这个购物车是否太满,是不是还能加。有的环节可能检查库存,有的环节可能要做风险的控制。所以在复杂的应用系统里,经常需要消息队列把很多的东西做一个异步的串联。


这个用的特别多,尤其电商行业对消息队列的要求也是极高的,要求消息绝对不能丢,要非常的可靠,性能要求也很高。


在2014年,公司中消息队列用的比较纷繁复杂,有的团队用开源的,有的可能是自己写一个简单的,有的可能用数据库来做一个消息队列。


基于当时的团队和技术力量,我们已经有能力和实力做一个非常高质量的、自主研发的消息队列,把公司整个消息队列的技术方向统一起来,服务所有的业务。这个工程相对来说很大,但是最后的收益是很高的。


我们能够用集中一个团队的力量,维护好这样一个共用的供应链的服务,让所有的团队去演绎他们的这种运维、各方面的服务,让所有人受益。


第二个中间件的项目叫服务框架,这个是在2014年上半年开始做,到2015年年底,项目全部实施完,公司所有的应用,特别是重要的电商应用全部都接入了。


那么这个出发点是什么呢?很多服务端的开发,它有很多共有特征,都要写一个服务器,收到网络请求,把这些请求定义一些格式,去做反序列化,处理完成之后,再序列化发送。


其实这个事情本来没有什么,但是因为公司大了之后,业务越来越复杂,应用系统就很多。应用系统一多,就要做 SOA。SOA 是把这个服务进一步的拆分,在大的企业里,可能有成千上万个服务。如果每一个人都要开发自己的非业务逻辑的技术部分,那么技术成本太高了。而且做 SOA,需要统一把服务做命名,做管理,做监控,还有一些管理上的约定,需要一个统一的服务框架来做。


当时公司还没有实现真正的统一,通过团队各自维护。所以我们就做这么一件事情,把一开始定位 JavaIDC 的服务,后续又扩展成多语言,用一个框架把这种服务端的开发统一的提供出来。


这个项目的益处是,一方面能够便于工程师快速的开发服务,另外一方面,有助于去做服务的注册,发现、管理、监控等等。这个项目真的是影响公司所有的应用,因为大部分的应用都要用这个来发布、管理,几乎用于公司所有的应用服务上。


弹性计算云


这里是讲内部的私有云建设,而私有云更多的是虚拟化等技术。这其实比较适合在规模不大的公司,而现在要在一个规模很大的公司进行底层系统再次实施,就会比较复杂。


打个比方来说,它比较像在一个房间里,已经站了很多人,现在要换地毯,这事情挑战是很大的。但是为什么要做这个事情呢?

一方面有很多技术的因素,举一个简单的例子,资源交付的时间过长,作为一家电商企业,经常会有大促,如大家熟知的 6.18、双 11 等,促销就要加机器、加资源,但是物理机器的交付时间还是很长。


另外是公司的整体资源利用率不高。从资源的管理来说,任何一个数据中心里面,物理机都已经按团队、按应用的小块进行了划分。比如说这个是订单团队的一些机器、网站的一些机器等,而这些机器并没有划分成统一的资源使用。


其实按团队、应用来分,也给管理带来很高的成本。比如分机器的时候,准确的评估应该给哪个团队、哪个应用多少机器是一件非常困难且棘手的问题。分多了会导致资源的浪费,分少了会导致业务的运行出现严重的问题。在2014年年底的时候,这个项目已经提升到公司技术战略层面。


起初推动项目的时候,也遇到了一些小波折。比如原来每一个人捧着一百台机器,每台机器上有多大 CPU、内存,都在大家手中实实在在地握着,比较有安全感。如果这个项目实施后,变成了好像机器都不是我的了,有种安全感的缺失。所以关键的难点,是如何让大家相信这件事情有意义,有价值,对他有好处。


实施之初,我们采用了让一部分人先富起来。

把一些团队先“骗”上来,形成一个示范效应。那选择先“骗”谁?经过再三思考后,我选定了网站成为第一个“受害者”,网站主要负责京东的首页、单体页、详情页等。选择它的原因在于,一方面大家都觉得它在业务中蛮重要,而且量很大;另外一方面是,在技术上也比较适合,比较好切。因为网站比较规整。整个的架构流量进来,通过Web服务器展现网页,从后台取数据和图片。而正好图片是我带的团队做的,跟动态内容已经有很好的配合。

2015年的上半年,我和团队用了整整半年的时间重点来做这个项目。网站的完成后,其他团队也都陆续开始实施。


到目前为止,除了存储类、数据库类的,全公司所有的应用都用Docker来发布。


机器学习


我很有幸在2013年、2014年、2015年三年干了比较大的四个领域,分别是存储(非结构化存储和结构化存储)、中间件体系、内部的云,都是比较大的项目。2016年年初,我做了很多的思考和研究,觉得在做好系统建设并持续维护好之余,我得做一点新的事了。


结合技术热点和公司需求,我开始做分布式的机器学习,把它平台化去支持比较多的业务。


这里面大家可能会问两个问题,机器学习是不是相对高冷,有的人或者很多产品是不是不太需要。


其实这个问题得这么来看,还是那句话,历史洞察未来。比较早的时候,一般程序员都不会写数据库,只有专业的DBA才会写存储过程。但是现在只要是一个码农,他都会写存储过程。大概十年以前,只有数据科学家,才会写。而现在一般的程序员,都需要写,这是一种必备的技能。


机器学习也一样,可能前两年,主要是一些博士毕业的人,可以搞一些机器学习和训练模型。我觉得接下来,可能很多公司,不论大小,对工程师来说,都需要用一些机器学习的方法来做一些工作。所以在一家有一定规模的公司里面,一定会出现一个情况,就像数据库平台化、中间件平台化、存储平台化等一样。


平台化一方面会预先训练很多模型,积累很多算法。另外一方面,会让这个东西形成体系,去更好地支持业务。所以现在主要在做的是机器学习平台化,找到一些点。比如智能客服、网站内容更多的个性化营销。


个性化营销什么意思?有一个用户想买一台彩电,他经常会浏览这个电视,但是一直没买。这个时候,其实可以通过数据处理,一些模型训练识别出来,用户是想买这台电视,有哪些特征等,然后预测,他是因为什么原因没有购买?如果是价格原因,可以为用户发放专属的优惠券,从而促使用户完成购买决策。这是京东专享已经实现的功能。


另外再讲一个订单履约,用机器学习来降低公司运营成本的有趣例子。大家都知道,我们有时候在电商平台下了单,其实也是可能取消的,而且这个取消一般来说都是在下单时间之后,基本上买完之后,立刻就后悔了。因为一开始他没付出,但花了钱,又很心疼,但是这种下单完成后又取消订单的行为,其实对电商平台运营成本有很大的影响。


为什么?原来的流程是这样的:你下了订单,买了手机,订单文本生成了。到了OFC模块,订单就下到库房。库房工作人员就扫码,把这个手机拿出来了。拿出来之后,如果用户过一会取消了,这等于之前的流程就白折腾了,相当耗费库房的资源。


所以我们通过机器学习做了这样一个事情——订单稳定。什么意思呢?结合用户的很多特征,比如说这个人的收入水平,在过去购物历史上是不是喜欢取消订单。如果有一个人在电商网站上买过一万次,没有取消过。那么接下来,他购物时应该也不会取消。我们判别这个用户是一个花钱绝对不会反悔的人。如果有一个用户购买过一百次东西,取消过20回,那么接下来这个用户购物后再取消的可能性也是很大的,这是用户的一个特征。


另外的特征可以根据订单的商品、价格维度等。如果某款手机,历史上很多人买了之后,都点了取消,那么它的被取消概率肯定还是高。单价高的商品被取消的概率也可能高,比如买一卷卫生纸,其实很少有人取消。所以就可以训练一个模型来预测:用户在什么情况下、下单后多长时间可能产生取消动作。


如果我们预测用户可能在十分钟左右取消,那么我们给他冷静十分钟。如果他没取消,我们再继续他的订单。做这个事情就会给公司节省不少成本。


这是其中的一方面改进,陆续还有一些其他项目。比如说我们会对用户的商品评论做情感分析,做更好的商品评论的排序,这都是使用机器学习系统。


写在最后

最后,想和大家分享一下,其实所有的技术、所有的项目,特别是一些大的系统,设计开发仅仅是第一步。把它设计好、开发好,最后推出来,这个项目并没有完成。所有项目都不是一锤子买卖,后续如何持续有效地维护它,改进它,让它更好服务于业务才是最重要的。


另外就是客户关系和服务意识也非常重要,所有人或者项目都是有客户的,不管你是在研发团队里,处于哪一个层次或做哪一个方向的,其实你都有客户,客户的关系和服务意识至关重要。


对于技术的负责人,不管是经理、总监还是CTO,都需要对于业务和技术都要有一定敏锐度和前瞻性。心比天高,脚踏实地!简言之可以想的比较高、比较远,但是事情还是需要脚踏实地地去做。


作者简介:

刘海锋,现任京东商城总架构师,基础平台负责人。2013年加入京东,曾担任京东云平台总架构师。曾担任首届京东架构委员会主任,推动各个技术团队的横向交流与合作。曾获得“2014年京东集团风云人物”奖,带领团队连续获得“2014与2015年研发体系优秀团队”称号。目前主要负责软件定义数据中心与容器集群、存储与数据库技术、机器学习应用、商城整体架构与运维等技术方向,并负责指挥618和双11技术备战。

长按订阅更多精彩▼

640?wx_fmt=jpeg



推荐阅读
  • H5技术实现经典游戏《贪吃蛇》
    本文将分享一个使用HTML5技术实现的经典小游戏——《贪吃蛇》。通过H5技术,我们将探讨如何构建这款游戏的两种主要玩法:积分闯关和无尽模式。 ... [详细]
  • 七大策略降低云上MySQL成本
    在全球经济放缓和通胀压力下,降低云环境中MySQL数据库的运行成本成为企业关注的重点。本文提供了一系列实用技巧,旨在帮助企业有效控制成本,同时保持高效运作。 ... [详细]
  • 本文探讨了如何在PHP与MySQL环境中实现高效的分页查询,包括基本的分页实现、性能优化技巧以及高级的分页策略。 ... [详细]
  • 我的读书清单(持续更新)201705311.《一千零一夜》2006(四五年级)2.《中华上下五千年》2008(初一)3.《鲁滨孙漂流记》2008(初二)4.《钢铁是怎样炼成的》20 ... [详细]
  • 如何将955万数据表的17秒SQL查询优化至300毫秒
    本文详细介绍了通过优化SQL查询策略,成功将一张包含955万条记录的财务流水表的查询时间从17秒缩短至300毫秒的方法。文章不仅提供了具体的SQL优化技巧,还深入探讨了背后的数据库原理。 ... [详细]
  • 利用Node.js实现PSD文件的高效切图
    本文介绍了如何通过Node.js及其psd2json模块,快速实现PSD文件的自动化切图过程,以适应项目中频繁的界面更新需求。此方法不仅提高了工作效率,还简化了从设计稿到实际应用的转换流程。 ... [详细]
  • 深入解析C语言中的关键字及其分类
    本文将全面介绍C语言中的关键字,并按照功能将其分为数据类型关键字、控制结构关键字、存储类别关键字和其他关键字四大类,旨在帮助读者更好地理解和运用这些基本元素。C语言中共有32个关键字。 ... [详细]
  • Maven + Spring + MyBatis + MySQL 环境搭建与实例解析
    本文详细介绍如何使用MySQL数据库进行环境搭建,包括创建数据库表并插入示例数据。随后,逐步指导如何配置Maven项目,整合Spring框架与MyBatis,实现高效的数据访问。 ... [详细]
  • CSS Border 属性:solid 边框的使用详解
    本文详细介绍了如何在CSS中使用solid边框属性,包括其基本语法、应用场景及高级技巧,适合初学者和进阶用户参考。 ... [详细]
  • 2023年,Android开发前景如何?25岁还能转行吗?
    近期,关于Android开发行业的讨论在多个平台上热度不减,许多人担忧其未来发展。本文将探讨当前Android开发市场的现状、薪资水平及职业选择建议。 ... [详细]
  • 本文详细介绍了 `org.apache.tinkerpop.gremlin.structure.VertexProperty` 类中的 `key()` 方法,并提供了多个实际应用的代码示例。通过这些示例,读者可以更好地理解该方法在图数据库操作中的具体用途。 ... [详细]
  • 软件测试行业深度解析:迈向高薪的必经之路
    本文深入探讨了软件测试行业的发展现状及未来趋势,旨在帮助有志于在该领域取得高薪的技术人员明确职业方向和发展路径。 ... [详细]
  • 二维码的实现与应用
    本文介绍了二维码的基本概念、分类及其优缺点,并详细描述了如何使用Java编程语言结合第三方库(如ZXing和qrcode.jar)来实现二维码的生成与解析。 ... [详细]
  • CentOS下ProFTPD的安装与配置指南
    本文详细介绍在CentOS操作系统上安装和配置ProFTPD服务的方法,包括基本配置、安全设置及高级功能的启用。 ... [详细]
  • 本文详细介绍了PostgreSQL与MySQL在SQL语法上的主要区别,包括如何使用COALESCE替代IFNULL、金额格式化的方法、别名处理以及日期处理等关键点。 ... [详细]
author-avatar
通天论坛it技术
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有