持续集成与迭代开发

来源:互联网 发布:网络销售外汇好开单吗? 编辑:程序博客网 时间:2024/03/28 18:43

我们应当怎样做需求调研:初识

需求分析 需求调研  敏捷开发  项目启动会议

很多需求分析的工作是从需求调研开始的,我们就从这里说起吧。需求调研是需求分析最重要的一环,也最集中地体现了需求分析的特点——既是一份体力活儿,更是一份技术活儿。它既要求我们具有一种理解能力、设计能力,更要求我们具有一种与人交往、沟通的能力。

在一个阳光明媚的下午,项目经理带领着项目组成员,参加了客户组织的见面会,一个新的软件研发项目就这样开始了。双方在一种友好的气氛中进行,双方相互寒暄,介绍与会人员,拉拉家常。逐渐地,会议开始进入了正题。初次接触客户,对于项目团队意义重大。对方对你印象的好坏,今后如何与你交往,都在这个阶段被确定下来。然而,在客户至上的今天,与客户保持适当的谦卑是有必要的,但过于的谦卑却常常给项目日后的进程带来风险。为什么这么说呢?过于的谦卑,处处都是诺诺诺,客户说什么就是什么,就会使客户变得非常强势。这样的结果就是,客户提出了许多变态的、不太现实的、不合理的需求,而我们呢却是一味地服从,客户说什么就是什么。最后我们做得很累,结果却不能让客户满意。

正确的做法是,我们对客户提出的需求进行深入理解以后,运用我们专业知识,提出比客户的原始需求更加合理、可操作的解决方案,让客户感觉你说的正是他们想要的。如果能够这样,客户不仅能够欣然接收你提出的方案,而且会感觉你非常专业,你在客户心目中的形象也会无形中提高,使你有更多的机会提出有利于开发的可行方案,降低开发的风险。这毫无疑问会形成一个良性循环,但要做到这一点并不容易,我们需要在与客户接触的初期,就运用自己的专业知识在客户心目中形成威信。

也许在见面会之前我们已经做足了功课,已经对客户提出的需求进行了一番详细的整理,也许有了一大堆疑问急需解答。但是,在最初的见面会上,不是解答具体问题的地方,这是我们常常会犯的一个毛病。作为客户,特别是客户方的领导,最希望了解的是这个项目在宏观上给他们带来的利益。因此,在这样一个场合,我们讨论的都是宏观上的问题:客户在宏观上对这个项目所要达到的目标,我们在宏观上给客户提出的解决方案,在宏观上能给予客户的利益,等等。

同时,这样的会议又是一个项目启动会议。客户方领导要传达给与会代表一个清晰的信号,就是与会代表今后要积极配合我们完成今后的工作。这时候,要清楚地弄清,客户方有哪些角色,谁是这些角色的需求制订人与负责人。这是什么意思呢?在软件项目中,特别是管理型软件项目中,客户都代表的是一个群体,而不是个人。他们代表的可能是一个单位、一个集团,甚至是一系列组织机构。在这样一个群体中,他们按照职能被划分成了不同的角色。拿一个单位来说,横向可能划分成不同的部门,财务部、销售部、采购部、生产部••••••不同的部门,由于业务的不同,对软件的需求自然是不同的;纵向又可以划分为多个层次,如高层领导、中层领导与基层人员,高层领导关心的是宏观的目标,中层领导关心的是具体的效益,而基层人员关心的是细节的每一步操作。划分清楚角色,弄清楚每个角色的需求制订人与负责人,才能在今后的需求调研中找对正确的人,使事半功倍。

俗话说:万事开头难。我们以往在项目开始的时候总感觉千头万绪不知如何着手。在这里我给大家的建议就是这三点:1)树立良好的职业威信;2)从宏观上制订目标与方案;3)进行角色分析,将与会各方代表对号入座。随后的工作,就是逐一拜访客户代表,各个击破。


一次迭代式开发的研究:什么是迭代式开发

迭代开发 需求分析

我们的软件开发存在巨大的风险,但问题到底出在哪里呢?这对于问题的解决至关重要。

1. 我们在没有深刻理解业务需求的情况下就必须完成需求分析;

2. 客户在没有弄明白自己的真正需求的情况下就被要求确定软件的业务需求;

3. 我们在没有与客户再次沟通的情况下埋头苦干,直到完成开发并交付客户。


既然问题出在这里,我们就可以制订我们的解决办法:


1. 业务需求的分析不再是一蹴而就,而是贯穿软件开发的始终。一方面,我们在与客户的持续沟通中加深业务领域的理解,进而加深对业务需求的理解,另一方面,客户也在加深对软件的理解,进而完善自己的需求。


2. 软件开发的过程不再是单反面的埋头苦干,而是双方的良性互动。定期的用户体验,可使用户及时了解项目进度,发现软件问题,并及时提出来予以纠正,使软件的开发不断朝着正确的方向前进。


这就是迭代式开发。它是对以往开发模式的一种革新,但不是对以往开发模式的完全否定与摒弃,而是一种改造。


以往的瀑布式软件开发模式将整个软件开发过程分为四个阶段:需求分析、设计、开发、测试。与瀑布式软件开发不同,迭代式软件开发首先将整个开发过程分为一个又一个的小段,每个小段大概在20个工作日左右,被称为迭代(Iteration)。一个迭代就是一个小的开发过程,如同瀑布式开发一样被分为四个阶段:需求分析、设计、开发、测试。


采用迭代式开发,就是将以往的一个瀑布,变成了数个循环往复的瀑布,使软件以进化的方式逐渐推进。


最初的迭代,开发的是软件最基本最主要的功能,经过第一次迭代以后交付给客户。这时候客户看到的,不再是虚无缥缈的需求描述,而是实实在在的软件界面。在此基础上,客户可能会认可我们的设计,也可能提出一些改进意见。修改这些意见,开始进入第二次迭代。第二次迭代可能是在第一次迭代的基础上进一步丰富和完善功能,也可能是进一步实现其它第一次迭代还未实现的功能,之后再次交付客户。


如此循环往复,使我们不断在需求分析、设计、开发、测试,以及交付中,推进我们的软件开发。这样的开发过程,注定最终交付给客户的是他们满意的软件。这就是迭代式软件开发。

 

 

 

一次迭代式开发的研究:软件开发的风险

迭代开发 需求分析 开发风险

我们的软件开发存在着巨大的风险,当我们经历了数月的辛苦工作后才发现,我们的软件并不是客户满意的软件。这时候往往出现几种情况:

1.客户开始频繁挑刺,大量的需求变更在很短的时间发生,加班再所难免,团队士气降到最低点;


2.甲乙双方开始相互推诿,谁是谁的责任,争吵不可避免,甚至最终谈判破裂,项目失败,双方不欢而散。


