---
# System prepended metadata

title: DevOps Handbook - Chapter 16. 啟動回饋機制，安全地部署程式碼

---

# DevOps Handbook - Chapter 16. 啟動回饋機制，安全地部署程式碼

先來個小故事畫完整張餅
### Right Media遇到的挑戰
業務需要對幾分鐘內對市場做出反應(快速改code->頻繁部署到production)
- 團隊內同時擁有開發、測試、部署人員
    - 自給自足
    - 減少團隊間溝通內耗、互相等待

但部署工作缺乏快速、頻繁且容易取得的feedback (log monitoring / metrics dashboard)，導致這次到底改對了沒有無法知道，都要等使用者回報

#### Solution
- 在code裡埋入telemetry data，並建立方便的監控機制，在使用者發現之前就能先主動知道並再次修復
    - 部署工作快速、頻繁、容易得到feedback(不要trigger部署後等個半天一天才知道還是弄爛了，造成心中恐懼)
- 減少部署規模(小批量發生問題機率低，發生了也容易抓到)

#### 工作文化&員工心理的問題
- 每個人只要經過幾次主動且成功的部署，大家漸漸都能都敢於部署並對其有信心
    - 知道部署能很快取得回饋，更主動去發現問題並修復
        - Flow健康穩定快速

有了CI -> 要有metrics -> 塑造文化 -> 健康開發團隊及環境


----

### 怎麼讓大家不害怕部署
#### 為什麼害怕？
假設部署全自動化、部署過程失敗會通知、也有自動化測試知道功能正確

- 貌似很可靠，但我還是不知道上了production後是否就馬上噴掉
    - 例如 Config有錯導致啟動時就毀滅
    - 毀滅後導致更多的dependency也毀滅
- 然後沒有人知道，最後User該該叫，加班

#### 怎麼避免？
1.  在 code裡<span style="color:red">**埋入 telemetry data (log、metrics)**</span>
2.  建立監控系統，<span style="color:red">**盡量即時地**</span>取得這些 telemetry
3.  使 telemetry data在監控系統介面上<span style="color:red">**容易看、容易懂**</span>
4.  設置條件讓監控系統發現不對勁時<span style="color:red">**自己叫**</span>

#### 發現佈署失敗，然後呢？
- Feature flag (在不重新部署的情況下快速關閉錯誤功能)
- Fix forward (趕快再修再上，有自動化測試不要怕，部署完馬上再從監控系統看)
- Roll back
    - 藍綠部署
    - 金絲雀發佈

因此要建立的文化/ Practice是，當任何人 deploy to production時，都能**主動監控telemetry data**，直到確定他至少順利運行，久了大家就敢做敢當了

> DevOps一條準則：優化平均故障恢復時間，而非企圖避免故障
----

### 部署不是問題了，但 Production Site永遠都會有 bug
#### 誰來修？
以往都交給營運工程師 (SEG工程師、維護團隊...各企業有自己的稱呼)
- 值班辛苦
- 非初始開發者，無共同context，無頻繁合作，可能不了解設計初衷
- 以解掉 case為優先的心態下，容易使用到不好的workaround，導致code越來越髒，難以維護 (或是反過來，開發人員code寫不好導致營運工程師也無力重構，惡性循環下這code已死)

#### 那轉回給開發團隊修呢？
- 不夠致命的問題永遠低於新功能開發
- 營運人員繼續面對錯誤及混亂
- 久而久之造成對立 (我自己認為的)

#### 爭什麼摻在一起做撒尿牛丸吧
整條value chain的人一同承擔
- 從上到下建立「Production出問題了我也有義務去關心」的文化
- 有了文化，開發團隊會直接參與，找到 root cause，提供最佳解的建議
- 營運團隊提供實際營運經驗，並同時透過開發人員更了解 code
- 開發團隊未來做事時也更加為營運著想 (E.g. 寫出更好的 log、文件)
- 甚至Manager、Architect也加入值班 (難)
- 良性循環，大家都變更強也更能為整體思考了

