正如《敏捷宣言》所說:“我們一直在實踐中探尋更好的軟件開發方法,身體力行的同時也幫助他人”。至少從2005年開始,我們就一直在進行有關用戶故事拆分的實踐、指導和撰寫。Richard的故事拆分流程圖已被下載數十萬次。在與客戶合作的過程中,我們發現這個領域的工作模式非常相似。現在,隨著我們共同組建人性化工作公司(Humanizing Work company)
,我們將所有故事拆分的內容整合并更新到這本新的指南中。這里面包括了在過去的十年里我們發現的一些“更好的方法”,這些方法中有一半是在指導客戶在各種情況下拆分待辦事項時發現的。
本指南內容
- 為什么故事拆分很重要
-
什么樣的用戶故事才算是恰當的故事?
- 用戶故事格式
- 恰當的故事應遵循INVEST原則
- 用戶故事是垂直切片
-
故事拆分流程圖
- 步驟1:準備好要拆分的故事/特性
- 步驟2:套用拆分模式
- 步驟3:評估拆分效果
- Cynefin和故事拆分
- 練習故事拆分
-
垂直切片和規模化
- 是否應該讓100+的人去開發一個產品?
- 規模化垂直切片的基線
- 下一步
為什么故事拆分很重要
從優先級最高的、工作量較小的用戶故事開始開發,可以讓產品團隊持續輸出高價值的產物,并獲得高質量的反饋。許多團隊都在努力將較大的用戶故事和特性(feature)
拆分成恰當的小故事,但是他們沒有從業務的垂直切片來拆分,而是從整個技術架構的的角度,拆分出了很多看起來更像研發任務(Task)
或架構組件(Component)
的故事,最終導致他們未能體驗到小故事應有的價值或反饋。
幸運的是,故事拆分是一種可以在較短的時間內學會的技能。我們已經看到,團隊僅需幾個小時的練習和一些簡單的工具,就可以從掙扎中解脫出來,快速地拆分故事。稍后,我們將介紹如何組織這種練習。
什么樣的用戶故事才算是恰當的故事?
在討論拆分用戶故事之前,我們需要確保我們對什么樣的用戶故事才算是恰當的故事、以及可以將哪些內容拆分為故事有一個共同的理解。
首先,讓我們看下用戶故事的定義:用戶故事是從用戶的角度描述系統行為的變化。它描述的是用戶想通過系統做的事情,或者希望系統為他們做的事情,而這些事情現在的系統里還沒有。
順便說一下,請注意,用戶故事位于方案域(solution space)
而不是問題域(problem space)
。它不是一個人想在某個地方完成一個任務的描述(就像JTBD[Job to be Done,待完成的工作]一樣),而是一個人想要在你的系統中完成某件事情的描述。JTBD在問題域中可以與客戶產生很好的共鳴,而用戶故事可以很好地將客戶的共鳴轉化為對軟件系統的一系列改變,同時在整個交付過程中保持客戶的視角。
用戶故事格式
你可能經常會看到以如下特定格式書寫的用戶故事:
作為角色
我想要功能或行動
以實現價值或目標
或者有的是這樣:
為了價值或目標
作為角色
我想要功能或行動
該模板的優點在于它要求你回答用戶故事中的三個問題:
- 它是給誰(WHO)使用的?
- 他們想要做什么(WHAT),或者讓系統做什么,而這些功能現在都還沒有?
- 他們為什么(WHY)要這樣做?
不過,重要的不是模板,而是回答這三個問題。
實際上,我們很少會用完整的模板來寫故事。無論是在便簽紙的頂部還是在在線項目管理工具的標題字段里,一個寫著“WHAT”的簡短標題都會是比較好的選擇。“WHAT”由標題提供,而“WHO”通常由產品愿景或版本目標提供,它描述了核心目標客戶。如果故事是為該目標客戶準備的,我們就不重復撰寫了,我們只有在為非核心目標客戶撰寫用戶故事時,才把“WHO”加上。最后,我們將確保在在線工具的“詳細描述”或類似的字段中,或者在便簽紙上用較淺的字體寫明“WHY”。
因此,如果我們要做一個公共圖書館的網站,并且圖書館的讀者是我們的默認用戶,則我們不會這樣來書寫用戶故事:
作為圖書館的讀者,
我想按書名搜索一本書,
以便我能在搜索結果中毫無干擾地找到我想要的書。
我們會這樣來寫:
按書名精確查找
因為我知道我想要的具體書籍,所以我不希望在搜索結果中出現干擾
有時我們會遇到將單獨的研發任務或架構組件偽裝成用戶故事的情況。即使你使用了諸如“作為開發人員,我想要一份數據庫關系圖,以便我能了解數據庫的結構”這樣的神奇描述,它仍然只是一個開發任務。
恰當的故事應遵循INVEST原則
幾年前,極限編程先驅Bill Wake提出了一個很好的首字母縮略詞,用來表示一個恰當的用戶故事應具有的6個關鍵屬性:INVEST。讓我們來挨個看一下:
- I代表INDEPENDENT(獨立的)。這意味著一個恰當的故事能夠足夠的獨立,它可以不用考慮技術依賴就可以排定優先級。有時,這意味著需要暫時提供一些Mock數據或接口,以便可以獨立測試故事,讓你在項目的早期就能更快地獲得價值或降低風險。
- N代表NEGOTIABLE(可協商的)。一個恰當的故事會為做什么、如何做等細節留下協商的空間。當然,隨著協商的進行、更多細節的敲定,故事的可協商性就會降低。
-
V代表VALUABLE(有價值的)。每個故事都應該為用戶增加一些可見的價值增量。現階段這似乎是不可能的,因為你的Product Backlog里可能有大量的技術組件和基礎架構的任務,這些技術任務偽裝成了用戶故事,但這并不能直接為用戶增加價值。隨著你故事拆分技能的不斷成長,你能更好地找到能直接提供價值的、短小的功能切片。
(故事并不需要單獨提供足夠的價值來直接發布。你可能需要積累多個故事,才能從有價值轉變為可銷售。我喜歡最小可銷售特性(MMF,Minimum Marketable Features)作為故事的容器。) - E代表ESTIMABLE(可估算的)。一個恰當的故事應該定義到足以讓團隊能夠估算它的工作量,這個工作量一般是相對于一個基準故事所做的相對估算。
- S代表SMALL(短小的)。經驗告訴我們,對于一個已排序的Product Backlog,你應該能夠將優先級最高的6到10個故事排入下一個Sprint中。這樣做既能經常獲得反饋和管理風險,同時也不需要管理太多的故事。不過這個故事數量只是一個建議,它會隨著Sprint長度、團隊規模、團隊速率等因素按比例縮放。
- T代表TESTABLE(可測試的)。我們應該有辦法知道我們已經完成了某個故事。它不能只是一個模糊的期望,而需要是系統行為的具體變化。
當然,這些屬性之間存在著一定的互斥關系。比如說,隨著故事的規模變小,使其變得獨立且有價值的難度就會變大;隨著故事的可協商性變大,其可估算和可測試的難度就會變大。
不過幸運的是,不同的屬性在不同的時間起主要作用。例如在進入Sprint計劃后,更重要的是故事要短小、可估算和可測試。這時我們仍然需要故事有一定的獨立性、可協商性和有價值,但這些屬性這時已經變得不那么重要了。而在Product Backlog中的故事,情況恰恰相反。
用戶故事是垂直切片
在提到恰當的故事時,你經常會聽到垂直切片(vertical slice)
這個詞。這是恰當的故事在軟件架構方面的要求。
垂直切片是指“一個能給系統行為帶來變化的有價值的工作項,它可能要觸及多個架構層級(architectural layers)
來實現這個變化”。當你把這個切片(slice)
稱為“完成”時,該系統對于用戶而言顯然更有價值。
水平切片(horizontal slice)
與垂直切片剛好相反,它是指“對一個組件(component)
或架構層級(architectural layer)
進行更改的工作項,它需要結合其他組件或架構層級的改變,才能對用戶交付可感知的價值”。
我們來看一個非常簡單的系統架構,這里有UI層、業務邏輯層和持久層。你的系統可能比這更復雜,但它可能至少包含這三層。
要想獲得INVEST的大部分屬性,故事必然會涉及這3個架構層級。如果不進行某些UI的改變、邏輯的改變、持久存儲的改變,我們可能就無法交付價值。因此,故事就是系統的一個垂直切片。
有時候,這些垂直切片非常寬。當我們進行故事拆分時,我們將討論如何在較寬的垂直切片中找到較薄的垂直切片。但是到目前為止,我們只需要知道故事應該在必要時跨越架構層級來提供價值就足夠了。
許多剛組建的敏捷團隊會嘗試按照架構層級來拆分故事:一個故事用來實現UI,另一個故事用于更新數據庫等等。雖然這個故事可能也很小,但在獨立性和價值交付上是失敗的。
當團隊以垂直切片的方式拆分時,他們將會得到如下收益:
- 使Backlog的價值明確
- 進行更多關于價值的對話
- 有助于避免意外地建立低價值的變更
- 更快獲得價值
- 更早獲得更高質量的反饋
- 更容易看到約束和待辦,并能做出相應的響應
- 交付價值時變得更加可預測(因為可工作的軟件是進度的首要度量標準)
我們還可以繼續說下去,但這些應該已經可以給你一些啟發了。當我們一起坐下來,寫下我們在成功的敏捷團隊中看到的各種習慣,以及各個習慣之間的關系時,我們發現垂直切片幾乎與所有其他習慣有關,或至少與部分習慣有關。
看看Product Backlog中的故事,有些是你最近完成的,有些是將來要做的。根據INVEST標準評估每一個故事,找出垂直切片和非垂直切片的故事。然后,看看你是否可以改進這些故事。
故事拆分流程圖
為了方便我們更好地指導團隊,Richard創建了一個故事拆分流程圖,該流程圖介紹了我們在幫助團隊拆分故事時要問的問題。
讓我們分別看一下圖中的三個步驟:
步驟1:準備好要拆分的故事/特性
首先要確保你要拆分的故事/特性滿足INVEST標準(短小的(Small)
除外)。大多數情況下,有價值的(Valuable)
是問題所在。當人們把他們認為是“不可拆分”的故事帶給我們時,它們其實是偽裝成故事的開發任務或架構組件。如果你不從增加價值的角度入手,就無法將其拆分并獲得價值增量。在這種情況下,下一步就是將非故事(non-story)
與其他水平切片結合起來,這樣,它們才可以共同代表一個價值增量。
接下來,是不是切片太大了?如果是的話,就可以開始拆分了。
步驟2:套用拆分模式
模式1:按工作流程步驟拆分
這是我的客戶在創建一個內容管理系統的故事:
作為內容管理員,我可以將新聞發布到公司網站。
聽起來故事并不大——直到我們深入研究了發布新聞的工作流程。結果發現,僅僅是把一個幾句話的新聞發布到公司網站上,就需要編輯和法律部門的批準,以及在預發布網站上做發布前的最終審核。像這樣的6-10個故事不可能在一次迭代中完成。
在這樣的工作流程中,最大的價值往往來自于開頭和結尾。中間的步驟會增加增量價值,但并不獨立。所以先構建簡單的端到端案例,然后再添加中間步驟和特殊案例,效果會很好。
新的故事包括:
…我可以直接將新聞發布到公司網站上。
…我可以在發布新聞前做一下編輯審核。
…我可以在發布新聞前做一下法律審核。
…我可以在預發布網站上查看新聞。
…我可以將一篇新聞報道從預發布網站發布到正式網站。
但有時,整個工作流程都很重要,你不能只從開頭和結尾開始。在這些情況下,尋找一個貫穿整個工作流的薄薄的切片。也許它支持最常見的情況;也許你可以硬編碼或以其他方式簡化工作流中最容易理解的部分,然后你才能探索更復雜的部分。
無論哪種方式,最明顯的拆分——從頭到尾按功能模塊一步一步執行——都是錯誤的方式。查看我的80/20產品所有權課程的這段摘錄,了解更多關于為什么這種拆分是錯誤的,以及如何使用其他兩種方法。
模式2:按不同的業務規則拆分
這個故事中隱藏著一些同樣復雜的故事,這些故事使用不同的業務規則來完成同一件事:
作為一個用戶,我可以使用靈活的日期規則搜索航班。
深入研究“靈活的日期規則”,會發現有好幾種不同的業務規則,每個規則都可以單獨成為一個恰當的故事:
“日期X和日期Y之間的N天”。
“12月的某個周末”。
“日期Z的前后N天”。
模式3:按主要工作拆分
有時,一個故事可以拆分為幾個部分,其中大部分的精力會去實現第一個部分。例如這個信用卡支付的故事:
作為用戶,我可以用VISA、MasterCard、Diners Club或American Express支付機票費用。
這個故事可以再拆分為四個故事,每種信用卡一個故事。但是,在處理第一個故事的時候就要建立起信用卡交易的基礎架構;增加更多的信用卡類型時這方面的工作就會相對較小了。我們可以估算第一個故事的規模大于其他三個故事,但是如果產品負責人后來改變了優先級,我們就必須記得要改變我們的估算。相反,我們可以如下述所示,推遲決定哪種卡的類型先被實現:
…我可以使用一種信用卡類型(VISA,MC,DC,AMEX)付款。
…我可以使用所有四種信用卡類型(VISA,MC,DC,AMEX)付款(前提是已經實施了一種信用卡類型)。
這兩個新的故事仍然不是獨立的,但依賴性會比為每一種信用卡類型編寫一個故事要清晰得多。
模式4:按簡單/復雜拆分
當你在計劃會上討論一個故事時,故事似乎越來越大("X怎么辦?"、"你考慮過Y嗎?"),這時候你應該停下來,詢問下大家:“最簡單的版本是什么?”把這個簡單的版本寫成用戶故事。你可能必須在現場定義一些驗收標準以保持簡單。然后,把所有的變化和復雜性拆分成其它的故事。比如這個故事:
作為用戶,我可以搜索兩個目的地之間的航班。
通過像下面的方式拆分變化來保持簡單:
...指定最大中轉次數。
...包括附近的機場。
...使用靈活的日期篩選規則。
...等等。
模式5:按不同類型的數據拆分
故事中的復雜性可能來自于處理數據的變化。例如,我當前正在開發的系統需要對運輸服務提供商所服務的地理區域進行建模。僅僅是處理復雜的服務區域的地理學知識,我們就可能燒掉整個項目的預算。當我講完這個故事后:
作為用戶,我可以根據行程的始發地和目的地來搜索運輸服務提供商。
與產品負責人討論后發現,雖然我們不需要成熟的GIS,但對地理環境進行建模仍然非常復雜。我們停下來反思:“什么是‘足夠好’的地理建模方案,以便我們現在就可以構建其他高價值的功能?”我們選擇了:
作為用戶,我可以按行程的始發地(市)和目的地(市)搜索運輸服務提供商。
這在一段時間內是沒問題的,直到我們收集了更多的數據,發現有些服務提供商只服務于某些縣城甚至鄉鎮。于是一個新的故事出現了:
作為用戶,我可以按行程的始發地(如市、縣、鄉/鎮、街道)和目的地(如市、縣、鄉/鎮、街道)搜索運輸服務提供商。
在查看新的服務提供商數據時,我們還發現,有些服務提供商會支持出發地為單一城市,但終點為周邊任意多個城市的行程。這就引出了下面這個故事:
服務提供商可以為行程的始發地和目的地提供不同的地理區域。
這三個故事都是從原來的地理故事中拆分出來的。這里的區別是,我們在構建最簡單的版本后,及時添加了新的故事。但有些情況下,你在項目前期就能知道數據的變化。典型的例子是系統的本地化:
作為內容管理員,我可以用以下語言創建新聞:
英語
日語
阿拉伯語
等等……
模式6:按不同界面拆分
有時,故事的復雜性在于用戶界面而非功能。在這種情況下,故事的拆分要從最簡單的UI開始,然后再構建更易用或更華麗的UI。當然,這些并不是獨立的——如果你先做第二個故事的話,第二個故事實際上就是初始故事——但它仍然可以是一種有用的故事拆分方式。
作為用戶,我可以搜索兩個目的地之間的航班。
...使用簡單的日期輸入。
...帶有精美的日歷界面。
模式7:延遲性能優化
有時,一個故事的基礎功能實現可能并不難,但是需要花很多時間在性能的優化上。如果你可以從較差性能的基礎功能中學到很多知識,并且它對用戶有一定的價值(比如沒有這個功能用戶就無法完成故事中的動作),在這種情況下,你可以把故事拆分為“使其能用”和“使其好用”:
作為用戶,我可以搜索兩個目的地之間的航班。
...(只要功能完成就好,加載時顯示一個“搜索中……”的動畫。)
...(加載時間限制在5秒以內)。
模式8:按不同的業務規則拆分
用戶故事中的“管理”會涵蓋故事的多個操作。這就為故事的拆分提供了一種自然的方式。比如說:
作為用戶,我可以管理我的帳戶。
...我可以注冊一個賬戶。
...我可以編輯我的賬戶設置。
...我可以注銷我的賬戶。
模式9:拆分出一個探針
一個故事之所以被大家認為工作量很大,可能并不是因為它的業務有多復雜,也有可能是因為開發團隊對其技術實現不太了解。在這種情況下,無論你怎么澄清故事的業務部分,都無法將其拆分。先拆分一個有時間盒限制的探針故事,以便解決開發過程中的不確定性,然后我們可以決定是直接實現,還是使用上述的8種模式來拆分它。假如我們不知道下面的故事如何實現:
作為用戶,我可以用信用卡付款。
那么,就把它分解成:
調研信用卡付款。
實施信用卡付款。
在“調研”故事中,驗收標準應該是你需要回答的問題。調研要點到為止,能回答問題即可,做調研很容易走火入魔。
探針拆分模式放在最后講解,是因為它應該是你最后的選擇。你目前已知的知識可能已經可以用來構建一些功能了,按照你已知的知識直接開始開發吧,隨著項目的推進,這些問題很有可能會不攻自破。因此,在求助于探針模式之前,請盡一切努力使用前面八個模式之一。
元模式:找出復雜性并減少變化
在我們指導團隊更有效地拆分故事的過程中,我們發現了這些模式共有的元模式:關注復雜性,并通過它減少變化。使用元模式的方法如下:
- 找出核心復雜性。最有可能讓你感到驚訝或者出現問題的部分是什么?這個問題的答案往往取決于人們的個人喜好或行為習慣。有時,這是一個需要重新整合或有外部依賴的部分。
- 識別出其中的變化。變化比較多的東西是什么?業務規則、用戶類型、接口、數據變化、實體等。
- 把所有的變化減少到一個。在復雜的部分中找到一個單一的、完整的切片。它可能是一個單獨的場景,也可能是通過單個業務規則變化出的一系列場景。
大多數故事拆分模式只是確定變化的來源并將其減少到一個的例子。
這種方法對于一個新事物的第一個切片特別好用,因為它直奔核心復雜性,并避免了任何可能會讓工作變得更大的內容。
步驟3:評估拆分效果
你可能會發現,有時你可以使用好幾種模式來拆分同一個故事。那我們應該選擇哪種拆分方式呢?我一般通過以下兩個經驗法則來判斷:
- 選擇能讓你降低優先級或扔掉一個故事的拆分方式。80/20法則表明,用戶故事的大部分價值來自于一小部分功能。當一種拆分方式揭示了低價值的功能,而另一種拆分方式沒有揭示,這說明后一個拆分方式在每個小故事里面都隱藏著浪費。選擇能讓你扔掉低價值功能的拆分方式。
- 選擇能讓你得到更多同等大小的小故事的拆分方式。把一個8點的故事變成四個2點的故事的拆分方式比產生一個5點和一個3點的拆分方式更有用,因為它能讓產品負責人有更多的自由來分別對這些拆分后的故事進行優先級排序。
可能需要多次嘗試才能找到最適合你的故事拆分模式——你可能需要不斷地試驗才能找到正確的模式。
Cynefin和故事拆分
Dave Snowden的Cynefin模型是一種根據問題的復雜程度來思考問題最優策略的有用方法。我們發現Cynefin非常有用,幾乎所有的工作坊都使用了它,有的是作為先決條件,有的是作為工作坊本身。如果你還不熟悉這個模型,請查看我們的概述。
Cynefin每個領域的故事拆分看起來都不一樣。下面是具體拆分方法:
- 簡單(Simple) - 只需構建即可。如果故事太大,找出所有的故事,先做最有價值的即可。
- 繁雜(Complicated) - 找出所有的故事,并首先做最有價值和/或最具風險的故事。
- 復雜(Complex) - 不要試圖找出所有的故事。找出一兩個能提供一些價值的,并能教給你一些關于問題和解決方案的知識,構建這些故事,然后利用你所學到的知識去尋找其余的故事。
- 混亂(Chaotic) - 先把手頭緊急的事情解決吧,現在拆分故事可能并不重要。
- 失序(Disordered) - 拆分之前先弄清楚你在哪個領域,以免采取錯誤的方法。
最重要的細微差別在復雜域(complex domain)
,從這里開始工作會讓你快速了解工作的內容。在這種情況下,試圖找到構成原始大故事的所有小故事是沒有意義的。找到一兩個可以立即開始學習的故事會更有效率。
有些人不喜歡這種方法,他希望把所有的故事都列舉出來,并確定大小,以便能夠把故事記錄到Backlog并估算時間。但如果你真的是處于復雜域(complex domain)
,這樣做只會給你帶來可預測性的錯覺——實際的故事很可能會隨著工作的推進而發生變化。最好對復雜工作中固有的不確定性保持透明。
練習故事拆分
就像我們之前說過的那樣,在較薄的垂直切片中工作是敏捷軟件開發的關鍵習慣。很多人都在努力尋找垂直切片,但其實這是一項非常容易習得的技能。團隊只需2.5-3個小時的練習,就可以從苦苦掙扎到快速地識別出其領域中的特性和大故事的切片。當然,練習的質量很重要。下面是我推薦的做法:
在1-2周的時間內安排兩到三次1小時的練習課程。邀請整個團隊或至少能很好地結合業務和技術觀點的組合。
為了準備第一次練習,看看你最近幾個月的Backlog。選擇幾個你曾難以拆分但現在已經成功實現的故事或特性。
用Cynefin的術語來說,這些已完成的特性現在是有序的(繁雜的或簡單的),因為出現了足夠的秩序來實現它們。未來的工作很可能是復雜和無序的。但現在這并不重要。在第一個練習環節中,你的目標是識別出在你的領域中使特性變大的原因。追溯已完成的工作是練習有效性的關鍵。
在第一個練習環節中,拿著你選擇的一個特性或故事,對照故事拆分流程圖中的問題一起過一遍。假設這個特性尚未實現,也可以檢測下你自己現在對它有多了解。
如果你使用其中一種模式找到了一個好的拆分方式,請不要停下來。繼續瀏覽其他模式,并嘗試找到另一種可能的拆分方式。
如果一次拆分不能產生足夠小的故事,請嘗試對拆分后的故事繼續拆分。
大約50分鐘后停下來。對于你準備的特性或故事,使用流程圖上的每種拆分模式后,請檢查下各模式下拆分后的小故事。
如果你在這個環節沒有找到合適的拆分方式,花點時間讓大家一起來頭腦風暴一下。當這些拆分模式應用到你的特性或故事時,大家是否已經達成了共識。
如果在第一次練習結束時,拆分已完成的特性似乎很容易,那么你就可以嘗試對后續的工作進行拆分了。如果不是,需要再重復下第一次的練習。在下次練習之前,找幾個合適的特性,重復上述過程。
這樣做的難點在于,它是一個“練習”。很多人只愿意通過正式培訓或在工作中邊干邊學來提升能力,他們往往不愿意花時間用來做一些練習,尤其是練習拆分已經完成的特性,因為這個活動不會有新的工作產出——比如說,它不會完善即將要做的Backlog。但這方面的練習可以快速提升團隊故事拆分的能力。千萬不要跳過它。
經過2到3個這樣的練習,你應該達到這樣的程度,即對于工作中的每個特性,每個人都能快速找出適當的拆分模式,并迅速拆分出適合迭代的故事。
垂直切片和規模化
當你有100+人在同一個產品上工作時,可以使用垂直切片嗎?
當你有多個敏捷團隊開發同一個產品時,可以采用這兩種組織方式:特性團隊(feature team)
或組件團隊(component team)
。
特性團隊的組織方式是,每個團隊都有足夠多的跨功能成員,以便可以在部分或全部產品上提供完整的價值切片(即“垂直切片”)。根據產品的規模,特性團隊可能會專注于產品的某些部分,有效地創建子產品,或者他們可能會完成整個產品中最重要的部分。
組件團隊的組織方式是,每個團隊專注于一個特定的組件、架構層次或技術方向。要想交付一個完整的價值片段,需要協調多個團隊的工作。
讓我們看一個大型商業軟件的具體例子:淘寶。(注:我不知道淘寶的實際組織方式或技術是什么樣的,但是這并不重要,我只是需要一個大家都熟悉的軟件產品來進行推理)。
淘寶有一個APP。它通過某種通訊協議與某種語言編寫的后端進行通訊。后端有一些流程處理的程序,比如搜索商品、生成訂單、支付訂單以及跟蹤物流信息等。
如果采用組件團隊結構,你會有APP團隊,例如,他們可以對APP界面進行修改,但他們很可能依賴于后端團隊對其系統部分進行相應的修改。各個團隊之間的協調將集中在確保他們的工作同步推進,以最終能夠提供價值。
在特性團隊的結構下,你可能會有一個團隊或一組團隊負責商品的搜索模塊,另一個負責訂單模塊,第三個負責支付模塊等。這些團隊中的每一個都擁有APP和后端技能。在這種情況下,各團隊之間的協調將集中于確保整個產品的設計和架構一致。
相同的產品,團隊以兩種不同的組織方式,將得到兩套不同的結果和協調方案。
所以,有關“垂直切片是否與規模相關”這個問題,答案取決于你的組織方式。組件團隊是不以垂直切片的方式工作的。但組件團隊可以圍繞更大的垂直切片(如MMF)協調工作,但在具體的工作項層面,組件團隊無法完成垂直切片所需的全部功能。構建組件團隊無法獨立交付價值,但這種組織方式可以針對其他方面進行優化(通常是更容易進行架構調整或更高的研發人員利用率)。
特性團隊與組建團隊的收益剛好相反。他們旨在獨立提供垂直切片,以便更快速的交付價值、獲取反饋,代價是需要明確地協調架構一致性。
特性團隊與組件團隊是2種主要的組織方法。當然,有些組織可能有細微的差別或混合,并且會隨著時間的推移而變化。我以前寫過這方面的文章,特別是在改造一個擁有大型遺留產品的組織的情況下。
是否應該讓100+的人去開發一個產品?
現在,我們心中還有一個更重要的問題,那就是:不管我們是否可以在大型產品/項目中使用垂直切片(正如我們所展示的那樣,如果我們以特性團隊來組織,我們是可以的),這么多人一擁而上,是否真的有效?
為單個產品/項目添加人員或團隊,都會帶來一些生產力和協調的開銷:項目如果只有一個人,那么這個人的生產力幾乎是100%;再增加一個人的話,我們不會得到2倍的生產力,可能只會得到1.8倍的生產力(平均每個人提供90%的生產力),因為這兩個人需要花時間用來進行工作的協調(每個人消耗10%的生產力用于協調);增加到3個人的時候,生產力會得到再次提升,這次有可能會提高到2.4倍(平均每個人提供80%的生產力),相應的,協調的開銷也會隨著上升(每個人消耗20%的生產力用于協調)。而且,這種協調的開銷會隨著人與人之間聯系的數量呈指數增長。
通過組建小規模團隊,使每個人只需要與少數人協調工作細節,并嘗試在團隊之間進行分工,盡量減少依賴性,從而能在一定程度上減少協調的開銷。但工作越復雜,依賴關系就越難以預測,團隊之間需要協調的可能性就越大。
因此,在某些時候,在項目/產品中再增加一個人或一個團隊,不僅不能提升生產力,還會給整個系統帶來協調開銷的增加,最終導致整體生產力的下降。
團隊規模的臨界點到底落在哪里,在很大程度上取決于項目/產品的具體情況。但拋物線的形狀至少應該讓我們對大型團隊產生懷疑,并慎重考慮人員或團隊的增加。
對于復雜的工作來說尤其如此,因為很可能需要我們在一個項目/產品上工作一段時間后才能了解真正的問題和解決方案。而在軟件開發過程中,復雜性似乎與價值高度相關。越是高價值的特性,項目/產品前期越可能發現不了。如果是一個新項目/產品,我們在工作中很有可能會學到一些新知識,從而改善我們交付的價值。
規模化垂直切片的基線
是的,你可以在每個細節層面和各種規模的工作上進行垂直切片,這樣做很有價值。但在大規模的交付中,你需要特殊定的方式進行組織:以特性團隊的方式,或者以某種強調功能交付的混合方式。而且,當你使用它時,需要考慮一下,你的需求是否真的需要如此大的規模。
下一步
我很樂意幫助你更好地掌握故事拆分和產品負責人的其他關鍵技能。如果你在拆分的過程中有任何問題,請留言告訴我。