这些都是我们不愿看到的,却不得不面对。到底问题出在哪里呢?就在我们的开发过程中。以往的开发过程被称为瀑布式开发,它要求我们在正式的软件开发之前,在需求分析阶段,就要把客户的所有需求都分析清楚,确定下来。而在正式的软件开发的数月间,我们不再与客户交流,而是按照需求规格说明书自己埋头开发,直到最终交付客户。这样的方式,最终交付客户的风险可想而知。这种开发方式的弊端主要有这几个方面:


1.客户描述不清自己的需求。客户不是专业人士,因此在起初他们描述不清自己的需求,只有一些简单的想法。一句经典的话是这样说的:When I saw it, I have changed.只有当他们看见我们制作的一个个demo版界面原型时,甚至操作着原型的模拟操作流程时,他们才开始整理,并使自己的需求逐渐清晰起来。这需要一个过程。


2.我们理解客户的业务领域也需要一个过程。我们是技术专家,我们掌握着丰富的软件知识,但我们不是领域专家,我们不了解客户的业务领域,因而这不能让我们的软件获得成功。我们只有深入理解客户的业务领域之后,才能深刻理解客户的业务需求,才能使我们的软件成功。这需要一个逐渐深入的过程,因此不可能在软件开发的初期那短短的需求分析阶段完成。


一切的一切说明了一点:我们必须改变我们的开发方式。我们需要一个持续的需求分析过程,这个过程应当与我们的设计、开发、测试过程同步;我们需要不断地向客户展示我们的软件成果,听取客户的意见,使我们开发的软件不会偏离正确的轨道。而这就是迭代式开发,另一种软件开发模式。


一次迭代式开发的研究:怎样进行迭代式开发

迭代开发 持续集成 需求分析 软件开发

前面我们提到了迭代式开发的巨大优势,它可以降低我们软件开发的巨大风险,它可以使我们把握用户的真正需求,它可以使我们从错误与偏差中及时纠正过来,那么我们应该如何进行迭代式开发呢?要回答这个问题,我们首先要弄清迭代式开发与传统的瀑布式开发的差别在哪里。

1.需求分析的差别

与传统的软件开发一样,迭代式开发同样需要与客户进行一个充分的需求分析。但与传统的软件开发不一样,迭代式开发不要求初期的需求分析是一个完全的需求分析。它承认需求分析需要一个过程,它承认需求的变化(或者说需求是一个进化的过程)。所以,在迭代式开发中,起初的需求分析只要进行到当时的阶段能够理解到的程度就可以了,而不是瀑布式开发那样需要完成所有的需求分析并最终确认下来。至于其它还没有分析到的内容,我们会在每个迭代的需求阶段逐渐加深理解,逐渐细化,直至最终完成软件的开发。因此,迭代式开发的需求分析始终贯穿整个软件开发的过程。


2.软件开发的差别

迭代式开发的软件开发阶段,与传统软件开发的方式存在着巨大的差异,迭代式软件开发采用的是持续集成(Continuous Build)的软件开发方式。传统的开发方式,当需求被确认下来并开始软件开发时,首先进行的工作是分模块进行开发,就如同车间生产一样,不同的模块被分配到了不同的小组或个人进行分头开发。在此期间,谁都不能拿出可运行的软件交付物,直到开发中后期的集成阶段。而迭代式开发不同,它将整个开发过程分为了数个迭代,并且在每个迭代结束时要交付可执行的软件,正因为如此,迭代式开发采用持续集成的方式。


持续集成的基本思想就是每个人每天完成的开发工作都能立即集成为一个可运行的软件产品。为了实现持续集成,我们必须改变我们的开发顺序。传统的开发顺序,首先是开发并完善各个子模块。当各个子模块都完成开发以后,才最终组装并集成为一个可运行的软件。采用这种顺序开发不可能保证持续集成。迭代式开发,在初次确认业务需求以后,首先开发的是软件最主要最基本的功能,在开发这些功能时也往往只考虑主流程而忽略分支流程。采用这种方式,可以在最短时间内交付可以运行的软件。之后我们交给客户去体验、去确认、给我们提意见,我们再不断去调整和完善这些主要功能,或者开发其它次要功能,使软件开发以一种进化式的方式进行下去。


采用持续集成的方式,使软件开发中利益攸关的各方随时可以了解软件开发的进度,以可视化的方式看到软件开发的成果,及时纠正软件开发过程中的问题。更重要的是,所有利益攸关方中最重要的一方——客户,由于自身的局限描述不清自己的需求,通过可视化的方式一次一次看见可运行的软件,更直观地提出自己的意见,使自己的需求越来越清晰,并有效地告知开发者。而我们作为开发中,通过这种方式,使我们有更多的机会与客户有效沟通,从而对业务领域理解越来越深刻,也使我们的开发成果始终有客户确认,与客户的需求保持一致。即使有时出现偏差,也能及时得到纠正。最终,我们交付的软件必然是客户满意的。


由此看来,迭代式开发与传统开发,其开发的过程差异真的不小。


一次迭代式开发的研究:迭代开发从这里开始

迭代开发 项目管理 工作量评估 优先级

古人云:运筹帷幄之中,决胜千里之外。一次成功的软件开发,制订完善的项目计划是决定性的第一步,迭代式开发更是如此。前面我们提到,迭代式开发与传统开发方式差异不小,迭代式开发其过程更加复杂,协调各方协同工作的步骤也就更多。

迭代式开发的特点就是迭代,在每个迭代期都包含需求分析、设计、开发、测试。因此,迭代式开发从一开始就要求开发中的各方人员,需求分析员、设计师、开发人员与测试人员,几乎同时开工。如何组织协调呢?另外,整个开发过程被划分为一个又一个的迭代期,那么,如何将所有的工作合理分配到每个迭代期里呢?这些都是一个迭代式开发项目计划必须考虑的问题。


那么,我们应当如何制订迭代式开发的项目计划呢?制订计划前的分析是其关键之所在。


我们采用迭代式开发的目的就是希望我们的开发获得成功。一次成功的软件开发主要需要解决的是三个问题:What is needed, on time, on budget.也就是需求、时间与经费。客户看待一套软件是否成功,就是三个标准:功能是否满足需求,是否按期交付,耗费的经费是否在预算内。功能是否满足需求,是在迭代开发整个过程中逐步解决的问题,而开发周期与经费预算却是软件开发初期的项目计划中就必须考虑清楚的问题。


工作量评估是预计开发周期与人员投入、制订经费预算的关键步骤。将软件划分为若干模块,将模块划分为若干功能,再将功能划分为若干项工作,仔细评估每项工作的工作量。合计每一项工作的工作量,就是整个项目的工作量。但实际的工作量评估并非如此简单,后面将会深入讨论。


工作量评估的直接作用就是评估开发周期与人员投入。一般认为开发周期与人员投入成比例,其实是一种误解。增加人员投入并非能够缩短开发周期。随着人员的增加,培训、沟通、协调的成本都将会增大。用户期望的开发周期与可以投入的人员是一对矛盾,最终需要寻找一个平衡点,当然这也是与客户反复讨论的过程。有时,当这对矛盾无法协调时,分期开发也许是一个不错的选择,毕竟客户始终是希望软件系统尽可能早地上线使用。最后,当开发周期与人员投入确定下来时,经费预算也就是计算出来了。


