打破铁三角:新的项目管理角度

时至今日,依然有很多项目受困于项目管理铁三角:范围,时间,和成本。是啊,

  • 必须在2月底完成,因为报税高峰期3月份就来了。必须在10月底完成,因为要撑过双十一的并发量。必须在10。1前完成,因为要国庆献礼。
  • 这些需求都得做,因为被替换的系统已经有这些功能了,好多人在用,没了他们会叫的。
  • 就这些人了,招人短时间内也招不到,再说你们不是说了加人反而会降低开发速度吗?

这些都是现实的困难,很难突破,这也是前面几项被称为”铁三角”的原因。那是否就一点办法没有了?

打破一条规则最有效的方法是推翻它的前提和假设。当我们重新审视铁三角的时候,会发现它至少有四个假设。其中有两个假设比较明显,早早就被人发现并利用了。而另外两个假设则需更进一步的洞察力,敏捷项目管理正是对准了这两个不那么明显的假设。对这四个不同假设的颠覆,导致了截然不同的软件过程管理方法。下面我们依次来看一下。

时间变慢

第一个假设较为明显,即铁三角中的时间是按每周工作5天,每天8小时来计算的。无数的团队发现了这一点,然后毫不犹豫的打破了它。每周工作6天,每天12小时如何?工作吞吐量立即可以提升(72-40)/40=80%。相当于时间的流逝减缓了近一倍。这就是我们常见的加班背后的原因之一。

牺牲质量

第二个假设也不难发现,即铁三角中没有提及质量,尤其是内部质量。其实就算客户和供应商的合同中对质量做出一定要求,由于其难以衡量和验证,以及延时效应,通常也沦为最弱的一种约束。”精明”的团队对此心知肚明,通过拷贝粘贴等牺牲内部质量的方式来快速堆积功能。这就是我们常见的匆忙赶工的产品其代码难以长期维护的原因之一。

对以上两个假设的颠覆导致了不利于团队,不利于客户的开发方法,长期来看都是输家。所幸我们还有第三和第四个假设,对它们的重新审视把我们引导到更加合理的项目管理角度。

关注价值

第三个假设是这样的:铁三角之所以这么引人关注,是因为大家认为只要在固定的范围,时间和成本的约束内完成项目,就是成功的。

这是一个看似合理的假设。然而考虑以下两种情况:第一种是在规定的时间和预算内完成了全部预期的功能,但产品没人用,投向市场没啥反应。第二种是工期超了一点,预算也超了,计划的功能有很多没做,相反根据变化做了点别的,但产品推向市场后反应不错,带来了利润。那么两种情况哪种算是成功呢?

我会选第二种。这么选的还有一个叫JimHighsmith的。他针对这个问题提出了新的三角,他称之为敏捷三角:价值,质量和约束。见下图(摘自Agile Project Managment):

其中传统的铁三角被局部化成一个维度,称为约束。而引入了新的维度,价值和质量。其中价值代表的是利润等正向的因素,而质量代表的是变化的成本。质量越好,意味着变化的成本越低。据此,我们打破铁三角的第一个手段是,关注真正的用户价值,降低变化成本,并为此而调整计划。

提高生产效率

铁三角的第四个假设是生产效率不会发生变化。因此固定其中两个只能调节第三个,铁三角因而是铁的。

这个假设具备一定合理性的原因是短时间内生产效率很难发生突破性的变化。但这不妨碍我们持续去提高生产效率,从而软化铁三角。

这方面有众多的选择,比如通过自动化减少手工工作,通过预防错误避免返工,而这里面最重要的,是持续学习,提升每个个体的效率。我们通常说程序员之间的效率差异会达到数量级的差别。花些时间在沟通交流培训反馈上,是我们即使在最严格的外部约束下,也可以做的,并且是为数不多的手段之一。

其实我们从来就只有两个问题…

做什么和如何做。

对做什么保持关注,就会得到敏捷三角;对如何做保持关注,就会得到持续改进;不思考才会被约束住。


更多精彩洞见,请关注微信公众号:ThoughtWorks洞见

Share

超越培训——比培训多做一点点

培训真的没用吗?

在我跟同事聊起培训的时候,他们对培训的认知大概是这样子:”我们团队成员的架构能力不足,没法落地微服务,你们来给我们上一个DDD的课吧…” 诚然,这种模式在培训市场是普遍存在的,组织斥巨资邀请大牌培训师,上个几天的课,培训师拿钱走人,然后呢,可能就没有然后了。

团队之所以需要一个培训,无非是因为面临自身无法有效解决的问题,亦或识别出潜在的风险(以花钱为目的另当别论)。问题通常源于流程和人两方面,流程的问题最终也能归结到人身上,人的问题又很容易被定义为能力的问题,如此一来团队便寄希望于借助外部力量来提升团队的能力。这种想法没毛病,毛病在于培训往往无法有效解决能力问题,除非培训能够回答以下两个问题:

  1. 如何让学员的认知发生实质性的转变?
  2. 如何让学员将知识有效地转化成技能?

实践证明,单纯的培训很难给出答案,从而产生了培训无用论[1] 的观点。然而,培训真的没用吗?如果没用,为什么一些大厂都在大力推行员工培训呢?

能力建设的团队自治观

思沃内训[2]是ThoughWorks中国区负责人员能力建设的团队,我们同样面临着跟外部培训相似的困惑:培训之后无法保证团队发生实质性的提升。 要改变现状,我们必须要比培训做的多一点,站在更高的视角去看团队对培训的诉求,不难发现团队是希望通过有效的能力提升去解决实际问题,这便升级为一个复杂的能力建设问题。

最理想的能力建设活动应该由团队内部自发组织,一来具备更好的On-Boarding土壤,二来更符合自组织的敏捷团队特征。在ThoughtWorks不乏这样的学习小组。然而,随着公司业务的扩张,新老同事快速更替,能力建设遭遇瓶颈,内训团队便承担起特殊的外部教练角色。

教练本身不会直接着手解决团队面临的问题,教练的主要职责是帮助团队自己解决问题,最终还是要依靠团队自身发力,取之于团队、用之于团队。知易行难,做好这一点呢?带着这些思考,我们落地了一场超越培训的训战

超越培训的训战模式

训战模式的核心思想是培训 + 实战,该模式需要统筹规划培训前、中、后三个阶段,做到训前瞄准、训中调整、训后复审,将单纯的培训变成一个有效的能力建设活动,实现价值闭环。