> #### 除此之外...
> 同時也讓開發人員意識到「完成」的定義，不是code在本機或QA測過沒問題，部署也沒問題就是完成了。能在 production site上**可靠且無須額外介入**運行一段時間(例如兩週)，才是真的沒問題
> #### 怎麼知道運行沒問題？ 
> 通常無法知道， user有觸發到不會告訴你，用了有錯也不一定會告訴你
所以埋 telemetry data吧！讓你知道新功能有人用了，然後完成任務了，沒有 error產生
>

> 案例分享：Luwak DRI (有人已經分享過了嗎XD?)
----
### 哦我好像有點了解營運人員的痛苦了，我還可以做什麼

    
**開發人員應更加注重非功能層面的產出及品質**
- 文件完善了嗎？
- 從無到有運行程式，手動的部分多嗎？通常要做多久？
- 充滿眉角和潛規則，各種不直覺，一定要觀落陰或求救才能讓程式啟動嗎？

#### 平常我就專心在寫程式，怎麼知道哪些地方其實我做得不夠好？

- 使用者訪談 - 詢問拿你寫好的程式繼續做他們工作的人，這樣的產出是否讓他們感到舒適安心
    - QA
        - 能方便設置 proxy、調整log level嗎？
        - 系統足夠彈性應付測試需求嗎？
    - 營運團隊
        - 系統設計不夠彈性導致部署困難(例如不同site需要有不同配置)
- 親身體驗
    - 一個新人單純照著文件來做，程式能成功運行嗎？
    - 如果我是 QA，我有辦法測這東西嗎？

> #### 建立同理心
> 如果每個人都能在處理自己工作時，同時為整條 value stream的其他成員著想，開發者跳脫「我只要寫好程式」的框架、QA跳脫「我只負責測試開單」的框架，透過訪談和親身體驗，知道合作對象要什麼，事先滿足，便能減少退票，加快速度，團隊更流暢。
> 
> 這是 DevOps的重要 mindset
> 

### 有道理喔，還能夠更有感嗎
#### 有啊，直接跳下來自己幹營運
1. 開發階段即考量可營運性
- Telemetry data覆蓋率，是否能主動觀測到錯誤，錯誤發生時是否能幫助恢復？
- 部署方式是否可被預測(手動含量極少)且穩定？
- 系統架構之設計是否低耦合，能支援未來可預期的變更？
- 是否儲存敏感性資料？
- 其他監管合規需求(PCIDSS、GDPR...)

2. 建立服務發佈規範(往往是營運團隊豐富經驗的天地精華，全組織的集體智慧)，通過才能上線
- 上述的可營運性
- 缺陷數及嚴重性
- Warning數量
- 開發習慣是否良好

> 許多不合規範都能在 CI階段就提前擋下，E.g. Style check、Fortify...

3. 開發人員自行管理 production，營運團隊扮演顧問角色
- 新服務，開發團隊負責自行營運一段時間，足夠穩定才交給營運團隊
- 現有服務，在變得非常脆弱常常爆炸時，自己拿回來擦屁股 (Sercie handback mechanism)


一樣，就是同理心，一旦自己有機會雷到自己，就會格外小心

> Google Practice
> - 開發部門平常衝feature
> - 正式上線前要進行上線就緒審核 (LRR，Launch Readiness Review)
> - 上線開發人員必須自行管理 production半年以上
> - 半年期限到要交接前，必須通過交接就緒審核 (HRR，Hand-off Readiness Review)
> (HRR，Hand-off Readiness Review)
> - 通過LRR或HRR的服務就會被分配到SRE，幫助了解實現需求
> - 若上線後的服務回歸成極度不穩定狀態，丟回給開發團隊
> >- LRR/HRR的審核清單隨著全公司任何服務的上線而越發豐富，這就是集體智慧、建立組織記憶，這是企業的重要財富
> >- 開發人員同時具備營運人員的視角，上下游間更有同理心

Google發現越早找到 SRE諮詢並在開發階段就重視審核的團隊，通常越快通過HRR
同理，開發團隊也應在盡早讓 QA加入，讓測試工作更加順暢

### Conclusion - 收集 Feedback以改善「服務」，不只是功能
- 「服務」的對象除了 user，還有下游工作同伴
    - 安全部署
    - 重視非功能性需求
    - 共享責任
    - 建立同理心

### <span style="color:red">沒有我完全不需要關心的事</span>