为每一项工作评估工作量的另一个重要作用就是将工作合理分配到各个迭代期中。迭代开发,迭代期就如同一个又一个的格子,而评估后的每一项工作就如同一颗又一颗大小不一的石子,被投放到每一个格子中。而它们孰先孰后,则是由工作的优先级决定的。靠近主营业务的、用户使用频率高的,优先级高;远离主营业务的、用户使用频率低的,优先级低。优先级决定了工作安排的顺序,它是制订计划前分析的另一个重要内容。


总之,迭代开发始于完备的项目计划,完备的项目计划的关键在于计划制订前的分析,也就是分解后的工作项目列表,及其工作量评估与优先级评估。


一次迭代式开发的研究:准确的工作量评估

迭代开发 工作量评估

当我问起无数人,什么是迭代式开发时,人们总是抛来一副不屑的神情:迭代开发!这还不清楚?就是按迭代的方式进行开发嘛,开发过程采用持续集成的方式。但我再详细询问怎么进行开发,甚至谈到如何制订计划,以及计划前的分析整理时,人们却投来诧异与迷茫的神情:啊!迭代开发这么复杂呢?

所有对迭代式开发的实践与研究中,工作量评估往往是最令人头痛、最大的难题。当人们信心满满地决定尝试迭代开发时,工作量评估就让不少人望而却步了。工作量评估真的有这么难吗?我们应当怎样进行评估呢?


毫无疑问,工作量评估的第一步应该是工作分解。将整个系统划分为数个模块,每个模块划分为数个功能,每个功能划分为多项工作。再逐项分解工作,直到确保每项工作能够正确评估为止。一项为其10天以上的工作是不能够准确评估的,所以应当分解,直到分解为2~3天以内的小块工作。完成工作分解以后,最终合并每项工作的工作量,就是一个功能的工作量;合并每个功能的工作量,就是一个模块的工作量;合并每个模块的工作量,就是整个系统的工作量。


但是,即使将工作量适当地进行了分解,由于每个人对需求理解的不同,对设计方式的不同,技术熟练程度的不同,对同一项工作的工作量评估也是不同的。因此,要客观地评估工作量,应当采用多人共同完成的方式,而不是一个人全搞定。


首先,将分解好的各项工作,按模块按功能罗列在一个表格中,依次描述每项工作的业务需求和工作任务,使每一个参与评估的人都清楚每项工作。然后将工作量评估分配给多个人,保证每项工作都有2~3个人同时给予评估。


该阶段的评估应当是独立的,即每个人的评估结果都不会影响另一个人。当每个人完成了自己的评估以后,项目经理收集每个人的评估结果,组织会议进行讨论。


在工作量评估讨论会上,会议组织者将一项一项地讨论每项工作。对某项工作,如果参与评估的每个人评估的工作量差异都不大,说明大家对该项工作的分歧不大,选取最合适的一个工作量评估;如果某个人的评估与其他人差距较大,认真听取他的意见。也许他对该项工作的某个细节存在误解,但也可能该细节正是需求不明确的地方。停下对该项工作的评估,联系客户明确需求,之后才可以继续该项评估。


实际上,工作量评估也是一个迭代的过程:客户提出需求、评估工作量、发现需求不明确的地方、与客户确认、再评估……如此往复数轮,不仅工作量评估出来,业务需求也能逐渐明确下来。


另外,迭代开发的每个迭代期应当包括需求分析、设计、开发、测试。因此在工作量评估时应当全面地考虑进去,而不仅仅只是开发。


最后,当所有工作量被评估出来以后,是否就可以提交客户了呢?一个成熟的项目经理应当考虑更多。并非所有人在所有时间都能满负荷工作,生病、接收突发任务、人事变动,都可能影响项目进度。因此,适当地为每项工作增加一个备用时间的系数,提供一些富余的时间,可以确保项目过程更加稳健。


一次迭代式开发的研究:功能的优先级评估

迭代开发 优先级 项目管理

前面我们提到,迭代式开发最重要的两项前期分析就是工作量评估和优先级评估。工作量评估不仅能够确定整个项目的开发周期、成本预算,而且能够确定每项工作的开发周期,为工作的时间分配提供了依据。

但是,如此多的工作,谁先做谁后做,如何安排它们的先后顺序,则是由工作优先级来决定的。


迭代式开发的特点就是持续集成,也就是首先开发最重要、最基本的功能,而暂时忽略掉分支的、次要的功能。正因为如此,迭代式开发需求将优先级最高的功能放到前面最先完成,然后安排次优先级的,依此类推。总之,优先级评估决定了迭代式开发的工作安排。


那么,如何决定每个功能,每项工作的优先级呢?其决定因此很多,但通常来说,有两个因素是最基本的:是否靠近主营业务,以及用户使用是否频繁。


一个组织想上线一套管理系统,我们首先要分析它的主营业务。一个医院的主营业务是门诊系统,一个ERP的主营业务是进销存。越靠近这些主营业务的功能优先级越高。


同时,我们在需求分析过程中还应考察用户对各项功能的使用频率。一般来说,一个事物处理系统中,完成各项业务操作的功能必然使用频率最高,对各项业务操作的查询次之,而那些各种各样的统计分析报表则是频率最低的。频率高的功能优先级高,频率低的功能优先级低。


当然,决定优先级的因素还有很多,比如每项功能的成本与收益、紧急程度、战略意义等。我们可以绘制一个优先级表,一边罗列出所有影响因素,一边罗列出所有的功能,一项一项地分析,最终综合评估各项功能的优先级。


优先级评估的最重要的作用就是排列各项功能的开发先后顺序。前面我们提到,迭代式开发的最大特点就是迭代。整个软件开发过程被划分为数个迭代期,每个迭代期结束时应当提交一份可独立运行的程序,向用户演示。按照这样的思路,当软件开发第一个迭代期结束的时候,我们提交的是一套完整的程序,只是不够健壮,操作不方便,没有那些辅助的、次要的功能而已。这些剩余的功能,我们将在之后的迭代期逐渐完成。


根据这样的思路我们就明白了为什么我们需要进行优先级评估。将主营业务的、使用频繁的功能首先开发出来。在开发时,也主要考虑主流程而忽略分支流程。经过第一次迭代,一个可运行的、主要功能都有的软件雏形就出来了。之后,再在此基础上继续丰富、完善,直到整个项目的完成。


一次迭代式开发的研究:一个迭代式项目计划

迭代开发 项目管理 项目计划

前面我们提到,当我们为软件分解工作项目,评估了工作量,确定了优先级。同时,整个项目的人员安排,也就是哪些人负责需求分析,哪些人负责设计,哪些人负责开发,哪些人负责测试,被确定下来,我们就可以制订我们的迭代式开发的项目计划了。