与传统培训方式不一样的是,我们在训前做得更加充分精确,为训中留有足够的时间和空间,实现课程快速迭代,后期结合至关重要的训后复审,通过实战来内化知识。该模式的核心指导原则是:跟团队保持紧密连接。基于这些创新的想法,辅以4个关键步骤来完成训战:

教练在前期深入团队,分析团队现状,准确定义问题,为团队量身定制解决方案。培训交付期间,通过教练引导技巧深度激发团队成员的思考和讨论来颠覆或加强他们固有的认知。最后,围绕训战计划来促进团队的知识转换。

下文我将通过实践案例对训战模式做一个全面的阐述。这是一个服务于海外知名大企业的业务团队,前期高质量交付赢得客户的信任,促成了更多业务合作机会,团队规模亟需扩充。此时,原本新人占比大的现状伴随着扩充继续加剧。如何提升团队开发人员能力、保证敏捷技术实践的良好落地成为团队即将面临的一大难题。

定义问题 – 深入团队

问卷或访谈的方式呈现出来的很可能是冰山上半部分的景观。为了探索下半部分,我在前期深入团队内部获取团队日常工作状态、技术栈选型以及人员的相关情况,并出了一个初步的分析报告:

基于分析报告,跟TL达成初步方案是上OOBootcamp五抓手(OO、Clean Code、Simple Design、Refactoring、TDD)。有了五抓手这把枪,不能着急开火,我需要弄清楚团队对这些实践的实际的落地情况。通过参加团队的代码评审以及详细的代码库扫查,我果然收到了惊喜 — 代码库测试覆盖率高达90%,代码分层、模块化都不错(似乎已经做的很好了)。

当前代码库的良好状态离不开团队的对Clean Code的重视,再加上团队刚刚对原本业务代码量不大的代码库做了较大规模的重构。即便状况良好,团队依然非常渴望掌握工程技术实践的最佳姿势,尤其是TDD。

基于这些调研分析,我对问题域重新划重点:

  1. 团队成员Second Tier入职时间偏短,相关敏捷技术实践掌握深度不够,担心影响后期交付质量。
  2. 技术实践在后期Ramp-up保持最佳姿势一致性有难度,存在辜负客户期望、降低客户信任度、难以保持标杆形象的风险。

设计方案 – 量身定制

不难看出此次能力建设活动属于风险预防性质的。虽然没有太紧迫的痛点,但团队已经暴露出一个关键的信号 — 团队已经在尝试的过程中产生困惑,渴望得到解答,并通过实践掌握最佳姿势。该信号给了我一个方向:借助大量的实践操练和充分的思维碰撞来加强训战的效果。基于此,我搬出了承载了五抓手的法宝OO Bootcamp[3],并一切为8,每周3次,每次晚上2~3小时,形成了非常6+1的两周拉锯战模式。

依赖于口口相传的OO Bootcamp在课件标准化上沉淀颇少,这也给了我充分的空间让我去设计训战方案,对于训的设计,我重点兼顾了两点:

  1. 定制化调整。针对团队的真实情况做适当的定制化,并做好在交付的过程响应变化的准备。
  2. 螺旋化共创。在课程中能够不断激发思考,试图让大家经历困惑、解惑、疑惑、再解惑的螺旋化过程。做到学员共创 Over 讲师讲解

交付培训 – 认知转变

本环节的核心目标是:通过持续调整,辅以螺旋化共创过程,诱发认知转变。 要引发螺旋式的认知转变,最重要的一点是:放慢步伐,以学员讨论、答疑解惑为核心宗旨。因为参与这次训战的成员特殊性(TL & Second Tier),讨论的焦点主要被我引导向价值层面(Why),通过操作层面(How)的冲突来激发讨论,并在How与Why之间螺旋交替冲击,最终回归到Why上,讨论的重点也大多聚焦在团队日常工作中面临的问题上。

有意思是,当大家对价值层面理解达成一致后,在操作层面的最佳实践往往都是无果而终(By Experience),我们对最佳实践虽然未曾有明确的定义,经过这样频繁的思维碰撞,团队往往能找到一些方向。比如TDD,做Story的时候,第一步是从业务视角去做Tasking,将Tasking可视化作为一个DoD[4],严格根据Task来编写测试用例,做到测试先行,并通过Pair来刻意练习。

铺设好明线,我在辅线上也做了一些必要的工作 — 跟团队做深入交流,了解他们当前面临的痛点,设计新的案例,尝试抛出一些引子,引发团队成员共同思考。比如如何在后端MVC架构下做TDD。

部署计划 – 技能转换

我认为一场好的训战应该由体验、反思、抽象、行动四个部分组成,相辅相成,并且能够形成一个闭环。在培训过程中,需求驱动、编码实践就是一种体验,在体验的过程中引发思考和讨论,最理想的情况下是学员自己能够从思考和讨论中抽象总结得出结论,并将结论付诸行动得以验证。

在文章一开始我就提到,能力建设最终要靠团队自身发力,主动权必须交还给团队,否则一旦教练离场,打回原形的风险很大。通过培训颠覆认知只完成了一半的工作,另一半的工作是将这些新的认知在实践中去验证。要打好下半场,就需要搬出核心法宝 — 训战计划。
训战计划类似于一个计划,它具备三个重要特征:

  1. 符合SMART[5]原则,难度适中
  2. 跟项目工作内容息息相关
  3. 学员自己拟定并认可签字

作为教练,我协助团队成员去制定有效的训战计划。有了训战计划,就一定能够兑现吗?理想情况下,团队成员的能够足够自我管理,并落实好计划。必要的时候,借助一些轻量的管理机制和有效的激励机制,比如,组建分队、队长责任制、公开承诺发布等,另外对计划完成后进行奖励等。
作为特殊的外部教练,我需要持续重点做的事情有:

  1. 培养团队内部教练,保证后期的可持续发展。
  2. 训战计划执行期间,响应团队的诉求,帮助团队解决执行过程面临的阻碍。
  3. 定期回访,跟踪训战计划的落实情况,了解团队的困难,并记录团队的变化。

训战的核心要素

训战的复杂度远超越了培训,既要大处着眼,用全局的视角统筹训和战,也要小处着手,紧抓各个环节,尤其是训战计划的落地跟踪。一场优秀的训战,除了方案设计、课程内容和呈现形式上的创新,还需要借助团队管理和激励的手段。综合来看,决定训战成功与否的几大核心要素有:

  1. 一致的期望
  2. 专业的培训
  3. 承诺的计划
  4. 严格的跟踪

