@gaoxiaoyunwei2017
2020-05-09T18:22:17.000000Z
字数 7620
阅读 717
白凡
今天给大家带来的分享叫做《那些年我们追求过的工程能力》,这个名字我之前和北大的一个老师在沟通的时候,他说其实现在有些人在做这样的事情,叫软件工程考古,我说我们这个行业还没有诞生多少年呢,考古怎么出来了?写这个PPT的时候我感触很多,非常有幸我经历了百度从非常传统的研发一直到现在DevOps,甚至AI工程的变化历史,回顾的时候,其实我发现,每一段新的方法、新的工具、新的理念出现,背后都也着非常强的业务诉求的驱动。我今天跟大家聊聊百度的软件工程发展的历史。
这是我的个人介绍,愧对资深二字,其实没干多少年,大概做了七年研发,六年项目管理以及研发管理的经验。我是2012年加入百度的,那时候进到百度是敏捷教练,非常有幸合作过的产品包括百度地图、百度糯米、外卖,现在已经拆分出去的小满,智能硬件、自动驾驶、手机百度都是我们的客户。今年负责百度效率云的运营和用户增长工作。
这是我们今天讲的故事,先讲讲前言,然后我们讲一下传统CMMI时代,讲讲工程规范是什么样,再讲讲敏捷开发时代和DevOps时代。
讲到工程能力,什么是工程能力?其实就是以最短的时间最少的人力作出最高效的东西,讲到软件研发的工程,如何以更少的成本更高的质量更快的速度交付出更有价值的内容、功能和服务。对于我们百度来说,因为百度非常推崇技术,如果说BAT三家哪家最有工程师文化,一定非百度莫属,所以工程能力四个字对我们胜于任何一家公司,这直接影响了我们的创新力。我们的高管CEO,包括去年前年的齐,都直接讲,只有不懈地追求卓越的工程能力,才能带来长期的核心竞争力,才能为每个用户每个企业客户创造价值。
这是我们的研发规模,百度大概有1000以上的工程师,包括测试、开发、运维,每天能看到新增的业务需求将近7000次,内部编译集成每天发起的3000万次以上,每天产品构建的次数7万以上,最终上线的700次,也就是我们每个工程师基本上每天要接受一个新的需求,每天要进行三次以上的链路,他们产出的系统每天至少要集成七次以上。百度有大大小小几十上百条产品线,大概每天经历700次发布,这是我们在研发过程中,我们的规模其实也是我们部门的挑战。
再举个例子,今年春晚大家都在手机上摇红包了,南方同学好像不怎么看春晚是吗?那是你们的损失。短短一个月,我们单单一个项目的维度,新增的需求大概1800,解决了线上的问题大概340个,代码评审1100多次,编译11000次,自动化测试12000次,发布的版本900,在哪一个月里部署了240次。所以说BAT三家也只有我们百度只有一个月的准备时间,把整个春晚的工作做起来,这是我们的现在。其实大家在大会上看的都是说我们现在如何如何,很少有人跟你讲我们以前是什么样的,大家都说我现在怎么样,我们也有很苦的时候,我今天就讲这些故事。
百度的工程能力,如果讲进化史,可以把它分成这样三个史,最早叫CMMI时代,那个时候华为刚刚开始,大概是那样一个时期,当时我们成立了叫做项目管理,那时候我们秉承的方法和背后的思维是CMMI,那时候我们讲研发和规范,这样一套工具是什么,那时候工具比较少所以叫工具。经历了2011年开始,其实一直持续到现在我们讲敏捷的时代,为什么呢?后面我会讲移动互联网,大家都在拼速度,那时候我们也做了很多东西,引入了新的方法,我们把原来简单几个工具扩展成完整的工具链。那时候我们开始提倡工程师的个人能力,再逐渐到2015、2016年的DevOps,DevOps总的来讲反馈闭环,但其实我看了很多方法,没有把闭环讲透。其实在我们内部,在方法、工具链、能力的基础上应该关注数据。
这几年工程效率部围绕研发数据做了非常多的东西。第三部分我会着重讲数据。这些年我们的发展百度讲工程能力或者效率带来了什么?这里有一个数据的统计,大概在我刚进百度的时候,百度修改一行代表提交到上线平均需要三天,现在平均大概三个小时。我们说迭代,以前讲一个项目,我们的统计是平均百度做一个项目要21天,现在平均是6天。以前2012年的时候,刚和百度地图合作,当时他们是百分位级的,大概到了2015年的时候,到了现在的规模,去年的时候我们平均手机百度的每个版本已经降到万分多了,这就是带来的变化。
从头讲,第一个,CMMI时代,那个时候其实国内只有少数的企业意识到了传统的基于某些模型的弊端,那时候大张旗鼓提倡轻量化的研发方法,我知道的只有华为。那时候奠定良好的基础就是我们的规范。凭着记忆,那时候我们定下来的规范,首先围绕代码库,百度所有的代码库都是产品线,所以我们看代码库就知道这是哪个产品,比如APP,这都是移动端的,搜索、知识,前两位是代码库。从第三位开始,这是我们核心的问题,叫模块,模块在百度定义为可以发布的最小的,模块有什么呢?模块有两个版本的概念,一个是4位版本,4位版本用来内部开发的,内部的开发每次的提测都会更新一次,以此来标识这个模块或者这个功能项目第几次提测。围绕4位版本还有bug,这个非常好,现在想起来非常正确。
3位版本是我们每次发布服务的线上版,它对应的是什么呢?我以前在微软待过,那时候所有其它公司定义的项目都是业务项目,我们要做一个系统,我们要完成一个客户功能,但是在百度它会讲说,每一次更新一个3位版本以下,为什么呢?因为那时候百度的主要业务是搜索,大家如果做过搜索会发现,后期搜索大量的在于策略,随着搜索架构的不断优化,当时我们的工程师已经把策略独立封装到一系列独立的模块里,你在更新策略对用户输出有感知的价值的时候,所以我们的项目是这样的设计,这是直接跟我们业务相关的。每个工程师对应的工作单元就是一个模块或者多个模块,我认为这是那个时候给我们留下最好的东西。那时候忽略了一些,现在想起来,其实敏捷大的方向是对的,但是我们没有把每件事做好。这是我们当时的规范。
讲一下那个时候的工具,这是我花了好长时间从一个线下的版本里面抠出来的,中间这是我们当时的流水线,讲的是每次新增一个版本,拉出一个新的4位版本,中间要合入版本管理、编译依赖管理,做单元测试的编译,最后发布到成品库里。那时候新增的时候要手工点一下,代表我要起一个新的项目。然后提测之前要写一个单元测试单,哪怕是空的也要交一个上去。手工提测,最后编译的时候我记得你在生成模块的时候,就要写这是一个windows下开发的还是什么,要32位还是64位,编译的脚本是什么,当你把这些都填好的时候回来手工提测。百度搜索大多是C++,C++其实不是那么高效的语言,那个时候我们还要手动去管理。那时候我们用SVN,这大概是2012年以前的状态。我们现在看这个东西很过时了,很旧。但是在当时,其实没有一个新的方法和思维去牵引大家说工具应该做到什么样子,研发的过程应该是什么样子。
所以那个时候我们总结,好的是什么呢?我们有规范了,我们到底整个的软件研发,我们在管理哪些对象,这些动对象之间的关系应该是什么样子,有一个清晰的规范,至少我们是有一个工具逻辑的,虽然这个工具现在看起来不好用,真的不好用。我记得那个时候,整个上面的流水线还是Flash做的,我们每天就是跟Flash在做。不好是大量的手工操作,还有关键产出的生产过程需要额外的动作,就像提测的报告需要自己写,很多时候为什么我们说有些工作不愿意做,或者有些关键的产出报告不愿意写,因为它跟你的工作是完全两条线,做完了自己的工作还要额外地为产出的报告花时间。另外很严重的一点是,缺少从业务视角对研发过程的聚合管理。那时候百度要做一个大的功能了,只有一个产品经理是总负责人,向下问研发人员,我说你们谁是研发项目经理?他说我是,没有一个说我也是,我说你们怎么分的?这个说我管这个模块,那人说我管那个模块,只有这个模块合在一起才是一个完整的业务模块,那时候百度割裂性非常严重。
到了2011年的时候,到了敏捷开发时代,2011年发生了什么?我搜了一下,苹果发布了4S,小米手机收购摩托罗拉,微信是2011年的年底做出来的,美团通过成O2O市场第一,唐岩成立陌陌,大家从PC时代转到移动时代。
2012年8月大概我入职前一天,我的另外一个同事,他研究了百度半年以来搜索模块发布的所有频率,两到三位版本之间发布的频率,21天,当时我们部门的总监跟老板说,百度一个模块平均的发布周期是21天,当时他觉得非常慢,但慢在哪里不知道,后来说要提速。
怎么提呢?我们先来看问题,有几大问题,这是最大的问题,我刚才讲了,我们不光有角色墙、业务、RD、QA、OP之间有墙,在百度之间还有墙,就是模块墙,哪怕RD跟RD都不是一样的,所以大量的工作浪费在这些沟通协作上。大家看到原来的工具链和方法,它有bug,有无法绕开的关键性环节,需要手工操作,需要额外的动作,我相信在敏捷转型之前每个企业都会遇到的问题。另外一个问题是我们内部提倡工程师文化,到底这个工程师应该是什么样子?工程师文化我们提倡的研发标准是什么,怎么落地?所以当时一个总监到我们商业的产品那边,他第一周做的事情,他说我要看看代码,看完代码说,第一件事把单元测试写起来,现在代码是有问题的。
我记得2013年跨过一道代码,那是我见过最最令人发指的代码,直接写了1+2+3+4等于一个变量,我现在想不起来为什么会写那样的东西,不知道背后的业务目标是什么,这是我们当时面临的问题。
正好外面东风吹来了,敏捷开发,那时候中兴、华为、电信企业都在做这件事情。腾讯那时候已经转型很成功了,他们把它落到GAP的产品里面,整个腾讯号称都是已经在敏捷了。当时我们老板说我们也要做,我就是被这样一阵大风吹到了百度。所以那个时候我们提倡什么呢?三管齐下,人,首先引入外部专家,我们引入了外部很多资深教练,乔帮主、现在滴滴的卢宁等等都来了,我们有工程师的能力,我们要讲人应该具备什么样的能力,这些能力如何引入进来。然后我们说技,技术,以前我们讲工具,那就是一个模块的生命周期管理工具,现在我们把它扩展成整个研发管理的工具链,我们要把那些手中的大家不愿意做的事情自动化。法,方法,敏捷的实践已经进来了,我们要带来新的案例。
这三管都是怎么做的呢?首先是方法,这是2016年年初的时候,我们敏捷教练在起草的,叫做百度方法+,百度方法+包括了这样几个环节,第一个是互联网思维到底是什么,不确定性是什么,如何做商业模式创新,更重要的是如何做数据驱动,理念上的新方法。右侧偏重于时代的方法,从最开始产品的创新,结合了内部的情况。最开始我到的时候,我觉得非常有意思的一个东西,但是我在百度的产品线,我们有一个非常大的团队叫US,相信很多公司也有,用户体验。当时我很感慨,我说我们有这么多的武器,但是没有很好地运用起来,那时候讲数据集成和数据交互。还有软件设计,这是我们方法层面,所以我们会分成,一类是注重管理实践的,更多在上面,产品中心、高校研发,一类注重工程时间的,软件设计和持续交付。我们当时讲的时候,我现在的总监这种课程是他讲的,互联网的思维和方法。我以前讲过持续交付。
工具,拥抱敏捷,深挖场景,最开始是SCM,还有一个需求叫Cafe,加上底层的SVN,结合底层方法,看到研发是完整的生命周期,简单几个工具,其实是每个场景无法挖掘深度的场景,也无法更好地服务产品线,所以拆成三大工具,基本也是我们现在整套工具链的雏形,左下角的产品能力和迭代工具ICafe,首先第一个用户式地图,产生可视化规化,之后进入ICafe,在ICafe里面分配能力。谷歌在所有代码发生提交之后,不会立即入库,会直接把这部分代码发到云端进行变形的编译,包括了编译,包括了单元测试,所有人提交代码之后,代码不会立刻给到用户,会经过多重之质量检查,第一道是百度的(英文),如果你刚入职百度,没有很好地做员工培训的话,发现一行代码都提交不上去。过了ICode之后到了编译集群,这是我们2012年开发出来的产品,那个时候搜索编译一个资料要一个小时,哪怕改一行代码,要一个小时,有了集群以后,现在编译时间是在5分钟以内,非常高效。
能力,能力其实这也很重要,我们团队最多的时候大概30多年,这是我2016年在平安科技分享的时候说的,当时对百度的敏捷要求,不是说做了多少场培训,把什么方法带进去了,不重要,重要的是你给产品线带来什么变化。然后你要把这些案例带回来,这是我们的主脑,我们主脑最后的产品就是方法,这是我们的教练。
能力上还有另外一个,Good Coder,Code master,谷歌也有类似的。每个同学来了要做什么事呢?有些产品线是强制的,第一在系统里发起申请,然后根据考题提交Patchset,然后有一个部门产品线的CMC评审,评审通过了不算完,还要看你最近三个月提交的代码,看里面的设计思维、智能,如果这些都通过了,你得到一个Good Coder的认证,如果你能保持这个Good Coder一年以上,你有资格发起Code Master申请,决定这个人能不能加入我们CMC。CMC做什么呢?你成为他们的评审,然后你要制定编码规范,公司所有C++、PHP、Java都是CMC指定的,到去年我们部门大概Java的主席在我们这里,PHP的主席在我们部门。所以这样一套极致保证了每个工程师进入到百度以后,在工程上的追求是什么,标准是什么,规范是什么。去年甚至有些产品线严格到什么,不是Good Coder不能提交代码。在快速的产出以及质量上,尤其是面向用户体验价值的质量上我们应该选择后面的质量。
中间讲两个故事,大家觉得做了这些事是不是就成了,其实不是,2012年到2016年我们相当于推着这样一个变革的马车,一步步地在爬坡。百度可能跟传统模块正好相反,百度非常崇尚自上而下,如果一线群众不认可你这个事情,光是从上往下来推,这个事做不成,所以那时候我们做什么呢?
第一,我记得当时做ICode的研发经理推动一件事情,就是迁移,迁移的时候甚至办了一场音乐会,告诉大家,一边让乐队来表演节目,一边介绍hack。
然后教练团队做了两个事,左边这是我做的,2013年Hack了内部的沟通工具接口,诞生了爆款产品“唠叨的小黄鸡”,我当时做了一个什么事呢,我把内部的百度嗨黑了一个接口,然后只要有失败,我就把谁提交了这次Hack,直接发了,他们的经理总经理都在看。一次两次就有人来黑我,这怎么点我名,这是谁啊?我说这是请了一个外包同学,他每天干这个活,他说能不能把我去了,我说行,你先把代码改了。所以这个代码60行一个脚本,当时公司里有两千多人在用。我起了一个名字,正好那一年大黄鸭,我叫了一个小黄鸡。这是我们教练自己做出来的。这样的话,我们相当于凭自己的影响和能力在推动这个事情,非常不容易,但是最终我们把这个事做成了。
到2016年的时候,最后统计,百度迭代的周期从21天下降到5.6天,95%以上的模块从SVN迁到Git。你看到它的日常工作不是那么土豪的产品线是物理看版,土豪的产品会买电子屏,开会的时候直接在屏幕上看到所有的流水线产品线都非常完美,也就是敏捷已经是百度开发的常规模式了,没有人再提了。但这个时代有一些不是很完善的东西,因为很多时候产品线是每个敏捷教练下的单,所以每个人的风格不一样,导致我们内部研发工具提了很多定制化的需求,这样我们的工具越来越臃肿。然后由于我们讲敏捷要轻量化,第一波百度推动敏捷的人说,大家都坐到一起,不要记录需求了,都用纸的卡片,后面稍微收敛了一下,不过还是丧失了一些数据,比如前面讲的在规范里面,我们bug原来是记录在一个模块上,但那个时候我们运维上就是记录到产品迭代就好了。现在看来,反而丧失了一些数据的精确性,只不过那个时候我们没有很好地想到这些bug如何很好自然地标记掉。这时候速度是第一目标,但成本没有考虑,大部分研发要考虑成本,但那个时候没有怎么考虑成本,导致技术平台都在做,你会发现公司里面做某一类技术方向的,比如2016年我们统计公司有十个左右的深度学习平台,大家都在做这个事情,本身就是成本上的浪费。
反思完这些问题以后,再讲DevOps,讲工具链、方法、能力、数据,数据是怎么回事呢?这是2017年的时候我们在讨论的一个命题,第一已经到敏捷以后,如何引导产品线进行深层次的改进,如何减少技术上的重复造轮子。
所幸的是我们讨论之后,我们需要做什么,红色的部分是这两年我们新做的,其中中间最重要的东西是数据,研发数据链,工程师的数据,以及在技术,在原来工具链上基于数据做了工程能力的地图,为了生产地图做了流水线的插件,为了提升技术能力还做了平台化。
研发数据链,之前大家说,软件研发有两条数据,有两条链路,一条链路叫信息流,沟通、需求、文档,这是信息流,还有一条叫做时间代码流,代码、基础构建、测试、可发布的交付物。它们之间原来在百度是断开的,后来在产品里做了这样的功能,就是commit message,实现端到端的数据全景。
拿了这些数据我们能做什么?包括这些数据后面在集成流水线上是怎么生产出来的呢?我每个环节的测试工具、质量保证工具、发布工具都是一个插件插上去的,首先要提供标准数据,所以去年前年两年时间,大量的插件平台和数据平台都在做数据上的改造,接入到数据仓库里面。
自动生成地图,我们基于数据以前标准的积累做了一个规程能力地图,这里面我们定义了百度的其它主要的技术形态,每一种类型从需求一直到上线,生命周期是怎样的,应该有哪些环节,这些环节里面标准的工具是什么,工程实践应该是什么,每一个实践背后都有一到两个最多标准插件。只要不断地接入插件,不断地按照标准去做,最终就会生成工程能力的展示平台。去年我们拉了一个后端产品线,43根,在去年的时候算是中等偏上的,今年我们百度所有的能够做到60分以上。然后工程师的数据,我们在以前说代码贡献、CR,现在可视化出来了,这个数据怎么用?
晋升的时候用,百度现在在每个公司,工程师在晋升的时候,所有工程数据会直接打到TC委员会,评审的时候首先会看最近这半年一年提交了多少次代码,是不是真正做了CR,我们故把一些有特征性的CR抽取出来,就是数据要用起来了。
到了现在,下一步在思考什么,这些年有一个非常火的名字叫做什么?Container,一个软件从最开始的需求,研发过程一直到运维过程,完整的生命周期都在云上,DevOps和CICD是我们现在做的,我们希望内部先建设成一个云上百度,对外提供完整的一套云生命周期的管理,这是我们现在做的。
这些年我们对外的产出有哪些?第一个研发方法,百度方法+,工程标准,百度工程能力白皮书,右侧现在正在做的,也是我们现在正在做的,工具链百度效率云。