迭代式开发的最重要的特点就是迭代,即将整个开发过程划分为数个迭代期,每个迭代期的时间长短并非完全一致,但却差别不大,这就是迭代周期。迭代周期的长短视项目情况而定,过短可能会使项目的变更过于频繁(每次迭代都需要提交交付物与客户沟通,从而产生变更)。迭代周期过短的另一个毛病是使迭代中的每个步骤的时间过短,而使项目组成员有一种匆匆忙忙赶进度而跟不上趟的感觉,使整个项目的组织混乱。相反,迭代周期过长会使项目成员不能集中精力工作,而使组织过于松散而产生拖沓的现象。同时,当项目进度、业务需求的理解,以及其它方面出现偏差而脱离正常轨道时,不能得到及时的纠正。一个比较合适的迭代周期是20个工作日,即一个月时间。


当我们制订出我们的迭代周期以后,下一步的工作就是像填空一样,将要完成的功能,以及相应的工作项目,填入各个迭代期中。先将整个开发周期划分为数个迭代期,将每个迭代期按开发人员划分为数个格子,从而将整个开发过程制作成一个Excel表格。


随后的工作就是根据优先级和工作量,将各项功能填入到表格中。首先将优先级最高的放置到最靠前的迭代中,然后是优先级次高的,以此类推。同时,各个迭代可能会出现一些缝隙,如迭代周期是20个工作日,但填入的功能只有15个工作日。这是,见缝插针地选取一些时间短、难度小的功能插入期间,是一个不错的选择。同样,虽然迭代周期是20个工作日,但我们也可以根据实际情况上下浮动该迭代的长短,如我们选择了一个工作量为6日的功能,与前面的15个工作日组成了一个21日的迭代,这也是可以的。


另一个值得注意的问题是,在制定时间计划时不要安排得太满,应当留有一些富余,以应对一些突发事件,如项目成员生病,或者有其它突发任务需求处理。每个迭代期结束的时候,都应当对项目进度进行一个评估,是超前了还是滞后了。一个留有富余的项目计划,可以使那些滞后的工作的处理拥有更多的回旋余地。


最后,一个迭代式开发的项目计划就制订出来了。这个项目计划实际上就是一个表,详细标注哪些功能,应当由谁在哪个迭代期完成开发,各迭代期什么时间结束。它将成为一个航标,指引我们成功地完成我们的软件开发。


一次迭代式开发的研究:开始真正的工作

迭代开发 极限编程 项目管理

我们经过以上一系列的分析,工作量评估与优先级评估,制订出一个迭代式的项目计划,再经过一系统用户确认与公司评审以后,终于可以开始我们真正的开发工作。
其实,迭代式开发的执行过程,也就是制作和不断去关注与评估项目进度表的过程。因此,当项目进入执行开发过程时,项目经理应当首先制作项目进度表。现在我们看看项目进度表长得啥样儿。
在一个项目进度表中,首先被纵向划分为三个区域:未开始任务区、正在进行任务区和已完成任务区,当然还可以增加其它区域,如下阶段完成任务区,以及工作进度、费用成本的统计图等。
同时,项目进度表又被横向地划分为数个区域,每个区域就是一个迭代期。在项目初始的状态下,所有的功能以及从中分解出来的工作,按照项目计划被分配到了对应的迭代期、未开始任务的区域。
另外,另一个统计表对整个开发进度的监控比较重要,它被称作Burn-Down Table(暂时翻译为剩余工作量统计表吧)。这个统计表的横轴是项目进行的时间,纵轴是剩余的工作量。项目开始时,横轴应当是0,而纵轴,按照项目计划,应当是该项目的总工作量。每完成一项工作,就减去该项工作的工作量,直到所有工作完成,纵轴为0。如果项目是正常而平稳地进行的,整个统计表就应当是一个平滑下降的直线,直到最后在计划交付时间(Deadline)结束,这跟直线被称作基准线,但它是理想的、实际情况往往不会是这样的。在整个项目的每天都记录下当天的剩余工作量,那么这个表就呈现出一副实际工作进度曲线图。当项目因各方面原因被延后时,该曲线就会高于基准线;当项目因进展顺利而超前时,该曲线就会低于基准线。所以Burn-Down Table可以为项目经理及其成员随时掌握项目进度,及时调整项目偏差,提供方便。
当项目进入第一个迭代期时,项目经理将第一个迭代期的功能及其任务描述清楚,填入到正在进行任务区,同时不要忘记填写各项任务的负责人。众所周知,迭代开发的每个迭代期分为需求分析、设计、开发、测试几个部分,但在这个表中监控的内容可详可简。如果希望更精细化管理,可以将每个任务再分解为需求分析、设计、开发、测试几个部分分别进行监控;如果项目不是非常复杂则不用划分如此精细,可以划分为开发与测试,或者不划分开。每天早上,项目成员召开一个简短的例会,或者通过其它方式,向项目经理汇报各项任务的工作进度。项目经理收集各项任务的工作进度,在这张表中详细记录下来。如果一项任务全部完成,则将其放置到已完成任务区域,再将其它刚刚开始的任务放置到正在进行任务区。最后,项目经理计算项目剩余工作量,并将其填写到Burn-Down Table中。
记得极限编程(XP)的其中一项重要的思想就是及时发现项目进行过程中的进度偏差,并及时进行纠正,而Burn-Down Table的使用正是体现了这种思想。通过整理和绘制Burn-Down Table,为项目经理及其成员提供了一个清晰的可视化图表,表明项目当前的进度是超前还是延后。如果是超前,项目组可以进行更多的检查与测试,进一步保证项目质量;如果是延后,则不得不通过赶工、加班等方式,加快进度。

一次迭代式开发的研究:从容应对需求变更

迭代开发 需求变更 项目管理

前面我们已经详细描述了一次迭代式开发的完整过程,首先是项目计划的前期分析——工作量评估和优先级评估,然后是制订迭代式的项目计划,最后是按照项目计划执行项目。每天,运用Burn-Down Table监控项目进程,随时掌握项目进度的偏差(是滞后还是超前),然后制订相应的应对方案予以调整,直到最后的项目结束,一切似乎进行得比较顺利。但真实的情况往往不是这样,这里忽略了一个最重要的因素,那就是需求变更。

如果没有需求变更,我们就不需要采用迭代式开发了,瀑布模型足矣。正如我在第一章谈到的,我们的软件开发存在着风险,这个风险就是需求变更。需求变更无处不在,就如同我们人类面对的浩瀚无垠的宇宙,必须得有防护措施应对可能的风险。需求变更的防护措施是什么呢?那就是采用迭代式开发。那么,迭代式开发是怎样防护来自用户的需求变更呢?我们用一个情景剧来详细解读。