一致的期望

在训前方案设计阶段,一项至关重要的举措是跟Stakeholder和团队成员对训战模式的期望达成一致 — 不仅仅是一场讲完就散的培训课程:

  1. 对于学员,要做出源于追求卓越的自我Commitment。
  2. 对于Stakeholder,要提供资源来促成训战计划落地,比如识别潜在内部教练,提供训练道场支持等。

专业的培训

教练需要对领域知识具备一定的深度,深刻理解正、反模式的利弊,拥有丰富的实战经验。同时对于教练引导能力也提出了较高的要求,推荐实施以学员为中心的共创式教学。另外,还需要具备对实时反馈的响应力,能够快速调整优化设计。

承诺的计划

学员基于培训的内容,结合实际项目中遇到的问题,亲自挂帅拟定恰当可行的训战计划,并立下”军令状”,最终做出公开承诺、告示”天下”,若能借助管理激励机制形成彼此轻量的竞争态势会取得不一样的效果。

严格的跟踪

训战的效果取决于训战计划是否合理以及能否有效执行落地,后期严格的跟踪尤为关键。首先,可以在团队内部培养教练,来帮助成员解决执行过程中遇到的问题,同时敦促计划的推进。其次,在流程管理和奖惩机制上,Stakeholder的关注、必要的激励以及恰当的惩罚技巧都会影响跟踪效果。至于如何操作,团队因地制宜即可,推荐正向激励。

写在最后

训前瞄准、训中调整、训后复审这种基于业务团队的训战模式,通过4个看似很平凡的关键步骤,围绕着训战计划来促进行动学习,帮助团队将知识转换成技能,有效地实现价值闭环。

培训到底有没有用,我们给不出一个标准的答案,我们能做的是探索更高效的能力建设模式,尝试比培训多做一点点。

注释

  1. 培训无用论,参考文章《然而培训并没有什么用》
  2. 思沃内训团队,ThoughWorks中国区负责人员能力建设的团队,相比于其他外部培训机构,内训团队的优势在于深耕ThoughtWorks,充分理解ThoughtWorks文化。
  3. OO Bootcamp,全名为“面向对象训战营”
  4. DoD, Definition of Done
  5. SMART
    • Specific
    • Measurable
    • Attainable
    • Relevant
    • Time-bound

更多精彩洞见,请关注微信公众号:ThoughtWorks洞见

Share

从领导力的角度谈ThoughtWorks的团队间协作

最近在看一本书——《Team of Teams: New Rules of Engagement for a Complex World 》。作者之一是2003年就任美军驻伊拉克联合特种作战部司令官的Stanley McChrystal将军。书中有个例子看上去是那么的眼熟,相信不少同事,特别是销售和PM都会有同感。

联合特种作战部队的一个执行小队登上桨声隆隆的直升机,驾驶员开始最后的检查。这时,距离直升机百米之外的指挥中心里指挥官收到了一个信息。当他还以为是关于攻击目标的实时状态更新,结果却是来自另一个作战单元的通知:负责监控目标的ISR (Intelligence Surveillance and Reconnaissance)被抽离行动现场,去跟踪巴格达另外一个优先级更高的目标,本次行动已不再具备所需条件,任务取消。指挥官当然非常郁闷,在直升机上整装待发的团队也只能无奈撤回。

随着作战环境变化速度的加快,承担战场实时监控的资源,比如捕食者无人机,还有提升作战部队移动性的资源,比如直升机,都是各团队激烈竞争的资源,以至于有时候地面部队的指挥官不得不在最后一分钟将已经到手的资源交出来。对团队来说,一时间紧盯目标的无人机还在他们手上,转眼就没了,原本可以搞定的任务却没法执行。这种感受就是:在这个零和游戏当中,我被牺牲了。这种情况如果发生几次,就会让人觉得为什么倒霉的总是我,甚至会认为这个系统是不是针对我,对我不公平。

就像书中提到美军联合特种作战部的地面行动部队和情报分析团队一样,ThoughtWorks的团队和个人也会不时感觉自己似乎处于囚徒困境当中:如果我主动协作会不会让其他团队在信息上、资源上获得不公平的优势,我是不是应该尽力博弈,通过力量的均衡达成公平的结果?最早的一篇脑洞《 把“墙”推倒 - 扁平组织中自主和责任》从团队定义的角度,初步探讨了Autonomy vs. Accountability直接的关系。下面是当时讨论的团队四个特点:

共同使命( common purpose)

互补的技能(complementary skills)

绩效目标(performance goals),

各自相互承担责任(hold themselves mutually accountable)

这次我尝试从领导力的角度来讨论我们应该如何面对这种情况。CCL(Center of Creative Leadership)发布的一篇白皮书把领导力文化分成了三个级别。CCL认为,一个组织在这几个级别之间的提升,意味着应对变化,解决复杂挑战的能力提升。

  1. Dependent leadership cultures(依赖型领导力文化):领导力的责任只来自处于权威地位的人。领导力发挥的作用依赖对权威的服从,效果主要体现于保持事物运转的顺畅高效。
  2. Independent leadership cultures(独立型领导力文化):领导力基于知识和能力,根据需要浮现自组织各处不同类型的个体,经常体现出去中心化的决策,尊重个体的责任和专业能力,并鼓励个体间的竞争行为。
  3. Interdependent leadership cultures(相依型领导力文化):领导力是一种需要共同探寻和学习的集体活动,是一种面对复杂挑战的负载能力。

看到这篇文章的时候,我感到这第三个级别的领导力文化似乎是破除组织中囚徒困境的关键。

最近看到一个很有意思的例子。有些同事可能知道公司有个推动安全相关实践的BSI团队。这个团队的起源是刘庆华、马伟和刘冉一起做的一套叫Build Security In的安全软件交付方法。团队本来就没几个人,随着庆华离开,实力更是大减,我当时是非常担心。不过最近却发现,安全团队的核心成员不减反增,除了BSI的原创成员马伟,还加入了安全策略咨询的杨璐,安全合规和基础设施专家李小雪,还有刚从厄瓜多尔历练归来加密专家蒋帆。这个团队竟然初步具备了安全领域比较完整的能力体系。如果我们看这个团队的组成,除了马伟是安全团队成员外,杨璐来自国内售前团队,李小雪来自TechOps的InfoSec团队,蒋帆来自咨询团队。

