同事预审


在如今大部分的组织里面,是否给申请技术职位的人提供工作机会——这个最终决定权属于管理部门。经理们雇人,经理们裁人:一切都天经地义。然而在某些组织里面,这些技术人员能否得到工作机会却是取决于——至少部分取决于——他们将来的同事。这种同事预审的最终结果只有一种:当经理们让技术职员拥有发言权的时候,每一个人——申请人、职员和经理——都会和盘托出自己的想法。

招聘流程的前期阶段基本上没有变化:通常由第一线经理对申请人的材料进行最初的筛选。经理也许会要技术方面的高级职员先审阅简历,把所有的申请人归为“下一步”和“不,谢谢”两类。经理也许会给那些简历看上去非常华丽的申请人拨打电话聊一聊,做一个初步审查,决定邀请哪些人过来现场参加面试。获邀的申请人会被告知他将和团队在一起呆上36个小时。一旦众多的同事参与到招聘的过程中,面试的当天往往非常的漫长。

在抵达公司并与经理寒暄过后,申请人就随同各位团队成员开始一系列的面试。每轮面试的会谈时间从30分钟到90分钟长短不等。

虽然每位参加同事预审的面试官从申请人身上得到的信息相同,但每个人都会使用不同的方式调查。很显然,每个人都希望对申请人的知识、技术和能力做出评估。所以,针对招聘职位的类型不同,从团队的角度出发也许会要求申请人编写一些代码,或者创建一组测试。但是,每个面试官都会再以个人的角度去评估申请人,他会问自己:“我能和这个人一起工作吗?”“他能适合我们这个团队吗?”“他会让我们团队变得更强,还是更弱?”

此外,每个面试官将以自己在团队之中担当的角色去评价申请人。举个例子,如果申请人是一名开发人员,相较于团队里的开发人员,身为测试人员的面试官就会提出不一样的问题,以挖掘申请人的个性特征。

每个面试官也会根据自己的以往经验去评价申请人,问自己这样一些问题:“这个人展现出的技能与解决问题的方式,是我最为欣赏的吗?”“这个人在多大程度上让我回想起曾经合作愉快的同事,又在多大程度上让我回想起无法合作顺畅的同事?”“这个人是不是像他表现出来的那般优异,又抑或他是在假装如此?”面试官背景的多样性,使得团队可以从多个视角和价值取向来甄别将来的同事。

在把申请人交给下一轮的面试官之后,这一轮的面试官向经理——或者面对面地交谈、或者通过邮件,又或者拨打电话——就他对申请人的印象和意见发表个人的观点。每位职员都需要针对“假如由我来裁决是否雇用这个人”这个议题投下自己的一票。

如果面试一切进展顺利,申请人最终会回到经理这里,而此时经理也已经知晓了所有面试官对该申请人的看法。经理现在要从他自己的角度出发来面试申请人,然后告诉申请人是否得到了工作机会。即使其他的面试官都表示认可这名申请人,经理也可能会由于某些原因决定不对其提供工作机会。但是,如果团队的大部分成员都对该申请人倒竖起了大拇指,那肯定是没有理由再雇用此人了。

当团队在招聘过程中真正拥有话语权的时候,此时就出现了多赢的局面:

  • 当前的团队成员是赢,因为新员工加入团队的时候,大部分的团队成员都已经跟他见过面——实际上已经接受了他;不被职员接受的那些人是绝对不可能跨过那道门槛的。

  • 申请人也是赢,因为他处在了更有利的位置来决定是否要加入这支团队。他可以接触到未来的同事,而不仅仅是老板。他可以询问工作的真实情况,同时也可以感知公司的文化。

  • 经理是赢,因为他可以借鉴整支团队在技术方面对申请人做出的评价,而不是仅仅凭借自己的揣测。他也知道团队在一定程度上已经接受了这个“新员工”,而且团队对他个人的成功也非常重要。

  • 最终,团队作为一个整体也是赢,因为团队成员在参与同事预审的过程中,可以向其他人学习。在阅读其他人对申请人的评价时,团队成员能发现其他人使用的问题和标准,而他们可以在以后的面试中把这些派上用场。经理也能对自己团队成员的思维方式有更深的了解。

从经理的角度上讲,同事预审在雇用团队领袖的问题上面同样有效。为什么不邀请团队里的一些成员去面试未来可能成为他们老大的人呢?

不管申请人是开发人员、测试人员,抑或是经理,寻找到一位真正合适的人选从来都不简单,但往往又很重要。这是团队参与的项目。

只有完成本垒打或者击球成功,管理才值得嘉许。”