A先生是一个项目经理,他准备开始一个新的软件开发项目。他首先组织需求人员与客户一起进行了深入的需求调研,进行了详细的需求分析,最后制定出一份需求规格说明书,与客户进行签字确认。同时,他又组织了设计人员,与需求人员进行讨论,将所有的需求进行任务分解、工作量评估,以及优先级评估。随后与公司领导讨论,与客户领导协商,确定项目需要配备的人员、花费的资金,以及所需的时间。最后,一个迭代式的项目计划制订出来。


万事俱备之后,项目开始进入执行阶段。A先生制作了一个Burn-Down Table监控项目进度,开始了第一个迭代期。一切进行得比较顺利,项目顺利地完成了第一个迭代期的所有任务,顺利提交第一份交付物。正当大家认为项目会一直这样顺利地进行而喜笑颜开时,事情发生了——客户看到第一份交付物时,对一些功能不太满意,对这样那样的功能提出了修改意见,甚至还提出了新的功能——需求变更发生了。


当客户对需求提出变更时,我们往往第一反应就是记录,然后回去照着做,但很多经验证明这样是不对的。不加分析而草率地修改客户提出的变更需求,是造成客户频繁变更需求的根本原因。我们前面提过,客户提出需求的一个重要特点就是,当软件没有真正设计出来时,客户往往是说不清楚自己的真正需求的。因此,当他再次看到上次提出变更以后修改的内容,很有可能还不满意,这就意味着还要继续改,直到他满意为止。这样,反复修改是再所难免。


当客户提出需求变更时,我们首先应当弄明白的是客户为什么要提出这样的需求。这时候,需求分析员应当站在使用者角度,站在业务角度,去理解这样的需求,理解其提出来的动机。也许客户在做这个操作时要查看一些相关信息,也许这个数据和那个数据有逻辑关系,甚至其原因就是一个非计算机专业的人看到这个界面不容易理解、有误解,或者操作就有困难。


当理解了用户提出变更的真实动机以后,随后分析的就是这样的变更有没有必要,可不可实现,或者是否有更合理的解决方案。每次我们都会将一些客户提出的不合理的,或者无法实现的需求变更退回去,并且提出我们的理由。只要遣词得当、理由充分,客户往往能接受我们的建议而取消这些需求(多用建议的语气,少用命令的口吻)。而另一些变更需求,我们常常从用户表面的语言中分析出他们真实的需求,并提出一个更加合理的建议。这样做,客户不仅会欣然接收你的建议,而且会有一种你就是他肚里的蛔虫那种感觉,对你更加信任,你在客户心里的威信也就随之增加。


当客户提出变更需求,并且经过分析已经确定出修改方案以后,A先生就马上回去组织人员进行设计和开发了,殊不知这将是项目后期出现巨大隐患的重要原因。迭代式开发的正确做法应当是怎样呢?这个问题我们下回详细分解吧。


一次迭代式开发的研究:需求变更的关键步骤

项目管理 迭代开发 需求变更 变更管理

前面我们提到了需求变更。当客户提出了需求变更,经过与我们的需求人员的详细讨论与分析,最后确定下来了变更内容和修改方案。但这时草率地开始进行设计和开发是不正确的,它将成为项目后期的一个巨大的风险,一颗定时炸弹,为什么呢?我们来详细分析分析。

每当发生需求变更的时候,不管是大是小,项目的许多因素都会相应地发生变化。首先发生变化的是工作量。每次的变更必然造成工作量的增加,到底增加了多少呢?我们需要对其进行评估。同时,我们还要对增加的工作进行优先级评估。一般来说,新增加的工作往往优先级都是最高的,是客户急切想看到结果的部分,那么其它的工作的优先级就会收到影响,优先级就会有所下降。当工作量的增加与优先级的调整完成后,随后的工作就是项目计划的调整。


前面我们说过,迭代式开发的项目计划与传统的项目计划是存在巨大差异的。迭代式开发的项目计划其核心,就是如何将各项任务合理分配到各个迭代期中去。任务就像一个个大小不一的石子,迭代期就如同一个个网格,项目计划就是将石子分发到各个网格中,虽然有一些空隙,但大体是满的。现在新任务来了,就如同要将新的石子放到已满的网格中,有几种可能:石子很小,利用网格的空隙就可以填满了;石子太大了,如果要把这个石子放进这个网格中,就必须将里面的某个石子取出来,放到别的网格里。现在项目计划的变更就是这样。


如果新的工作量很小,往下一个迭代期挤一挤,即使超了1、2天也能挤下,那就挤挤吧,但这个迭代期可能会延期,后面工作的时间节点也必然随之调整;如果新的工作量还不小,优先级还比较高,那么只能将下一个迭代期中已有的任务取出,调整到其它迭代期中,这可能会导致后面整个的工作计划都将调整。不论怎样调整,我们都应当将调整后的工作计划告知客户。


不论业务需求怎样变更,不论项目计划怎样调整,通知客户,让客户理解,并与我们共同承担项目延期的风险,这是从无数失败的项目中总结出来的血的教训。一定要让客户明白,你们可以改需求,可以提出修改意见,但必须与我们一同承担风险。当客户意识到这一点时,也许他们就会慎重考虑了,甚至一下变更需求就会被取消。


在变更项目计划的同时,另一项重要的工作就是变更我们的产品需求说明书。在项目管理中,需求文档往往分为两个:原始需求和产品需求说明书。原始需求是客户编写的,站在客户角度描述的业务需求,而产品需求说明书是我们在对原始需求分析、理解、调研以后,剔除那些技术无法实现的内容,最后形成的文档,是我们的软件最终做成什么样的依据性文档(需求文档其实很多,如需求规格说明书、产品规格说明书等等,但都大同小异)。产品需求说明书是程序开发的依据,软件测试的依据,用户验收的依据,贯穿整个软件开发的核心。因此,当业务需求发生变更之后,产品需求说明书一定要进行相应的变更,并做好变更的记录,与客户签字确认。这样做的另一个好处就是防止客户随意变更需求,使客户对变更的提出更加慎重。


另外一个需求变更中常常出现的尴尬局面就是,当所有情况都清楚告诉客户以后,客户提出需求必须要变更,但最终交付时间却不能改变。这着实是一个相当矛盾的问题,变更必然造成工作量增加,工作量增加必然影响最终交付时间,但交付时间又不能变,这听起来既不合情又不合理,但在现实的项目中经常发生,而且各有个的充分理由,我们这怎么办呢?其实解决这种情况的办法就是在制订项目计划之初就提前考虑到。记得我们前面提到,我们在制订项目计划时应当在时间上留有一定的富余。如何制订项目计划,《越狱》这部电影给了我们很多的启示。如何成功越狱,主人公在越狱过程中的每个风险点都制订了风险规避和补救的办法,项目计划也是这样。项目需求变更就是一个风险点,因此项目经理应当在制订计划之初就应当做好准备,并提前预留出相应的时间,当项目进行过程中风险出现时才能从容应对。


总之,需求变更不是什么洪水猛兽,也不是一个项目可以完全规避得了的。我们提前准备好,从容应对之,就不是什么大不了的事情。