虽然拉通了四个部门,这个跨界团队的形成却并不是一个自上而下的安排。我还记得几个月前刚刚加入公司不久的售前杨璐找到我说,听说公司有个安全方面的团队,提出希望能够参与相关能力和业务的建设。从那之后,杨璐和马伟开始一起组织起了这个团队。不仅核心团队的能力更加丰富和多样化,BSI团队还在各个office建设起了安全技术社区,小伙伴们一起来研究和提升安全能力,实施安全实践。

当前这个团队还是以一个虚拟团队的模式在运行。团队成员之间并没有直接的隶属关系,而这个团队的目标跟大多数团队成员所属的BU、Office和部门也没有直接的责任关系。一方面我们看到大家都热情地投入到这些活动当中,另一方面他们工作的开展还得到了各方面Leader的大力支持。在国内项目上,销售团队开始寻求安全相关的项目机会,国内交付团队帮忙在现有客户的项目上,在新客户的inception加入安全活动,海外项目团队则开始推进安全能力提升的活动,Office Principal们一起帮忙协调支持社区的活动。这样的网状的互依互助的的领导模式让我们整合多个团队的不同能力,快速应对市场的需求和变化。

不过坦白来说,这个模式要产生好的效果很不容易。不仅对团队leader的要求很高,对整个组织中其它单元的Leader来讲,也都是领导力的巨大挑战。或许这也是为什么CCL会把相依型领导力文化作为最高的第三级。

囚徒困境的挑战来自全局优化 vs. 自主驱动 (Global Optimisation vs. Self-driven)之间的矛盾。组织效率的一个来源是清晰地结构、边界和责任,因此我们建立了一个个的团队,每个团队都有自己的目标。驱动力的重要来源则是Autonomy,我们的团队和leader被授予很大的操作空间来达成目标,这是我们很多ThoughtWorker热情工作的驱动力之一。我们都知道全局优化的重要性,但当每个独立团队都盯着自己的目标,坚持自己的方式的时候,却经常会让我们偏离全局优化的目的。

McChrystal将军认为,全局上下文的缺失是团队做出局部优化行为的主要原因,对其它团队视角、能力缺乏了解,是信任感下降的症结所在。因此提出的一个方法是设立在部门之间人员交换的轮岗项目,二是在部门之间派遣关键联络官,这些关键联络官都得到充分授权,在关键时候可以代表派出部门做决策。一方面,可以让我们了解组织的其他部分如何看待业务活动的开展。另一方面,联络官或交换人员可以真实地为对方团队贡献价值,这是在团队之间建立信任的重要基石。

除了结构上的设计,我们还可以从领导力角度来看这个问题,或许还有一些不同的解决问题的关注点。

首先是对于目标的定义,相依型领导力文化里对成功有多层面的定义。这几年不时有人会问我这样的问题:请用一句话描述你的目标,你公司的业务…… 以前我会尝试去总结回答,但却发现这种问题的答案通常都是一句广告词,糊弄一下别人也罢了,自己可千万别当真。一个团队自己业务目标的达成,并不是团队Leader成功的唯一衡量。对内,要能够发展团队;对外,要能够站在公司战略层面上,为其它团队提供支持;而站在公司使命的角度,我们还有平衡使命的期望。这些目标有的时候可能比更好地完成自己业务目标更加重要。正因为对Leader有着多层次的期望,Leader就需要尽可能掌握更多的上下文,更深刻地理解公司策略,尽可能做出平衡的决定。这是为什么前面支持安全团队的其它团队Leader们并没有花力气去分辨是你的我的,没有去问“为什么我团队的人在干你的事情”,而是力所能及地提供支持。

此外,作为一个ThoughtWorks Leader必须能够推动开放、坦诚地跨组织边界协作,面对变化的环境和问题随时驱动新的组织结构的浮现。在ThoughtWorks,只要登高一呼,就可以启动一个虚拟团队,俗称“基于微信的机构重组(Wechat based ReOrg)”。CLT的组织就是根据具体目标来动态组合的执行团队模式,比如去年出现的新团队就有胜任力推广团队,领导力发展团队,招聘改革团队等等。这些虚拟团队运转一段时间,如果有持续的需要和价值,就可能会转为BAU团队,如果目标达成,也可以随时解散。

最后是Leader在建立共同使命( common purpose)应该发挥的作用。很多刚进入Leadership角色的同事第一的感觉可能是ThoughtWorks的会多,团队内部的会、兄弟团队的会、还有各种1on1的Catchup。更让人郁闷的是这里有不少会议并不直接产生后续的行动计划,而是美其名曰share context。但是在不以流程驱动信息流转的环境里,让信息能够在需要的人之间流动起来,并且通过讨论形成共识,是一个Leader的关键职责。McChrystal在书中管这种沟通叫建立共享意识(Shared Consciousness),我们的胜任力模型对Lead有个相关的要求叫做Establish Focus。这还是为什么ThoughtWorks全球核心团队的名字叫GCG(Global Coordinatation Group),而不是用什么“管理决策团队”之类的名字。郭晓在描述自己的工作时最常用的词是Orchestration,也是类似的意思。当然,这么做必然有些副作用。在一个网状联系的组织里,有时候并不确定传递的信息是否对所有人都有价值,因此可能会让有些参会者觉得浪费时间。

ThoughtWorks的Leadership 角色经常处于一个纠结的状态,总是在根据情况的变化痛苦地寻求新的平衡点,但这或许就是新型组织的新常态。

MD心声

  • 相依型领导力文化中如何兼顾效率?
  • 大家身边有什么既能兼顾权衡各种矛盾,又能展现的英明神武形象的role model?

推荐阅读

  1. Team of Teams: New Rules of Engagement for a Complex World
  2. Transforming Your Organization – WHITE PAPER from Center of Creative Leadership

更多精彩洞见,请关注微信公众号:ThoughtWorks洞见

Share

RPA工具初体验

引子

一年前,在一次客户(老外)的演讲中,晕晕乎乎的在一大段英文中听到了RPA这个词,当时大概查了一下,了解到RPA是机器人流程自动化(Robotic Process Automation)的简称,跟自动化有些关系,但是当时也没搞太明白。

