ref: https://www.forbes.com/sites/greatspeculations/2021/10/12/gitlab-another-overpriced-tech-company/?sh=5480a1235286
不知道大家有沒有注意到 GitLab 於 10/14/2021 正式於美國 IPO 上市,代號 GTLB。
本篇文章的作者從別的角度來解釋為什麼他認為 GitLab 又是一個估值被高估的科技公司。
估值來看,作者認為每股 $55-60 的 Gitlab 價格實在是過高了,實際上大概只有 $5 左右,而接下來的文章內容都在闡述為什麼作者會有這樣的想法
# 盈利模型不可靠
Gitlab 的營收模組與很多軟體公司都一樣,採取免費版本讓你用,進階版本收你錢的模式。直到 06/2021, GitLab 全球大概有三千萬的使用者,但是真正付費的使用者數量只有一萬五千多。
簡單來說,GitLab 的營收轉化能力不到 1%,低於同業營收模型的 2%~5% 轉化率,而且大部分付費的使用者都採取價格較低,利潤較低的方案,以 GitLab 的資料來看,大概有 3632 的基本客戶每年提供 $5000 美元的收入,
只有大概 383 位用戶每年提供超過 10 萬美元的收入。
從淨收入來看, 2021 相對 2020 的年成長率高達 87 %,所以是有更多使用者願意付費,但是其核心業務盈利(Core Earnings)則從 -1.25 億美元下降到 -2.13 億美元,這意味核心業務的賺錢能力是下降的。
GitLab 的營收策略顯然更像是專注於增長收入能力而放棄於整體營收,其他數字包含 (2020 -> 2021)
1. 稅後淨營業利潤(NOPAT)從 -158% 提升到 -141 %,整體小成長但是賠錢的。
2. 投資資本回報率(ROIC)從 -41% 下降到 -76%
3. 現金流從 -1.49 億美金下降到 -2.29 億美金
作者認為雖然整體收入提升,但是對於股東來說整體價值是下降的。
整體文章非常長,從非常多角度去探討,對於這個議題有興趣的可以參考看看
不知道大家有沒有注意到 GitLab 於 10/14/2021 正式於美國 IPO 上市,代號 GTLB。
本篇文章的作者從別的角度來解釋為什麼他認為 GitLab 又是一個估值被高估的科技公司。
估值來看,作者認為每股 $55-60 的 Gitlab 價格實在是過高了,實際上大概只有 $5 左右,而接下來的文章內容都在闡述為什麼作者會有這樣的想法
# 盈利模型不可靠
Gitlab 的營收模組與很多軟體公司都一樣,採取免費版本讓你用,進階版本收你錢的模式。直到 06/2021, GitLab 全球大概有三千萬的使用者,但是真正付費的使用者數量只有一萬五千多。
簡單來說,GitLab 的營收轉化能力不到 1%,低於同業營收模型的 2%~5% 轉化率,而且大部分付費的使用者都採取價格較低,利潤較低的方案,以 GitLab 的資料來看,大概有 3632 的基本客戶每年提供 $5000 美元的收入,
只有大概 383 位用戶每年提供超過 10 萬美元的收入。
從淨收入來看, 2021 相對 2020 的年成長率高達 87 %,所以是有更多使用者願意付費,但是其核心業務盈利(Core Earnings)則從 -1.25 億美元下降到 -2.13 億美元,這意味核心業務的賺錢能力是下降的。
GitLab 的營收策略顯然更像是專注於增長收入能力而放棄於整體營收,其他數字包含 (2020 -> 2021)
1. 稅後淨營業利潤(NOPAT)從 -158% 提升到 -141 %,整體小成長但是賠錢的。
2. 投資資本回報率(ROIC)從 -41% 下降到 -76%
3. 現金流從 -1.49 億美金下降到 -2.29 億美金
作者認為雖然整體收入提升,但是對於股東來說整體價值是下降的。
整體文章非常長,從非常多角度去探討,對於這個議題有興趣的可以參考看看
Forbes
GitLab: Another Overpriced Tech Company
I think this stock could be worth less than $1 billion and that its freemium strategy may never be profitable.
ref: https://engineering.linkedin.com/blog/2020/making-the-linkedin-experimentation-engine-20x-faster
今天這篇是 LinkedIn 的記錄部落格,探討到底 LinkedIn 的 A/B Testing 到底有多瘋狂,如何並行高達三萬五千多種不同的 A/B Testing.
因為 LinkedIn 依賴基於資料分析來辦別每個改動是否能夠達到預期上的效果,因此 LinkedIn 所有新功能都必須要經過 A/B Testing 來決定每個新功能最後的方向。
其內部開發了一套專門針對有大量 A/B Testing 需求的系統,該系統著名的指標有
1. 網路呼叫高達 800,000 QPS (Query Per Second)
2. 並行運行了 35,000 不同的 A/B Testing 實驗
3. 每天會執行高達 23 trillion (23,000,000,000,000,000) 次的邏輯判斷
4. 邏輯判斷的平均延遲時間是 700ns,99百分位的時間則是 3μs
5. 有高達 500 個正式上線服務使用這個平台
這個 A/B Testing 的平台準確來說稱為 Lix Engine,整個運作流程就如同 A/B Testing 的想法一樣。
Service 發送 A/B Testing 的請求到 Lix Engine,該系統去計算與評估來確認到底該次 Request 是屬於控制組還是不變組,最後將結果給回傳給 Service
最後 Service 根據這個結果讓使用者有不同的行為。
文章後半部分就開始針對這個名為 Lix Engine 的平台進行詳細介紹,包含
1. 到底什麼是 Lix Engine,其實際上到底做了哪些事情
2. 這個從 2012 左右就開發的系統實際上又遇到了哪些困境與缺陷
3. 該系統最後打算重寫,而重寫的過程中是如何決定各項重要指標,譬如使用何種指標,何種使用方式
4. 最後探討整個實作細節
整篇文章非常深入了去介紹這個系統,不單純只是從表面去介紹其功能,而是從內部跟實作方面都有涉獵,非常推薦對 A/B Testing 或是系統設計有興趣的人閱讀一番
今天這篇是 LinkedIn 的記錄部落格,探討到底 LinkedIn 的 A/B Testing 到底有多瘋狂,如何並行高達三萬五千多種不同的 A/B Testing.
因為 LinkedIn 依賴基於資料分析來辦別每個改動是否能夠達到預期上的效果,因此 LinkedIn 所有新功能都必須要經過 A/B Testing 來決定每個新功能最後的方向。
其內部開發了一套專門針對有大量 A/B Testing 需求的系統,該系統著名的指標有
1. 網路呼叫高達 800,000 QPS (Query Per Second)
2. 並行運行了 35,000 不同的 A/B Testing 實驗
3. 每天會執行高達 23 trillion (23,000,000,000,000,000) 次的邏輯判斷
4. 邏輯判斷的平均延遲時間是 700ns,99百分位的時間則是 3μs
5. 有高達 500 個正式上線服務使用這個平台
這個 A/B Testing 的平台準確來說稱為 Lix Engine,整個運作流程就如同 A/B Testing 的想法一樣。
Service 發送 A/B Testing 的請求到 Lix Engine,該系統去計算與評估來確認到底該次 Request 是屬於控制組還是不變組,最後將結果給回傳給 Service
最後 Service 根據這個結果讓使用者有不同的行為。
文章後半部分就開始針對這個名為 Lix Engine 的平台進行詳細介紹,包含
1. 到底什麼是 Lix Engine,其實際上到底做了哪些事情
2. 這個從 2012 左右就開發的系統實際上又遇到了哪些困境與缺陷
3. 該系統最後打算重寫,而重寫的過程中是如何決定各項重要指標,譬如使用何種指標,何種使用方式
4. 最後探討整個實作細節
整篇文章非常深入了去介紹這個系統,不單純只是從表面去介紹其功能,而是從內部跟實作方面都有涉獵,非常推薦對 A/B Testing 或是系統設計有興趣的人閱讀一番
Linkedin
Making the LinkedIn experimentation engine 20x faster
ref: https://towardsdatascience.com/3-python-projects-that-will-help-automate-your-life-b6d48a4c1fa2
本篇文章作者想分享三個能夠幫忙自動化日常工作的 python 專案
日常工作中如果有些事項需要反覆執行,而每次執行又覺得有點煩瑣惱人的話,通常都可以考慮看看是否有自動化的價值,因此作者就分享自己使用過且有巨大幫助的三個專案。
# Automate Excel Reporting(mito)
為了準備一個 Excel 報表,通常除了基本資料外,還會使用內建函式,資料轉換然後會畫各種不同圖表。
這類型的工作執行一次可能還行,但是如果今天需要頻繁的準備 Excel 報表,那就可以考慮將其自動化。
Python 方面有很多相關的專案可以用來處理,譬如 openpyxl 與 Pandas 來完成,但是 openpyxl 的問題在於不容易上手,初學者要先花不少時間熟悉其架構與語法。
因此作者推薦另外一套更為簡單的專案 mitosheet(mito),該專案最爲特別的是其提供了一個友善的介面讓使用者去操作,接者會將這些操作全部轉為 Python code,所以對於初學者來說
可以達到所見即所得的方式。
文章中有作者使用 jupyter notebook 的範例來操作 mitosheet 並且產生相關的程式碼最後完成自動化 Excel 報表的範例。
# Automate Data Visualization(mito)
# Web Automation(Selenium)
後面兩個領域有興趣的可以參閱全文
本篇文章作者想分享三個能夠幫忙自動化日常工作的 python 專案
日常工作中如果有些事項需要反覆執行,而每次執行又覺得有點煩瑣惱人的話,通常都可以考慮看看是否有自動化的價值,因此作者就分享自己使用過且有巨大幫助的三個專案。
# Automate Excel Reporting(mito)
為了準備一個 Excel 報表,通常除了基本資料外,還會使用內建函式,資料轉換然後會畫各種不同圖表。
這類型的工作執行一次可能還行,但是如果今天需要頻繁的準備 Excel 報表,那就可以考慮將其自動化。
Python 方面有很多相關的專案可以用來處理,譬如 openpyxl 與 Pandas 來完成,但是 openpyxl 的問題在於不容易上手,初學者要先花不少時間熟悉其架構與語法。
因此作者推薦另外一套更為簡單的專案 mitosheet(mito),該專案最爲特別的是其提供了一個友善的介面讓使用者去操作,接者會將這些操作全部轉為 Python code,所以對於初學者來說
可以達到所見即所得的方式。
文章中有作者使用 jupyter notebook 的範例來操作 mitosheet 並且產生相關的程式碼最後完成自動化 Excel 報表的範例。
# Automate Data Visualization(mito)
# Web Automation(Selenium)
後面兩個領域有興趣的可以參閱全文
Medium
3 Python Projects That Will Help Automate Your Life
Beginner and advanced projects to automate your life with Python.
ref: https://medium.com/system-design-concepts/distributed-cache-system-design-9560f7dd07f2
本篇文章是一個系統設計分享文,內容不會非常深入,我認為算是一篇如果滿好的入門文。
該文探討的是如果想要設計一個分散式的 cache 系統,到底要從何處切入以及整體架構上需要考量的點。
Cache 的概念現在無所不在,從作業系統, CDN, DNS 到各式各樣的應用程式都有快取的概念。談到快取時最簡單的想法就是比硬碟讀寫快,能夠讓應用程式夠有效率地去讀寫資料。
文章接者針對幾個核心概念去探討,包含
1. Cache 的存取模式
2. HashTable 的運作模式
3. 分散式架構下的 HashTable
4. Cache 驅逐舊資料的演算法
5. 內部程式設計
6. Fault-Tolerant
7. 高可用性
這邊就針對幾個議題進行簡單摘要,對於整個細節都有興趣的可以參考
# Cache 的存取模式
三種常見模式,分別是 Write through, Write around 以及 Write back (實際上有更多做法,甚至還要考慮 Read 的路徑,本篇文章只是介紹幾個)
從這三個模式的名詞可以觀察到差異主要是針對寫入這個選項去探討,使用者今天要新增一筆資料時到底該整個更新路徑是如何
rite through: 先寫到 Cache 並且寫入到 DB,當資料同時寫入到 Cache 與後端 DB 且都成功才可以算是該筆寫入成功。
Write around: 資料只會寫到後端 DB,當相同資料下次發生 Cache Miss 時才會讓該資料被寫入快取
Write back: 寫入到 Cache 並且馬上回傳給應用程式,應用程式感受到的延遲性最低。會需要有額外的應用程式幫忙將 Cache 的資料同步回後端 DB
# Cache 驅逐舊資料的演算法
因為 Cache 通常代表的就是小而貴,能夠存放的資料量也不能這麼多,因此當愈來愈多的資料需要被快取使用時勢必要有所取捨,哪些資料要保留,哪些不保留。
一個比較直覺的做法就是 LRU,將最近沒有使用到的資料給剔除,文章內就針對 LRU 寫了一個範例 Code.
# Fault-tolerant
假設 Cache 內的所有資料都存放於記憶體中,那運行節點如果出現問題譬如斷電重開機,記憶體清除就會導致 Cache 的資料都完全消失,這邊列舉兩種做法來處理
1. 定期針對資料進行快照。透過一個背景程式定期地將記憶體內的內容給複製一份給寫入到硬碟中,這樣當系統重開機時就可以從硬碟中的內容還原上次的 Cache 資料
2. 透過 log 的方式重造系統。讓 Cache 系統針對每次操作都會撰寫一個相關的 log,所以系統重開機時可以針對這些 log 內容重新操作來復原之前的資料
本篇文章是一個系統設計分享文,內容不會非常深入,我認為算是一篇如果滿好的入門文。
該文探討的是如果想要設計一個分散式的 cache 系統,到底要從何處切入以及整體架構上需要考量的點。
Cache 的概念現在無所不在,從作業系統, CDN, DNS 到各式各樣的應用程式都有快取的概念。談到快取時最簡單的想法就是比硬碟讀寫快,能夠讓應用程式夠有效率地去讀寫資料。
文章接者針對幾個核心概念去探討,包含
1. Cache 的存取模式
2. HashTable 的運作模式
3. 分散式架構下的 HashTable
4. Cache 驅逐舊資料的演算法
5. 內部程式設計
6. Fault-Tolerant
7. 高可用性
這邊就針對幾個議題進行簡單摘要,對於整個細節都有興趣的可以參考
# Cache 的存取模式
三種常見模式,分別是 Write through, Write around 以及 Write back (實際上有更多做法,甚至還要考慮 Read 的路徑,本篇文章只是介紹幾個)
從這三個模式的名詞可以觀察到差異主要是針對寫入這個選項去探討,使用者今天要新增一筆資料時到底該整個更新路徑是如何
rite through: 先寫到 Cache 並且寫入到 DB,當資料同時寫入到 Cache 與後端 DB 且都成功才可以算是該筆寫入成功。
Write around: 資料只會寫到後端 DB,當相同資料下次發生 Cache Miss 時才會讓該資料被寫入快取
Write back: 寫入到 Cache 並且馬上回傳給應用程式,應用程式感受到的延遲性最低。會需要有額外的應用程式幫忙將 Cache 的資料同步回後端 DB
# Cache 驅逐舊資料的演算法
因為 Cache 通常代表的就是小而貴,能夠存放的資料量也不能這麼多,因此當愈來愈多的資料需要被快取使用時勢必要有所取捨,哪些資料要保留,哪些不保留。
一個比較直覺的做法就是 LRU,將最近沒有使用到的資料給剔除,文章內就針對 LRU 寫了一個範例 Code.
# Fault-tolerant
假設 Cache 內的所有資料都存放於記憶體中,那運行節點如果出現問題譬如斷電重開機,記憶體清除就會導致 Cache 的資料都完全消失,這邊列舉兩種做法來處理
1. 定期針對資料進行快照。透過一個背景程式定期地將記憶體內的內容給複製一份給寫入到硬碟中,這樣當系統重開機時就可以從硬碟中的內容還原上次的 Cache 資料
2. 透過 log 的方式重造系統。讓 Cache 系統針對每次操作都會撰寫一個相關的 log,所以系統重開機時可以針對這些 log 內容重新操作來復原之前的資料
Medium
Distributed cache system design
What is caching?
ref: https://medium.com/capital-one-tech/10-microservices-best-practices-for-the-optimal-architecture-design-capital-one-de16abf2a232
本篇文章探討十個關於微服務架構的十個實戰技巧。
微服務概念的出現大大地改變整個應用程式的組成架構,從過往單一包含所有功能與商業邏輯的 monolithic 架構變成由多個單一功能的元件互相合成的微服務架構,本篇文章分享十個微服務的基本概念,希望透過這些概念能夠讓你打造出更有效率且少走冤枉路的架構
相對於 monolithic 來說,微服務的架構會有幾個不同點,包含
1. 每個元件可以採用不同的程式語言實作,同時可以有自己的開發與發佈週期
2. 組織中的每個團隊都有自行維護的微服務元件,不同團隊可以併行開發與測試,整體來說會更快速與有效率的去面對市場變化
3. 由於目前是多個元件共同組成服務,所以單一元件的壞掉不太會導致其他的元件一起壞掉。過往 monolithic 的情況很有可能一個地方沒寫好導致整個應用程式都無法運行,最後所有功能都沒有辦法正常運行
然而當微服務的元件數量逐漸成長,彼此之間的關係沒有仔細規劃時,可能會導致這些元件之間的關係錯綜複雜,這會使得整個維護成本上升,跨團隊之間的合作成本也會一起提升,
因此設計一個良好的微服務架構是需要訓練與學習的,並不是單純把所有功能都單獨拆開就是一個好架構,因此底下的十個架構就是希望能夠避免打造出一個悲劇的微服務架構
1. The Single Responsibility Principle
微服務應該要與過往寫程式的習慣一樣,每個元件都專注一項功能,同時牽扯太多服務就像一個 class 同時牽扯過多不同的商業邏輯一樣,基本上是個不好的設計
2. Have a separate data store(s) for your microservice
過往 monolithic 架構下很容易看到所有服務都採用相同的 database,但是因應微服務架構的特性,這種架構未必是好的。任何對該 DB 的修改或是問題都會影響到所有使用到該 DB 的微服務元件,
因此比較好的做法是針對每個應用的需求去選擇自己的 DB,不需要強迫與勉強所有微服務共用同樣的 DB。
3. Use asynchronous communication to achieve loose coupling
為了避免打造一個非常複雜互相依賴的元件關係圖,可以考慮使用非同步的方式來處理不同元件之間的溝通請求,這邊提出兩種方式
譬如可以考慮使用 message bus 之類的系統,讓你的元件將相關的事件內容都推向到 Message bus 的系統,然後其他的元件針對自己有興趣的主題去讀取內容來處理。
4. Fail fast by using a circuit breaker to achieve fault tolerance
5. Proxy your microservice requests through an API Gateway
6. Ensure your API changes are backwards compatible
7. Version your microservices for breaking changes
8. Have dedicated infrastructure hosting your microservice
9. Create a separate release train
10. Create Organizational Efficiencies
剩下有興趣的就去閱讀全文囉
本篇文章探討十個關於微服務架構的十個實戰技巧。
微服務概念的出現大大地改變整個應用程式的組成架構,從過往單一包含所有功能與商業邏輯的 monolithic 架構變成由多個單一功能的元件互相合成的微服務架構,本篇文章分享十個微服務的基本概念,希望透過這些概念能夠讓你打造出更有效率且少走冤枉路的架構
相對於 monolithic 來說,微服務的架構會有幾個不同點,包含
1. 每個元件可以採用不同的程式語言實作,同時可以有自己的開發與發佈週期
2. 組織中的每個團隊都有自行維護的微服務元件,不同團隊可以併行開發與測試,整體來說會更快速與有效率的去面對市場變化
3. 由於目前是多個元件共同組成服務,所以單一元件的壞掉不太會導致其他的元件一起壞掉。過往 monolithic 的情況很有可能一個地方沒寫好導致整個應用程式都無法運行,最後所有功能都沒有辦法正常運行
然而當微服務的元件數量逐漸成長,彼此之間的關係沒有仔細規劃時,可能會導致這些元件之間的關係錯綜複雜,這會使得整個維護成本上升,跨團隊之間的合作成本也會一起提升,
因此設計一個良好的微服務架構是需要訓練與學習的,並不是單純把所有功能都單獨拆開就是一個好架構,因此底下的十個架構就是希望能夠避免打造出一個悲劇的微服務架構
1. The Single Responsibility Principle
微服務應該要與過往寫程式的習慣一樣,每個元件都專注一項功能,同時牽扯太多服務就像一個 class 同時牽扯過多不同的商業邏輯一樣,基本上是個不好的設計
2. Have a separate data store(s) for your microservice
過往 monolithic 架構下很容易看到所有服務都採用相同的 database,但是因應微服務架構的特性,這種架構未必是好的。任何對該 DB 的修改或是問題都會影響到所有使用到該 DB 的微服務元件,
因此比較好的做法是針對每個應用的需求去選擇自己的 DB,不需要強迫與勉強所有微服務共用同樣的 DB。
3. Use asynchronous communication to achieve loose coupling
為了避免打造一個非常複雜互相依賴的元件關係圖,可以考慮使用非同步的方式來處理不同元件之間的溝通請求,這邊提出兩種方式
譬如可以考慮使用 message bus 之類的系統,讓你的元件將相關的事件內容都推向到 Message bus 的系統,然後其他的元件針對自己有興趣的主題去讀取內容來處理。
4. Fail fast by using a circuit breaker to achieve fault tolerance
5. Proxy your microservice requests through an API Gateway
6. Ensure your API changes are backwards compatible
7. Version your microservices for breaking changes
8. Have dedicated infrastructure hosting your microservice
9. Create a separate release train
10. Create Organizational Efficiencies
剩下有興趣的就去閱讀全文囉
Medium
10 Microservices Best Practices for the Optimal Architecture Design
Microservices have fundamentally changed the way server side engines are architected. Rather than a single giant monolithic codebase…
ref: https://towardsdatascience.com/tired-of-airflow-try-this-c51ec26cd29d
本篇文章是探討的是類似於 Airflow 但是更為輕量與簡易的管理工具,Prefect
作者加入公司初期的首要目標就是決定一個用來分析資料的架構,網路上查來查去會看到很多關於 airflow 的相關介紹文,但是作者仔細比較與評估後,認為 Airflow 更加適合一個團隊專屬維運與使用,
而自己這家新創公司能夠負責這個工作的只有一個人,也就是作者自己。
時間有限的情況下,作者希望能夠將大部分的時間放在最有價值的工作,因此會希望這個解決方案能夠盡量的簡潔有力,最後就找到一個名為 Prefect 的替代方案。
Prefect 是一個 workflow 的解決方案,一樣可以用來建制,運行與監控各式各樣的 data pipeline。使用方面也不會太困難, Prefect 是基於 Python 撰寫的,所以熟悉 Python 的使用者都可以滿輕鬆的去建立屬於自己的 Data pipeline.
作者有先嘗試過使用 Airflow,結果整個環境建置複雜,嘗試使用 astronomer 來搭建整個環境結果也屢屢碰壁,讓作者更為崩潰的是 astronomer 的支援服務也不好,有問題有找不到圖隊處理
因此花費不少時間測試後,最後還是決定轉往 Prefect,因為其整體使用起來更容易上手
文章中還有其他關於這兩個專案的比較以及作者其他在意的點,對於這領域有興趣的可以參考
本篇文章是探討的是類似於 Airflow 但是更為輕量與簡易的管理工具,Prefect
作者加入公司初期的首要目標就是決定一個用來分析資料的架構,網路上查來查去會看到很多關於 airflow 的相關介紹文,但是作者仔細比較與評估後,認為 Airflow 更加適合一個團隊專屬維運與使用,
而自己這家新創公司能夠負責這個工作的只有一個人,也就是作者自己。
時間有限的情況下,作者希望能夠將大部分的時間放在最有價值的工作,因此會希望這個解決方案能夠盡量的簡潔有力,最後就找到一個名為 Prefect 的替代方案。
Prefect 是一個 workflow 的解決方案,一樣可以用來建制,運行與監控各式各樣的 data pipeline。使用方面也不會太困難, Prefect 是基於 Python 撰寫的,所以熟悉 Python 的使用者都可以滿輕鬆的去建立屬於自己的 Data pipeline.
作者有先嘗試過使用 Airflow,結果整個環境建置複雜,嘗試使用 astronomer 來搭建整個環境結果也屢屢碰壁,讓作者更為崩潰的是 astronomer 的支援服務也不好,有問題有找不到圖隊處理
因此花費不少時間測試後,最後還是決定轉往 Prefect,因為其整體使用起來更容易上手
文章中還有其他關於這兩個專案的比較以及作者其他在意的點,對於這領域有興趣的可以參考
Medium
Tired of Airflow? Try This.
A new tool that does what Airflow does but better
一個 patch 去修改 Linux Kernel 底層針對 TCP 連線釋放 skb (Kernel 內放所有網路的物件) 的時間點,竟然可以讓 100G 網卡的效能提升不少
Tested:
100Gbit NIC
Max throughput for one TCP_STREAM flow, over 10 runs
MTU : 1500
Before: 55 Gbit
After: 66 Gbit
MTU : 4096+(headers)
Before: 82 Gbit
After: 95 Gbit
從 MTU 1500 的情況來看提升竟然有 20% 左右,MTU 4096 大概也有 15% 左右。
這故事告訴我們底層基本功還是很重要,資源的使用與釋放的時機沒有處理好是可能白白浪費你一堆的系統效能的。
Tested:
100Gbit NIC
Max throughput for one TCP_STREAM flow, over 10 runs
MTU : 1500
Before: 55 Gbit
After: 66 Gbit
MTU : 4096+(headers)
Before: 82 Gbit
After: 95 Gbit
從 MTU 1500 的情況來看提升竟然有 20% 左右,MTU 4096 大概也有 15% 左右。
這故事告訴我們底層基本功還是很重要,資源的使用與釋放的時機沒有處理好是可能白白浪費你一堆的系統效能的。
ref: https://fluxcd.io/blog/2021-11-10-flux-security-audit/
Flux 與 ArgoCD 可以說是 Kubernetes 中較為出名的 GitOps 解決方案,而這篇文章是 Flux 來分享關於該專案目前針對資安方面的安全性進展,也包含一個近期的 CVE-2021-41254 介紹。
Flux 本身是 CNCF 內的孵化專案,資安方面與 OSTIF (the Open Source Technology Improvement Fund) 與 ADA Logics 等互相合作,而這篇文章就是 ADA Logics 再分析 Flux 開源程式碼後所觀察到的相關問題
最重要的是 Flux 專案的第一個 CVE 就此誕生,任何可以創建 Kubernetes Secret, Service Account 與 Flux Kustomization CRD 的使用者都可以透過一系列的手法提權最後透過 kubectl 來獲得整個 Cluster 的權限。
這個 CVE 已經於 Flux v0.15.0 修復,所以如果你有使用 Flux 且版本是低於 v0.15.0 的,那非常推薦趕緊升級來修復 CVE,避免叢集被人提權操控。
ADA Logics 總共發現 22 獨立的潛在問題,其中包含 5 個 informational 等級, 13 個低嚴重性, 3 個中等嚴重性以及一個被判為 CVE 的高危險性。
本篇文章後續還有分享這些問題的相關分類以及這些問題該如何處理,有興趣的可以閱讀全文
Flux 與 ArgoCD 可以說是 Kubernetes 中較為出名的 GitOps 解決方案,而這篇文章是 Flux 來分享關於該專案目前針對資安方面的安全性進展,也包含一個近期的 CVE-2021-41254 介紹。
Flux 本身是 CNCF 內的孵化專案,資安方面與 OSTIF (the Open Source Technology Improvement Fund) 與 ADA Logics 等互相合作,而這篇文章就是 ADA Logics 再分析 Flux 開源程式碼後所觀察到的相關問題
最重要的是 Flux 專案的第一個 CVE 就此誕生,任何可以創建 Kubernetes Secret, Service Account 與 Flux Kustomization CRD 的使用者都可以透過一系列的手法提權最後透過 kubectl 來獲得整個 Cluster 的權限。
這個 CVE 已經於 Flux v0.15.0 修復,所以如果你有使用 Flux 且版本是低於 v0.15.0 的,那非常推薦趕緊升級來修復 CVE,避免叢集被人提權操控。
ADA Logics 總共發現 22 獨立的潛在問題,其中包含 5 個 informational 等級, 13 個低嚴重性, 3 個中等嚴重性以及一個被判為 CVE 的高危險性。
本篇文章後續還有分享這些問題的相關分類以及這些問題該如何處理,有興趣的可以閱讀全文
ref: https://engineering.linkedin.com/blog/2021/building-in-the-cloud-with-remote-development
本篇文章是 LinkedIn 的技術分享文,探討如何透過 Kubernetes 打造一個遠端開發環境,什麼叫做遠端開發環境呢? 就是本地開發,但是所有的資源消耗都是使用雲端資源來進行處理的開發模式。
LinkedIn 過往的經驗證明透過該套遠端開發環境能夠有效地簡化大部分產品的開發流程,讓所有的初始化與建制時間從過往的 10-30 分鐘降低到只要 10 秒左右,而這篇文章就是細探這套系統的概念。
LinkedIn 內的產品多元,使用的程式語言超多,譬如 Java, Python, C/C++, Go, JS, iOS 以及 Android,多元的環境其實對於對於每個新人來說都是個環境惡夢,設定方面總是要花費好多時間去處理,
同時作者也聽到不少同事討論產品建置與編譯的速度過慢連帶影響整個產品的開發效率。
COVID-19 期間,整個公司都採取遠端工作模式,所有的開發環境都變成以筆電為主,相較於桌機來說筆電的規格會使得如何使用有限的 CPU/Memory 等資源來建置與開發公司產品。
遠端開發環境這個專案的目的就是希望能夠改善開發效率,希望能夠提供一個基於遠端存取,高依賴性,高效率且簡易操作的遠端開發環境,而這套環境就稱為 RDevs。
RDevs 架構是基於 Container 去提供每個開發者一個開發建置環境,而這些 Container 透過 remote SSH 的方式來開發者存取,同時因為架構的關係,這些 container 能夠更有效與更快地去存取各種網路資源,
圖中提到以 LinkedId 一個大型的應用程式來看,使用 PDevs 建制的時間大概只有一兩分鐘,而一個本地擁有 16Core 的 macOS 則需要五分鐘, 4 core 數量的 macOS 則需要高達 15 分鐘左右的建置時間。
這種情況下開發者就可以用 RDev 來處理所有的建置需求,而所有的操作都是基於 SSH,因此只需要確保自身的網路環境能夠提供有效率的 SSH 環境即可,也不用擔心筆電上的各種背景應用程式影響整個建置速度。
RDev 架構是基於 Kubernetes 開發的,所有的建置環境其實就是一個又一個的 Kubernetes Pod,每個 Pod 是由多個不同功能的 Container 所組成,同時這些 Pod 也會透過 Mount 的方式來準備相關的使用資料,譬如開發者的家目錄
為了讓整體運作更加順利, RDev 還開發了自己的 Operator,能夠根據開發者的需求而動態產生 Pod 來使用,此外也有提到使用 PostStart Hook, Startup Probe 等相關概念。
這篇文章非常實在的展現了 Kubernetes 的不同用法,如何透過 Kubernetes 來提升團隊內的建置與編譯速度進而提升開發效率。
本篇文章是 LinkedIn 的技術分享文,探討如何透過 Kubernetes 打造一個遠端開發環境,什麼叫做遠端開發環境呢? 就是本地開發,但是所有的資源消耗都是使用雲端資源來進行處理的開發模式。
LinkedIn 過往的經驗證明透過該套遠端開發環境能夠有效地簡化大部分產品的開發流程,讓所有的初始化與建制時間從過往的 10-30 分鐘降低到只要 10 秒左右,而這篇文章就是細探這套系統的概念。
LinkedIn 內的產品多元,使用的程式語言超多,譬如 Java, Python, C/C++, Go, JS, iOS 以及 Android,多元的環境其實對於對於每個新人來說都是個環境惡夢,設定方面總是要花費好多時間去處理,
同時作者也聽到不少同事討論產品建置與編譯的速度過慢連帶影響整個產品的開發效率。
COVID-19 期間,整個公司都採取遠端工作模式,所有的開發環境都變成以筆電為主,相較於桌機來說筆電的規格會使得如何使用有限的 CPU/Memory 等資源來建置與開發公司產品。
遠端開發環境這個專案的目的就是希望能夠改善開發效率,希望能夠提供一個基於遠端存取,高依賴性,高效率且簡易操作的遠端開發環境,而這套環境就稱為 RDevs。
RDevs 架構是基於 Container 去提供每個開發者一個開發建置環境,而這些 Container 透過 remote SSH 的方式來開發者存取,同時因為架構的關係,這些 container 能夠更有效與更快地去存取各種網路資源,
圖中提到以 LinkedId 一個大型的應用程式來看,使用 PDevs 建制的時間大概只有一兩分鐘,而一個本地擁有 16Core 的 macOS 則需要五分鐘, 4 core 數量的 macOS 則需要高達 15 分鐘左右的建置時間。
這種情況下開發者就可以用 RDev 來處理所有的建置需求,而所有的操作都是基於 SSH,因此只需要確保自身的網路環境能夠提供有效率的 SSH 環境即可,也不用擔心筆電上的各種背景應用程式影響整個建置速度。
RDev 架構是基於 Kubernetes 開發的,所有的建置環境其實就是一個又一個的 Kubernetes Pod,每個 Pod 是由多個不同功能的 Container 所組成,同時這些 Pod 也會透過 Mount 的方式來準備相關的使用資料,譬如開發者的家目錄
為了讓整體運作更加順利, RDev 還開發了自己的 Operator,能夠根據開發者的需求而動態產生 Pod 來使用,此外也有提到使用 PostStart Hook, Startup Probe 等相關概念。
這篇文章非常實在的展現了 Kubernetes 的不同用法,如何透過 Kubernetes 來提升團隊內的建置與編譯速度進而提升開發效率。
Linkedin
Building in the cloud with remote development
ref: https://medium.com/system-design-concepts/tinyurl-system-design-16868b5435de
本篇又是另外一個系統設計的分享文,想要探討的是如何想要設計一個 tinyurl 的系統,那到底有哪些事項需要注意?
TinyURL 的概念很簡單,使用者輸入一串 URL,最後回傳一串很短的 URL 讓使用者更方便存取,然後整個設計簡單為主。
這次的 tinyurl 先假設該系統需要滿足的條件有
1. 使用者數量: 三千萬使用者
2. 短網址長度: 使用 7 個字元
根據上述需求,先來估計要使用的資料結構與整體大小
1. Long URL: 2KB -> 2048 chars
2. Short URL: 7 bytes -> 7 chars
3. Created at: 7 bytes -> 7 chars
4. Expire at: 7 bytes -> 7 chars
所以每一個欄位大概需要 2069 Bytes,大概就是 2.021 KB,所以三千萬個使用者來說,如果要
1. 保存一個月,那至少需要 60.63 GB
2. 保存一年就需要 727 GB
3. 保存五年則需要 3.6 TB 左右
根據這些使用量會用來幫忙評估最後要使用 RDBMS 或是 NoSQL DB
# 7個字元的產生
作者提出兩種簡易方法來產生一個長度七的URL
1. 給定一個大數,使用 base62(0-9a-zA-Z) 的方式去產生出一個長度七的字串
2. 給定一個唯一字串(Long URL)並且基於 base62 回傳一個長度七的字串,譬如使用 MD5 來處理,但是MD5前七個字元就有可能會發生重複的問題,不同的 Long URL 最後得到相同的 7個字元。
基於 base62 的短網址總共有 62^7 總可能,相對於 Base10 只有一百萬來說,62^7 大概有 3.5 兆左右可能性。
所以如果採用第一個方式就是針對每個 LongURL 去產生一個不重複的隨機數字,並且將該數字以 base62 呈現來代表短網址。
# 第一種方式
假設今天已經選好短網址了,下一個步驟就是要將這個 long url 與 short url 的關係給寫入到資料庫中
但是寫入並不是單純寫入這麼簡單,因為亂數的產生是有可能重複的,因此當前產生的 short url 是有可能已經存在於 DB 之中,這種情況下就需要重新產生亂數直到找到一個沒有被使用過的 short url.
如果整個系統只有一個人會進行讀寫的話,這種操作基本上沒有問題,但是要是同時有多個系統要進行讀寫又沒有相關機制妥善處理的話,就會發生重複資料被同時寫入到DB內了。
一種解決方式就是讓 shortURL 變成所謂的 unique key,同時還可以搭配 `put if not exists` 等概念讓 DB 本身來處理這類型的限制,不過這部分的功能通常只有 RDBMS 有支援,如果是 NoSQL 的話則沒有辦法搞定。
# 第二種方式
假設採用的是 MD5 的方式來處理 long url 並且取前七個字元來使用,基本上跟前述會有一樣的問題,都有可能會發生不同的 long url 最後獲得相同的短網址,
這情況下還是會有重複資料的問題
# 別的想法
使用 counter 的概念,將 counter 以 base62 的方式來呈現,不過這個作法只適合單一 server 來處理,當同時有多個 server 時又變成要維護 counter 的共同讀寫問題。
雖然探討的是 TinyURL 的簡易實作,但是作者後半部分還繼續探討如何導入 ZooKeeper 讓上述的環境可以同時部署多個 server,藉此來處理更大規模的需求。
有興趣的可以閱讀全文
本篇又是另外一個系統設計的分享文,想要探討的是如何想要設計一個 tinyurl 的系統,那到底有哪些事項需要注意?
TinyURL 的概念很簡單,使用者輸入一串 URL,最後回傳一串很短的 URL 讓使用者更方便存取,然後整個設計簡單為主。
這次的 tinyurl 先假設該系統需要滿足的條件有
1. 使用者數量: 三千萬使用者
2. 短網址長度: 使用 7 個字元
根據上述需求,先來估計要使用的資料結構與整體大小
1. Long URL: 2KB -> 2048 chars
2. Short URL: 7 bytes -> 7 chars
3. Created at: 7 bytes -> 7 chars
4. Expire at: 7 bytes -> 7 chars
所以每一個欄位大概需要 2069 Bytes,大概就是 2.021 KB,所以三千萬個使用者來說,如果要
1. 保存一個月,那至少需要 60.63 GB
2. 保存一年就需要 727 GB
3. 保存五年則需要 3.6 TB 左右
根據這些使用量會用來幫忙評估最後要使用 RDBMS 或是 NoSQL DB
# 7個字元的產生
作者提出兩種簡易方法來產生一個長度七的URL
1. 給定一個大數,使用 base62(0-9a-zA-Z) 的方式去產生出一個長度七的字串
2. 給定一個唯一字串(Long URL)並且基於 base62 回傳一個長度七的字串,譬如使用 MD5 來處理,但是MD5前七個字元就有可能會發生重複的問題,不同的 Long URL 最後得到相同的 7個字元。
基於 base62 的短網址總共有 62^7 總可能,相對於 Base10 只有一百萬來說,62^7 大概有 3.5 兆左右可能性。
所以如果採用第一個方式就是針對每個 LongURL 去產生一個不重複的隨機數字,並且將該數字以 base62 呈現來代表短網址。
# 第一種方式
假設今天已經選好短網址了,下一個步驟就是要將這個 long url 與 short url 的關係給寫入到資料庫中
但是寫入並不是單純寫入這麼簡單,因為亂數的產生是有可能重複的,因此當前產生的 short url 是有可能已經存在於 DB 之中,這種情況下就需要重新產生亂數直到找到一個沒有被使用過的 short url.
如果整個系統只有一個人會進行讀寫的話,這種操作基本上沒有問題,但是要是同時有多個系統要進行讀寫又沒有相關機制妥善處理的話,就會發生重複資料被同時寫入到DB內了。
一種解決方式就是讓 shortURL 變成所謂的 unique key,同時還可以搭配 `put if not exists` 等概念讓 DB 本身來處理這類型的限制,不過這部分的功能通常只有 RDBMS 有支援,如果是 NoSQL 的話則沒有辦法搞定。
# 第二種方式
假設採用的是 MD5 的方式來處理 long url 並且取前七個字元來使用,基本上跟前述會有一樣的問題,都有可能會發生不同的 long url 最後獲得相同的短網址,
這情況下還是會有重複資料的問題
# 別的想法
使用 counter 的概念,將 counter 以 base62 的方式來呈現,不過這個作法只適合單一 server 來處理,當同時有多個 server 時又變成要維護 counter 的共同讀寫問題。
雖然探討的是 TinyURL 的簡易實作,但是作者後半部分還繼續探討如何導入 ZooKeeper 讓上述的環境可以同時部署多個 server,藉此來處理更大規模的需求。
有興趣的可以閱讀全文
Medium
Tinyurl system design
What is TinyURL?
ref: https://www.linuxjournal.com/content/everything-you-need-know-about-linux-containers-part-i-linux-control-groups-and-process
本篇文章是個深度技術文,認真探討 Container 技術底下的 Control Groups 以及 Process Isolation 到底是什麼。
Container 這個詞大家都聽說,也很多人聽過到底如何實作 Container 這種輕量級虛擬化概念的,但是以 Linux 為範例,到底真正技術上的實作是什麼這點則是硬知識,而本篇文章是個 container 系列文
希望能夠讓讀者對於 Container 的實作有更進一步的理解。
為了穩定性與安全性,事實上大部分的應用程式都應該受到相關程度的控管與限制,避免應用程式出現問題影響到其他應用程式或是機器本身,而 Linux Kernel 有提供一個名為
Control Groups (cgroup) 的概念用來限制與隔離不同的資源,譬如 CPU, Memory, DIsk I/O 以及 network。
cgroup 當初設計的目的是希望提供一個統一的介面讓管理者可以去管理多個 process 或是系統本身,該系統能夠達到
1. 資源控管: 控管群組特定資源的使用量不能超過多少
2. 優先順序: 控管該群組可以使用的資源量是更多或是更少,跟其他群組競爭時使用的優先權。
3. 資源監控: 可以監控與測量群組內的資源用量
4. 控管: 可以凍結,停止或是重啟群組內的應用程序
每個 cgroup 都是由數個 process 所組成的,這些 process 都會套用到相同的設定。同時為了提供更好的管理方式, cgroup 還提供了階層式的管理,就像 Tree 的架構一樣,
子節點會繼承自根節點的設定。
Kernel 內根據不同的資源實作不同的 controller,譬如 memory controller 則是專注於 memory 相關的設定,而 cpuacct 則是專注於 CPU 的使用量。
文章後半段就是實戰操控,如何透過系統上的 /sys/fs/cgroup 資料夾來跟 cgroup 互動,包含基本的資料檢查與創建一個範例應用程式
簡易的方式也可以使用 cgroup 系列的工具,譬如 cgcreate, cgexec, cgdelete 來操作。
如果系統中有運行 Kubernetes 環境有設定相關資源控管的話,是很推薦使用這類型的工具來幫忙釐清 YAML 設定與底層的關係,藉此加強自己對這方面的認知。
本篇文章是個深度技術文,認真探討 Container 技術底下的 Control Groups 以及 Process Isolation 到底是什麼。
Container 這個詞大家都聽說,也很多人聽過到底如何實作 Container 這種輕量級虛擬化概念的,但是以 Linux 為範例,到底真正技術上的實作是什麼這點則是硬知識,而本篇文章是個 container 系列文
希望能夠讓讀者對於 Container 的實作有更進一步的理解。
為了穩定性與安全性,事實上大部分的應用程式都應該受到相關程度的控管與限制,避免應用程式出現問題影響到其他應用程式或是機器本身,而 Linux Kernel 有提供一個名為
Control Groups (cgroup) 的概念用來限制與隔離不同的資源,譬如 CPU, Memory, DIsk I/O 以及 network。
cgroup 當初設計的目的是希望提供一個統一的介面讓管理者可以去管理多個 process 或是系統本身,該系統能夠達到
1. 資源控管: 控管群組特定資源的使用量不能超過多少
2. 優先順序: 控管該群組可以使用的資源量是更多或是更少,跟其他群組競爭時使用的優先權。
3. 資源監控: 可以監控與測量群組內的資源用量
4. 控管: 可以凍結,停止或是重啟群組內的應用程序
每個 cgroup 都是由數個 process 所組成的,這些 process 都會套用到相同的設定。同時為了提供更好的管理方式, cgroup 還提供了階層式的管理,就像 Tree 的架構一樣,
子節點會繼承自根節點的設定。
Kernel 內根據不同的資源實作不同的 controller,譬如 memory controller 則是專注於 memory 相關的設定,而 cpuacct 則是專注於 CPU 的使用量。
文章後半段就是實戰操控,如何透過系統上的 /sys/fs/cgroup 資料夾來跟 cgroup 互動,包含基本的資料檢查與創建一個範例應用程式
簡易的方式也可以使用 cgroup 系列的工具,譬如 cgcreate, cgexec, cgdelete 來操作。
如果系統中有運行 Kubernetes 環境有設定相關資源控管的話,是很推薦使用這類型的工具來幫忙釐清 YAML 設定與底層的關係,藉此加強自己對這方面的認知。
ref: https://kubernetes.io/blog/2021/11/12/are-you-ready-for-dockershim-removal/
Dockershim 從 Kubernetes 中移除的時間逐漸逼近,所有 Kubernetes 的使用者都明瞭這個改變並且準備好面對了嗎?
Dockershim 這個元件過去設計的目的是為了讓 Kubernetes 可以使用 Docker 作為底層的 Container Runtime,Kubernetes 意圖使用 CRI 來兼容百川,所以需要 dockershim 這層將所有的請求給轉移到 Dockerd 進行處理。
如今有愈來愈多的 Container Runtime 原生或是更容易支援 CRI 的標準,所以 Dockershim 存在的必要性也就逐漸下降。
根據目前的計畫, dockershim 將於 kuvernetes 1.24 給正式移除,大概會於 2022/04 左右發布該版本,對於 1.24 想要進行測試的玩家可以於今年年底先行使用看看 1.24 的 alpha/beta 版本。
文章中還有列出一份 dockershim migration documentation 的文件來介紹該如何檢視當前系統的設定以及要轉移需要注意哪些事項
此外如果你的 Kubernetes 是由第三方服務所架設與維護的,譬如 GKE/AKS/EKS/Rancher..等諸如環境,那就需要去確認這些服務是否有提供其他的 container runtime 選擇以及未來更新時應該要採取何種升級方式。
如果對於 dockershim 移除對於 kubernetes 使用者會有什麼影響還是不清楚的可以參閱這個影片
https://www.youtube.com/watch?v=nc3mBN3LzvM&t=62s
Dockershim 從 Kubernetes 中移除的時間逐漸逼近,所有 Kubernetes 的使用者都明瞭這個改變並且準備好面對了嗎?
Dockershim 這個元件過去設計的目的是為了讓 Kubernetes 可以使用 Docker 作為底層的 Container Runtime,Kubernetes 意圖使用 CRI 來兼容百川,所以需要 dockershim 這層將所有的請求給轉移到 Dockerd 進行處理。
如今有愈來愈多的 Container Runtime 原生或是更容易支援 CRI 的標準,所以 Dockershim 存在的必要性也就逐漸下降。
根據目前的計畫, dockershim 將於 kuvernetes 1.24 給正式移除,大概會於 2022/04 左右發布該版本,對於 1.24 想要進行測試的玩家可以於今年年底先行使用看看 1.24 的 alpha/beta 版本。
文章中還有列出一份 dockershim migration documentation 的文件來介紹該如何檢視當前系統的設定以及要轉移需要注意哪些事項
此外如果你的 Kubernetes 是由第三方服務所架設與維護的,譬如 GKE/AKS/EKS/Rancher..等諸如環境,那就需要去確認這些服務是否有提供其他的 container runtime 選擇以及未來更新時應該要採取何種升級方式。
如果對於 dockershim 移除對於 kubernetes 使用者會有什麼影響還是不清楚的可以參閱這個影片
https://www.youtube.com/watch?v=nc3mBN3LzvM&t=62s
Kubernetes
Dockershim removal is coming. Are you ready?
Reviewers: Davanum Srinivas, Elana Hashman, Noah Kantrowitz, Rey Lejano.
Poll closed This poll closed on January 7, 2022. Last year we announced that Kubernetes' dockershim component (which provides a built-in integration for Docker Engine) is deprecated.…
Poll closed This poll closed on January 7, 2022. Last year we announced that Kubernetes' dockershim component (which provides a built-in integration for Docker Engine) is deprecated.…
ref: https://medium.com/system-design-concepts/whatsapp-system-design-b094cbded096
本篇也是一個系統設計的分享文,這類型的文章都是從一個真實應用出發去分享一些可能的設計方式,這些設計方式不是萬靈丹也不是準則,單純是一個不同的思考方式
對於讀者我們來說也是一個思考的好機會,看看作者所講述的架構是否合理,以及如果自己去實作的話可能會採取何種架構去實作。
這篇文章想要探討的是類似 WhatsApp 這類型聊天通訊軟體的實作架構,聊天軟體不外乎就是
1. 互相傳遞訊息
2. 訊息是否已讀
3. 傳送不同類型的檔案
4. 加密
5. 通話
而這篇文章大抵上只有涵蓋前面三個功能的探討。
作為一個聊天通訊軟體,基本的架構都會是 Client/Server 架構, Client 就是所有使用該 app 的使用者,而 Server 則是背後幫忙進行訊息交換複雜處理的角色,文章中使用 messaging server 的代號來形容這個 server。
為了能夠處理大量的使用者,適度的根據用量去調整 messaging server 的數量是必要的,所以 client 連接上就不會直接跟這些 server 進行連線,相反的則是會使用 load-balancer 的概念來幫忙處理連線。
接者 server 架構中一定也會有相關資料庫的存在,文章中沒有特別探討要使用 RDBMS 還是 NoSQL。
試想一個情況,當 Client A 想要離線傳送訊息給 Client B 的時候,偏偏這時候 Client A 的手機沒有網路,沒有辦法連上 server,那這些訊息勢必都會存在於
手機端上的空間,可能是伴隨app的小型資料庫或是任何形式。當 Client A 順利連上 server 後就會將這些訊息給傳送到 server 上。
但是如果此時 Client B 也沒有跟 server 有連線,那這些要傳送的訊息理所當然的也要先暫時存放到 server 上,待 Client B 連上線後就會將這些訊息一次性的傳送給 Client B,接者 Client B 就能夠順利的收到這些訊息。
從上述的一個流程就可以看到只是簡單的傳送訊息中間就會牽扯到三個不同的角色,更何況有些軟體想要提供點到點的加密傳送服務,基本上還是要依賴 server 幫忙轉發,只是傳送的內容是否加密與否而已。
文章後去探討使用基於 Thread/Process 的概念來處理每個連線,然後不同的情況下要如何做到已讀的功能,同時如果還想要知道對方上一次看的時間是什麼時候這類型的功能該怎麼實作。
對於傳送檔案如圖檔之類的檔案,如果想要整合 CDN 等概念近來家速食,又會導入其他 HTTP Server 來進行檔案存放,並且讓每個訊息都是夾帶這些媒體檔案的資訊,動態其他的 CDN server 抓取。
對於整體有興趣的可以閱讀全文。
本篇也是一個系統設計的分享文,這類型的文章都是從一個真實應用出發去分享一些可能的設計方式,這些設計方式不是萬靈丹也不是準則,單純是一個不同的思考方式
對於讀者我們來說也是一個思考的好機會,看看作者所講述的架構是否合理,以及如果自己去實作的話可能會採取何種架構去實作。
這篇文章想要探討的是類似 WhatsApp 這類型聊天通訊軟體的實作架構,聊天軟體不外乎就是
1. 互相傳遞訊息
2. 訊息是否已讀
3. 傳送不同類型的檔案
4. 加密
5. 通話
而這篇文章大抵上只有涵蓋前面三個功能的探討。
作為一個聊天通訊軟體,基本的架構都會是 Client/Server 架構, Client 就是所有使用該 app 的使用者,而 Server 則是背後幫忙進行訊息交換複雜處理的角色,文章中使用 messaging server 的代號來形容這個 server。
為了能夠處理大量的使用者,適度的根據用量去調整 messaging server 的數量是必要的,所以 client 連接上就不會直接跟這些 server 進行連線,相反的則是會使用 load-balancer 的概念來幫忙處理連線。
接者 server 架構中一定也會有相關資料庫的存在,文章中沒有特別探討要使用 RDBMS 還是 NoSQL。
試想一個情況,當 Client A 想要離線傳送訊息給 Client B 的時候,偏偏這時候 Client A 的手機沒有網路,沒有辦法連上 server,那這些訊息勢必都會存在於
手機端上的空間,可能是伴隨app的小型資料庫或是任何形式。當 Client A 順利連上 server 後就會將這些訊息給傳送到 server 上。
但是如果此時 Client B 也沒有跟 server 有連線,那這些要傳送的訊息理所當然的也要先暫時存放到 server 上,待 Client B 連上線後就會將這些訊息一次性的傳送給 Client B,接者 Client B 就能夠順利的收到這些訊息。
從上述的一個流程就可以看到只是簡單的傳送訊息中間就會牽扯到三個不同的角色,更何況有些軟體想要提供點到點的加密傳送服務,基本上還是要依賴 server 幫忙轉發,只是傳送的內容是否加密與否而已。
文章後去探討使用基於 Thread/Process 的概念來處理每個連線,然後不同的情況下要如何做到已讀的功能,同時如果還想要知道對方上一次看的時間是什麼時候這類型的功能該怎麼實作。
對於傳送檔案如圖檔之類的檔案,如果想要整合 CDN 等概念近來家速食,又會導入其他 HTTP Server 來進行檔案存放,並且讓每個訊息都是夾帶這些媒體檔案的資訊,動態其他的 CDN server 抓取。
對於整體有興趣的可以閱讀全文。
Medium
WhatsApp System Design
Understanding the scale and features:
ref: https://medium.com/@arielstkuo/not-just-a-pretty-face-%E9%81%8A%E6%88%B2%E7%95%AB%E9%9D%A2%E5%BE%8C%E4%BD%A0%E4%B8%8D%E7%9F%A5%E9%81%93%E7%9A%84%E4%BA%8B-frame-1-2d-3d-2-5d-f0465ad4b736
本篇不探討 Cloud Native 相關概念,而是從一個科普文來分享一下遊戲世界的基本概念。
作者身為一個前暴雪員工,對於遊戲開發有諸多經驗,且本文非常貼近一般玩家日常同時又不會有太過於艱深的詞彙與技術,更重要的還是一篇實實在在的中文分享文。
資深遊戲玩家來說一定對於 2D(平面)/3D(立體) 世界不陌生,從早期的 Gameboy 到現在 Switch/PS4/PS5 等擁有更佳運算效能的主機後,愈來愈多的遊戲都會採用 3D 的方式來製作,但是你知道除了簡單的 2D 與 3D 之外,還有一個介於中間的 2.5D 嗎?
2.5D 的遊戲想要透過 2D 的平面素材來打造出一個類似於 3D 立體環境,同時看起來又不能太假,不能讓玩家一眼就覺得這整體不協調太奇怪,
文章中列舉了不少範例來解釋不同類型的 2.5D 以及使用最近才重製的 Diablo II 來進行比較,讓你看看到底早期的 Diablo II 是如何用 2D 裝 3D 以及後來採用全 3D 重新製作後的差異。
文章內科普了基本的固定視角模式外,也介紹了利用視差錯覺造成的距離感,可以讓開發商用較低的遊戲成本來打造出一個近似 3D 的遊戲環境。
簡單來說,本篇就是一個遊戲科普文,分享一些關於 2D, 3D, 2.5D 的一些概念,
有興趣的歡迎閱讀全文
本篇不探討 Cloud Native 相關概念,而是從一個科普文來分享一下遊戲世界的基本概念。
作者身為一個前暴雪員工,對於遊戲開發有諸多經驗,且本文非常貼近一般玩家日常同時又不會有太過於艱深的詞彙與技術,更重要的還是一篇實實在在的中文分享文。
資深遊戲玩家來說一定對於 2D(平面)/3D(立體) 世界不陌生,從早期的 Gameboy 到現在 Switch/PS4/PS5 等擁有更佳運算效能的主機後,愈來愈多的遊戲都會採用 3D 的方式來製作,但是你知道除了簡單的 2D 與 3D 之外,還有一個介於中間的 2.5D 嗎?
2.5D 的遊戲想要透過 2D 的平面素材來打造出一個類似於 3D 立體環境,同時看起來又不能太假,不能讓玩家一眼就覺得這整體不協調太奇怪,
文章中列舉了不少範例來解釋不同類型的 2.5D 以及使用最近才重製的 Diablo II 來進行比較,讓你看看到底早期的 Diablo II 是如何用 2D 裝 3D 以及後來採用全 3D 重新製作後的差異。
文章內科普了基本的固定視角模式外,也介紹了利用視差錯覺造成的距離感,可以讓開發商用較低的遊戲成本來打造出一個近似 3D 的遊戲環境。
簡單來說,本篇就是一個遊戲科普文,分享一些關於 2D, 3D, 2.5D 的一些概念,
有興趣的歡迎閱讀全文
Medium
Not just a pretty game — 2D, 3D, 2.5D??
放大檢視 2D 遊戲與 3D 遊戲的差異,事情也許不如你想得單純。
ref: https://git.kernel.org/pub/scm/linux/kernel/git/netdev/net-next.git/commit/?id=d40ce48cb3a68b54be123a1f99157c5ac613e260
又是一個非常有趣的 kernel patch, 光看標題「af_unix: Replace unix_table_lock with per-hash locks.」就可以感覺到這次的改動很有機會帶來效能上的改變。
過往的 AF_UNIX socket 依賴一個大 lock 來管理 kernel 內所管理的所有 AF_UNIX socket,而這個 patch 就採用基於 hash 的方式創建多個小 lock 來個別管理,光用直覺都覺得整體效能會有進步的空間。
不過要特別注意的是本 patch 修改的只有 AF_UNIX socket 這類型的服務,所以採取 TCP 等 socket 依然還是本來的做法。常見使用這種 domain socket 有 containerd, cri-o 等,不過這類型的服務本身就不是 I/O 為主,所以就算改成多 lock 似乎也不會有什麼明顯的幫助。
不知道大家有沒有注意有什麼 I/O 很重的服務預設都會吃 domain socket 的?
有的話不彷使用包含該 patch 版本的 kernel 來測試看看效能是否有顯著的改變
又是一個非常有趣的 kernel patch, 光看標題「af_unix: Replace unix_table_lock with per-hash locks.」就可以感覺到這次的改動很有機會帶來效能上的改變。
過往的 AF_UNIX socket 依賴一個大 lock 來管理 kernel 內所管理的所有 AF_UNIX socket,而這個 patch 就採用基於 hash 的方式創建多個小 lock 來個別管理,光用直覺都覺得整體效能會有進步的空間。
不過要特別注意的是本 patch 修改的只有 AF_UNIX socket 這類型的服務,所以採取 TCP 等 socket 依然還是本來的做法。常見使用這種 domain socket 有 containerd, cri-o 等,不過這類型的服務本身就不是 I/O 為主,所以就算改成多 lock 似乎也不會有什麼明顯的幫助。
不知道大家有沒有注意有什麼 I/O 很重的服務預設都會吃 domain socket 的?
有的話不彷使用包含該 patch 版本的 kernel 來測試看看效能是否有顯著的改變
ref: https://refactoring.guru/design-patterns/
本篇是一個關於重構的教學網站,該網站主要分享重構與設計模式的概念,其中針對設計模式的介紹相對完整與豐富。
網站內從設計模式的基本概念以及設計模式的歷史,大部分人學習設計模式時勢必都聽過所謂四人幫,由 Erich Gamma, John Vlissides, Ralph Johnson, and Richard Helm 四人於 1994 年所發行的書籍 Design Patterns: Elements of Reusable Object-Oriented Software
該書籍介紹了 23 種針對不同問題的設計模式,每個設計模式都是基於物件導向的概念去實作,而這本書可說是設計模式的推手,很多人都是從該本書開始學習設計模式的概念。
註: 之後會再分享一篇文章來探討 20 年後的程式語言特性,還需要過往這些四人幫的設計模式嗎?
網站內最精華的部分大概就屬於程式碼範例的部分,設計模式分為三大類(Creation, Structural, Behavioral),總共收入 22 種不同的設計模式,而這些模式又基於 C++, C#, Go, Java, PHP, Python, Ruby, Swift, TypeScript 這些程式語言來介紹該如何實作。
所以如果對學習設計模式有興趣的話是可以參考參考這個網站,稍微看一下自己習慣的程式語言可以如何撰寫這些設計模式。
至於到底學習設計模式有沒有必要這又是別的議題,但是時間有餘力的情況下多學一些不同的概念其實也會幫助自己去閱讀程式碼,特別是不同的開源專案時能夠幫助你快速理解其設計的可能目的。
本篇是一個關於重構的教學網站,該網站主要分享重構與設計模式的概念,其中針對設計模式的介紹相對完整與豐富。
網站內從設計模式的基本概念以及設計模式的歷史,大部分人學習設計模式時勢必都聽過所謂四人幫,由 Erich Gamma, John Vlissides, Ralph Johnson, and Richard Helm 四人於 1994 年所發行的書籍 Design Patterns: Elements of Reusable Object-Oriented Software
該書籍介紹了 23 種針對不同問題的設計模式,每個設計模式都是基於物件導向的概念去實作,而這本書可說是設計模式的推手,很多人都是從該本書開始學習設計模式的概念。
註: 之後會再分享一篇文章來探討 20 年後的程式語言特性,還需要過往這些四人幫的設計模式嗎?
網站內最精華的部分大概就屬於程式碼範例的部分,設計模式分為三大類(Creation, Structural, Behavioral),總共收入 22 種不同的設計模式,而這些模式又基於 C++, C#, Go, Java, PHP, Python, Ruby, Swift, TypeScript 這些程式語言來介紹該如何實作。
所以如果對學習設計模式有興趣的話是可以參考參考這個網站,稍微看一下自己習慣的程式語言可以如何撰寫這些設計模式。
至於到底學習設計模式有沒有必要這又是別的議題,但是時間有餘力的情況下多學一些不同的概念其實也會幫助自己去閱讀程式碼,特別是不同的開源專案時能夠幫助你快速理解其設計的可能目的。
refactoring.guru
Design Patterns
Design Patterns are typical solutions to commonly occurring problems in software design. They are blueprints that you can customize to solve a particular design problem in your code.
ref: http://blogs.tedneward.com/post/reclaiming-design-patterns/
本週分享了另外一篇探討設計模式與分享相關範例的網站,而今天要分享的也許設計模式有關,不過本文不是宣揚設計模式多好多棒,反而是一個思考文。
本文發表於 2016 年,也就是四人幫著名書籍發行 20 年後的日子,作者想要探討現今的程式語言特性與架構,是否過往的 23 種設計模式都還適用?
這是作者關於設計模式系列文的第一篇文章,實際上沒有探討每個設計模式於現代程式語言的用法與寫法,反而是探討設計模式的歷史與初衷,看完後覺得全文講得非常有趣,非常推薦大家一讀。
以下就幫忙節錄幾個重點
# 到底什麼是模式?
四人幫的書籍也有提到設計模式是一個微妙的藝術與科學,其書籍的最後一章有特別去說明(作者特別說明很少人會讀到最後一章)
1. 本書沒有開創任何新的演算法,沒有任何新的 Coding 技術
2. 相同的也沒有任何新的設計理論,也沒有任何嚴謹的系統設計方式。
3. 整本書就是把一些已知的設計給整理一下,可以說是一個不錯的教學。
4. 一個熟悉物件導向設計的工程師基本上不能從本書中獲得太多新知
作者的朋友甚至說 23 種設計模式就是 23 種指標的用法來戲謔一番XD
千萬不要認為將本書丟給一個新手去學習念一念他們就會功力大增什麼的會了,這跟本不可能。
那到底設計模式有什麼幫助? 四人幫的書籍中是這樣解釋的
1. 希望讀者可以有不同的思維去面對問題
2. 將已知的設計方法給列舉出來並且給予對應名稱
3. 熟悉它們更能夠讓我們改進它們
後來設計模式逐漸火熱,整個業界都在討論設計模式,甚至從四人幫書籍的 23 種設計模式為基礎延伸出各種不同模式,更重要的是整體事情變得更加抽象更加脫離底層。
設計模式不再只是一個設計模式,而是一個語言了,甚至還有所謂的元模式(Meta Pattern),以及反面教材的反向模式(Anti-Pattern)。
接者更可怕的事情就是人們發現到設計模式的火熱可以帶動書籍的銷售,因此各種關於模式的書籍開始被出版,IDE 業者開始探討如何自動產生符合各種設計模式的程式碼,連 UML 與其他設計也都搭上設計模式的風潮。
2000 年左右開始迎來一波反感,愈來愈多的反向討論去思辨模式的存在性與必要性。
直到現今,設計模式這個詞還在,其最初定義的模式名稱也還是被廣泛使用。
四人幫的書籍其實有更精準的去探討為什麼要有設計模式這個概念
1. 設計一套通俗的名稱便於交流與討論
2. 用更高的抽象概念來描述一個設計思路,相對於直接撰寫完整程式碼來說會更適合與同事進行早期討論
3. 理解本書的 23 種的設計模式可以幫助你理解現有系統,能夠更有效率的去面對物件導向設計
4. 設計模式提供一種方式去說明“為什麼”如此設計,而不只是一個單純的結果與用法,其背後的思考邏輯反而是更重要的。
5. 開發一個重複使用的軟體本來就會歷經各種重構,好的設計模式會幫助你決定如何重構,可以讓你重構起來更加有效率。
最後該書籍也有去預言設計模式會衰敗的原因,敘述包含
1. 單純把設計模式當作一個可被重複使用的技術,卻沒有辦法去理解為什麼要使用它是不正確的。
2. 就像看別人寫程式一樣,看別人程式做了什麼很簡單,但是為什麼這麼做非常困難,這也就是設計模式想要解決的問題
3. 學習設計模式是要去理解系統的設計,而不只是單純能動就好
大多數的人看到一個模式就會很著急的去 copy/paste 相關程式碼,能動就好,但是都沒有去思考背後的原因,到底該模式為什麼要這麼做,要解決什麼問題,這麼設計有什麼樣的好處,這樣背後的思緒才是學習設計模式的正確態度。
文章後半部還有一些討論,有興趣的可以繼續觀看
本週分享了另外一篇探討設計模式與分享相關範例的網站,而今天要分享的也許設計模式有關,不過本文不是宣揚設計模式多好多棒,反而是一個思考文。
本文發表於 2016 年,也就是四人幫著名書籍發行 20 年後的日子,作者想要探討現今的程式語言特性與架構,是否過往的 23 種設計模式都還適用?
這是作者關於設計模式系列文的第一篇文章,實際上沒有探討每個設計模式於現代程式語言的用法與寫法,反而是探討設計模式的歷史與初衷,看完後覺得全文講得非常有趣,非常推薦大家一讀。
以下就幫忙節錄幾個重點
# 到底什麼是模式?
四人幫的書籍也有提到設計模式是一個微妙的藝術與科學,其書籍的最後一章有特別去說明(作者特別說明很少人會讀到最後一章)
1. 本書沒有開創任何新的演算法,沒有任何新的 Coding 技術
2. 相同的也沒有任何新的設計理論,也沒有任何嚴謹的系統設計方式。
3. 整本書就是把一些已知的設計給整理一下,可以說是一個不錯的教學。
4. 一個熟悉物件導向設計的工程師基本上不能從本書中獲得太多新知
作者的朋友甚至說 23 種設計模式就是 23 種指標的用法來戲謔一番XD
千萬不要認為將本書丟給一個新手去學習念一念他們就會功力大增什麼的會了,這跟本不可能。
那到底設計模式有什麼幫助? 四人幫的書籍中是這樣解釋的
1. 希望讀者可以有不同的思維去面對問題
2. 將已知的設計方法給列舉出來並且給予對應名稱
3. 熟悉它們更能夠讓我們改進它們
後來設計模式逐漸火熱,整個業界都在討論設計模式,甚至從四人幫書籍的 23 種設計模式為基礎延伸出各種不同模式,更重要的是整體事情變得更加抽象更加脫離底層。
設計模式不再只是一個設計模式,而是一個語言了,甚至還有所謂的元模式(Meta Pattern),以及反面教材的反向模式(Anti-Pattern)。
接者更可怕的事情就是人們發現到設計模式的火熱可以帶動書籍的銷售,因此各種關於模式的書籍開始被出版,IDE 業者開始探討如何自動產生符合各種設計模式的程式碼,連 UML 與其他設計也都搭上設計模式的風潮。
2000 年左右開始迎來一波反感,愈來愈多的反向討論去思辨模式的存在性與必要性。
直到現今,設計模式這個詞還在,其最初定義的模式名稱也還是被廣泛使用。
四人幫的書籍其實有更精準的去探討為什麼要有設計模式這個概念
1. 設計一套通俗的名稱便於交流與討論
2. 用更高的抽象概念來描述一個設計思路,相對於直接撰寫完整程式碼來說會更適合與同事進行早期討論
3. 理解本書的 23 種的設計模式可以幫助你理解現有系統,能夠更有效率的去面對物件導向設計
4. 設計模式提供一種方式去說明“為什麼”如此設計,而不只是一個單純的結果與用法,其背後的思考邏輯反而是更重要的。
5. 開發一個重複使用的軟體本來就會歷經各種重構,好的設計模式會幫助你決定如何重構,可以讓你重構起來更加有效率。
最後該書籍也有去預言設計模式會衰敗的原因,敘述包含
1. 單純把設計模式當作一個可被重複使用的技術,卻沒有辦法去理解為什麼要使用它是不正確的。
2. 就像看別人寫程式一樣,看別人程式做了什麼很簡單,但是為什麼這麼做非常困難,這也就是設計模式想要解決的問題
3. 學習設計模式是要去理解系統的設計,而不只是單純能動就好
大多數的人看到一個模式就會很著急的去 copy/paste 相關程式碼,能動就好,但是都沒有去思考背後的原因,到底該模式為什麼要這麼做,要解決什麼問題,這麼設計有什麼樣的好處,這樣背後的思緒才是學習設計模式的正確態度。
文章後半部還有一些討論,有興趣的可以繼續觀看
ref: https://jpetazzo.github.io/2021/11/30/docker-build-container-images-antipatterns/
本篇文章分享的是建置 Container 中的 Anti-Patterns,不講哪些好反而探討哪些不好。
文內列舉了不同的主題,包含
1. Big images
- All-in-one mega images
- Data sets
2. Small images
3. Rebuilding common bases
4. Building from the root of a giant monorepo
5. Not using BuildKit
6. Requiring rebuilds for every single change
7. Using custom scripts instead of existing tools
8. Forcing things to run in containers
9. Using overly complex tools
10. Conflicting names for scripts and images
以下針對內文幾個部分摘錄一下為什麼作者認為是個不好的模式
# Small Images
Image 小本身不是什麼問題,但是有時候過度追求容量會使得一些常用有幫助的工具沒有辦法於容器內執行,這可能會導致未來要除錯時要花費更多的時間去處理,可能要研究如何重新安裝該工具等。
作者有強調這個議題是非常看環境與需求的,有些情況可能團隊根本不需要進入到容器內去執行 shell 來處理,有些可能會需要到容器內執行 ps, netstat, ss 等指令來觀察不同狀態。
作者推薦可以使用 gcr.io/distroless/static-debian11 這個 image 做為基礎然後將其之間的 busybox 給複製環境中,至少確保有基本工具可以使用
# Not using BuildKit
BuildKit 是 docker build 的新版建置方式,相對於舊版方式來說 Buildkit 提供了更多功能,譬如平行建置,跨平台建置甚至效能上也會比過往的更好。
為了讓舊有使用者可以無痛轉移,所以 BuildKit 完全相容既有的 Dockerfile 的語法,所以切換方面是完全無腦的。
目前新版的 Docker Desktop 基本上已經預設採用 BuildKit 來進行建置,不過某些系統譬如 Linux 的環境下,還是需要透過設定環境變數來啟用這個功能,譬如 DOCKER_BUILDKIT=1 docker build . 等方式來建置。
此外透過 BuildKit 建置的產生結果跟過往不同,所以只要看建置結果的輸出就可以判別自己是否使用 BuildKit。
剩下的8個項目就留給有興趣的讀者自行閱讀
本篇文章分享的是建置 Container 中的 Anti-Patterns,不講哪些好反而探討哪些不好。
文內列舉了不同的主題,包含
1. Big images
- All-in-one mega images
- Data sets
2. Small images
3. Rebuilding common bases
4. Building from the root of a giant monorepo
5. Not using BuildKit
6. Requiring rebuilds for every single change
7. Using custom scripts instead of existing tools
8. Forcing things to run in containers
9. Using overly complex tools
10. Conflicting names for scripts and images
以下針對內文幾個部分摘錄一下為什麼作者認為是個不好的模式
# Small Images
Image 小本身不是什麼問題,但是有時候過度追求容量會使得一些常用有幫助的工具沒有辦法於容器內執行,這可能會導致未來要除錯時要花費更多的時間去處理,可能要研究如何重新安裝該工具等。
作者有強調這個議題是非常看環境與需求的,有些情況可能團隊根本不需要進入到容器內去執行 shell 來處理,有些可能會需要到容器內執行 ps, netstat, ss 等指令來觀察不同狀態。
作者推薦可以使用 gcr.io/distroless/static-debian11 這個 image 做為基礎然後將其之間的 busybox 給複製環境中,至少確保有基本工具可以使用
# Not using BuildKit
BuildKit 是 docker build 的新版建置方式,相對於舊版方式來說 Buildkit 提供了更多功能,譬如平行建置,跨平台建置甚至效能上也會比過往的更好。
為了讓舊有使用者可以無痛轉移,所以 BuildKit 完全相容既有的 Dockerfile 的語法,所以切換方面是完全無腦的。
目前新版的 Docker Desktop 基本上已經預設採用 BuildKit 來進行建置,不過某些系統譬如 Linux 的環境下,還是需要透過設定環境變數來啟用這個功能,譬如 DOCKER_BUILDKIT=1 docker build . 等方式來建置。
此外透過 BuildKit 建置的產生結果跟過往不同,所以只要看建置結果的輸出就可以判別自己是否使用 BuildKit。
剩下的8個項目就留給有興趣的讀者自行閱讀
ref: https://matduggan.com/mistakes/
本文是作者踩過的各種 Infrastructure 雷,希望讀者能夠避免這些雷。
總共有幾大類,分別
1. Don't migrate an application from the datacenter to the cloud
2. Don't write your own secrets system
3. Don't run your own Kubernetes cluster
4. Don't Design for Multiple Cloud Providers
5. Don't let alerts grow unbounded
6. Don't write internal cli tools in python
其中第六點簡短扼要,大概就是「沒有人知道如何正確地去安裝與打包你的 python apps, 你真的要寫一個內部的 python 工具就給我讓他完全跨平台不然就給我改用 go/rust, 不要浪費生命去思考到底該如何安裝那些東西」
這讓我想到你的 Python 跟我的 Python 每次都不一樣,有已經不支援的 python 2.x, 還有各種可能會互相衝突的 python 3.x....
本文是作者踩過的各種 Infrastructure 雷,希望讀者能夠避免這些雷。
總共有幾大類,分別
1. Don't migrate an application from the datacenter to the cloud
2. Don't write your own secrets system
3. Don't run your own Kubernetes cluster
4. Don't Design for Multiple Cloud Providers
5. Don't let alerts grow unbounded
6. Don't write internal cli tools in python
其中第六點簡短扼要,大概就是「沒有人知道如何正確地去安裝與打包你的 python apps, 你真的要寫一個內部的 python 工具就給我讓他完全跨平台不然就給我改用 go/rust, 不要浪費生命去思考到底該如何安裝那些東西」
這讓我想到你的 Python 跟我的 Python 每次都不一樣,有已經不支援的 python 2.x, 還有各種可能會互相衝突的 python 3.x....
matduggan.com
Don't Make My Mistakes: Common Infrastructure Errors I've Made
One surreal experience as my career has progressed is the intense feeling of deja vu you get hit with during meetings. From time to time, someone will mention something and you'll flash back to the same meeting you had about this a few jobs ago. A decision…
ref: https://linuxconfig.org/how-to-propagate-a-signal-to-child-processes-from-a-bash-script
基本 Bash 介紹文,探討 trap 的用法,如何於不同的情況下正確攔截 SIGNAL,同時如果 script 中運行的程式有無背景執行
會有什麼差異,推薦給對 Bash 不熟的讀者閱讀重新複習
基本 Bash 介紹文,探討 trap 的用法,如何於不同的情況下正確攔截 SIGNAL,同時如果 script 中運行的程式有無背景執行
會有什麼差異,推薦給對 Bash 不熟的讀者閱讀重新複習
LinuxConfig
How to propagate a signal to child processes from a Bash script
Learn how to terminate child processes in Bash when receiving signals. Master traps, wait command, and process groups to handle signals effectively.
ref: https://emmer.dev/blog/docker-shell-vs.-exec-form/
Docker 基本介紹文,不知道常寫 Dockerfile 的讀者能不能分清楚 Dockerfile 內 Shell 與 Exec 兩種格式的差異
RUN, CMD, ENTRYPOINT 等指令都同時支援這兩種格式
Shell 格式就是 RUN command arg1 arg2 arg3 這種直接描述的格式,而 Exec 則是用 [] 包起來,每個參數單獨敘述,譬如
RUN ["command", "arg1", "arg2", "arg3"] 等。
本篇文章推薦 RUN 指令採取 Shell 格式而 CMD/ENTRYPOINT 都應該採用 EXEC 格式。
如果自己不清楚差異以及沒有想法為什麼平常自己這麽寫的話可以參考全文
Docker 基本介紹文,不知道常寫 Dockerfile 的讀者能不能分清楚 Dockerfile 內 Shell 與 Exec 兩種格式的差異
RUN, CMD, ENTRYPOINT 等指令都同時支援這兩種格式
Shell 格式就是 RUN command arg1 arg2 arg3 這種直接描述的格式,而 Exec 則是用 [] 包起來,每個參數單獨敘述,譬如
RUN ["command", "arg1", "arg2", "arg3"] 等。
本篇文章推薦 RUN 指令採取 Shell 格式而 CMD/ENTRYPOINT 都應該採用 EXEC 格式。
如果自己不清楚差異以及沒有想法為什麼平常自己這麽寫的話可以參考全文
Christian Emmer
Docker Shell vs. Exec Form | Christian Emmer
The RUN, ENTRYPOINT, and CMD, instructions all have two different forms they can be written in, and those forms change how each of those instructions behaves.