一次迭代式开发的研究:Where you are

迭代开发 项目管理 需求管理 进度管理

其实做一个项目经理真不是一个好的职业,它需要太多的千锤百炼才能修炼出来。这不仅需要反复经历失败-总结-再失败的轮回,而且需要有一颗无比坚强的心,能够在无数次经历无比艰难并且令人沮丧的时刻而能坚持不懈、毫不气馁。一个项目经理就像一位将军。将军百战死,而项目经理呢,经历无数项目以后沉淀下来的,更多的是疲惫与沧桑。

但凡一个好的项目经理都是要经过一次又一次项目失败的教训,似乎只有失败才能留给他们更深刻的教训与更巨大的提升。当然,这种失败可大可小。即使一些项目最终是成功了,也只是结果的成功,而项目进行过程中的失误,以及因此带来的成本的提高,过程的曲折,同样是一种失败。项目管理之难,作项目经理之难可见一斑。


项目管理之难,其真正的难处就在于,要将其做好,需要注意的地方实在太多。任何一个方面没有做好,都会造成项目的失败。文章之初提出的软件开发的风险,实质就是软件需求的风险,在项目管理中就是需求管理。需求管理的失败是大多数项目失败的根本原因,这其中包括需求理解的准确性、需求变更的管理,等等。这篇文章讨论迭代式开发,就是给大家需求管理带来一种思路。


而另一个非常重要的方面就是项目进度管理。当项目计划制订出来以后,就必须按照项目计划进行,任何的项目延期都会是一种巨大的风险。如何避免项目延期,是项目成功的关键因素。作为项目经理,如何避免项目延期呢?那就是在项目进行的任何时刻都要清楚地知道where you are,让用户清楚地知道where you are


where you are,对于我们来说就是项目进行到什么程度了。我们要随时问我们这个问题,随时评估项目进度的偏差,及时进行调整,才可能使项目如期交付。如何做到这一点呢?我们制订了详细的项目计划,计划中将每一项工作的进行时间都制订出来。这个计划就是我们的航标,将计划与进度比较,就可以随时清楚项目进度的偏差。同时,制作Burn-Down Table,随时关注还有多少工作没有完成,还剩多少时间,就可以从另一个角度直观地认识项目的进度。


当需求发生变更时,必然造成工作量的增加。重新调整我们的项目计划,就如同重新调整我们的航线。这还包括重新调整我们的人员、我们的分工,以及我们的工期,使其符合实际情况。然后我们就可以按照新的航线前进了(以往很多项目的失败,正是因为发生变更以后还是按照原有的航线前进,其风险可想而知)。


完成项目计划修改的同时,不要忘了我们的Burn-Down Table。我们要重新评估我们的剩余工作量和剩余时间,绘制到当前的时间上。只有这样,我们才能随时知道where you are,才能有效地监控项目进程。


那么,为什么要让用户清楚地知道where you are呢?一个软件项目的进行其实不光是我们自己的事情,也是客户的事情。项目一旦进行,其实客户与我们是绑在一根树上的蚂蚱。让客户知道我们的进度,能增加客户对我们的信任感;让客户知道我们的难处,会让客户与我们共同想办法去解决问题,去规避项目风险。这样做,其实对大家都有好处,何乐而不为呢?


所以,迭代式开发对有效避免软件开发的风险,作用是巨大的。但问题是,如何在项目中实际运用起来,挑战也是巨大的,很多难题需要解决,我们只有不断上下而求索,总结、总结、再总结••••••


如何提高研发质量与持续集成

持续集成 研发管理  极限编程  敏捷开发  迭代开发

随着软件业的不断发展,软件项目的规模越来越大,软件结构越来越复杂,技术要求越来越高,参与人员越来越多,管理也变得越来越难。在这样一个大背景下,如何提高软件研发质量,相信是所有软件公司都在关注的话题。但是,如何提供研发质量,这决不仅仅是一个口号,我们必须有一套行之有效的方法加以管理。然而有效的管理带来的负面影响往往是成本的提高,这包括时间的成本、人力的成本、资金的成本。在大多数软件研发项目中,时间总是很紧,人力和资金也是有限的。这样,管理者往往步入一种两难的境地:一方面为了提高研发质量而需要加大对时间、人力、资金的投入,另一方面现实情况却不允许我们这样做,这也是很多管理制度不能真正实施下去的原因。难倒没有第三种方案能兼顾二者吗?时下正流行的持续集成技术为我们提供了一个答案。
持续集成(Continuous Integration,简称CI),又被称为持续构建(Continuous Build),最初是以一种研发管理的思想被提出来。1996年,持续集成的思想首先在Kent Beck的极限编程中被提了出来。Kent Beck在他的书中是这样描述的:团队编程就是先分而治之地解决问题,然后集成。但集成的过程是不可预知的,你等待集成的时间越长,付出的代价就可能越高。因此,每完成一段时间编程,系统就应当进行一次集成,并进行相应的测试。Kent Beck先生将这里的一段时间设定在几个小时,并提出了集成的同时应当进行测试的思想(这就是敏捷开发中的测试驱动设计)。
后来,持续集成的思想被敏捷开发所吸收,并进一步提出了增量开发的思想。过去,我们解决复杂软件系统问题的编程思想是分而治之。所谓分而治之,就是将大系统划分成若干小模块,再划分为一个个小问题,分别予以解决,最后再集成。运用这样的思想,集成的周期必然很长,可能是数周甚至数月,其风险不言而喻。
增量开发改变了这样的思想。虽然它依然是将大系统划分为无数的小模块、小问题,但它不是一股脑地立即去解决所有问题,而是有选择性地解决最核心、最主要的问题,然后再以进化的方式增量开发、逐渐完善,进而解决其它问题。在这样一个过程中,每进化一次就集成一次,产生一个可运行的成果,以此循环往复,直到最终完成。这样一个过程就是迭代式软件开发的过程(详见《一次迭代式开发的研究:怎样进行迭代式开发》)。
然而,采用持续集成的方式固然好,但每几个小时就要集成一次、测试一次,如果人为地去完成,成本依然是巨大的。因而,在敏捷开发大师Martin Fowler的推动下,持续集成工具诞生了。
持续集成工具,就是将程序员提交的代码,定期从配置管理库(如svn、vss)中下载下来,集成、编译、测试,最后发布到应用服务器(如weblogic)中,同时打包形成一个版本的发布产品。一个持续集成工具,需要一个配置管理库,一个构建工具(如Ant、Maven)。同时,它还可以集成一些静态代码检查工具(如CodeStyle、PMD、FindBugs),进行自动化的代码规范性检查,以提高代码编写质量。最后,它还需求我们提供JUnit测试用例程序,进行自动化测试,虽然这并不是必选项目。
持续集成工具将不可靠的人为操作,转变成了机械自动化操作,使不提高项目成本的前提下提高了研发质量成为了可能。


持续集成工具简介