半年前,听说客户的IT部门开始培训大家用RPA工具UiPath来做自动化测试,但是遇到了一些麻烦,问我们这边是否有相关经验。还真不好意思,没有接触过,于是决定研究一下RPA到底是个什么玩意。

RPA初印象

首先看到的是埃森哲的《Getting Robots Right》文章,介绍了RPA的常见误区、案例分享,以及RPA的关键成功因素等,都是高大上的介绍,对于我这个没有接触过的人来讲还是有些云里雾里,只是对RPA有了大概的认识。

文章提到RPA是使用软件来完成重复的、结构化的、基于规则的任务,从而大规模地自动化业务流程,最终实现企业级智能自动化,它是基于办公室的等效生产线机器人,基础技术是机器学习和人工智能。

简而言之,RPA就是用机器人(软件)来取代人完成工作任务。

文章还介绍了RPA可以做的事情,有处理事务、操纵数据、触发响应,以及与其他数字系统通信。其实就是像人工作那样操作不同的系统,处理不同的任务。

理想的可以用RPA工具来操作的应用程序可以在财务、人力资源、采购、供应链管理、客户服务/经验和数百个行业特定业务流程(例如保险索赔处理)中找到。

到此为止,感觉还是很抽象,了解到RPA主要是用来自动化业务流程的,但是不清楚RPA具体是什么样的。

因此,还是先体验一下RPA工具吧。

RPA工具初体验

下载了目前市场占比最大的工具UiPath试用版,尝试使用它提供的录制回放功能录制了一个简单的步骤,的确可以工作,但发现对于复杂的、有条件跳转的还不能这么简单的实现。

通过研究入门手册,琢磨着编写了几个程序实例:一个是猜数字游戏,有两个版本;另一个是从网站查询指定城市的实时天气。它们长这样:

左边的游戏是序列(sequence)形式,右边两个是流程图(Flow chart),跟平时画的流程图非常的类似,很直观可读。好像有点意思!

这是怎么做到的呢?麻烦吗?

UIPath工具提供一个图形化的编程界面UIPath Studio,由三个主要部分组成,Activities(默认在左边)、Properties(默认在右边)、中间是编辑和展示上图中那样的序列或者流程图的地方。

Activities里有各种活动的控件,比如:Input Dialog、Write Line等输入输出控件,以及If、While/Do While等条件/循环判断控件。将活动控件拖拽到中间编辑区域,设置跟其他已有控件的关系。FlowChart里可以通过箭头连接不同控件来设置其相应关系,而Sequence里则是按照控件摆放的上下顺序为先后顺序。

然后,选中编辑区域的控件,可以在右侧的Properties里设置对应的控件属性,比如:猜数字游戏,判断输入的数字跟实际数字的大小以确定弹出不同的消息内容,这些都可以在Properties里对应的设置。

同时,还支持设置相应的变量,比如猜数字游戏中的实际数字和输入数字都可以用变量代替,方便多次使用做比较。

因此,在UiPath里通过拖拽和相应的属性设置,全部在图形化界面上完成,就可以实现一个程序的编制,并不需要有编码工作,对编程技能没有什么要求。对于普通的业务工作人员来说,也是非常简单的。

这个简单实现业务流程自动化的工具似乎跟传统的UI自动化很有相似之处,是不是真的可以像我们客户那样用来做自动化测试呢?

RPA与UI自动化

研究了一阵UiPath的用法后,我给团队做了一个分享,用前面做的程序给大家演示UiPath的使用的时候,本来工作的好好的获取天气程序竟然挂了…原因是网页上的元素有了变化,重新修改获取新的元素路径才得以通过。

由此可见,RPA工具也跟UI自动化工具一样受到UI元素影响较大。

UiPath提供的图形化编程界面,对于没有编码技能的人来说,新建一个工作流拖拖拽拽就能完成,的确很方便。

但是,UI自动化测试都会随着UI的变化需要做相应的修改,通过图形化界面修改流程感觉还是有些麻烦的(或许是因为我还不够熟练使用这工具),作为QA,我更喜欢通过代码的方式来修改。而UiPath后台存储的是Xaml格式,可读性一般般,要改代码也没那么容易的感觉。

另一方面,UI自动化测试最好跟持续集成工具集成起来,而主流的RPA工具都是不能在CI pipeline上运行的。

不像UI自动化工具那样运行于测试环境,RPA工具主要是适用于生产环境,基于相对稳定的系统来实现流程自动化。

当然,开源RPA工具TagUI,可以编程,也支持命令行运行,但是这个工具不太像是RPA工具,更像是被RPA耽误的UI自动化工具。

RPA工具用于UI自动化测试不仅没有太多的优势,反而带来很多不便,有杀鸡用牛刀之嫌,不合适。

对于自动化测试还是要基于测试分层理念,考虑尽可能把UI层自动化测试下移,对于必要的UI自动化测试也可以用更轻量级更适合的工具来做。

由于各种不适,我们客户用RPA工具做自动化测试的事情当然是无疾而终。

既然RPA不适合做自动化测试,我们来看看它的真正用途吧。

RPA技术的真正用途

RPA技术可以模仿各种基于规则而不需要实时创意或判断的重复流程,在电脑上不间断地执行基于规则的各种工作流程,它不仅比人类更快,还可以减少错误和欺诈的机会。简言之,就是“像人类一样工作”,“把人类进一步从机械劳动中解放出来”,让人类自由地开展更高价值的工作。这是RPA技术的初衷,是RPA技术的真正用途。

基于上述特点,RPA技术目前在财务领域应用比较成熟。财务是一个强规则领域,财务领域内的很多事务流程和报告流程大多是可重复、有规律可循的,因此也最易于实现流程自动化。在财务决策过程中相对标准化、有清晰的规则和可重复的活动,也可以应用RPA技术。

把财务相关的输入- 处理 – 决策 – 输出的流程进行分析、拆解,再用机器人软件模拟人的操作,把原本要在各种软件平台——包括会计软件、ERP软件、报表软件,甚至是CRM软件和税务软件上需要很多人力完成的填写、报送、执行命令、菜单点击、输出报表等动作,交由机器人来完成。这就是RPA技术在财务领域的应用场景。

其他基于规则的结构化的业务流程,也可以应用RPA技术,比如HR领域、保险报销流程等。目前,国内外已经有不少成功应用案例,例如:四大会计师事务所的财税机器人、阿里云RPA等。

