代码改变世界

MARTIN FOWLER谈敏捷开发

2018-01-29 20:38  sophia194910  阅读(625)  评论(0编辑  收藏  举报

转自:http://www.scrumcn.com/agile/scrum-knowledge-library/agile-development.html#tab-id-9

每个人都在谈论敏捷开发(Agile Development)。但是,你是否选择了正确的方法学?你所选的方法是否正常运转?你是否应该请求顾问的帮助?你应该如何管理开发的过程?还有,如何修补那些“先天不足”的代码?轻量级方法学的大师Martin Fowler 将回答这些问题。

应该问什么?

记者:在寻找适合自己团队的方法学时,开发经理应该提怎样的问题?

Fowler:首先,他们需要 对自己的项目有一个充分的了解。他们需要了解项目中主要的风险,同时应该了解企业的文化和涉及此项目的团队成员。我一直都认为:你应该选择适合于团队的方 法学,而不是相反。实际上,“敏捷宣言”的主要规则之一就是:个人之间的交流比过程、工具更重要。团队中的个人以及这些个人协同工作的方式,这是项目成功 的一个重要因素,比对过程和工具的选择要重要得多。

记者:回到前面那个问题。第一件应该问的就是:“你所做的是什么项目?”是这样吗?

Fowler:准确地说,应该 是“你所做的是什么类型的项目”。涉及上百人的航空软件项目和只涉及六个人的网站项目,它们采用的方法学肯定是不一样的。曾经有一个人跟我谈起他的工作。 以前他认为由小变大是一个困难的过程,但是后来他发现由大变小也同样困难。大型项目所选择的方法学对于小型项目通常就不适用了。另外,软件产品的类型也是 影响因素之一。嵌入式系统和商用软件,它们采用的方法学肯定也是不同的——这有一点猜测的成分,因为我从来没有开发过嵌入式系统,只开发过商用软件。

记者:你刚才还提到,开发经理应该了解他们可能遇到的风险?

Fowler:是的,开发经理 必须知道哪些因素可能导致项目失败。例如,敏捷社群一直关注的一个重要问题就是需求的易变性。如果需求不确定、无法将需求固定在某个合理的层面上,那么选 择敏捷开发方法就会比较合适。传统的软件工程方法总是要求你将需求固定住,并且在后续过程中不再变化。因此,需求的易变性就会成为一个重要的风险源。我认为, 这种风险对于“是否选择敏捷方法”起着决定性的作用。

记者:你刚才提到的第三点是“企业或者开发团队的文化”。你好象认为这比方法学本身还要重要,为什么?

Fowler:很明显,如果我 能有一打顶级的程序员,而他们又能很好地合作,我就会让他们自己去尽情发挥。这时,使用什么过程根本就无所谓,因为他们的天才一定会让我们胜出。这是我们 这一行中的一个决定性因素:如果优秀的人能很好地合作,那么他们一定比普通团队做得更好,因为他们自己就会找到最适合他们的工作方式。实际上,这也是敏捷开发过程中的一个非常重要的概念。OTI 的Dave Thomas说,这个世界上有两种开发者:适合他的和不适合他的。他的方法学就是:雇佣那些适合他的人。这正是OTI 之所以获得成功的重要因素之一。

记者:假如你的公司里没有一个真正意义上的“明星程序员”,而只有一些不那么出色的、需要大量管理工作才能保证代码质量的程序员,你会怎么办呢?你有什么办法弥补人员上的缺憾吗?或者你要把他们全都解雇掉,然后再从头开始?

Fowler:呵呵,如果可行 的话,我就会把他们解雇掉,然后重新雇一批聪明的人来。不过,这通常都不可行,你必须充分利用手上的资源。你必须认识到:即使没有一批天才,只要让一批庸 才很好地合作,也能获得很好的效果。而作为经理,你应该做的就是:给没有良好传统的团队灌输一个合适的过程。同时,对于个人能力不那么突出的团队,我会非 常重视提高他们的能力。如果你能提高他们的个人能力,那么你也能获得更多的优势。不过,这并不意味着我要放弃过程的引入。

记者:现在,开发经理已经知道自己要开发的是什么样的项目,也知道项目的主要风险所在,对企业文化也有了足够的了解。那么,他应该如何借助这些信息来指导他的团队选择正确的方法学呢?

Fowler:在了解了 这些情况之后,就应该去阅读各种不同的方法学,并拿你拥有的这些信息去和这些方法学的约束条件作匹配,从中做一个最佳选择。然后,让你的团队实施所选的过 程,并坚持几个月。注意:应该完全按照这种方法学所说的去做,哪怕它所说的听起来并不是一个好主意,也照着它去做。我看到很多人选择一种方法学,却不照着 它所说的做。这是一个非常严重的问题。比如说,在极限编程(Extreme Programming,XP)的典型情况下,人们会说:“我们想要进行极限编程,不过不想采用其中‘测试’那一部分。”当然了,如果你不按照XP 的要求那样进行严格的测试,整个过程都会失败。因此,你应该根据自己的经验来判断哪种方法学适合于你,然后全力以赴地实施它。这是敏捷开发的一项重要原则。

何时寻求帮助?

记者:假设一个开发团队已经提出了恰当的问题,挑选了一种方法学,并且开始尝试⋯⋯但还是遇到了困难。开发团队应该在什么时候寻求外部的帮助呢?

Fowler(笑):我的公司从事大量的顾问工作,恐怕我的答案会有个人因素吧?正如我前面说过的,经验丰富的、聪明的、优秀的程序员,他们总是能干出卓著的成效。因此,引进一些好的经验和一些好的建议总是会有所帮助的。

记者:外部的帮助对开发团队有什么好处?

Fowler:有几种不同的方 式。很多干这一行的人采用的都是“导师制”的方式:从团队之外带来一个人,让他作为整个团队的导师。这个人要成为项目组的一员,并且确实做一些开发工作, 但他的主要职责是指导其他人。显然,如果你涉足一个比较新的领域,导师制会是一个不错的选择。我们在ThoughtWorks 采用的方式则是所谓的“合作制”:开发团队中大约1/3 甚至1/2 的人来自顾问方。这些人有两件事要做。首先,他们帮助项目获得成功;同时,他们还要教给其他人如何工作。合作制的好处在于:顾问能更好地理解团队的工作, 团队的成员也能获得更合理的指导,并从中学到更多的东西。

记者:哪些迹象表示团队需要帮助呢?

Fowler:哦,我是 坚定不移地相信迭代式开发的,也就是说,我们应该在每次迭代结束时都发布有商业价值的代码。如果你发现某次迭代发布的东西不够多,或者发布的质量不够好, 这就意味着你遇到困难了。此时,你就应该寻求帮助。的确,迭代式开发很有价值。比起瀑布式开发,迭代式开发能让你更好地跟踪项目的进度。开发者可以管理自 己吗?

记者:能不能让开发者自己管理自己?或者,在什么时候需要专门让一个人来管理开发者?

Fowler:呃,这个 问题的答案取决于你如何看待“管理”这个词。任何一个团队中都有非常重要的管理者:他们帮助人们分工协作,他们保持团队中、团队与外部良好的人际关系。这 些东西,从传统角度来看并不属于“管理”的范畴,但这的确是管理者的责任。为了进入软件开发这个行业,你必须有一定的才华。我是说,在软件开发者这个圈子 里,哪怕比较差的那一部分,他们也是相当聪明的。只有那些才华横溢的人才可能出人头地。所以,我一直都认为:软件开发是一项专业工作,正如律师、医生的工 作是专业工作一样。而软件开发者,他们所做的是专家的工作,也应该得到专家的待遇。你不可能让一个普通行业的管理者到律师事务所去教这些律师怎么工作,也 不可能让一个非医学专业的人到诊所去教医生如何治疗病人。同样,你也不应该让一个没有技术背景的人去指挥程序员、设计师们的工作细节。因此,管理很重要, 但我们所说的这种“管理”和大多数人所理解的“管理”根本不是一回事。

记者:那么,管理者应该做什么呢?

Fowler:呃⋯⋯创造一个良好的环境,让所有人能齐心协力解决问题。然后,保证团队所有成员都能顺畅地彼此交流。我见过一位非常优秀的经理,他就很善于促进团队成员之间的交流。在他的团队中,每个人都知道项目的进展情况,成员能够很好地协作解决问题。

重构适用于什么地方?

记者:你可以算得上是“重构之父”了。重构似乎在很多方法学中都适用。你对于重构的定义是怎样的?

Fowler:重构(refactoring)是这样的一种技术:在不对代码的功能特征作任何改变的前提下,修改现存代码的结构,以提高设计的质量。

记者:你认为重构适用于开发过程的什么地方?

Fowler: 人们通常会在两个地方使用重构。最显而易见的就是:当你接手一块设计质量不高的代码时,你可能想要改进它,因此就需要使用重构。如果代码的设计质量很糟 糕,那么新功能的添加和错误的修复都会非常困难。但是你又不愿意从头开始重新编写整个软件,因为工作量太大。这时,重构就给了你第三种选择:你可以借助这 一系列技术有条不紊地逐步改进软件的结构。对于重构的第二种用法则是在XP 项目中的那种方式。在进行极限编程时,你会持续不断地使用重构。每天你都会对自己写下的代码做一些重构。所以,每当你要开始一个新任务时,你就会看着以前 的代码说:“这些代码能让我轻松地加入这项新的功能吗?”如果不行,你就会重构它,使得新功能的加入更容易。在努力让测试能够通过的过程中,你可能并不太 关心设计的质量,而只是关心如何实现功能;但是,一旦测试能够顺利通过,你就必须进行重构,将设计质量提高。总之,在进行极限编程时,你会持续不断地对代 码进行重构,以保证设计质量不会降低。因此,这种方式与前面所说的“处理遗留代码”的方式有所不同。不过,如果你成功地通过重构将遗留代码的质量提升到了 一个相当高的标准上,那么你应该会采用XP 的风格进行后续的开发。

记者:除了XP 之外,重构还适用于别的方法学吗?

Fowler: 重构适用于任何方法学。只要你现有代码的设计质量不合你的要求,你就应该考虑重构它。不过,如果有一整套自动化测试的支持,那么重构会更有保障,因为自动 化的测试是重构的一个重要的前提条件。如果你无法使用自动化重构工具的话,至少要有自动化的测试。有很多人在瀑布式的开发中也成功地使用了重构。所以,只 要你希望改进代码的质量,重构就是值得考虑的技术。

记者:有没有哪种方法学不鼓励重构呢?

Fowler:我想,的确有一些方法学试图降低对重构的需要。基于工程的方法学的核心思想就是:在写任何一行代码之前,你必须先完成整个设计。这种思想认为:如果你的设计做得正确无误,你就不需要重构,因为代码质量一定是非常高的。当然,实际上很难把设计做得那么好。

记者:既要让开发者有重构的自由,又不能失去对代码和配置的控制,开发经理要如何应对这种矛盾呢?

Fowler: 重构与代码的所有权并不矛盾。不过,在那种强调代码所有权的方法学中,的确难以进行重构。在我看来,代码的所有权大抵有三种形式:强所有权、弱所有权、以 及集体代码所有权。XP 鼓励的是集体代码所有权,有人认为这是“没有代码所有权”,但实际上这意味着“所有人拥有所有代码”——任何人都可以在任何时候修改任何一部分的代码。之 所以将它称为“集体代码所有权”而不是“无代码所有权”,是因为团队作为一个整体负责保证所有代码的质量,因此代码就是集体所有的。“强代码所有权”则是 另一个极端:这种模型将代码分成几大块,交给每个开发者一块,每个开发者只能修改自己的那一块代码。而在“弱代码所有权”的模型中,仍然需要将代码分成 块,并分配到人,每个人负责确保自己那一部分代码的设计质量。但是,如果有需要,其他人可以来修改他负责的代码。这也可以看作是与代码的拥有者之间的某种 合作关系。可以看出,强代码所有权的开发模式并没有阻止开发者进行重构,但在这种模式下重构的确会变得困难。一个典型的例子就是给方法改名:你的代码中有 一个方法,它的名称不能很好地描述它的用途,因此你希望将它改名,给它起一个更具有描述能力的名称。但是,如果你的团队采用了强代码所有权的开发模式,而 你想要改名的又是一个公开的方法,你就必须费很大的力气才能完成这次改名。因为这个方法可能被很多其他的地方调用到,而那些调用它的代码可能是由其他人来 拥有的。在这种情况下,你必须将改名之前的旧方法标记为“不推荐使用”,并使其调用改名后的新方法。这会大大降低你的效率,并且让你感到非常烦躁。而在弱 代码所有权的模式下,你也许就完全可以直接修改那个方法的名称,并修改它所有的调用者。这并不是说没有人对其他的代码负责,只不过他们可以给你一定程度的 方便,让你完成你的修改。如果你使用了自动化重构工具的话,这样的方便就尤其重要了——在这种工具中,给一个方法改名只需要点击一个按钮并输入新的名称就 行了。如果要选择弱代码所有权或者集体代码所有权的开发模式,就必须同时选择一个同步控制系统来进行源码控制。CVS 就是这样的一个系统,它允许多人同时更新同一块代码,并通过冲突检测等技术来保证不会把事情搞乱。

要不要敏捷开发?

记者:什么时候不应该使用敏捷开发?

Fowler:当你能获得固定不变的需求时。如果你知道需求是固定不变的,你也了解自己要使用的技术,对于开发团队的能力也很清楚,那么传统的软件工程方法会更合适。

记者:你遇到过这种时候吗?

Fowler: 呵呵,问题就在这里,不是吗?实际上,我们总是遇到无法确定的需求。那么,你要怎么面对这些变化不定的需求?敏捷开发者们说:好吧,让我们假设“无法确定 的需求”是随时都存在的,并提出一种能够包容它的开发过程——实际上,还不仅仅是包容,而是欢迎这种不确定性。传统的软件工程方法教我们如何将需求固定下 来。Alan Cooper、Larry Constantine 和Lucy Lockwood 所提倡的交互式设计方法很大程度上正是为了这个目的。有很多人从事于需求工程的工作,他们也是朝这个方向在努力。他们说:“我们要将需求固定下来。为了这 个目标,我们全力以赴。”但是,对于一个项目,你必须要判断它的需求是否天生就无法固定。如果有可能将需求固定,这样的开销是否值得?传统方法和敏捷开发方法,哪一种的性价比更高?说实话,我对这两者之间的权衡并没有太多的发言权,因为我几乎都没看到过有谁成功地将需求固定下来的。