我理解的卓越工程
「卓越工程」是近期曝光量比较大的概念。其根本的动力我理解是因为软件工程虽然发展了有几十年,但是软件无论在交付质量和效率上都无法达到一个“工程”的标准,我们亟待有一个根本性的全面解决方案,来帮我们解决软件实施中的各种问题。
我觉得卓越工程这个词组非常好,一个形容词,一个名词,比较好的说明了要解决软件实施问题的思路。
首先我们来看名词:「工程」。不论是原先的软件工程的叫法,还是卓越工程的说法,工程这个词一直没有变化。这意味着,软件交付是一项工程类的工作,而不是研究类的工作,也不是艺术类的工作。工程是一个应用科学,我们不能把软件实施按照艺术的方式来随性发挥,是也不能把软件实施当作研究类工作的方式来无限制的创新。软件作为一个工程,要符合工程的特点:
首先,工程一定有确定的时间周期。根据软件项目的复杂程度,这个周期可以是周、月、年,甚至几年,但是一定要有一个明确的时间期限。
其次,工程是应用科学范畴。我们应该遵循二八原则,80%需要建立在成熟可复用的能力上。可以有少量的应用新型创新,但不应该是主流。
第三,工程需要有可复制性,不需要太特殊的资源。在工程中的任何一个成员都应该是可替换的,虽然交替可能会产生成本,但是我们不应该依赖一些独一无二的资源。
最后,工程需要有能预测的结果,有明确的交付质量标准。软件项目的质量可以有差异,但是应该有明确的质量标准底线,什么是合格品。
总之,把软件实施视之为工程,需要用应用客户和工程项目的态度去应对,需要有期限、有确定性、有复制性,有质量标准。
接下来我们来分析形容词:「卓越」。怎么才算卓越的工程,我们应该怎么做才能达到卓越。这个也是本文的重点。
《从优秀到卓越》,优秀和卓越之间是有程度差异的。那软件工程优秀和卓越的标准在哪里呢?
没有任何文献来读进行过比较,我们从制造业的工程来类比这两个程度的差异。
如果是优秀的工程,它至少不应该差,所以应该能到达工程基本的标准,按照上面所述,在期限、质量上都能达到交付的基本要求。
如果是卓越的工程,在优秀的基础上,应该有所提升,在市场上会更有竞争力。一个产品或者公司要有竞争力,无非就是在产品的质量、产品的成本,产品的产量(或者单品的生产周期)上较竞对有优势,概括起来就是三个字:好、快、省。
我们确定了卓越的含义之后,就需要进一步论述怎么来达到这个目标了。
首先,我们先分析一下好快省这三个目标的关系以及是否有优先级和重点。
我们对于三个目标及其组合的分析,可以得到如下文氏图:
从中我们可以看出来,好快省三个目标事件是一个三角平衡的关系,如果偏废其中任何一个,得到往往是贵慢糙这些不良的后果。
所以,我们好快省三个目标不能有优先级和偏废,必须三个目标同时达成。这样,我们接下来的分析逻辑就变得简单了:
首先,单独分析每个目标达成的手段;
其次,进一步分析这些手段中相互有抑制作用的。
首先分析好,也就是软件要达到高质量的手段。
对于高质量,我们如果类比实物产品的生产,可以有几个常识:
简单的产品一般达到高质量相对简单;
重复和规范的动作一般质量相对可控;
量产和可复制的标准产品一般质量相对有保障。
通过这三个常识,我们可以推论出,在架构上,我们需要保证我们软件产品的标准可复用以及减少架构的复杂度,同时需要有标准可控的流程。
同时,我们可以进一步拆解成功能性和非功能性的高质量。对于功能性,就是软件和需求的匹配度。
在非功能性上,有很多点,这里重点指出的是软件的可读性、可维护性、可延展性。
对于功能性的质量,我们一般通过测试来覆盖,测试的质量决定功能性的质量。测试质量的评判一般通过覆盖率,单元测试的行/分支/条件覆盖率,契约测试和功能测试的场景覆盖率。
对于非功能性的质量,也有测试手段可以保障,但是我们一般用架构、标准和 CR 来保证这部分。
综上,对于软件工程的质量保障,我们从架构、流程和测试三个方面采取手段:
在架构上,通过分层、解耦、内聚等手段,降低软件架构的复杂度;
同时,在架构上采用成熟的参考架构,复用已有的软件组件,提升软件架构成熟度;
在流程上,我们首先通过制定架构和编码规范,加以 CR 和静态扫描能力保证代码的质量标准;
在测试上,我们采用分层测试以及提升测试覆盖度和测试的频次来保证测试的质量。
同时,在流程上,我们对于每一个软件开发的步骤需要有明确的质量标准,分段保障质量。
在这些手段中,CR、静态扫描、测试都会增加相应的开发成本,和省是有冲突的。同时,质量标准以及各阶段严格的质量要求,客观上会引起返工延长交付周期,和快也有冲突。
接下来,我们来分析快这个目标。
在传统的制造业,提升生产效率最有效的手段就是 Mass Production,通过标准和可复制的手段,提升效率。这个手段,在质量和效率上是可以做到双重提升的。
同时,在现代制造业,产品往往是由于各种标准的零部件组装起来的,零部件的批量标准化交付,在组装环节可以极大的提升效率。
在软件开发上,也可以采用类似的手段:
将大的软件产品在架构上分解成小的子系统和组件,分批交付;
将全的目标产品拆分成 MVP 和扩张功能,分阶段交付;
采用成熟的软件架构和可复用的标准组件,提升软件实施的标准化程度和复用性。
同时,在整个软件交付的过程中,如果可以引入自动化技术,做到代码即产品,也可以提升研发效率。
自动化部署、容器、serverless 等技术,降低部署和发布成本,提升效率。
最后,我们看一下省这个目标。
在软件开发中,主要的消耗就是人力成本。所以,要做到省,最关键的就是需要减少人力的投入。
我们也可以参考传统的制造业是如何降低人力成本的。降低人力成本的手段无非有两个:用更便宜的资源和用机器替代人。
在软件行业,这两个手段也是有效的。
用更便宜的手段,无非就是要减少相应功能开发的门槛。以前所有的软件开发都需要机器语言和汇编语言,对比现在可以用高级语言进行开发,对于开发者的要求是明显降低了。未来,对于一些功能,可以引入类似低代码的方式,比如现在对于报表开发就有各类拖拽式的 BI 工具,那么人员技能要求这块就可以进一步降低,甚至可以将软件开发和业务分析的人员做到合一。
用机器替代人,指的就是自动化。在测试中,我们自动化的手段比较高,包括持续集成、契约测试、场景回放,都是说的测试自动化。在架构和编码上,自动化程度相对较低。一些编码规则的扫描目前可以说做到了一定的自动化、开发流程的 pipeline 也可以做到自动化。架构上的自动架构设计,包括功能点和参考架构的自动匹配;编码上的代码自动生成,是可以考虑的点。相信也是外来会突破的方向。
所以,对于省这个目标,我们可以采用的手段包括:
低代码方式进一步降低开发门槛;
测试自动化;
开发流程自动化、平台工程;
自动化代码扫描;
参考架构库和架构自动化;
代码自动生成。
这些自动化的手段都是对开发效率补充,目前看没有太多和高质量的矛盾,代码自动扫描这个手段可能在一定程度上会对拉长开发周期。
最后,我们归纳一下前面对于不同目标有抑制最用的手段:
CR、静态扫描、测试都会增加相应的开发成本,在好和省上面有冲突;
质量标准以及各阶段严格的质量要求,客观上会引起返工延长交付周期,在好和快上面有冲突;
代码自动扫描这个手段可能在一定程度上会对拉长开发周期,在省和快上面有冲突。
对于前两条,我们更倾向于质量的保障,在省和快上面的冲突可以通过自动化以及复用的方式去提升解决。
对于最后一条,这个扫描我们在实践中基本上是十几分钟到小时级的开销,基本上还可以接受。
最后,我们将卓越工程的范围,概括成一张图:
版权声明: 本文为 InfoQ 作者【agnostic】的原创文章。
原文链接:【http://xie.infoq.cn/article/9db2d1140cec826e17ab8cc12】。文章转载请联系作者。
评论