(图片来源:https://www.pwccn.com/zh/tax/tax-robot-solve-aug2017.pdf)

RPA,需谨慎前行

RPA技术可以用于结构化的基于规则的业务流程自动化,因此被认为是可以把人类从重复劳动中解放出来的技术,是一个完美的、高效的、低成本的数字化转型方案,被众多企业所青睐。

但是,RPA技术尽管颇具吸引力,目前的RPA产品仍存在明显的技术局限性,阻碍RPA项目发挥完全价值。 这些挑战包括:

  • 非数字流程输入的转换
  • 识别非结构化文档格式中目标数据字段的能力
  • 相对轻松地适应不断变化的规则或业务逻辑的能力
  • 从自动化流程的事务性数据中生成洞察的能力
  • 根据上下文解释和理解机器活动上游指令集的能力

RPA技术要跟AI技术结合,利用认知和智能识别技术来应对这些挑战,才能较好应用于数字化转型。

另一方面,仅从业务层去考虑利用RPA技术来实现数字化,容易忽略底层支撑系统的技术改造,并不利于整个IT环境的改造与企业的彻底数字化转型。2018年11月ThoughtWorks发布的第19期技术雷达,RPA第一次上榜,但是被置于“暂缓”环,正是这个原因。

(下载第19期技术雷达)

技术雷达建议:

RPA这种仅关注自动化业务流程而不解决底层软件系统或功能的方法的问题在于,引入额外的耦合会使底层系统更改起来更加麻烦。这也会让未来任何解决遗留IT环境的尝试都变得更加困难。 很少有系统能够忽视变化,因此RPA的进展需要与适当的遗留系统现代化战略相结合。

同时,也有德勤、安永等咨询专家表示,就许多企业客户的流程管理与系统的基础能力现状来看,仍存在着大量的基础建设工作有待开展。不用着急实现RPA,首要的还是把自身的流程管理和系统构建好。

因此,RPA生态还不够成熟,暂不能作为理想的数字化工具。RPA要怎么用还是要根据企业自身特点和具体需求,谨慎前行,不可冒进。


更多精彩洞见,请关注微信公众号:ThoughtWorks洞见

Share

7个你需要知道的结对礼仪

结对编程远远不是两个程序员坐在一起写代码那么简单。 — 鲁迅(没有说过)

结对编程

结对编程可能算是比测试驱动开发更具有争议的敏捷实践了,事实上,仅有很少的团队可以很好的实施它并从中受益,对于更多的团队来说,即使在践行敏捷的团队中,也常常会分为旗帜鲜明的两个阵营。提倡者往往会强调结对编程在“传递领域知识”,“减少潜在缺陷”,“降低信息孤岛的形成”等方面的作用;而反对者则认为结对编程在很多时候都是在浪费时间:开发者在实践中很多时候都难以聚焦,容易产生分歧,另外个人的产出往往也难以度量。

这篇文章不打算讨论结对编程对效率的影响,也不讨论要不要进行结对编程,当然也不会涉及以何种力度来执行结对。这里的假设是团队决定采用结对编程,但是对于如何实施存在一些疑虑;或者已经在采用结对编程的团队里,发现很多时候结对编程并没有很好的发挥作用,需要一些更有实践意义的指导。

结对编程远远不是两个开发者坐在一起写代码那么简单。作为一种科学且充满趣味性(才不是)的工程实践,事实上它是有一些基本原则的,团队里的开发者需要正确的实施这些原则,结对编程才有可能为团队带来实际的受益。

假设你找到了另一个程序员,并且已经准备好一起来编码实现一个具体的业务需求。在开始着手开始结对之前,你首先需要setup环境。

硬件设置

工欲善其事,必先利其器。首先你和你的peer需要一个大的外接显示器和有一个可以调节高度的桌子(当然也可以用纸箱子DIY一个低配版)。这一点往往被初学者忽视,而事实上它可以直接决定结对能不能作为一个可持续的团队工程实践。如果你的颈椎长时间处于不舒服的状态,你的注意力很快会退散,精神会变得难以集中,而一个处于病态的身体是无法支撑长时间的编码工作的。

在开始之前,请将屏幕调整到舒适的高度,以不仰头不低头为度(身高不一样的两个人可以通过调整椅子的高度达到基本一致)。此外还要注意看屏幕的角度,如果你需要抻着脖子才能看清楚屏幕,那么当时间稍长一点时,你的颈椎也会非常吃力。因此,如果条件允许的话,你和你的peer可以使用双屏来进行结对。

当然,还有一些常见的其他关于硬件准备的细节,比如:

  • VGA/HDMI转接头
  • 充足的电源
  • 键盘/鼠标转接头
  • 便签和笔

纸和笔永远是你(们)的好朋友,在实际动手写代码之前,请拿出纸笔来将要做的事情划分成更细粒度,可以验证的任务列表,贴在显示器的下边缘。最后,另外记得将手机调成震动模式,利人利己。

软件设置

硬件准备好之后就可以进行软件的配置了。软件问题远比硬件复杂,因为大部分开发者都有自己钟爱的工具集,小到curl/wget,大到Vim/Emacs,不要期望在这个问题上和peer达成一致,这是可遇而不可求,可望而不可即的。

根据我自己的经验而言,高级一些的IDE比如JetBrains出品的Intellij,WebStorm等都可以随意切换快捷键集合(keymap)。如果你和peer就快捷键的使用上无法达成一致,在轮到你输入代码的时候,你可以切换到自己熟悉的Keymap,反之亦然。

在Intellij/WebStorm里,你可以通过ctrl+来切换各种设置,比如选择3就可以切换不同的Keymap,然后在下一步的窗口中按照自己的喜好进行切换预设的Keymap。某项目的王晓峰(Vim党)和张哲(Emacs党)尤其擅长此技,他们两人结对时,可以做到在抢键盘的瞬间将keymap切换到自己的挚爱而对方无察觉的地步。

这种技法事实上仅仅对于结对双方都有很高超的键盘操作能力的前提下,也唯有这种场景下,双发可以互不妥协。对于另一种场景(可能在实际中更为常见),比如结对一方键盘技巧和操作效率低下,影响结对流畅程度的场景,则需要效率低下的一方自己摒弃陋习(使用鼠标而不是键盘),快速赶上。

和别人结对之前,你需要至少熟悉一个IDE/编辑器,比如通过纯键盘的操作完成

  • 按照名称查文件
  • 按照内容搜索
  • 定位到指定文件的指定行/指定函数
  • 选中变量,表达式,语句等
  • 可以快速执行测试(可以在命令行,也可以在IDE中)

熟常基本Shell技能和常用命令行工具的使用,可以完成诸如

  • 文件搜索
  • 网络访问
  • 正则表达式的应用
  • 查找替换文件中的内容

等操作,这样在结对时可以大大提高效率。这些都是稍加练习就可以掌握的技能,并没有多少技术含量在内,而且学会了可以收益很久。

当知识不对等时

好了,铺垫了这么多,终于到了正题部分。最理想的结对状态是,双方的技能水平相当,知识储备基本类似,可以非常流畅的进行交流,在结对过程中可以完全专注在需要解决的问题本身上,讨论时思想激烈碰撞,编码时键动如飞,不知日之将夕。这种场景下完全不需要任何技巧,随心所欲,自由发挥即可。与此对应的另一种场景是双方都没有任何储备,技能也无法胜任,这种情况我们需要在项目上完全避免。

这两种极端的情况之外,就是不对等的场景了,这也是现实中最为常见的case:很多时候,结对双方会有一个人比较有经验,而另一个人则在某方面需要catchup。比如一个老手带一个新手,或者一个擅长业务的开发和另一个该领域的新人结对等。

一般而言,需要双方有一个人来做主导,另一个人来观察,并在过程中交互,答疑解惑,共同完成任务。与传统的教与学不同的是:结对需要的是两个智慧头脑的碰撞,而不是单方面的灌输。因此观察者不是单方向的被动接受,主导者也并非完全讲述。事实上结对是一个会有激烈交互的过程。

主导者

对于主导者来说,千万不要太投入,而无视peer的感受。这种场景非常常见,我自己有时候也会不自觉的忽略掉peer,自顾自的写代码,很多时候把peer当成了小黄鸭。这时候你的peer会有强烈的挫败感,也很难跟上你的节奏,从而影响结对的效果。作为主导者,需要更耐心一些,不断的和自己的peer交互。

另一个极端是,主导者太热心的coach,而忽视了给新人实际锻炼的机会。这时候需要主导者给peer更多的实践机会:比如在带着新人编写了一个小的TDD循环(红绿重构)之后,可以抑制住自己接着写的冲动(我知道这个非常困难),然后将键盘交给你的peer,让他模仿你刚才的做法来完成下一个。

有时候,当你看到peer正在用一个不好的做法来完成任务时,你可以即使让他停下来,并通过问问题的方式来启发他:

  • 还有更好的做法吗?

如果peer仍然在迟疑的话,你可以进一步提示:

  • 你觉得XXX会不会更好?

一个实际的例子是,你们在写一段JS代码来迭代一个列表,你的peer正在用for循环来操作一个数组,而你可以提议使用Array.map。有些时候,你的peer会给你一些惊喜的回答!他的回答甚至比你预想中的更加出色,你也可以通过这种方式来向他学习。

观察者

另一方面,作为观察者而言,结对毋庸置疑是一种特别好的学习机会,你应该抓住一切可能的机会来向你的peer学习。包括快捷键的使用,命令行工具参数的应用,良好的编程习惯等等。保持你的专注力和好奇心,比如你看到peer神器的通过快捷键删除了花括号(block)中的所有代码,或者将curl的返回值以prettify过的样式打印到控制台,或者通过命令行merge了一个PR等等。

在实践的时候,可以采取Ping-Pong的方式来互换主导者和观察者的角色。比如,A写一个测试,B来写实现,A来重构,然后换B来写测试,A来实现,B来做重构等等。开始时,可能会由一个人来主导,随着合作越来越顺畅,你们可以提高交换的频次。

保持专注

在选定了要两人一起解决的问题之后,你们需要一起完成任务划分。这样可以确保你们可以永远关注在单一任务上,避免任务切换带来的损耗。

在做完一项任务后,用mark笔轻轻将其从纸上划掉(或者打钩)。千万不要小看这个小动作的威力,它既可以将你们的工作进度很好的表述出来,也可以在任何时候帮助你们回到正在做的事情上(特别是在吃完午饭之后),另外这个微小的具有仪式感的动作是对大脑的一个正向反馈,促进多巴胺的分泌(代码写的这么开心,还要什么女朋友?)。

很多时候,我们需要暂时搁置争议,保持前行。

无法统一的意见

如果你遇到了一个固执己见的同事,而不凑巧的是你也是一个难以被说服的人,那么如何处理那些无法避免的争论呢?特别是那些没有对错之分的技术问题。比如那种编程语言更适合Web开发,比如如何践行TDD(比如自顶向下的TDD和自底向上的TDD)等等。

有时候,我们会非常坚持自己觉得对的东西,觉得那就是真理。挑战这个真理的不是傻就是二,但是用不了多久,我们就会发现,换个角度好像也说得通,特别是在和其他人结对,并突然意识到以前的那个完全无法接受的做法似乎还是有几分道理的。

在我刚做完的一个前端项目中,做技术选型时我自然的选了更早项目中使用的scss module,而团队里的另一个同事则提议使用styled-component。我们谁也没有说服谁,最后写代码的时候就有两种风格。直到有一天,我在代码库里看到了用styled-component写的很漂亮的组件,我自己尝试着把相关的scss重写成styled-componet,结果发现确实比单独的scss文件要更好维护一些,而且也不影响既有的测试。

我突然意识到,我所坚持的只是一个假的“真理”,先前的坚持和做技术选型时的理由就变得很可笑:那只不过是为了使用自己熟悉的技术而编造的理由而已。保持open mind是一件知易行难的事情,希望大家在争辩时能念及这个小例子,可能会少一些无谓的争辩。

对于这种难以统一意见的场景,我建议可以将其搁置,先按照某一种提议进行,知道发现明显的,难以为继的缺陷为止。往往你们会发现一条比较折中的路,或者一个人被另一个人说服。

棘手的任务

即使很有经验的程序员也会遇到新的领域,或者在熟悉的领域遇到新的困难。有些情况下,作为结对的两个人都对要完成的主题没有头绪。这时候非要挤在一起反而会降低速度,无助于问题的解决。

一个好用的实践是,两人分头研究,并严格控制时间。比如Time box 30分钟。不过很可能在30分钟后,你们中至少有一个人已经对要怎么做有了头绪,如果30分钟还没有头绪,则可以求助团队其他成员。

比如我在最近项目上遇到了Kerberos认证的问题,我和peer都没有接触过,在经过20分钟的独立spike之后,我发现了一篇细节很丰富的,看起来很靠谱的技术博客,而我的peer则在内部github上找到了另一个团队的可以工作的代码(虽然代码质量不是很好)。我们最终决定copy+paste,然后做重构的方式继续前进。而那篇技术博客则是一个很好的课后学习的资料。

张弛有度

注意力是一种非常稀缺的资源,普通人很难全神贯注在某件事情上超过30分钟。一旦超过这个时间,大脑就开始偷懒,开小差。这时候一个短暂的break可以让大脑得到很好的休息。人类的大脑有一个非常有趣的特性,就是它的后台任务处理能力 — 而且后台处理能力好像远远强大于前台。你可能会在去冲咖啡的路上,突然灵光一闪,那个困扰你多时的问题有了思路,而此时此刻的你的大脑明明在想如何用咖啡机冲一份拿铁。

如果遇到一个难以理解的bug,或者在设置测试环境是遇到了困难,休息一下很可能帮助你找到解决问题的新角度。为了避免长时间纠缠在冥思苦想中,你和你的peer可以采取比如番茄工作法之类的时间管理工具:

  1. 从Todo列表中找出下一个任务
  2. 设置一个不可中断的25分钟,开始工作
  3. 时间到了之后,休息5分钟
  4. 重复2-3,4次之后休息15分钟

这里有一个在线工具可以直接使用 ,你也可以用手机的闹铃工具。

结对轮换

如果结对的对象长期固定的话,pair本身又会变成新的信息孤岛。比如A和B长期负责订单模块,而C和D则一直在写门店管理,那么毫无疑问,一段时间后,A和B就不知道C和D在做什么了,不论是领域知识还是技术实践,都很难得到有效的知识传递。当一个团队规模变成10+之后,这还可能演化成更为严重的项目问题。

因此需要定期或者不定期的轮转,比如一周轮换一到两次,A和C来写订单,B和D来写门店管理,这样可以保证领域知识,工程实践,工具的使用等等知识都很好的在团队内部共享。

在一些场景下,团队采取前后端分离的方式进行开发。前端和后端的技术栈选择大相径庭,每一端都有不同的约定和复杂的配置,这会对结对轮换的实施造成障碍,而且短期来看还会影响开发效率。如果团队再大一些,DevOps可能会独立出一个小组来负责,这将导致结对的轮换更加困难。

在实践中,我发现让不同角色的团队成员轮换结对所带来的好处(伴随着短期阵痛的)远胜过知识的隔离带来的坏处。团队中的前端开发如果花费一些时间和DevOps一起结对,他会对系统的整个架构更加清楚;而后端开发和DevOps结对则可能让他意识到代码中的潜在缺陷和解决方法(比如会话外置,缓存策略等)。

尊重

作为一个最小单位的团体活动,你常常要站在你的peer的角度来看问题。如果你不愿意和某一特性的人结对,那么首先不要让自己成为那样的人。比如你讨厌只闷头写代码,不理会peer有没有跟上的那种结对方式;又或者你不喜欢和用鼠标完成又低效又别扭操作的人一起写代码(我在和这样的人结对的时候,都需要费很大力气抑制自己,才不会从peer的手中把鼠标抢过来扔掉),那么首先让自己不是那样的人。

除此之外,尊重还体现在很多其他细节中。当你不得不中断结对而去做其他事情时,务必让你的peer知道。而且在离开之前,你应该表示歉意,不要凭空消失,然后若干分钟后又凭空出现,没有人喜欢和一个不靠谱的人工作。比如10点30分的水果时间到了,你看到有人拿着你喜欢吃的桃子从厨房方向走了回来。你可以示意peer暂停一会,然后去厨房拿点水果,记得给你的peer也带上一些。

另一方面,当你的peer回来之后,你需要及时和他catchup,告诉他你正在做什么,已经做到了哪一步等等。快速的将他带入到上下文中。

控制情绪

情绪是一件非常微妙的事情,它具有很强的传染性。当你们的工作任务收到各种blocker,被各种其他事情干扰而导致进度难以推进时,一定要注意自己情绪的控制。如果你的peer一直在旁边唉声叹气,或者抱怨连连,你会变得非常沮丧,并且很难集中精力在积极解决问题上。

你可以通过积极的寻求外部帮助,或者将blocker更快的可视化出来,让团队了解,并提供可能的帮助。

课后练习

和你的peer完成了充实而卓有成效的一天之后,你需要总结一下自己记录的知识点,这是一个绝佳的提升自己能力的方法。通过实战,发现自己的缺点,并通过近距离观察别人如何解决该问题,最终会以很深刻的印象记录下来,这时候针对性的查漏补缺是可以取得非常好的效果。

比如你已经习惯使用grep来做搜索,结果你的peer娴熟的awk技巧使你打开眼界,你可以在课后专门学习一下这个工具的各种选项,并尝试熟练应用。或者你们在代码库中探索到webpack的一些特殊配置,它可以良好工作,但是你不是很明白背后的原理,这些都可以放在结对结束之后自己消化。花一些额外时间来更新你的技能可以让你在第二天的结对中更加得心应手,也可以更好的融入到结对编程带来的快乐中。

这些结对的基本礼仪,都是一些微小的细节,做好了可以让和你一起工作的人比较舒服,也会帮助你自己建立一个更加高效的工作环境。

小结

在这篇文章中,我总结了一些有关结对编程的常见的问题和解决方法。在开始进行结对之前,首先需要确保硬件设施正确setup,这样可以保证大家可以在很轻松舒适的环境中工作。在软件设置上,保证效率的前提下,可以有不同的偏好设置。当能力不对等时,恰恰是结对编程最能发挥作用的场景,不但对于观察者来说是绝好的学习过程,对于主导者而言,也可以从coach过程中看到一些不同的东西。

在结对编程过程中,你们需要始终保持专注,可以通过任务拆分的方式来帮助一直关注在单一事项上。此外,应该有定期的休息,让紧张的情绪得到缓解。为了避免大尺度上的信息孤岛,团队还需要定期的进行Pair的轮换。

总而言之,通过这些方法的使用,可以有效的促进工作效率,促进个人成长为前提,并和可以形成很好的团队氛围。


更多精彩洞见,请关注微信公众号:ThoughtWorks洞见

Share