持续集成 敏捷开发  CruiseControl Hudson

2001年2月,在软件开发各领域有所建树的17位大师联合发表了《敏捷软件开发宣言》,提出了敏捷开发这一概念,至此敏捷软件开发风靡世界,为无数软件开发项目所采用。而在所有这些运用敏捷开发获得成功的软件项目中,运用持续集成工具无疑成为一项最重要的最佳实践,因为它集中体现了敏捷开发的各项思想。

持续集成工具的意义


首先,它促进了项目团队的沟通与反馈。想想看,持续集成工具使每个人每天的劳动成功及时发布到应用服务器上。你只要登陆服务器,就可以运行和查看整个项目的每项功能。开发人员可以相互学习各自的设计,需求人员可以确认开发成功是否符合需求,测试人员可以及时测试各项功能。再这样一个平台下,沟通变得简便,反馈也因而变得及时。如果需要,项目组可以随时拿出最新开发成果向客户展示,以便获得他们的反馈。


其次,它促使项目开发过程中的许多工作变得简单。每天都要无数次地下载最新代码、集成、编译、发布,还要检查代码是否规范,测试各项功能是否正常运行,这是多么巨大而繁琐的工作啊!因为持续集成工具的存在,你只需要及时上传代码,时不时看看反馈结果,多么easy的事情。它使我们腾出了大量时间去做更重要的事情——程序应当怎样设计,这无疑提高了团队工作效率。


另外,它使得增量与迭代的开发模式成为了可能。需求人员可以尽早地看到开发成果,以便尽早地与客户确认需求,纠正需求方面的问题;测试人员可以与开发过程并行,使测试工作更加充分,时间更加充足;项目经理则可以更加实时地掌握项目进度,保证项目顺利完成。


最后,它为开发团队提供了机会和勇气去及时纠正他们的错误。这一点可能不太能让人理解,但却是极度重要的。再有经验的需求分析师也有理解不到位的分析,再有经验的开发工程师也有设计不到位的程序代码。每天集成的工作,为我们及时发现问题提供了条件(问题发现得越晚,付出的代价就越大)。发现问题以后怎么办呢?也许就需要及时的摒弃有问题的代码,及时进行重构。但在过去,我们常常没有这样的勇气去重构,因为害怕它影响其它的程序。这是一个谁多说不清的潜在威胁。而现在,有了持续集成和自动化测试过程,我们可以勇敢地重构代码、彻底地解决问题。


主流的持续集成工具


