我的 Rust 之旅,以及如何學習 Rust
Rust 越來越受歡迎。通過 2022 年 StackOverflow 開發者調查,我們可以看到很多人對 Rust 感興趣。
Rust 已經連續 7 年成為最受喜愛的編程語言,87% 的開發者表示他們想繼續使用 Rust。
Rust 也與 Python 并列成為最受期待的技術,TypeScript 緊隨其后。
最受期待
圖片
最受喜愛 vs 最令人憎惡
圖片
但 Rust 有一定的學習曲線。
這讓我想分享我的 Rust 學習之旅,為什么選擇 Rust, 以及如何學習 Rust。
接觸 Rust
我在 Rust 剛剛發布的時候就聽說過它,我的印象是它是一種系統編程語言,可以替代 C/C++, 而且足夠安全。但是我當時并沒有真正學習和使用它 (我只寫過 "Hello World"!)。
回到 5 年前,我正在領導公司基礎設施向云原生架構的轉型。
我需要構建一個完全基于 Prometheus 的監控棧,來替換公司內部使用了 10 多年歷史的一些監控軟件,如 Nagios、Zabbix 和 Graphite。
是的,你沒有看錯,我們使用了很多監控軟件。這主要出于幾個原因:
- 單一的軟件無法滿足所有需求
- 團隊分散,大多數時候引入新軟件只是為了滿足特定需求,而不是解決問題
總之,這是一些歷史原因。
從我之前提到的情況來看,我們有一套自研的監控軟件,歷史超過 10 年,可以看出,我們的基礎設施迭代速度很慢。
因為我們有自己的物理數據中心,這也導致了很多舊機器在我們的服務器上沒有更新過。(這也是我后來使用 Rust 的一個原因)
我首先在一個新啟用的小數據中心 (約 400 臺機器) 替換了監控棧,效果很好。使用 Prometheus 完成了該小數據中心所有服務器及其運行的各種服務的監控。我們還在 Grafana 上創建了儀表板,并通過 Alertmanager 創建了告警通知。
后來,我在兩個數據中心推廣了這種轉型,整體來說比較順利,包括 Kubernetes 的監控也是在這個過程中完成的。
但是當它實施在最后一個數據中心時,我遇到了最大的挑戰。
node_exporter 無法在某些機器上啟動,一些機器在運行一段時間后會自動崩潰。
我開始調查這個問題。對于自動崩潰的問題,我暫時通過添加一個重啟腳本來修復了。
我主要關注的是為什么 node_exporter 無法啟動。我發現這部分機器的操作系統是 CentOS 5, 內核是 2.6.18。
我發現社區中已經有類似的問題: https://github.com/prometheus/node_exporter/issues/691
與此同時,我也注意到 Go 文檔明確指出 CentOS 5 不受支持,需要 2.6.32 或更高版本的內核。
(我忘了在我當時排查問題時,所需要的依賴的最低版本,但通過 Web archive[1],我看到 2017 年需要的最低內核版本是 2.6.23)
經過一些搜索,我也看到了類似 "如何在 CentOS 5.9 上安裝 Go 1.1" 的內容,但同時也提到了一些已知的問題。
所以我不打算繼續在這里浪費時間。
我想自己換個技術棧重新實現一個類似 node_exporter 的工具,也就很自然的可以解決上述自動崩潰的問題了。
經過一番權衡,最終,我使用 Rust 實現了一個類似 node_exporter 的工具,并完成了監控系統的升級和轉型。
這就是我開始在生產環境中使用 Rust 的起點。
接下來,讓我介紹為什么我選擇 Rust。
圖片
為什么選擇 Rust
我上面介紹了一些背景。當時最簡單的選擇應該是 Python, 它足夠簡單,生態也很豐富。與此同時,我在 Python 開發也有多年經驗,我可以快速構建所需的工具。
當時我不選擇 Python 的原因是:
- 并非所有這些機器都有 Python 環境,Python 版本也不盡相同。我被要求盡量不要修改這些機器上的環境;
- 因為我可能會對我開發的新工具做一些修改,所以后續的分發可能不太方便;
然后我重新思考了我的目標:
- 可以編譯成二進制可執行文件,方便分發和部署。我使用 Ansible 進行統一部署。
所以更合適的選擇是 C/C++/Rust。
我在 C 開發上有更多經驗,C++ 也有一些經驗。對于我的第一個需求,上述三種語言都可以很輕松地實現。
當大多數人比較 Rust 和 C/C++ 時,他們在比較它們的性能和安全性。
而在當時我的用例中,我認為在其他兩種語言中的結果不會比 Rust 差,盡管這也是一個考慮因素。而且當時我剛開始學習 Rust, 我的 C 實現可能會比 Rust 更好。
但我想挑戰自己,嘗試一些新事物,而且就 Prometheus 監控而言,C/C++ 相關的生態并不太活躍。另一點是我認為 Rust 將有很大的發展前景。
所以最終我選擇了 Rust。
我是如何學習 Rust 的
Rust 并不簡單,它與其他語言也有一些不同,所以在其他語言中有效的一些做法在 Rust 中可能無法奏效。
由于我有一個具體的問題需要解決,我需要實現一個 node_exporter 來完成監控棧的轉型。所以我是通過 "邊學邊做" 的方式來學習 Rust 的。
我首先快速瀏覽了以下內容:
- The Rust Programming Language[2]: 這本書非常完整,我一開始并沒有完全讀完。取而代之的是,使用它來理解 Rust 的主要概念和一些用法。
- Rust By Example[3]: 這里有很多示例,你也可以通過練習這些示例來增加對 Rust 的熟悉度;
- Rust std lib docs[4]: 標準庫文檔,快速概覽,了解一些關鍵詞、模塊等。但最初沒必要完整閱讀。
通過這種方式,我很快就實現了一個基本的 node_exporter 版本。然后繼續迭代并應用到生產環境,完成了 Prometheus 監控棧的構建。
后來,我繼續在 Rust 中實現了一些小工具,學習了它的最佳實踐,并學習了一些用 Rust 實現的開源項目,以增加我的 Rust 經驗。
推薦一些 Rust 學習資源
現在有很多 Rust 的學習資源。除了我前面列出的,我還推薦以下免費內容:
- Take your first steps with Rust - Training | Microsoft Learn[5]
- rust-lang/rustlings: 一些小練習,讓你適應閱讀和編寫 Rust 代碼!
視頻:
- Rust Crash Course | Rustlang - YouTube[6]
- Rust Tutorial - YouTube[7]
- Rust for Beginners - YouTube[8]
總結
這就是我的 Rust 學習之旅的開始,它一直在繼續。
盡管我仍然持續的關注云原生和 Kubernetes 相關的技術,并且我寫 Go 語言更多,但我也仍然會用 Rust 編寫一些工具,并在 WebAssembly 中使用 Rust。
參考資料
[1]Web archive: https://web.archive.org/web/20170916192117/https://github.com/golang/go/wiki/MinimumRequirements
[2]The Rust Programming Language: https://doc.rust-lang.org/stable/book/
[3]Rust By Example: https://doc.rust-lang.org/rust-by-example/
[4]Rust std lib docs: https://doc.rust-lang.org/std/index.html
[5]Microsoft Learn Rust path: https://learn.microsoft.com/en-us/training/paths/rust-first-steps/
[6]Rust Crash Course: https://www.youtube.com/watch?v=zF34dRivLOw&utm_source=blog.moelove.info&utm_medium=content
[7]Rust Tutorial: https://www.youtube.com/watch?v=T_KrYLW4jw8&list=PLzMcBGfZo4-nyLTlSRBvo0zjSnCnqjHYQ&utm_source=blog.moelove.info&utm_medium=content
[8]Rust for Beginners: https://www.youtube.com/playlist?list=PLlrxD0HtieHjbTjrchBwOVks_sr8EVW1x&utm_source=blog.moelove.info&utm_medium=content