轻巧建模之需求篇
目录
需求初始阶段(Initial Requirements up front – IRUF)
需求从哪儿来?
来自于项目甲方,还是直接或间接的用户、经理、高级经理、操作人员、支持人员、测试人员,与你的系统有联系的其它系统的开发人员,或是维护人员?这是所有的正式需求的来源吗?事实上,提供需求、解释需求、指定需求和排列需求优先级是项目甲方的职责所在。此外,项目甲方有权利要求开发队伍投入时间去辨别和理解这些需求。要想以这种轻巧建模的方式获得成功,理解这个概念是非常重要的。项目甲方负责提供需求,开发组负责理解和实施。
这是否就意味着你可以坐等你的项目甲方来告诉你他们需要什么呢?当然不是。针对他们所告诉你的内容,你可以提出问题,进行分析,促使他们给出更具体的内容,甚而至于可以提出你自己的见解使之改变初衷。你可以建议增加一些新的需求,请注意你所提出的仅是建议,他们可以考虑作为正式的需求加以接受(可能会作出修改)或拒绝。为了找出潜在的需求,你应该经常与甲方保持联系,并借助于一些已有的文档,比如公司政策法规、以前的系统,或者公开的可用资源,比如web上的信息、书籍、杂志或你竞争对手的产品和服务。再次声明,你的项目甲方是需求的最终决定者,而不是你。我不能不强调这一点。
那么项目甲方又从哪里知道他们的需求呢?“我真希望我能这样做”,他们经常会这样抱怨现有的系统,因为他们的竞争对手能做到,但他们却不能;或者想避免过去所出现的问题;或者仅仅是想多增加一个新的功能。一些甲方,尤其是操作人员和高级IT部门经理,可能需要集成现有或即将上马的系统;或者由于某项(象必须削减计算机数量)政策而带来的需求。值得注意的是你的项目甲方应该基于大量的依据明确地阐明需求,而这些依据是应该存在的,你可以通过与之交流确定这一点。
我的经验告诉我在项目中邀请相关方面的专家的加入对找出潜在的需求是很有价值的。例如构建一个电子商务系统,我会邀请有国际化软件设计经验的人员、税法专家或者供应专家的加入。当你对系统中的某些方面不熟悉时(有可能这是你首次构造面向世界各地用户的电子商务系统),这个方法尤其有效。我经常会邀请一些外部的专家和几个甲方在一起交流一两天,来帮助我们检查是否由于我们的经验欠缺而遗漏了什么。这对于确保我们的系统是否完整是一个很重要的方式,特别是在最初定义项目所应包括的范围。这同样也能够帮助甲方进一步的思考。但是,你意识到其中存在危险吗?你所邀请的外部专家提出一些建议可能听上去是非常好的,但目前根本就用不上的。换句话说,你依然得从这些专家意见中精挑细选。
一些基本原理
项目甲方的积极参与对构造需求是非常关键的。实际操作中要做到这点存在着两个问题:第一,甲方自身的提供需求的能力以及他们(或者你)是否愿意积极地参与进来。从我的经验来看,一些项目组并没有足够的途径与甲方联系(或不知道甲方在哪),这完全是项目组自身的问题。你的项目肯定有资金,不是吗?这些资金一定是来自于以某种形式存在的项目甲方,所以他们是确实存在的。同样,用户也是肯定存在的。即使你的系统是面向大众,也至少存在着潜在的用户,你可以找到他们,同他们交谈。所以一定存在着你可以向之询问的人。你可能会说,“有时要找出这些人有一定困难”,“要让他们参与进来不是很好办”。是的,确实存在这样的难处,想办法克服它。在“解决需求分析建模中的常见难题”一节中我谈到了一些解决办法,包括没有足够的途径与甲方联系的问题。我的原则是,如果你的项目甲方不能或不愿意参与,这就意味着你的项目失去了内部支持这条成功的条件,因此你要么解决这个问题要么干脆取消这个项目,以减少损失。如果你听之任之,至少你不能宣称使用的是灵巧建模(Agile Modeling)的开发方法(甲方的积极参与是其中的一项核心内容,在AM的开发方法中必须实施)。
那怎么才算项目甲方积极地参与进来了呢?图1使用UML活动图(UML activity diagram)大体上描述了需求阶段的流程,标示出开发人员与甲方各自应承担的任务。图中的虚线把这两部分任务分开来。从图中可以看出有一些任务是共同承担的,如想法或建议的确定(identifying ideas or suggestions)、潜在需求的讨论(discussing a potential requirement)、建模(modeling),可能还有文档的开发(potentially documenting)。项目甲方单独负责指定需求的优先级,系统是为他们开发的,这当然是他们的责权所在。同样的,开发人员负责估计实现这个需求所需的资源,因为他们是实际工作人员。如果自己不作估计而采用来自于项目组外部的估计,这是不合理的也是不可取的。虽然需求的优先级确定和估算超出了AM的讨论范围,但是你可以在如XP和UP这样的软件流程(Software Process)中找到它,理解它们对于整个需求分析是很重要的。AM并不是一个软件流程,它只是应用于这些软件流程中的一种建模方法。[/url]
[url=http://www.csdn.net/editor1/images/requirementsprocess.jpg]
图 1 需求分析阶段的流程(使用UML的activity diagram)我的观点是:项目甲方应该加入需求的建模和文档开发中来,积极地参与,而不仅仅是提供信息。为达到这点,肯定需要开发人员对甲方进行培训、导引和指导,这是完全可能做到的。我曾经见过一些刚起步的小公司、大企业和政府机构中的甲方能够以非常高的效率建造需求模型以及将这些需求文档化。在电信业,在金融业,在制造业,在军队里我都看见这样的人存在。为什么这点这么重要?因为你的项目甲方才是需求的真正专家。他们知道他们想要的是什么(参见“解决需求分析建模中的常见难题”,如果他们不知道)。而且只要你愿意,他们是能够学会如何建造需求模型和将它们写下来(译注,这样你们之间就可以同一种语言进行沟通)。从轻巧的观点看,这是很有意义的,因为有更多的人将会分担需求建模的工作。
为了让项目甲方更容易地参与进来,消除行业术语方面的障碍,你应该遵循使用最简单的工具这一做法。表1列出了许多需求阶段的artifact,他们都可以用简单或复杂的工具得到。对于每一种artifact,表中都给出了对应的简单工具。图2和图3是使用简单工具的两个例子。图2表示的用粘贴纸针模拟出一个显示界面。图3是使用索引卡片建立概念模型的例子。当你在需求分析阶段引入新的技术时,比如一些可以制作很好的使用案例图的绘制工具或有强大功能的CASE工具,这就会使得你的项目甲方很难加入进来。因为他们不但要学习建模的技术,而且还要学习如何使用这些工具。使用越简单的工具,进入的门槛也就越低,由此你才有更多的机会去增进相互之间的有效协作。
图 2 一个基本的用户界面原型[url=http://www.csdn.net/editor1/images/crccardexample.gif]
图 3 两个CRC卡片我坚信需求的建立是独立于技术的。面向对象的需求、结构化的需求、基于组件的需求,这些都属于实现技术的范畴。虽然你可以选择某种技术来分析需求建立需求,但必须牢记你所真正关心的是需求本身。下面所讲的所有技术,你可以选择其中一种或几种来进行需求建模的工作。
但有时你又不得不抛开“建立与技术无关需求”的想法。比如一个很普遍的限制就是大多数的项目可以从已有的基础技术上获益。在这个层次上,需求仍然是独立于技术的。但如果你仍执著要抛开已有的一些基础技术,比如某个版本的Sybase数据库或要与SAP R/3给出的模块集成,而非得从最底层开始,那就过头了。只要你知道你在做的是什么就可以了,但不要经常性地这样干。
记住从小事做起。越小的需求(象特性(features)或者用户故事(user stories)),相对于越大的需求(象使用案例(use case))就越易于估计和实现。平均的来说,一个使用案例涵盖的功能要多于一个使用情景,这就是“大”的含义。
对于需求跟踪表(requirements tracebility matrix)的使用也需要三思而后行。跟踪能力是指能够由项目进行中所生产的某个artifact的某一方面追踪到另一个与其相关的artifact,而需求跟踪表就是用来记录这些关联关系的。它从每个需求为起点,可以追溯到所有与之相关的分析模型、架构模型、设计模型、源代码或者测试用例。使用跟踪表的组织为了保证各个阶段artifact(包括跟踪表本身)的一致性,必须要经常进行更新工作,而不是仅在受到影响时才改动。使用它的好处是你可以很容易地分析出系统中的哪些部分将会受到该需求改变的影响。但是,如果你有一两个熟悉系统的人(译注:当然你得留住他们),当系统需要改变时,通过他们来进行评估影响会更容易而且费用也会更低。在我看来,给予跟踪表的评价过高了,因为维护它所带来的开销远大于所得到的好处,即便你有特殊的工具去做这件事情。让你项目的管理层认识到它真正的价值和代价所在,让他们来作决定是否使用它。毕竟,跟踪表是一份有效的文档。他们可以据此做出决定。
需求的类型
我认为需求可以分为两类:行为类型的(behavioral)和非行为类型的(non-behavioral)。行为类型的需求描述的是用户如何与系统交互(用户界面)、如何使用该系统(用法)、或者是系统如何实现一个业务功能(业务规则)。非行为类型的需求描述的是系统的技术方面,典型的如可用性、安全性、性能、互用性、可信度和可靠性。要注意的是这两类需求有时并不一定能够完全分开来。对存取数据速度的性能要求明显是技术方面的需求,但它也会反映为用户 界面的响应时间,从而影响到可用性和某些用法。访问权限管理,比如谁能够获取特定的信息,这明显是一个行为类型的需求。但它也同样涉及到安全性这个非行为类型的需求。别紧张,不要死揪住这类问题。关键的是能够确定和理解所给出的需求。如果你把一个需求分错了类,谁又会真的去关心呢?
可能的需求分析的artifact
由于存在几种类型的需求,有可能其中一些或全部适合于你的项目;又因为每种模型都有长处和缺点,你应该综合利用这些模型,取长补短,以发挥最好的效率。表1列出了一些常用的需求分析建模的artifact,更详细的描述可见Artifacts for Agile Modeling 一文。表中的“简单工具”一栏指出生成相应artifact所常用的简单工具(使用简单工具的重要性在“一些基本原理”一节中讨论过)。
artifact
类型
简单工具
描述
业务规则定义Business rule definition
行为类型
索引卡片(Index card)
业务规则是软件必须满足的一条有效的原则或政策。
变化案例
change case
两者之一
索引卡片(Index card)
变化案例常用来描述新的潜在的需求,或对已有需求的修改。
CRC模型
CRC model
两者之一,通常是行为类型
索引卡片(Index card)
CRC模型是一组标准的索引卡片。每一张卡片被分为三个部分,分别是类的名称,类的职责,以及该类的合作者。类是一类相似对象的抽象,职责是该类所知道的或要去做的,合作者是另外一个与该类有交互的类。在需求建模过程中,CRC模型用在概念建模中,用来揭示某一领域内的概念和它们之间高层的关系。
约束定义Constraint definition
两者之一
索引卡片(Index card)
约束是对你提供解决方案的自由度的限制。把约束作为全局的需求对你的项目来说是很有效的。
数据流图
Data flow diagram(DFD)
行为类型
白板
数据流图展现系统中数据在处理过程间、实体间、以及数据存储站间的流动情况。它常用来描述系统的环境,指出与你的系统相交互的主要外部实体。
基本用户界面原型Essential UI prototype
两者之一
粘贴纸
基本用户界面原型是低精度的。它表现的是界面背后的大致想法,而非细节。
基本使用案例Essential use case
行为类型
纸张
一个使用案例(use case)就是针对一个参与者(actor)的一连串动作,通过使用案例可对该参与者的价值进行测量。基本使用案例是一个简化了的、抽象的、一般化的用案例。它以与特定技术和实现无关的方式攫取一个使用者的意图。
特性
Feature
两者之一,常用于行为类型
索引卡片(Index card)
从用户的角度来看,特性是一个小的、有用的结果。一个特性是可以用于计划、报告和跟踪的一个计量单位。它是可理解的和可衡量的,可以在两个星期内完成(同其它几个特性一起)(Coad, Lefebvre, &Deluca, 1999)。(译注:一个特性在大多数情况下等同于一个功能)
技术方面的要求
Technical requirement
非行为类型
索引卡片(Index card)
技术上的要求是属于系统中非功能性的部分,比如性能上的问题、可靠性的问题或者技术环境方面的问题。
使用情景
Usage scenario
行为类型
索引卡片(Index card)
一个使用情景通过一个或多个的使用案例或用户故事描绘一条单一的逻辑路径。一个使用情景可以表示一个使用案例中的基本路线,即愉快路径;或者该使用案例中的其它路径;或者一条跨越几个使用案例或用户故事的路径。
使用案例图
Use case diagram
行为类型
白板
使用案例图由一些使用案例、参与者和它们之间的关系组成。或者还会有一个系统边界盒。建模时,数据流图用来描述系统的环境,指出与系统相关的主要外部实体。
用户故事
User story
两者之一
索引卡片(Index card)
一个用户故事就是你与项目甲方进行的一次谈话的备忘录。它是高层次的需求,包括行为需求、业务规则、约束和技术要求。
表 1 可选的需求建模artifact
应该注意的是,并不意味着你需要将所有上面所列出的都用在任何一个项目中。熟悉你的模型这条原则(见The Principles of Agile Modeling一文)说的就是你要知道每个artifact适合在什么时候用。你对模型了解得越多,就越能够根据实际情况运用正确的artifact。
artifact的选择往往被所采用的底层软件开发流程所左右。在主页上,我简要地说明了AM与其它有着完整生命周期的软件开发流程一起使用的情况,比如XP或UP。通常不同的底层软件开发流程对需求分析artifact有着不同偏好,象XP使用用户故事而UP用使用案例。这也是你在为需求建模时应该考虑的问题。详细内容请参见AM and XP和AM and UP。
以使用为中心的方法
如何在一个商业应用中以灵巧的方式为需求建模呢?让我们来看下面的例子。在这个例子中,我们要为一个SWA Online的系统建立需求模型。在开始之前,读者必须认识到几个问题。第一,因为本文主要集中在需求建模的讨论上,如涉及到其它类型的建模,如分析建模、构架建模或设计建模,我会就此打住并给出我所著的相关文章的连接。灵巧方式的软件开发是高度反复的过程,由此实际上需求建模与其它类型建模的界线不是很明确的。第二,这里所讲的只是许多可用方式的一种,其它的方式也可能是灵巧的。记住,AM是一套基于实践的方法,它没有定义特定的,规范的一种做法,因此可采取的方式是多样的。不用担心,我会在过程中给出我可能会采用的另外的方式,但这也不是所有的 -- 保持你开放的思维。第三,由于SWA Online的开发小组采用的是Enterprise Unified Process(EUP)(Ambler,2001b)开发流程,那么使用案例就会起主要的作用。反之,如果采用的是eXtreme Programming(XP)(Beck,2000)的话,用户故事就会占主导地位。我在AM and XP一文中从XP的角度重新讨论了这个例子。第四,这个例子虽然是基于我的实际经历所虚构的,但我想这会使我们的讨论更加形象而简单。第五,最好将需求建模化分为两个不同的阶段:需求初始阶段(initial requirement up front(IRUF))和详细需求建模阶段。
需求初始阶段(IRUF)
需求初始阶段(IRUF)发生在整个项目生命周期的开始,对应于Rational Unified Process(RUP)(Kruchten,2000)中的Inception phase和XP中的第一个迭代之前。它有三个主要的目的:第一,至少从高层次上确定系统的范围,以明确你所要做的工作的范围;第二,定义系统的高层需求;第三,对于需求的含义,在甲方和开发项目组间取得一致。如果你和项目甲方在同一个地点,而且他们能就该系统应该做什么达成比较一致的意见,这个阶段可能只需要几个小时;否则的话,有可能会延长至几天或数周(参见“解决需求分析建模中的常见难题”一节)。你可能需要召开一个大的建模会议,主要是实现需求初始阶段的这三个目的。这些会议有如下特点:
§ 时间长。对一个大的项目可能需要几天。
§ 有许多项目甲方参加,以便广泛地听取他们的需求。
§ 趋向于比较正式的形式(主要由于参加会议的人数众多,而且项目甲方对哪些灵巧的方式并不熟悉)。
§ 包括一些开发人员。尤其是当你开始想让项目组理解该系统是完成什么样的功能时。
系统范围的定义可能用一句话就够了,对SWA Online就可以简而言之为“通过互联网向客户出售产品”或者详细一点的如“在美国本土向新老客户出售有形的而非虚拟的产品”。系统范围同样可使用环境模型(context model)来定义,该模型表示你的系统如何适应所有的环境。它经常使用使用案例图进行表示,参见图5;或用数据流图(DFD),参见图4(常叫做level-0 DFD)。搞清楚系统的范围非常重要,只有这样才能限定你的开发工作。上面的第一句话过于笼统,它可能意味着面向的是国际上的客户,明显这比仅针对美国本土客户的工作量大很多。同样,出售虚拟产品如在线音乐需要另外一套在线交付系统的支持。随着时间的推移,这个范围有可能由于甲方的决定的改变而变化,所以时刻准备好迎接变化。
图 4用数据流图(DFD)建造的SWA Online的环境模型[url=http://www.csdn.net/editor1/images/contextdiagramuc.jpg]
图 5 用使用案例(Use Case)图建造的SWA Online的环境模型
那么哪一个最适合描述系统范围呢?一句话,DFD,还是使用案例图?根据你的情况而定。语句直接了当,但不如图形的内涵丰富。图4的DFD以所要建造的系统为中心,表述了其与其它外部实体(组织、人或其它系统)的关系,这些外部实体超出了你的系统的控制范围但与你的系统有相互作用。这种方式的主要优点是它以合理的细节描绘了你的系统与外界间的主要信息流动。图5的使用案例图同样以所要建造的系统为中心,以及与该系统有交互的参与者(组织或人)。它的主要优点是描绘出与系统有交互的外部的和内部的参与者,而DFD仅有外部的。主要的缺点就是它没有给出任何一点系统与参与者交互的细节。你应该使用哪一个呢?他们都有各自的优缺点,你可能会考虑都使用。嗯… …?这对我而言不是很灵巧。一个较好的解决办法就是稍稍违反一下规则,结合这两种方式优点仅生成一个图,就象我在图6中所作的。注意一下我的风格:在两个实体的左上角用“I”表示出这是内部实体;移去了DFD中的数字标识符(数字标识符难于人工维护),我宁愿遵循一定的规则以使实体的名称唯一,在需要时这个唯一的名称可以起到标识符的作用。虽然我选择了显示数据流而不得不打破一些使用案例图的规则,但我仍然能够轻易地使用使用案例图的符号。幸运的是我的项目甲方喜欢DFD,我也就投其所好了。记住有目的地建模这条原则就是要你了解你的听众,选取最适合他们的artifact。
不要害怕打破规则。一般经验告诉我们不要在level-0 DFD中包含内部实体,引入内部实体意味着你开始挖掘细节。但我之所以在这里却选择了这样做,是因为它能让我不用再画第二张图。我不会因此而死到临头,也不会招致建模警察的控诉。是的,我违反了应用建模标准这一条做法,但这样做我减少了开发和维护的费用。当这对于某些人成为一个很大的问题时,我想我的组织可以重新考虑一下标准。
图 6 使用包含内部实体的DFD建造SWA Online的环境模型
为了确定系统的高层需求,我推荐采取基于使用的方法, 即注意力集中在用户如何利用该系统工作这一点上。根据我的经验,这是一个对绝大多数的软件开发都有效的方法。如果你对用户如何使用系统没有一点概念,很难想象你所生产的软件能够支持他们的工作和改善他们的工作方式。我会将这个方法用在建立组织内部使用的商业应用,由客户所使用的商业软件,包装出售的软件(如CASE工具或文字处理软件),数据仓库的开发,甚至于集成现有的商业系统(COTS)如SAP R/3或Oracle Financials。在数据仓库系统的开发中,存在着一个普遍的错误,那就是首先收集“数据需求”。罗列出用户想存储在数据仓库中的数据元素或数据实体。乍看上去,这是个好主意,但如果你不知道用户如何使用这些数据,那么你很难定出优先级或者你根本就不清楚你所做的是否就是甲方所想得到的。对于COTS系统,你需要根据需求来选择使用何种建模方式。如[url=http://dev.csdn.net/#Table_1]表1所列出的有特性(Feature)、使用情景(Usage Scenarios)、使用案例(Use Case)和用户故事(User Stories),这都是比较好的方式。根据使用恰当artifact这一条,我会选择使用案例,因为SWA采用EUP作为软件开发的主要流程,而使用案例是最适合于这个流程的。如果他们选择的是XP,则用用户故事为佳。如果为Feature Driven Development(FDD)(Coad,Lefebvre,Deluca,1999),那特性就是我的选择。
图7是一个高层的使用案例图,它是一张数字照片,来自于我和我的项目甲方讨论时在白板上所画的图。这是一个基本使用案例图(Constantine & Lockwood, 1999; Ambler, 2001a),因为它以技术无关的观点来显示系统。基于这张图,你既可以全手工的方式来实现这个系统,也可以建造一个全自动的系统。其中的一个使用案例“Post Product Review”可以改名为“Write Product Review”以使之更趋于一般化,但我的项目甲方更偏爱前者。我一直在为尽可能地使需求无关于特定的技术而努力,但事实上许多系统已经局限于某个领域内。例如,SWA Online被限定为基于互联网的解决方案之上,此时如花费精力去尝试将其抽象出来,只会得不偿失。记住保证甲方的投资获得最大利益这条原则,将你的精力集中在能带来效益的那些需求模型上。
图 7 一个高层的SWA Online使用案例图使用案例应力求简单,在初始阶段(IRUF)对每个案例有一点提纲挈领式的逻辑描述就足够了。你不必在此时进行细化,你仅需要对该系统的用途有个基本了解,确定初始的范围,再对每个使用案例和参与者加一点提纲挈领式的描述。如果得到项目甲方的认可,你就不用花费更多的精力在初始阶段。可能三到四个使用案例就足够了。然后遵循有目的地建模这条原则,我们就可以终止初始阶段的工作,进入到详细建模阶段去建立详细的模型和实现你所确定的这些需求。注意这种方法更多地是运用在实行XP的项目中,而非实行UP的项目中。
你们可以看见在[url=http://dev.csdn.net/#Figure_7]图7所示的需求图中我使用了UML的构造型(stereotype )<<Include>>,然而在《The Object Primer 2/e》(Ambler, 2001a)一书中我曾建议在分析层次的使用案例图中使用构造型(stereotype),典型的如系统使用案例图,因为它们经常反映了架构和设计方面的问题,而需求层次的使用案例图却并非如此。同样,我也不会因为如此而受到建模警察的控诉。这个图是有意义的,因为它显示出它对处于流程中不同阶段的模型是公共的,在这里它表示我要考虑的包含需求和分析两方面的问题。
要在项目甲方之间达成一致的意见,这说起来容易,作起来难,尽管你有了“解决需求建模中的常见难题”这几招。每个甲方的背景、优先权和喜好都各不相同。为了达成一致意见,每个人都必须认识到这点,相互交流他们需要从该系统中得到什么,倾听他人的意见,准备为了达到一个共同的目标而努力。在我所工作的组中,只要发生意见分歧,我们都会在屋内所有人都能看见的一块白板前写下每人的问题,再进行讨论。这种方式将这些意见的不同之处可视化,可以集中讨论的焦点。在某个问题的提出者认为它不再需要或至少相对于其它问题不那么重要后,我们会将它擦去。虽然有时它是一个较好的意见,但也简单地将之擦去,因为通常我希望记录的是最后的决定。对于两个相互对立的问题,我喜欢在它们之间画一条其它颜色的连线,以突出它们需要进行讨论。
由于我们集中在高层次的使用需求上,相关的业务规则和约束常常也会被同时确定下来。同样,一些技术需求和将来可能或不可能被实现的需求也会确定。在初始阶段(IRUF)你应该将业务规则、约束和技术需求排列出来,常用的方法是将它们写在粘贴纸上或白板上,找出你是否已具备了足够的信息以进行后一阶段的工作。尽快地结束初始阶段的目的是防止你在这个阶段就投入时间探究细节。当你在初始阶段需求讨论会上就进行细节的讨论时,你就给你的项目带来了风险,因为此时你不会收到对你工作的具体反馈,从而陷入分析的泥潭。记住这条原则你的主要目的是软件,而不是那些设想你的软件如何运作的模型和文档。例如在SWA Online的初始需求建模会上,项目甲方提出了一些业务规则和执行顺序的约束,象如何打包某类的货物,某些产品具有一定的上架时间限制,以及分捡流程。当我听到诸如此类的需求时,我就会叫某个人将其写在白板上或索引卡片上,稍后再将这些索引卡片放在每人都能看到的公用桌上。
这里有一个重要的观点:建模会议是交互的,每人都参与其中的。会议的开始需要一个有经验的模型设计者来段开场白,解释一些技术,推动与会者进入状态。这可能就是简单地叫某人走上台来,解释一下正在谈论的内容,演示一下通过填写一张索引卡来总结一条业务规则,或者为一个可能需要的报表在粘贴纸上记录下数据的要求。当与会者熟悉了这种建模方式后,依照灵巧建模的甲方的积极参与这一做法,你会发现不用花太多的精力去鼓励他们的参与。是的,有些人比较开始害羞而需要更多的鼓动,但那毕竟是人的本性(如果我能选择的话,我更喜欢选择那些外向甲方的加入,而非那些内向不愿开口讲出他们意见的人)。
当你的开发组在确定目前版本的需求时,常常伴随着一些后续版本的需求或一些你可能在某时需要实现的潜在需求。虽然此时你不想过多地深究,而且你也不想实现过多的功能去满足这些潜在的需求,但你并不想就此丢弃它们。它们也是有价值的。这些潜在的需求可能会影响到你对系统架构的选择。变化案例(change case)(Bennett, 1997; Ambler, 2001a)是一项用于记录潜在需求的简单技术,图8是SWA Online中的两个变化案例。在定义项目范围时一项重要的工作就是指出哪些需求是现在应该实现的,哪些是超出范围的。变换案例中的需求就是超出当前项目范围的。如何有效地使用变化案例的详细内容可参见Agile Architecture一文。
变化:扩展至北美地区
可能性:非常可能
期限:12-18个月
影响:
§ 必须支持向加拿大和墨西哥的用户交货。与新托运商的关系需要建立。
§ 需要计算相关的税收和关税。
§ 由于法律和当地风俗习惯,在这些市场出售的产品有可能会有所不同。
§ 多语言支持(英语和法语是加拿大的官方语言,墨西哥是西班牙语)。
变化:销售虚拟产品(在线音乐、录像、书籍… …)
可能性:非常可能
期限:6-12个月
影响:
§ 不能与实际产品的运输流程混在一起。
§ 我们可能需要对某些产品支持数字许可。
§ 个别产品的销售可能有某种限制(有效时间、拷贝数量)
图 8 SWA Online 的两个变化案例
那么你需要多少文档来记录项目的范围,初始的、高层次的需求呢?就象我在Agile Documentation一文中所建议的“刚好够用就行”。对于SWA Online这个项目,我们也许建立一个HTML页含图6的环境图,图7的使用案例图,和一个简短的指出范围的列表就够了。为建立高层次需求文档,我会尝试将使用案例转写在一个单独的能进行文字处理的文档上,或者就是一个简单的文本文件。之所以这样做,是因为在详细建模阶段我们要细化它们。有这样一份电子文档使得共享和处理更容易。至于那些记录了业务规则、约束、技术需求和变化案例的索引卡片,让它们保持原样,因为它们会在详细建模阶段得到进一步的细化。我会让我的项目甲方相信,如果我们发现它们确实是需要的,我们会处理的,因为我们那时需要它们。这样由于避免了一些有可能不必要的在文档上的工作(有些业务规则是不合逻辑的,因此在你知道它们的真正价值前所投入在文档上的工作都是浪费),就可以使得开发组能够很快地进入详细建模阶段,然后进入实施阶段。
详细需求建模阶段
一旦系统的范围和高层需求得到认同,基于该阶段的成果,你就可以开始为你的开发工作制定进度,将这些需求带进一个迭代过程(iteration)。该计划随着你对需求的理解的不断发展而演化,由此你就开始了真正的开发。
迭代过程的开始
在这个过程的开始阶段,这些需求会分发到各个开发者手中。在一个实施XP开发流程的项目组中,开发人员会结成对子,自愿地对给定的用户故事进行处理。每个用户故事都以相同流程得以处理,这个过程不断反复直到处理完所有的用户故事。实施UP的项目组或者以类似的方式运行,或者由项目经理将需求分配给某个开发者或一个小组。无论以何种方式,开发小组/对子都处于实现这些需求的状态。第一步就是要详细了解你的项目甲方想要得到是什么东西,这可能需要进行一些需求建模分析。
在这个迭代过程的开始阶段有两种方式进行建模工作:
集中所有需求在一起进行建模。采用这种方法,整个项目组以及能到的项目甲方会在一起探讨详细的需求,分析这些需求,对已有的系统设计提出修改建议以支持这些需求。假设这整个迭代过程是两个星期,我希望这个会议的持续时间一个小时到半天。如果这个过程更长,假设四到六周,你可能需要花一整天的时间在这上面。这个时间不希望超过一天,因为你不会收到具体的反馈,具体的反馈只有当你用代码验证它时才会得到的。这个方法的优点是可以对所要进行的工作和打算如何去做有一个具体视图,而且可以得到所有项目成员的想法,因此增大了确立一个良好开端的机会。它的缺点就是只适用小项目组,一般少于十个人。而且也比较浪费时间,因为不是与会的每个人以后都要参与各个方面的工作。注意一旦完成了这个初期阶段的工作,每个开发小组仍然需要对它们所负责的部分进行详细的建模。
各个开发小组对它们所负责的需求直接进行建模。有些开发组会在迭代过程的开始阶段放弃以上做法,而简单地就直接让各小组进入到其所负责的部分。这种方式的成功需要有这样的前提:需求间没有联系,或至少联系不是太多;开发人员遵循集体所有制这个做法;基于共有的代码之上。它的优点就是能够使得项目组在迭代过程开始的第一天就进入详细分析建模。但它有几个缺点:第一,当需求映射到设计上有交叉时,可能有两个小组都在处理有关定单计算的问题(比如一个小组负责计算税款,而另一个小组负责折扣的计算),这就会有两个小组工作重叠的风险。但这不算一个严重的问题,因为每个小组都应该知道其它小组正在做什么,当需要时可共同工作。第二,这会经过较长的时间后项目的整个实现视图才会明了。第三,在开始会引起对项目甲方的争夺,因为每个小组工作的开展都需要从他们那里得到输入。
迭代过程中
一旦结束了开始阶段的工作后,项目组很快就进入到持续的迭代过程中,建模、编码、测试、编译,或者进行软件配置。你和项目甲方的大部分需求建模的工作会在这段时期中体现,这个过程的目的就是探究、细化这些需求。实际上,更准确地说这些工作就是一些建模会议,因为你可能会不断地重复着需求、分析和设计。这些会议一般是由一小组人即席召开的,一般包括开发小组成员和由一个或几个项目甲方提供输入。这类会议一般讨论某一类别的问题,如“莎利,你能花几分钟时间讲一下客户是如何搜索一个定单的吗?”。
那么我在SWA Online这个项目中是如何进行详细需求建模的呢?首先,假设我们有两个人结成对子。在这个迭代过程中,我们要实现定单的定义和使用案例中“下定单”(Place Order)这个行为的基本路线(basic course of action)中的定购部分。在这里,我们不去实现查找功能,任何类型错误和异常的处理,税金计算和折扣计算[1]。一个行为的基本路线常称为“愉快路径”(happy path),因为沿着这个基本路线所有操作都是正常的、愉快的。行为的备用路线(alternate course of action)是描述当有不正常的操作时所走的路线,这里比如一个用户向一个缺少存货的产品下定单的情况。我们现在仅关心“愉快路径”,其它的需求会由其它的小组或者我们在以后处理。
我们要做的第一件事是充实这条基本路线的逻辑过程,如图9所示。同时也进行关于这个使用案例的基本用户界面原型的工作,如前面的图2所示。之所以我们要并行地进行这两部分工作,是因为它们从两个不同方面来解决这个问题。使用案例描述的是用户在下一个定单时要做什么,基本用户界面原型则是构造一个支持该行为的用户界面。请注意使用案例“Place Order”利用构造型(stereotype)<<Include>>调用了另一个使用案例“Search for Item(s)”,见图7。虽然这个功能是该使用案例中的一部分,但我们并不在这里实现它,因为它超出了范围。我们会采用另一种方式来替代,有可能就是直接给出一个假设的查询结果的页面。这个查询功能会在稍后恰当的时候实现(记住,我们使用的是增量的方式)。同样现在也没有考虑任何类型的技术问题,我们会在以后的分析中或设计中决定这些问题。现在我们只是想了解这个下定单的基本过程,稍后(可能就几分钟后)我们才关心实施的细节。对那些我们不会在这个迭代过程中实现的逻辑步骤,比如税款和折扣计算,当我们在编码时会留下接口。
这个使用案例从一个用户选择下一个定单开始。
用户通过另一个使用案例“Search for Item(s)?”来搜索物品。
用户选择一个物品并加入到他/她的定单中。
用户指定他们想购买该物品的数量。
系统通过该物品的单价和购买数量计算出总价。
用户重复第2步到第5步继续订购其它物品。
用户结束向他们的定单加入物品。
用户提供送货信息和付款信息,包括他们的名字、电话号码和邮寄地址。
系统计算定单中所有物品的总价。
系统按照“Calculate Taxes for an Order”这条规则计算适用于该定单的税款。
系统按照“Calculate Discount for an Order”这条规则计算适用于该定单的折扣。
系统显示税款和折扣。
系统加上税款和减去折扣,得出最后的总价。
系统显示该定单的汇总表。
用户验证该定单是否正确。
系统为该定单下计划(参见使用案例“Fulfill Order”)
系统给出一张该定单汇总收据。
图 9 下定单的行为基本路线
虽然我们知道该系统使用浏览器进行操作,但我们不会现在就用一个HTML的编辑器进行用户界面的设计,而是仍旧使用粘贴纸。因为在用户界面设计的初期,我们会经常地很频繁地增减控件、改变布局,我们希望用一种工具来支持,而粘贴纸所具有的灵活性和弹性正是我们所需要的。当这个页面的布局稳定下来后,我们会转到HTML编辑器上,因为我们此时想生成一个更加具体的界面可以让甲方进行评估。眼下,我们就简易行事。
在这个阶段,我们遵循了灵巧建模的几个做法。明显的有并行建立多个模型(Create Several Models in Parallel)这一条,因为我们同时进行了使用案例和基本用户界面的工作;有同他人一起建模(Models With Others)这一条,因为包括了两个我们的开发人员和至少一个负责提供需求的甲方;有简单地建模(Depict Models Simply)这一条,通过图2中的这个简单模型我们可以看到这点;有创建简单内容(Create Simple Content)这一条,图9所示就是一个很好的例子,它刚刚好足够详细地描述了使用案例的业务逻辑;有使用恰当Artifact(s)(Apply The Right Artifact(s))这一条,业务规则不在使用案例中体现而在另外单独的业务规则artifact中,虽然你可能会提出异议“计算定单的总价就是一条简单的业务规则”(此时,对于计算定单的税款和计算定单的折扣这两个业务规则,你可能会在文档或所引卡片这类用于业务规则的artifact中预留下位置)。此外,用户界面的需求使用的也是另外一个artifact,即基本用户界面原型。如果我们还有数据方面的需求的话,它将会使用概念模型;有切换到另外的Artifact( Iterate To Another Artifact)这一条,当我们在用户界面原型上增加了一项时,会发现在使用案例中缺少相应的逻辑,反之亦然,这时我们就会在使用案例和基本用户界面原型间来回修改;最后,也用到了使用最简单工具(Use The Simplest Tool)这一条,用户界面原型用的是纸张,使用案例逻辑写在白板上。
一般我们花费在上面建模的时间是三十至六十分钟。假设我们对建模的结果感到满意,要么就会继续进行分析和设计工作直至编码,要么会先花上几分钟时间用刚才所学到的去更新一下项目组的概念模型。我建议使用尽可能简单的概念模型,就像图3所示的CRC卡片,因为它们易于使用而且非常容易被项目甲方理解。它们不仅用来表示系统中主要的实体,而且可以表示出这些实体的职责(包括数据和行为)。对于概念建模,你下一个最好的选择就是采用UML的类图(class diagram)。它的优点在于能够表示出类或实体间的关系,例如多重性(multiplicity)和角色(roles)。CRC模型中的类合作者就隐含地表示了类之间的关系。问题是对于你的项目甲方来讲,类图不如CRC卡片那么容易理解,即便他们努力地积极参与,但类图还是过于复杂了。传统上数据模型用于概念建模,经实践验证即使当使用结构化的技术进行实现时也是可行的,但UML的类图却难以做到。
尽管我在这里所讲述的建模工作很有可能花不了一个小时,但你可以很容易地组织你的建模工作,更好地进行划分。或许首先集中解决前几层的使用案例及其相应的用户界面,实现这部分的功能,然后再回过头来解决下几层的使用案例。这种方法在两层的时候工作得很好,你应该采用最适合你自己的方法。
认识到在这个迭代过程中需要不断地反复是很重要的,当需要时就要回到需求建模的工作上。当你开始实现下定单这个功能时,有可能会发现你对其工作的细节并不清楚,比如对某类物品可能有购买数量的限制。如果发生这样的情况,你就会有新的功能需要进行评估、要指定优先级和将其带入以后的迭代过程中。有可能你的逻辑顺序颠倒了 – 客户可能应该首先提供送货和支付信息;还有可能应该提供一种能让客户一次性地建立他们送货和支付信息的途径。总而言之,新的需求必须要在新一轮的迭代过程中加以处理。
解决需求建模中的常见难题
为了能以灵巧的方式进行需求建模,需要具备一定的条件。但不幸的是,很多项目组并不具备。需求建模工作常常被你所处的环境所影响和破坏,一般是组织所奉行的文化不利于有效的软件开发或者项目甲方不清楚他们的决定所带来的影响。在这一节中,我列出了一些在需求建模中多数项目组经常碰到的问题,并讨论了可能的解决方案。这些常见的难题如下:
难于接近项目甲方 (Limited access to project stakeholders)
项目甲方分散在各处 (Geographically dispersed project stakeholders)
项目甲方不知道他们想要得到的是什么(Project stakeholders do not know what they want)
项目甲方改变主意(Project stakeholders change their minds)
优先级冲突(Conflicting priorities)
过多的项目甲方想参与进来(Too many project stakeholders want to participate)
项目甲方指定了技术方案(Project stakeholders prescribe technology solutions)
项目甲方墨守成规(Project stakeholders are unable to see beyond the current situation)
项目甲方含糊其词(Project stakeholders are afraid to be pinned down)
项目甲方不懂建模artifacts(Project stakeholders don’t understand modeling artifacts)
开发人员不懂业务(Developers don’t understand the problem domain)
项目甲方过于集中于某一类需求(Project stakeholders are overly focused on one type of requirement)
项目甲方对于需求的确定有许多繁文缛节(Project stakeholders require significant formality regarding requirements)
开发人员不懂需求(Developers don’t understand the requirement)
难题 #1 难于接近项目甲方
这是一个经常发生的问题。由于某些原因,高层管理部门有时愿意投资数百万美金进行一项系统的开发,但却不愿意或不能指派一些合适的人选来告诉你这个系统需要干什么。“为了项目的成功,开发人员需要得到项目甲方的积极支持”,项目甲方常常严重缺乏对这一点的认识,他们不清楚软件是如何开发的;或者他们一直以来都是以这种方式工作(译者:即不委派人员协助开发),而不知道有更好的方法。
要解决这个问题,首先你需要与项目甲方进行沟通,告诉他们你需要同他们紧密地协作,他们必须投入宝贵的时间与你一起工作。有时可能没有可以确认的用户,这种情况通常是当你在开发一个零售产品或一个供你(潜在)客户使用的基于web的新系统时出现,在这种情况下你需要找一些人来代替。一个较好的方法是选择你的市场人员或销售人员,因为他们熟悉客户,他们脑中对你的系统会有一个大致的轮廓。或者直接找一些可能的用户(你可以自己从用户的角度去想这个系统应该提供什么;或者从外面聘请一些人,他们应该是你的产品所面向的用户)。根据我的经验你肯定可以找到能为你的系统提供需求的人,曾经有好几次我都被告之不可能提供人员与我一起工作(但最终都找到了[译注])。记住你的项目甲方不仅仅是系统的直接使用者,你应该认识到你是在冒风险如果没有任何直接使用者参与到你的软件开发中。
难题 #2 项目甲方分散在各处
对于上一个问题,还有一个原因就是你的项目甲方与你的开发组不在同一个地点,使得你没办法与他们很好协作。这种情况常发生在比较大的组织内,一些项目外包给其他组织;或者在一个由多个组织合作开发的项目也会出现这个问题。解决的办法有几种。一是,想办法将开发小组和项目甲方集中到一个地方。正如我在《交流》一文中所提到的,面对面的交流是最直接有效的方式。如果做不到这一点,下一个最好的做法就是让项目甲方和开发人员在一段时间内在一起,另外的时间通过其它手段进行交流(在《交流》一文中,我提出了几种可选择的方式,如电子邮件,视频会议,和一些支持协作建模的工具)。我曾经参加一个由300人组成的项目组,项目甲方在每三个星期中用一个星期同我们的开发人员一起工作,而其它两个星期通过电子邮件和电话联系,这种方式运行得相当好。如果上两种方法都不适用,那下一种较好的方法就是让开发人员到项目甲方所在的地,与之共同工作。我在好几个项目中成功地使用了这种方法。但要注意这对那些出差的人来说非常艰苦的(我就经常出差,幸运的是我喜欢旅行)。还有一种方式就是让业务分析师先到项目甲方那里去了解他们的需求,然后再让他们回来与开发人员定义需求。当然,你可以根据你的情况组合使用这几种方法。
难题 #3 项目甲方不知道他们想要得到的是什么
这就是你什么要花时间进行建模的原因。通过建模来探寻他们想得到什么以及哪些对他们而言是重要的。现今的商业非常复杂,甲方经常意识到有问题需要解决或存在着改进的机会,但他们不知道如何去做。这是十分正常的。你曾经重新装修过房间,或者重新布置过家具吗?你知道你想有一个更好的居住环境,但却常常措手无策。可能你会去查阅一下杂志上的图片,参观一个家具店,或者去朋友家看看他们是如何摆设的。如果你对构想一个居室的布置感到困难,可想而知,你的项目甲方要确定一个什么样系统是多么的不容易。
这是一个正常的现象,我们从接受这个观点开始。如果你的用户不能确切地告诉你他们想得到的是一个什么样的东西,告诉他们这没有关系。他们现在所需要做的仅是告诉你他们想让你干什么。同重新装修房间类似,可能你现在还没有一个整体的布局构想,但你可以从着重于安装一个书架开始。着眼于他们对系统中有最清楚想法的一个方面,对这个小部分建模,然后实现一个可运作的系统(遵循用代码进行验证这一做法)。他们就可以实地操作,向你提供反馈。如果他们甚至连一小点的需求都提不出来,就好像你完全不确定是否会有书在房间中,那么就从调查他们现在的工作方式开始。通过对现有工作流程的建模,你会进一步了解他们的工作,从中看到他们可能需要的改进以及最差的环节在哪,由此就可以向他们建议。
难题 #4 项目甲方改变主意
项目甲方也是人,是人就会改变主意。你把家具按想象中的位置摆好,但当你回过头来端详一番,可能觉得这样并没有达到想象中的效果。象布置家具这样简单的事你都会改变主意,何况那复杂的系统呢。项目甲方百分之百会改变主意。
要解决这个问题,你首先得接受这个事实,拥抱变化。不管发生了什么变化,都是与建模有关的,因为你会发现要么是他们开始时不清楚他们自己的需求(参见上一个讨论),要么就是你没有弄明白他们所想要的。当你同项目甲方一同讨论时,你应该从他们的角度以他们的语言达成一致的认识,这会确保你没有作出另外的假设,而且会提高谈话的质量。我曾经参加过为一个电子商务系统开发管理系统的项目,在这个项目中我们得出了一个公正而准确的需求。第一个星期,我们提供了两个网页:一个是主页,上面包含了关键功能的菜单项;另一个实现了一个高优先级的功能。我们完全按照他们所要求的来做。当我们想他们演示以后,他们意识到最初的想法不好,然后要求我们重新构造。变化来了。最后,当用户对系统中某一部分的想法发生改变时,你会发现实际上是由于他们没有弄清楚需要解决的问题,这意味着需要同他们开一个关于构想的会议(参见需求建模会议的相关内容);或者是由于某个有不同构想的甲方的意见没有被正确处理。
难题 #5 优先级冲突
你所建造的系统必须反映多方面的需要,包括直接使用者,高级管理层,你的实施人员,支持人员,以及维护人员。各方面都有不同的优先级要求和目标,即使是同一类中的不同个体也是如此。这就会出现冲突,有冲突就必须进行处理。
再一次,首先是接受这种现象。系统的优先级需要协商而定。注意到我所说的吗?你需要定义你系统的优先级。每个项目甲方心目中都有一个自己的优先级,这很好,但你的目的是要决定整个系统的优先级,这往往不同于他们个人的想法。一种方法是实行代表制:指定一些代表,他们每人都能代表某一大组的项目甲方,让他们来协商作出决定。你可能想自己来支持这个协商工作,但这项工作非常耗费时间,而且有可能其结果会导致项目甲方与你和你的项目组之间形成敌意(费力不讨好)。我建议尽可能地让别的人来做这个苦差事。如果协商没有结果,你最后一招只有寻求金牌业主(就是付钱的人)的帮助,要求他们进行仲裁。在我曾经参与的一个面向国际的电子商务系统的开发中,有些甲方设想该系统一开始就能够支持多种语言(美国英语、英国英语、西班牙语、德语、日语和粤语)。这样,唯有我们能服务于每个主要的市场。另外一些甲方想让这个系统运行迅速,而仅愿意支持美国英语,因为他们觉得这对于客户来说是可以接受的(你的项目甲方也有笨的时候)。我们不能对此达成一致,于是我将这个问题向上反应。最后的决定是第一个版本仅支持美国英语,然后在确实需要其它语种时再进行需求评估。
难题 #6 过多的项目甲方想参与进来
有时你会发现想参与的人太多了。这种情况通常发生在项目的初期,大家都抱有浓厚的兴趣,或者你的项目与个人的业绩相关,很多人都想沾光。最好的办法就是感谢每个人的热情,让他们明白你现在得到的帮助已经足够了,而且你已经挑选了一部分人,告诉他们以后当你需要他们的帮助时会同他们联系。当我处于这种境地时,我会尽量挑选最合适的人选,那些能提供最好的见解而且愿意花时间同我的开发组共同工作的人。同时,我不会疏远那些现在没有加入进来的人,有可能在某个时候他们某方面特殊的专长正是我们所需要的,或者可以通过他们来宣传我们的工作。一般来说,一个积极参与的项目甲方会对这个系统越来越熟悉,但同时盲点也在增加,而越来越难发觉一些潜在的问题。因此保持对合格的外部人员的联系是颇有价值的。
难题 #7 项目甲方指定了技术方案
我曾经遇到过这样的情形,一个项目甲方人员说我们需要使用某种技术,比如某个版本的Oracle。而此时我真正需要的是从他们那里得到行为类型的需求,比如“客户能够将钱存入一个账号中”。确实,技术方面的约束是肯定存在,也是开发组应该知道的,但此时有可能他们只是想告诉你Oracle是他们组织的数据库标准这样一个事实。很多时候,真正的问题在于你的项目甲方难于区分系统的需求和系统架构的选择,有可能这个人是技术出身而喜欢讨论技术方面的问题,或者只是由于他们刚好从最近 一期的商业周刊上读到一则成功使用Oracle数据库的文章。
最好的解决办法是定义好项目甲方的权责,制定一个适当的工作框架,以使他们能将注意力集中在定义系统需要做什么这个问题上,而开发人员则集中精力在系统如何做这个问题上。另外一种策略就是问他们“如果你已经有了适当的技术,哪它还那么重要吗?”或者“你想如何使用这项技术”这类问题来识别实际的需求。
难题 #8 项目甲方墨守成规
许多组织中,人们多年来使用同样的工具以同样的方式工作着。他们可能从来没见过另外的方式或从来也没想过。他们对改变怀有恐惧感,可能是他们害怕没有所需的技能来适应新的系统,也可能是担心会被新系统取代。出于这些担忧,他们会按照适合他们的方式给出需求。 解决这个问题最好的办法是同他们讨论目前的情形,辨别哪种方式运作良好而哪种方式不好,以及向他们讲明当前形势正在如何地发生着变化。假设在SWA Online这个项目中,某个甲方人员在确定需求时告诉你任何一个定单最多只能订购十样物品。什么?明显是因循守旧。如果你就此详细地询问,很快就会得知他们目前的运作流程是客户邮寄或传真他们的定单到公司,再由客户服务代表进行定单信息的输入。每张定单表格只有十行,而且得知以前的绿屏幕(译注:即单显)系统也被设计为每屏仅允许输入十条信息。 其实不必问这么多,你应该指出填写纸张表格的定单是造成这个限制的真正原因,因为纸张的大小是有限的,然后向他演示你可以很轻易地实现在一条定单订购多于十样物品。一会儿之后,他就会认识到这完全是可能的,特别是当你向他展示其竞争对手没有这项限制时,就更会消除他的疑虑。
难题 #9 项目甲方含糊其词
有时因为项目甲方不愿意做出具体的答复,给出的需求非常含糊。这主要是由于他们害怕犯错误。他们以前的经验告诉他们重新实现一个改变的需求要付出昂贵的代价,需求事先都必须得弄正确。这基本上是做不到的,由此他们就选择了含糊其词,在某些问题上不表态。
“你已经做好准备迎接变化;你的开发方式是迭代式的、递增式的,这样能降低变化所带来的开销;你的目标是为他们提供最好的解决方案,而这意味着有些需求会随时间的过去而演化的”,要解决这个问题你就应该给项目甲方留下这样的印象。言行一致,在实施过程中能够接受和支持变化。日久见人心,随着时间的推移,你项目的甲方就会认识到他们可以现在做出决定,日后如果需要可以安全地改变。当你在每个迭代过程完后交付软件,你的甲方看见软件随着他们对系统理解的不断发展而发展时,害怕表态的疑虑很快就会消去。
难题 #10 项目甲方不懂建模artifacts
绝大多数的项目甲方,可能还有绝大多数的开发人员,都没有正式地学习过建模。很有可能他们不知道如何去看一个UML活动图、或一个数据模型、或一个UML使用案例,因为这不是他们的日常工作所需的技能。问题在于他们需要懂得你所作的这些artifacts,这样才能明白你所表达的意思,才能积极地加入到建模得工作中来。
首先是确定你的项目甲方需要懂得哪些artifacts,这样才能知道你应该集中精力在哪。对此使用最简单的工具这个做法可以帮助你。如果你争取采用诸如索引卡片、纸张和白板这类简单的工具建模,你就降低了甲方的学习曲线。第二步就是教给他们这些技术,我倾向于Just In Time(JIT)这种方式。即当我们在一个建模会议中第一次需要某项技术时,我会先大致地讲解一下,然后就我们所讨论的问题深入讨论如何应用该项技术。在一个项目的开始,我会概括地讲一下一些常用的建模技术,使他们对将要进行得工作有个感觉。同时也会给他们提供一些读物,一般是The Object Primer 2/e (Ambler, 2001a),其中详细地讲述了这些技术(译注:随时不忘作广告J)。使用这种方法,我教过那些从来没有建过模的甲方,象CRC和基本用户界面原型这两种简单工具,每个都用了不到十五分钟。对于那些复杂一点的技术,如流程图或类模型,需要一段时间来慢慢学习。第三步是尽可能快地基于模型生成可运行的软件并得到具体的反馈。当这些模型变为现实时,你的项目甲方一下就能看到他们写在粘贴纸上的基本用户界面模型变为了一个HTML页面,CRC卡片上描写客户的概念反应在软件的功能中。
难题 #11 开发人员不懂业务
一个普遍的问题是在项目的开始阶段开发人员不懂甲方的业务,使得与甲方人员交流起来比较困难。这是自然的,就像建模不是甲方人员的日常工作一样,开发人员也不是一个熟悉甲方业务的专家。这就是为什么需要两组的人都积极地参与需求建模工作,就如三人行必有我师这条原则指出的,每个人都能为之做出贡献。开发人员需要花时间去学习相应的业务,虽然他们随着项目的进展最终能学会,但我们常常发现这样太慢,必须要通过某种方式来加快这个进程。多年以前,我工作过的一家公司,他们确实地理解到开发人员学懂业务的重要性。在前三天中,我和另外一个新来的员工都是由甲方的副总裁进行培训。这是一个数十亿美元的金融机构,他们向我们描述了他们各部门的基本情况。每个副总裁每次都要花几个小时对两个(是的,两个)开发人员进行培训。如果你的组织不是这样的,你可以找几本与该业务相关的书籍看一下,介绍性的大专院校的教程比较理想。我认为开发人员应该广泛地阅读。我经常阅读财富杂志、经济家、Utne Reader和国家地理杂志,而不仅仅局限于The Communications of The ACM和IEEE Software这类有关软件开发的刊物。这使得我有广阔的知识背景,对我在进入一个新的环境时帮助很大。
难题 #12 项目甲方过于集中于某一类需求
有时你会发现甲方虽然提供了一大堆的需求给你,可能以使用案例或使用情景的形式,但对于非行为类型(或行为类型)的需求来说还不足够。这个迹象就说明没有找对人,或者你遗漏了某个方面的人比如操作人员和支持人员。因此,需要重新考虑需求建模中甲方人员的组合。
难题 #13 项目甲方对于需求有许多繁文缛节
许多甲方认为正式(计划好的会议、需要他们审查和签字的正式需求文档和正式的讲演)就是职业化的表现。我认为这是我们的软件产业在过去的两个时代中所形成的软件流程理念,我们的甲方不知道有另一条路可走。这同样也是由于信息界与商业界间的紧张关系所造成的。我们的甲方不信任我们,他们坚持要履行这许多的繁文缛节,以此获得对他们并不熟悉的开发流程的更多控制。
你需要同他们进行沟通,向他们讲解有另外一种更灵巧的方式,让他们明白现在这种方式所带来的问题(开发进度缓慢、没有足够的机会去理解需求、超支的费用… …)。问问甲方,他们真正的目的是什么。是开发一个可运行的系统呢,还是开会和制造文档?如果是前者,肯定是它,然后问他们为什么要坚持这些手续。不要接受他们的第一个回答,应该刨根问底,找出真正的原因。如我在Agile Documentation 一问所指出的,他们不相信我们,这是他们拴住我们手脚的一种方式。接下来就是要他们相信你,一般来说比较困难,这主要看他们在以前的软件开发中经历了什么样痛苦。以及要求他们去掉一些手续。然后你就要以事实证明(即交付软件),向他们展示没有很多的手续一样可以取得成功。通过循环的迭代过程减少手续,直到你的软件能够有效地工作时交付给用户。
难题 #14 开发人员不懂需求
“开发人员弄不懂由业务分析师和用户建立的需求artifacts”,在没有采用灵巧建模的项目组中,时常听到这样抱怨。幸运的是,在采用了灵巧建模的项目组中你不会碰到这个问题。首先,熟悉你的模型和熟悉你的工具这两条原则告诉你,开发人员应该对所使用的artifacts和常用的工具受过足够的培训和有足够的经验。如果没有,那么他们就必须接受培训和指导。第二,增量改变这条原则建议你将一个系统分为许多小部分,每次针对一小块,一个一个地建立,这也反映在小增量建模这个做法中。这避免了开发人员一次需要理解太多的需求,陷入一个大的需求文档之中。第三,项目甲方的积极参与这一做法和三人行必有我师这一原则保证了你的项目甲方能够向开发人员解释他们的需求,而开发人员愿意这样做。第四,创建简单内容和简单地建模这两条原则确保了你的需求模型做到尽可能的易于理解。
技巧
以下所列出的技巧能够帮助你提高为系统的需求建模的效率,它们也遵循灵巧建模的做法:
需求的收集贯穿于整个项目过程中。大部分项目均是如此。虽然大部分的需求工作是在项目的开始阶段,但很有可能你仍需要回到需求上来,直到代码完全冻结时。记住拥抱变化这条原则。
解释技术。每个参与的人员,包括项目甲方,都应该对建模的技术有个基本的理解。如果他们从来没听说过CRC卡片?花几分钟解释一下它们是什么,你为什么要用这项技术,以及建立它。如果你的项目甲方不能够使用正确的建模技术,那么甲方的积极参与也就无从说起。
使用用户的术语。不要强迫项目甲方使用你的软件开发方面的术语。这个系统是为他们而建造的,因此应该是你使用他们的术语来为系统建模。
乐在其中。建模可以不是一项艰涩的工作。事实上,你完全可以寓模于乐。讲些笑话,轻松一下。人处于轻快的环境中,可以更加有效率。
取得管理层的支持。为需求模型投入时间,特别是本文所讲的以使用为中心的设计技术,对于许多组织来说是一个新的概念。项目甲方积极地参与建模工作,这也许对大多数的组织来说是根本文化的改变。任何涉及到文化改变的事情,没有高级管理层的支持是不可能取得成功的。你需要取得你的信息部门以及用户那边管理层的支持。
采取宽度优先的方法。我的经验是最好在开始时勾勒出系统的轮廓,尽可能大地了解系统的面貌,然后再集中在某一个小的方面。这样做,你很快会对系统的整体有个了解,选择好切入点。
已有的文档是需求的很好来源。象政策手册、政府法律、甚至于学校的教科书这些已有的文档都是很好的需求来源。在我曾经参与的一个电子商务系统中,我第一件事就是找到一本关于电子商务方面的书来确定一些基本的需求(比如支持信用卡的交易)。记住复用已有的资源这一做法。
记住今天的用户就是明天的分析者和以后的开发者。三人行必有我师这条原则其实也就意味着你的项目甲方在参与软件项目的同时也在学习软件开发的基本技能。常常会看见一个用户先成为一个业务分析者,而后通过学习更多的开发技能而成为一个真正的开发者。因为灵巧软件开发比以往的软件开发方法更加强调项目甲方的参与,这种现象会更经常地发生。注视这些愿意进行这种转变的人,给予他们帮助。有可能以后有人帮助你建立业务方面的技能,而帮助你跳出技术的世界。
参考资料及推荐读物
参见http://www.agilemodeling.com/essays/references.htm.
脚注
[1] 这个例子揭示了使用案例的常见问题。对于单一的一个迭代过程,它们通常过粗。你可以让一个使用案例在多个迭代过程中完成,从项目管理的角度来说这不是很好;或者你可以将其重构为更小的一组使用案例,这从建模的角度来说不好。
译注
Artifact -- 在一个软件项目中制造或使用的最终或中间产品。
它用于记录或传达项目的信息。它可以是文档、模型
或者模型元素。
本文翻译征得原作者Scott W.Ambler先生的同意,在此表示感谢。