目前,比较主流的持续集成工具很多,最著名的当数CruiseControl,而当下的新锐则是Hudson。CruiseControl(http://cruisecontrol.sourceforge.net/)是敏捷大师Martin Flowler旗下的产品,又是免费和开源产品。凭借大师与开源产品的号召力,当仁不让成为持续集成领域的巨无霸。它提供了与几乎所有主流配置管理工具的集成,包括CVS、SVN、VSS、CM Synergy等等,(CruiseControl没有提供对SourceAnyWhere for VSS的支持,但SAWV 5.4以上提供了对CruiseControl.Net的支持)。同时,它提供了对最主流的Ant与Maven构建工具的集成,提供了对.Net和Ruby的支持,功能不可谓不强大。


虽然CruiseControl功能强大,但随着后起之秀的一个个出现,它的劣势被凸显出来,如安装配置过于复杂、功能扩展能力不足等。在众多后起之秀中,Hudson无疑是最耀眼的一个。Hudson(http://java.net/projects/hudson/)最吸引人的特性是它很容易配置:很难找到如此容易设置的 CI 服务器,也很难找到开箱即用特性如此丰富的CI 服务器。而Hudson 容易使用的另一个原因是它具有强大的插件框架 ,所以很容易添加特性。例如,一个 Hudson 插件可以随时间的推移不断跟踪FindBugs 和代码覆盖。但Hudson只能运行在JDK1.5以上版本,这对于一些老项目来说只能是望洋兴叹。


持续集成工具是怎样工作的?

持续集成 配置管理  构建工具  静态代码检查  自动化测试

不论哪种持续集成工具,使用过程都是相似的,我们来听听敏捷大师Martin Fowler对持续集成的定义就可见一斑:持续集成是一种软件开发实践,即团队开发成员经常集成它们的工作,通常每个成员每天至少集成一次,也就意味着每天可能会发生多次集成。每次集成都通过自动化的构建(包括编译,发布,自动化测试)来验证,从而尽快地发现集成错误。许多团队发现这个过程可以大大减少集成的问题,让团队能够更快的开发内聚的软件。

每天,程序开发人员将各自开发的代码上传到配置管理工具(如SVN、VSS)中,而配置管理工具会记录下谁在什么时间上传了什么代码文件。随后,持续集成工具会定期(可以是几个小时、半天,或者一天,由使用者自己定义)向配置管理工具询问,从上一周期到现在是否有代码上传。如果有,则下载到持续集成工具中进行集成。之后,持续集成工具会调用构建工具代码编译、自动化测试,以及执行静态代码检查。如果这几项工作执行成功,则打包复制到应用服务器(如Weblogic)上执行重新发布,并形成代码检查与测试等报告;如果执行失败,则及时通过邮件通知管理者,并记录相关日志。


配置管理工具


毫无疑问,配置管理工具对持续集成工具来说是绝顶重要的,它是所有最新代码的来源。持续集成工具会定期向配置管理工具询问代码是否有更新。只有有了更新,持续集成工具才会去完成后续的工作,否则就没有了意义。目前在Java开发项目中,最主流的无疑是Subversion(简称SVN)。SVN是对CVS的升级,它通过插件的形式被集成到开发工具中,并且提供了更加方便的上传下载操作,使开发人员最厌恶的上传下载操作变得简便。SVN的另一个巨大贡献是改变了VSS那样的串行修改模式。众所周之,VSS的版本管理思路就是串行修改模式,即对于同一个文件只能一个人修改,其他人不能修改。这样的模式对应大规模团队开发来说无疑是非常蹩脚的。SVN改变了这种模式,同一个文件可以多人并行操作,但同时SVN又提供了强大的版本冲突处理机制,当并行操作的多人各自提交版本时,通过版本冲突处理机制可以顺利的合并版本,使最终形成统一版本。

当然,所有的持续集成工具都支持VSS,但VSS现在显得过于陈旧,用它的人是越来越少。这其中一个最重要的原因是,它要求服务器端必须以共享文件的形式提供给各个客户端,存在着相当的安全隐患。SAWV(SourceAnyWhere for VSS)是VSS的替代产品,它通过客户端远程接入方案下载代码,很好地解决了这样的安全隐患。但十分遗憾的是,只有SAWV 5.4以上版本才仅仅支持CruiseControl.Net这一个持续集成产品。


构建工具


对于持续集成工具来说另一个重要的工具就是构建工具。构建工具就是对源代码进行自动化编译、测试、代码检查,以及打包程序、发布到应用服务器上的工具。可以说,从配置管理工具上下载最新源代码后,所有的后续工作都是构建工具在完成。目前,主流的构建工具就是Ant与Maven。Ant是老牌的构建工具,几乎成为构建工具的一面旗帜。它通过简单的XML文件的配置,就能定义一个软件项目复杂的构建过程(就是前面描述的那个过程)。许多软件项目在发布源代码的同时都会同时附带一个Ant配置文件。一个不熟悉该项目的人,只要使用Ant运行这个配置文件,软件就被发布到服务器中,十分方便。

但随着时间的推移,人们发现了Ant的弊病。当公司里的软件产品越来越多时,虽然每个产品的构建过程都不一样,但大体过程是相似的。如果每开发一个软件产品都要重新编写一次配置文件,那实在太麻烦了,能不能将构建过程继承下来呢?为此,Maven就诞生了。


对于一个有着丰富产品,并且业务还在不断扩大的软件公司,使用Maven实在太适合他们了。同时,Maven强大的中央库概念令管理者们无比地兴奋。现在的软件项目往往需要使用第三方的软件框架,而第三方的软件框架又要使用其它的软件框架。这样,项目在引入jar包的时候会处于一种绪乱状态。如使用Spring框架的时候需要引入aopalliance.jar;使用Hibernate框架的时候需要使用cglib.jar。当项目引入的框架越来越多时,哪些jar包有用,哪些jar包无用,谁也说不清楚。当我们使用Maven后,只需要告诉Maven我们使用Spring,Maven的中央库就可以完成后续的工作。如果下一个项目与这个项目的架构相同,则我们继承这个项目的配置就可以了,一切是不是就变得很easy?


静态代码检查工具


如何提高代码质量,代码规范无疑是必不可少的一项要求。过去,代码能运行,能满足用户的业务需求,一切就OK了。但是随着软件生命周期越来越长,软件需求变更与功能扩展越来越频繁,以及人员更替的增加,管理者开始意识到代码质量的重要。提高代码质量,就是提供代码的可读性、可维护性和易变更性。话虽然这样说,但真正要做到却并不容易,特别是那些刚刚参加工作的新手。软件项目中的新手常常让管理者无可奈何,使用他们则代码质量无法得到保证,不使用呢又无法保证项目进度,也不利于新人的培养,十分两难。一个比较公认的最佳实践就是制订代码规范。

由比较有经验的开发人员制订的代码规范,可以有效地提高代码可读性,为初学者提供开发指南,避免低劣甚至错误代码的产生。但是,当项目组制订出详尽的代码规范以后,检查开发人员是否按照规范编写代码,成为管理者面临的另一个难题。静态代码检查工具正是这个难题的解。


静态代码检查工具是一种机器自动检查代码编写是否规范的工具软件。它首先有一个代码规范库,它是无数有经验的软件开发专家制订的代码规范。作为使用者,我们可以定义我们到底使用哪些规范,哪些规范不使用。然后定义出一个代码检查的范围,即哪些代码需要检查。之后运行静态代码检查工具,工具就会依次对范围内的所有代码进行规范检查,最后形成检查报告,报告哪些代码,在哪行,不符合哪项规范。


使用持续集成工具以后,静态代码检查工具就会大放异彩。每当开发软件将代码上传配置库以后,不久持续集成工具将下载这些代码,进行自动化的静态代码检查,最后将代码检查报告发布的持续集成控制台,或者发邮件给管理者。随即,管理者就会通知相关人员进行修改。

目前,比较主流的静态代码检查工具包括CodeStyle、PMD、FindBugs,它们都可以有效地集成在构建工具中。同时,它们除了拥有丰富的代码规范库以外,还支持自定义代码规范,以及对已有代码规范的规则调整。


自动化测试过程


在敏捷开发众多的实践原则中,“测试优先设计”无疑是相当重要的一个,但也是比较有争议的一个,后来逐渐形成了“测试驱动开发”方法。测试驱动开发(Test-Driven Development,简称TDD)是一种不同于传统软件开发流程的新型的开发方法。它要求在编写某个功能的代码之前先编写测试代码,然后编写相应的功能代码,通过测试来推动整个开发的进行。测试驱动开发要求开发软件不仅要编写功能代码,也要编写测试代码,这无疑将加大开发人员的工作量,延长开发时间。但是,测试驱动开发提高了代码编写质量,特别是对于频繁业务变更与增量开发更是如此。

前面提到,增量开发要求我们先开发业务功能中最主要的部分,然后再逐渐添加次要的部分,直到最终完成开发。这样一个过程中,代码始终处于变化当中,可能出现的问题就是,后面的代码完成开发了,但前面的代码出现问题了。采用测试驱动开发,每次完成代码开发,都要对所有功能进行测试,可以有效避免以上情况的出现。


同样,在大规模的团队开发中,相互协作和调用是越来越多。当某个人修改了自己的代码,可以导致另一个的代码发生错误。在这样一种风险下,持续集成中的自动化测试过程就变得重要起来。当每个开发软件进行功能开发时,都分别编写各自的测试代码,并与功能代码一起发布到配置库中。当持续集成工具下载最新代码时,同时也下载了测试代码。代码集成以后,它将对所有的测试代码执行测试。这样的过程就相当于对整个项目进行一次完整的测试,只是测试工作是由机器自动执行。通过这样一个过程,以上的集成问题就会马上发现,并及时通知相关人员进行修复。


另外,敏捷开发强调拥抱变化,这就意味着开发团队随时在应对和响应来自客户的变更。这种变更有时会很小,但有时也会很大,以至于开发人员不得不对部分代码进行重构。重构以后会怎样呢?是不是会对其它功能呢?通过自动化测试就可以及时发现并修复问题。


目前,Java开发常用的自动化测试工具就是JUnit,它可以被所有的构建工具所支持。另外值得我们关注的还有一些测试覆盖率统计工具,它们检查测试代码对被测程序的覆盖率,并形成覆盖率报告。一个比较优秀的开源测试覆盖率统计工具就是Cobertura(http://cobertura.sourceforge.net/),它可以统计整个项目的覆盖率、各包的覆盖率、各类的覆盖率,最后展示哪些代码被覆盖,哪些代码没有被覆盖。


持续集成报告


当一个软件项目使用了持续集成工具以后,许多的管理工作由不可靠的人为操作变为了机械自动化操作。作为项目开发成员,特别是项目经理,最关心的就是持续集成报告。进入持续集成控制台,可以看到所有在用的持续集成项目,哪些当前有问题,哪些没有问题,一目了然。进入一个项目后,它的历次持续集成操作被罗列出来,什么时候执行的,执行是否成功,执行失败的问题日志,都可以看到。除了这些,我们还可以看到,每次都有谁在何时提交了什么代码,自动化测试结果及其问题日志,代码检查结果及其问题日志,最后是测试覆盖率报告。

摘录自ITEYE的博客: http://www.iteye.com/blogs/subjects/fangang2

0 0
原创粉丝点击