——卡西·史丹格(Casey
Stengel

一叶知秋

(一)
与客户吃饭。客户抱怨,“我司人员流失大,无法建设团队文化。”我说,“以你司推行的工具为例,其思路就是把团队定位于低级、傻瓜式的水平。那么,超出这个水平的人离去、不足这个水平的人加入,不正是延续并巩固了这种傻瓜式的团队文化么?”

(二)
工具或许无关好坏,但要警惕的是工具传递的创建者的价值观。推广工具遭遇困境,原因就在于推广者的价值观与接受者不合,双方价值观上面的认同没有到位。如果以外力强制推行,甚至上升为价值标准,孔夫子曰:始作俑者,其无后乎?

玩的就是心跳(Adrenaline Junkies)



电话响了。

我们想这周完成需求的规格说明书。你能过来,看看可以做些什么吗?”
规格说明书怎么了?”
我们很急,所以新招了许多人来撰写规格说明书。我们觉得他们完全不清楚自己在做什么。”
如果由我们来指导他们编写需求,效率不是更高么?”
但是我们这周就需要规格说明书。”
好吧,我明天过来。”

两个小时之后:

你能过来看看我们评估的工作量吗?”
规格说明书怎么办?”
我们没时间了。我们就照现有的需求规格说明书进行。老板要求今天就把评估的工作量交上去……”

你可能已经识别出这一类“玩的就是心跳(Adrenaline
junkie
)”型组织的特点了:优先级总是变化不休;所有事项都是“昨天”就要;总是没有足够的时间交付项目;紧迫的项目却源源不断。每个人都忙得焦头烂额……不可开交。

这些组织里面的人不会从战略层次上思考问题,只是按照紧迫程度来完成工作。除非“忙乱指数”非常高,否则项目通常都会被忽略——尽管它承诺将带来显著的长期优势。人们会一直对其不闻不问,直到它突然(绝对出乎意料地)变得非常紧迫。“玩的就是心跳”分子相信最好的工作方式不是谋定而后动,而是竭力追赶时间。

这种组织文化在令人绝望的紧迫性和高效的绩效之间划上了等号。如果身陷这种文化,你很难不受感染:紧迫性是被鼓励的。那些为了某个短得可笑的期限而加班到深夜的程序员被视为英雄(根本不在乎他们交付的程序质量)。每个周末,团队的所有成员都照常上班,以保持他们的工作量:这样做的团队比不这样做的团队更受人赞许。此外,如果你不是一直都过度加班,或者发疯一般忙碌,你就会被贴上“不是自己人”的标签;你不是保障组织运转流畅的大忙人之一。非英雄行为绝对不能被接受。

绝大部分的“玩的就是心跳”型组织至少存在一个瓶颈,就是那位英雄。他包揽了所有设计的决定,是全部需求的唯一来源,或者一个人决定框架的方方面面。他扮演了两个角色:一是让自己表现得比极少数人所希望的还要忙;二是引发了决策阻塞的局面,这种局面一旦形成,就会导致组织的其他部分更加忙乱。

大部分的“玩的就是心跳”型组织满腔热情地拥护客户服务的理念:他们把值得赞赏的响应和对紧迫事件的响应弄混淆了。当客户提出了一个请求,不管是否存在
潜在的利润(甚至有效性),该项请求都会立即被转化成一个项目,而且通常会设定一个很短的截止日期。(更多讨论,请参阅第
38项模式“Project
Sluts”
。)这个新项目自然会加重本已超出负荷的英雄们的工作,新的繁忙出现了——所有的这一切无休止地引发了让组织变得非常、非常忙碌的需求。很多这一类的组织都(错误地)认为这就是敏捷的全部。

玩的就是心跳”型组织倾向于断然行动,而不是三思而后行。这样导致的结果就是大部分工作都处在不断变化、无法固定的状态,没有什么可以固定下来,或者保持较长的时间。这种不固定的状态一直延续:需求规范不固定——没人真正清楚要构建什么;设计和计划也不固定——它们很可能明天就会改变。紧迫性是唯一的标准,没有人尝试按照重要性或者工作价值来对工作排定优先级。

对于“玩的就是心跳”型组织,回春妙手是不存在的。除了戒除再玩心跳,而且解雇经理,雇用那些明白“组织只有不再忙于处理突发事件才最有效率”的人,也别无良策。这样的人事变动或许根本不可能被采纳,毕竟高层领导,通常是CEO希望看到组织长久地保持匆忙的状态,因为工作匆忙让人生出一种生产率健康的幻觉。而且,如果公司的经理们是“玩的就是心跳”分子,项目团队也不会相去太远。

玩的就是心跳”型组织并不是总会遇上失败,其中有一部分在很多年的时间里面一直保持着匆忙的节奏。但是,它们都不可能构建重大的东西——那需要稳定性和计划。亢奋型行为不可能扩展——由一些相关的人在没有方向,也没有战略指导的前提下,光凭借非常、非常忙碌地工作所能达到的效果太有限。

实事求是地讲,任何组织内都会遇上紧迫的事情,也会有一些角色需要去关心紧迫的任务。但是,不是所有的事情都是紧迫的,也不是所有的角色都要关心紧迫的任务。除非化紧迫性为优先级和约束,否则,这种“玩的就是心跳”的治愈希望是微乎其微了。

保姆型项目经理

一个优秀的项目经理要对手下员工的能力了如指掌。他分派任务、制定计划,在可用的技能和任务本身的要求之间寻求最佳的契合。这是显而易见的。还有一些项目经理们更进一步:他们提供一个工作环境——不仅是技术性的,而且是社会性的——让人们可以最大限度地使用自己的技能,并且提高自己的技能。这些项目经理确保自己的员工拥有完成任务所必需的工具。这些项目经理鼓励提问,并且乐意、与员工辩论;他们给每位团队成员设定最合适的挑战;他们在需要的时候提出批评;他们建设一个人人乐于工作的场所;而且他们采取必要的调整以保障各项事宜运作良好。简单地说,好的经理们培养他们的员工,就像保姆培养她们照看的孩子一样。

一个保姆,在传统的英式文化中,受雇于某个家庭照看对方的孩子。保姆——通常被训练成教师、护士和厨师——对孩子的体格、心灵、社交、创造性和智力发展都要负责。在每天的日常活动中,保姆要确保孩子远离伤害,保证孩子们得到了足够的新鲜空气与锻炼、食用有营养的食物,并且增进对世界的理解,学会更多在世界上生存的技巧。除了照看孩子,保姆还需要与孩子的父母就他们在孩子成长方面的顾虑进行沟通,鼓励孩子的特殊天赋。保姆创建出一个可以承担风险和学习的安全环境。

当经理们拥有这些与保姆类似的才能,他们就能通过鼓励和培养员工的天赋,从员工那里获得更多、更好的工作结果。

迄今为止,我所共事过的最好的经理是Peter
Ford
。这再明显不过了,比如他确保协调好我们每个人的要求,以做好个人的手头工作。举一个例子,我们有一个开放计划办公室——不是最好的思考环境——而且,他设法为团队弄到一些消音的屏幕,并预订了几间“静室”。所有的这些,以及他为我们做的其他事情,牵涉了我们所不知情的协商和政治。他鼓励我们阅读,在系统开发的时候讨论新的想法。他为我们团队购买书籍和杂志,并安排时间让我们聚在一起讨论。当我们觉得不开心或者不舒服的时候,他会注意到这一点,跟我们交谈,帮助我们。他保护我们不受组织其他人、事的干扰,但如果他对我们不满意,他会让我们知道。他的办公室门很少关闭。Peter就是我们的保姆。

——SQR

如果注意到如下一项或者多项情况,你能发现在你所在的组织已经有一些“保姆型”经理:不必预约就能见到你的头,或者不必在琐碎和生厌的管理工作上花费太多时间。周围是开放的氛围;人们畅所欲言,互相学习。这种经理认为培训或进修非常必要,而不是视为奢侈烧钱。他们还会抽出单独的时间(比如早晨咖啡闲谈或者周五下午阅读探讨),让大家在一起讨论新的想法。

在任何由人组成的团体里面,总会有流言蜚语、小道八卦,和一些磨洋工的情况。然而,在被经理细心呵护的办公室里面,这类浪费时间的事情会被最小化,因为经理确保团队成员对于实际进行中的事情都非常清楚。人们不需要去靠打探小道消息以得知组织内发生的事情。与之相反,他们觉得自己充分知情和受到信任,把精力都放在自己的本职工作上面。

一个类似于保姆的经理会把他自己看成是工作的催化剂。传统保姆的工作满意度来自于看到孩子能力的发展,“保姆”型经理的工作满意度则来自于看到每个团队成员在个人角色方面得到发展、生产率得得提高,并对自己工作更加满意。

这个模式的反模式有:经理把工作重心放在政治上面、放在流程上面,抑或放在逢迎更上层领导上面;绘制、调整PERT图和甘特图比与团队成员交谈更重要;还有一些经理承担了太多的实际开发工作,而不是去解决好团队的需求。

你们组织如何看待这样的经理角色?他们会因为“催化”了工作受到赞扬么?你们是雇佣“保姆”,还是“管理者”?

欢乐的鼓掌会议



高涨的士气永远象征着组织的健康。与之类似,低弱的士气则说明肯定有什么地方做错了。有一种管理理念就是奉这种关系如圭臬,试图从相反的方向来利用这种关系。逻辑是这样的:把士气鼓舞起来,其他美好的东西也就跟随而至。

啊哈,那如何鼓舞士气?尤其是如何在不增加时间、精力和花销——虽然它们是改善事物的必要投入——的情况下鼓舞士气?这是个难题,但别以为人们就不会去尝试。于是,才有了这样的谚语:“打气,打到士气提升为止。”

鼓舞士气的常见举措是仪式性的会议。会上老板笑容可掬,站在集合在一起的团队前面,
大开言路:“让我听听你们的心底话,”他大度地告诉大家。“任何事情都行,即使坏的消息和尖锐的问题。”注意这里的腔调和背后传达的信息:没有什么好隐瞒的,我们是一个欢乐的大家庭。(欢乐,该死的,欢乐。注意了。)

我知道有一家公司,这样欢乐的鼓掌仪式被称作全体会议。之所以称为全体会议,是因为所有人都获邀参加。但是一旦哪位勇敢的人果真举起手,向CEO提出尖锐的问题,最后的结果却根本不是他所预想的。CEO咕哝了几句,就迅速找了个台阶下。在当天的晚些时候,这个冒失的提问者就被他的直接上司叫去训了一顿,打消其尖锐问题受到欢迎的幻想。从此以后,在私底下大家都把这种会议都称为一言堂,因为没人会再次举手发言了。

——TDM

一旦你理解到老板并不是在征求你们的发言,而只是你们的同意的时候,你就能清楚地知道什么在上演:欢迎参加欢乐的鼓掌会议。

一次非典型性JSF调试过程

问题

前一阵子使用JSF开发web应用程序的过程中,碰到一个需求:A页面上存在一个链接,用户点击链接会被重定向B页面。页面B上存在一个单选框,如果是通过A页面的链接过来,会把单选框置为“选择”的状态。这是非常典型的页面转向,根据JSF的页面转向配置,以及对JSF隐含对象param的介绍,下面的代码“貌似”可行:

A页面:

<h:commandLink value=”Add” action=”add”>
<f:param name=”type” value=”student” />
</h:commandLink>

B页面:

<h:form>
<h:selectOneRadio id=”type” value=”#{param.type}”>
<f:selectItem itemlabel=”student” itemvalue=”student” />
<f:selectItem itemlabel=”teacher” itemvalue=”teacher” />
</h:selectOneRadio>
<h:commandButton id=”add” action=”#{backingBean.add}” />
</h:form>

编译、部署、重新刷新页面。不错,B页面上单选框的状态能根据是否来自A页面的链接呈现选中或否的状态:一切看上去都很美,似乎已经完成了功能开发。但是,等等,让我们提交表单。浏览器刷新了一遍,又回到了这个页面。通过检查后台数据库以及日志文件,我们发现:

  • 数据库里面并没有添加新的记录
  • 系统也没有按照配置的navigation转向正确的页面
  • glassfish的日志文件中没有add方法执行打印的日志,也没有任何异常信息

这三点说明,#{backingBean.add}方法并没有调用,原来可以工作的添加功能出现了bug。JSF在处理页面提交请求的过程中发生了什么?让我们来调试一下。

原则

在软件开发中,调试的目的是解决“如何定位系统问题所在”的问题。一般意义上,解决问题的原则,套用胡适先生的话,就是“大胆假设,小心求证”;套用《麦肯锡方法》,则是“以事实为基础,以假设为导向,结构化推理”。具体来看,调试是这样一种分析问题的方法,面对复杂的问题,通过逐步确定正确或者错误的事情,缩小问题范围,直到定位问题所在为止。把事情确定化,也可以细分为以下步骤:

  • 提出猜想
  • 验证猜想 or 捕获异常
  • 提出新的猜想

在调试过程中,上面的步骤周而复始,并借助于严密的逻辑论证来推动,直到定位最终的问题原因为止。同时,因为调试的过程中,开发人员面对的是已经“编码完成”的系统。“编码完成”的系统可以从如下两个层面来看分解:

  • 技术层面
  • 业务层面

如何高效调试不仅仅是调试工具的问题,更是人对技术和业务领域的理解问题。在面对具体问题的时候,是采用“步步为营”,还是“分而治之”,都是依赖于当时的具体问题,以及开发人员对问题场景的理解程度和技术熟悉程度。那么,高效地调试应该是什么样子呢?我觉得应该是这样的:

  • 划定问题域边界
  • 选择确定的出发点
  • 借助其他已经确定的点走查问题域,缩小问题域

好,来看看针对JSF的这个问题如何调试。

步骤

我们先来划定我们初始的问题域:JSF请求提交后,JSF不能正常调用后台方法进行处理。我们想知道,JSF处理请求过程中哪个地方出问题了。那么我们确定的点是什么呢?JSF规范。因为我们使用的是SUN开发的JSF RI,所以它必然满足JSF规范。在规范中,JSF的请求处理过程一共分成六个阶段:

  1. Restore View
  2. Apply Request Values
  3. Process Validations
  4. Update Model Values
  5. Invoke Application
  6. Render Response

我们可以定义一个PhaseListener,注册到faces-configs.xml文件里面,看整个请求过程发生了什么?通过查看 glassfish的日志文件,我们发现update model values之后就直接render response,没有 invoke application。 如果一切正常,应该是从第一步执行到第六步,但现在跳过了第五步,直接从第四步到了第六步,是哪里出现了问题?好,从“JSF的处理过程”到“第四步 Update Model Values”,我们已经缩小了问题域的范围,现在确定的点已经有JSF规范和 “Update Model Values”了。继续,从JSF规范对步骤“”中寻找“Update Model Values”的说明:

If any of the updateModel() methods that was invoked, or an event listener that processed a queued event, called renderResponse() on the FacesContext instance for the current request, clear the remaining events from the event queue and transfer control to the Render Response phase of the request processing lifecycle. Otherwise, control must proceed to the Invoke Application phase.

这里提到如果我们在updateModel()方法或者事件监听器里面调用了FacesContext的renderResponse()方法,就会从事件队列里面直接清空剩下的事件,转向Render Response步骤。但是我们没有注册任何的事件监听器,也没有自定义任何组件的 updateModel()方法,那就只能是在系统组件的updateModel()方法里面抛出异常被JSF引擎捕获,然后直接 render response。现在进一步缩小范围了,让我们来看看Javaapi doc里面是如何介绍UIInput.updateModel() 方法的。

Call setValue() method of the ValueExpression to update the value that the ValueExpression points at.

问题转移到javax.el.ValueExpression的setValue()方法,我们来看看这个方法的API:

Evaluates the expression relative to the provided context, and sets the result to the provided value.
Throws:
PropertyNotFoundException – if one of the property resolutions failed because a specified variable or property does not exist or is not readable.

再来看看组件的ValueExpression,我们写的是“${param.key}”,从文档里面可以得知param就是 externalContext.getRequestParameterMap(),而 ExternalContext.getRequestParameterMap()的文档描写是这样的:

Return an immutable Map whose keys are the set of request parameters names included in the current request, and whose values (of type String) are the first (or only) value for each parameter name returned by the underlying request.

因为表单提交时的request跟之前页面转向时的Request肯定不是一样,那是否由于该ValueExpression导致的问题。让我们来验证一下,把B页面上单选框组件的值改成字符串字面值“student”。现在B页面的单选框组件就变成了:

<h:form>
<h:selectOneRadio id=”type” value=”student”>
<f:selectItem itemLabel=”student” itemValue=”student”/>
<f:selectItem itemLabel=”teacher” itemValue=”teacher”/>
</h:selectOneRadio>
<h:commandButton id=”add” action=”#{backingBean.add}”/>
</h:form>

部署,运行。不错,现在的页面组件能保持选中的状态,也能顺利创建新纪录,日志文件中也有add方式的执行信息:说明的确是因为#{param.key} 表达式的求值出错导致异常。这里的#{param}已经不再是上一步的#{param},自然无法从externalContext的 RequestParameterMap里面找到参数名为type的值。因此,JSF运行到这里,因为无法取到参数值去更新页面的单选框组件,所以就跳出了处理过程。

现在,回过头来看一下问题的原因:JSF在处理请求的时候,会对页面组件树上的所有组件进行递归更新,它会根据组件定义的EL表达式来重新计算值,更新组件状态,以保证JSF页面组件的状态性。我们得到的教训是param等JSF隐含对象或许能用,但最好不要放在JSF组件里面。“进什么庙,拜什么神”,我们还是选择JSF推荐的backingbean来保持组件的值。

结语

软件调试是一项很有意思的活动,常常给开发人员带来解谜般的快感,或者一团乱麻的纠结。导入代码、设置断点、逐步调试并不是最好的办法,清楚地划分问题域,找准确定点可能会事半功倍。当然,在找出水面下面的暗礁之后,别忘记给自己、给其他人mark上这块区域的暗礁位置,能极大减少以后触礁的痛苦。

浅谈软件开发的权利和权力

在日常生活中,有各种各样的法律规则和道德准则来约束、指导行为。比如在初次的商业合作中,双方都会选择制定一份详尽的合约来规约双方,包括双方拥有的具体权利、以及单方出错时对方享有的权利等。软件开发,在商业上面也必然会有详尽的合约,处理的是两个组织之间的利害关系。但是,软件开发同时作为紧密involve商业客户与开发团队的活动,正如Alistair Cockburn把它比喻称为game——由客户、管理层和开发人员共同play的game,其中也需要由参与play game的各方利害人来共同制定规则,让大家都能玩得开心、尽兴,甚至长久。这样,围绕着多赢长赢的出发点来play game,就同样需要这样一份“权利法案”,对开发过程中的三方利益利害人的权利做出基本的原则上的规定。在敏捷软件开发方法中,特别是极限编程中,就存在这样一份“权利法案”。

其实,我一直不知道原来极限编程里面还存在这样一个“权利法案”,问一些朋友,也有不清楚的。正巧,在翻译《ThoughtWorks Anthology》中的“What is an Iteration Manager Anyway?”一章时,原文写到:

the IM(注:Iteration Manager) must facilitate, enforce, and defend the team member’s rights. For many agile teams, these rights come from the developers’ Bill of Rights.

多亏一位资深同事透明指出,其中的Bill of Rights就是前面所讲极限编程中的“权利法案”,并给出了出处Extreme Programming ‘Bill of Rights’。该文由Steve Hayes发表,对play game的客户、开发人员和管理层都规定了各自的基本原则,试图对各方都定义一份清楚的职责和权利范围,减少各方因为认知不同造成的混乱。

Customer rights

  • The customer has the right to plan on a large scale with costs and options.
  • The customer has the right to set development priorities weekly.
  • The customer has the right to see progress in the form of a working system at the end of the first week, and to see a little more functionality every week thereafter.
  • The customer has the right to updates of the schedule, good or bad, as soon as the information is available.
  • The customer has the right to change his/her mind without paying exorbitant costs.

Programmer rights

  • The programmer has the right to estimate work and have those estimates respected by the rest of the team.
  • The programmer has the right to honestly report progress.
  • The programmer has the right to produce high-quality work at all times.
  • The programmer has the right to know what is most important to work on next.
  • The programmer has the right to ask business-oriented questions whenever they arise.

Manager rights

  • The manager has the right to an overall estimate of costs and results, recognizing that reality will be different.
  • The manager has the right to move people between projects without paying exorbitant costs.
  • The manager has the right to monthly updates of progress, and to help the customer set overall priorities.
  • The manager has the right to cancel the project and be left with a working system reflecting the investment to date.

从内容来看,这份法案给客户、开发人员(这里的开发人员包括项目团队中主要工作是与软件开发相关的各种角色,比如BA/DEV/QA)和管理层提出了很高的要求,但也在一定程度上让各方认清自己享有的权利。各方都有自己的权利,也就是在play game时可以行使的权力,让game的规则尽可能摆出在桌面上面,减少对规则的误解。但是,在具体的game中,各方毕竟不是完全对等的,如何避免对权力的误用,使各方保持一个清晰的远景?

这些天读Scott Berkun的《The Art of Project Management》,其中提到权力的来源和挣得颇有意思。拨去笼罩在“权力”一词上面的褒贬,Random House College Dictionary里对“权力”的解释是:

权力(power,名词):做事或行动的能力,进行或完成事情的能力。

Scott指出权力通常分为授予型和挣得型,授予型来自于阶级体制或者职衔,而挣得型则必须由效能和行动耕耘而得:“权力在团队中不断流动、改变方向,在不同时刻对不同人会有辅助或阻碍。因为权力在使用前纵使晦暗难明,谁有什么权力,很容易搞混”。Scott把权力误用定义为“只要无法为项目及参与项目的人提供利益,任何行动都是权力误用”,并指出“因为权力来源是自然的,而使用权力以影响和推动决策则是团队工作的副产品,这些事情本身并不邪恶”。如何防止权力误用?Scott也指出“最佳方式就是大量依赖项目远景所定义的目标,借此推动权力的应用。”

 

AgileChina 2009: Pragmatic Agile [转]

AgileChina 2009大会官方网站

由在敏捷领域最具有影响力的技术社区InfoQ中文站、敏捷方法论的领导厂商
ThoughtWorks共同主办的敏捷中国技术大会(Agile China
2009),将于9月11日~12日(周五、周六)在北京举行。届时将有超过500人来自电信、金融、互联网、教育等行业在内的高级软件开发人员、项目管
理人员等参加。本次大会将特别邀请敏捷宣言缔造者、敏捷编程(XP)方法学创始人Kent
Beck,敏捷开发权威人士、敏捷宣言的创始人之一,Dave Thomas,敏捷宣言签署人之一Steve
Freeman等国际敏捷领域专家,以及在团队中成功应用敏捷的阿尔卡特、赛门铁克、诺基亚-西门子、华为、腾讯等公司的项目负责人参与此次大会并分享他
们的心得。

敏捷中国技术大会(Agile China
2009)是国内敏捷技术领域最高水平的大会,本次大会将由InfoQ中文站负责大会策划、营销和项目实施。InfoQ中文站在今年4月已成功举办了
QCon全球企业开发大会,邀请了国内外30多名讲师,超过550位架构师、技术总监、项目经理和高级工程师参加了本次大会,大会及其运营团队获得了空前
的好评,并誉为国内“技术含量最高”的大会。而今年的敏捷中国技术大会,也将一改往年的风格,参会者以高端开发者和技术管理者为主,融合管理和工程实践,
推广全面敏捷之路。

会务咨询: 010 – 89880682 agilechina@cn.infoq.com

赞助咨询: 010 – 89880682 sponsor@cn.infoq.com

郑重声明:本文转自熊节的“透明空间”,原文地址:http://gigix.thoughtworkers.org/2009/7/5/agilechina-2009-pragmatic-agile,一切权利归原作者所有

线上出版社的一些想法

    上周末参加openparty,来自译言的几个朋友详细解释了他们预想的译言的收费模式。简单来说,译言会出面买下一些文章或书刊的版权,签约译者进行申领翻译。当译文通过审核,译言就把原文以及译文打包作为收费文章挂在译言收费频道上,按点击率来收费;或者转卖给其他网站,也可以按整文收费。最后,原文作者、译文作者和译言三方来分取利润。如果受好评足够高,译言还可能将译文提供出版,不再仅仅局限在网络上面,而是进入广大的书店。
   
    译言是一家专注于高质量译文翻译的网站,我曾在上面翻译了一些文章,也经常上去读些最新的业界资讯。译言向广大的网友提供翻译发布平台,由网友提交自认为有意思的原文,再由网友自发翻译提供译文。这种互联网化身为平台、集体参与贡献智慧、变发布为参与的模式,带着鲜明的web2.0的烙印。我们不妨命名曰:翻译2.0。与此形成鲜明对比的是,在传统的出版工作之中,一般是出版社提前做好翻译书刊的计划,再通过个人关系或者熟人介绍找到一定的潜在译者,把书交给译者进行翻译。这种方式也不妨名曰:翻译1.0。
   
    翻译1.0与2.0的特点对比,本文就不做分析了,相信读者能很好地通过类比web1.0与2.0的特点来得到。下面着重谈谈译言的出版计划,在这个时代,谁更有可能脱颖而出,引领行业浪潮?
   
    首先,我们看到文章书刊,特别是高质量的原创文章,因为在智力创造方面的特点,在版权方面的控制都是非常严格的。这类原创文章和充斥互联网的大部分转载、口水文章,质量上有天壤之别。而正是那些原创文章,才有可能真正产生足够的用户粘性,也是译言这类网站的立足之本。但是,我们来看国内外在版权这块是怎么做的?国外的有名作者的作品,通常都是被某家大的出版商把持着。比如,罗琳的《哈利波特》就是由英国出版商Bloombury买下了出版许可,任何意图翻译或者引入的出版社就必须找到Bloombury交涉版权。这种源头的单一性或者垄断性,其实更适合翻译1.0时代,也更适合大的出版厂商垄断整个出版源头。对于这类的书刊,译言集体智慧和参与能体现出来的优势就不大,而图书公司更有财力、人力以及影响力拿下版权。相反,对于一些传统报刊杂志,比如英国《卫报》、《华尔街日报》等等,它们已经建立了网上报刊,也提供了很多高质量的新闻或者专栏。因为图书公司大多不可能在这块投放资源,译言如果能谈下它们的翻译版权,也是一种比较稳定的原创文章来源,颇有发展潜力。
   
    其次,在中国正式出版书刊,都是需要书号的。新闻出版总署署长柳斌杰做客CCTV《决策者说》时指出,“中国标准书号作为一种图书的编号,本来只是一种正式出版物的标志,本身并没有价值。但在我国对出版业实行审批制的政策背景下,拥有专有出版权的出版单位,才能获得书号的使用和经营权,书号成了国家赋予国有出版单位特许经营权的标志。”大型的图书公司,比如图灵、华章,其实都是挂靠在相应的国有出版社的,依托国有出版社的资源获取书号。那么,译言如何进入图书出版市场?基于现实,就也可能需要依托某家国有出版社才能获得一定的书号,才能进行公开发行图书。就译言朋友的解释来看,译言在这一块准备的还是不足。但是,现有一些规模比较大的图书公司在这块可以说是游刃有余。
   
    最后,图书出版又涉及销售渠道的问题。我对这块不熟,但根据我的观察,书市、图书发行所和书店,这就是最基本的销售渠道。如果译言想自己包揽下所有的营销、货运、发放等工作,估计是不可能的。如何找到一家图书代销商或者代理,由对方来做渠道推广和营销,译言专注于做翻译会更有利。但是,作为在这个行业积攒不深的译言,如何建立市场,如何得到广大的代理信任,也不是轻而易举。
   
    从上文分析可以看出,图书出版作为环节繁杂、层层代理的市场,又因为知识版权的独特性和唯一性,可能传统的图书公司更有优势来做好做大这个平台,召集出版行业上下游的其他公司一同加入进来。对于译言,还有很长的路要走,才有可能走到舞台的中央。但是亚马逊也从与传统书店的厮杀中脱颖而出,谁又知道呢?

敏捷,把纪律留下(下)

(本文发表于《程序员》2009年第6期,转载请注明。

 

敏捷实践

下面,我们从个人-团队-组织的不同层次分别选取几个突出实践简要解释它们是如何提供频繁、直接的反馈。

l       
个人层级

测试驱动开发能给开发人员提供最直接也是最快捷的反馈:先写测试,再用最简单的方式实现,再重构代码以符合简单设计的原则。如此短间隔的反馈能很快地告诉开发人员刚才增加的代码是否破坏了已有的功能。而且,已完成test case的列表能很清晰地告诉其他人开发任务的完成情况。对比着用户故事的验收条件,开发人员很容易评估剩余的工作量,并不至于破坏已有的功能。

l       
团队层级

敏捷实践中的持续集成,强调尽可能快尽可能频繁地提交代码,与系统的其他部分进行集成。在提交新代码之前,必须保证本地的构建过程是成功无误的。谁提交代码使得持续集成服务器构建失败,必须立即停下手中的活,负责修复构建直到成功。下班之前必须要保证持续集成服务器上的集成构建状态是成功的。这样,开发人员和团队很容易检查新功能与其他模块的集成,另外也把未来的集成风险降到最低。

l       
组织层级

用户故事是开发团队与客户之间讨论需求的基础。用户故事必须对客户有真实可见的业务价值,并且必须包含对该需求完成的验收条件。用户故事作为业务分析人员、测试人员、项目经理与客户一起确定的用户需求,具有经过验证的确切性。开发人员开发故事之前,必须和业务分析人员、测试人员沟通理解需求;开发完故事之后,必须要由业务分析人员与测试人员根据验收条件进行验收。组织和客户之间可以针对达成共识的故事列表来分析项目状态,从而验证或者修改项目计划。

上面只是从个人-团队-组织的层次分别挑出了测试驱动开发、持续集成,以及用户故事的实践阐述了敏捷实践如何在不同的层次提供频繁的反馈,一孔窥豹,还有其他若干实践在这里就不再赘述。总之,敏捷众多的实践就像组成了一张全面立体的安全网,时时刻刻从各个角度给项目成员、团队,以及组织提供短周期的反馈,帮助团队成员不仅感受到开发过程中的同伴约束,而且也可以感受到来自整个团队的约束,甚至是来自组织之间的约束。这些外来约束也像是缠绕在个人周围的催化剂,纠正或改善个人的行为,达到提升个人的纪律性。

实际团队

经过几天魔鬼般的技术实践培训,我们在第三天给学员们安排了全天的模拟项目演练。在演练中,由学员自行组织自己的团队:选出自己的团队名称和口号、推选出项目经理、各自分配开发任务,所有人都信心满满。在刚开始接触开发任务的时候,他们还是有一些不好的习惯,这时候,我们鼓励他们把前几天学到的敏捷实践都用起来。于是就出现了这样的形式:当结对中的一人先写实现,而不是先写测试时,另一个人会指出问题,然后重新使用测试驱动的方式;在提交代码时,会有培训讲师监督着他们按照正确的方式来提交;开发用户故事,要求开发人员必须跟分析人员沟通清楚细节,验收故事时,开发人员必须与分析人员和现场客户同时参与验收……虽然有些磕磕碰碰,但整体上团队还是有条不紊地进行下去,而且每个人只需要关注自己手头的那部分工作,也易于让他们把事情做得正确。

到了下午,随着学员对技术和业务理解的加深,他们也开始自觉地维护起开发过程,使其保持顺畅。开发过程中,结对的两人激烈地讨论实现的方法,达成一致后又一起开怀大笑;碰上了问题,主动招手找业务分析师询问需求细节,如果业务分析师也弄不清楚,再找现场客户来解答,直到三方都满意;多人开发遇上了冲突,主动找到对方,商量沟通解决方案,实在不行,就找项目经理进行沟通协调;当有人提交了代码使得持续集成服务器构建失败,所有人会善意地提醒犯错的人,督促他们修复;谁遇上了技术问题,有人听见了他们的讨论就会自发上前提供自己的信息;项目经理因为团队自组织也就从繁杂的管理工作里面脱身而出,饶有兴趣地与开发人员一起结对干起了开发的活……整个团队像一列火车一样,前轮带动后轮,后轮推动前轮,井然有序,毫不停歇地往前行进。

最后,我们作为模拟客户参加了这个团队的show
case
会议,惊讶地看到这个团队的士气和活力,以及他们完成的工作。特别是他们表现出来的团队集体感,让人会以为他们是一个磨合很久的团队。项目经理还在为没有完成更多的工作任务觉得惋惜,但对于如果给更多时间,是否有信心这个团队可以更好地完成更多的任务这一问题,他表达了明确的认同。然后再问为什么,他说,这个团队的士气和纪律让他刮目相看,目前完成任务的质量让他对未来的任务充满信心。最后问愿意率领这样的团队么?,答案是为什么不?

 

作者简介:金明,ThoughtWorks咨询师,InfoQ中文社区编辑,SCJP,系统分析师。他在机械模具、数字安全证书,以及海洋航运等行业拥有超过4年的企业应用开发经验。他对敏捷方法学,特别是敏捷咨询和项目管理,以及面向对象分析和架构设计等方面有浓厚的兴趣。


--完--