我們爲什麼選Rust重寫核心服務?

{"type":"doc","content":[{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"兩年多來,Kraken的Core Backend 團隊一直在用Rust來對原本使用PHP編寫的服務進行現代化改造,同時還在用Rust開發新產品、擴展功能集合並支持不斷增長的加密貨幣交易活動。"}]},{"type":"heading","attrs":{"align":null,"level":2},"content":[{"type":"text","text":"重寫核心服務"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"針對一個問題從頭開始構建一個解決方案往往會給我們帶來另一個問題。當原來的開發人員沒有參與新解決方案的設計和實現時,這種情況尤其常見。還有一些情況下,新的方案理論上更好用,但是做起來費的時間太久,拖慢了系統響應需求的進程。雖然我們可以設法避免這些常見的陷阱,但不管怎樣我們在重寫之前都要三思而後行。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"2011年Kraken成立時,PHP提供了一個兼顧執行安全性、速度和生產力的選項。彼時我們用PHP構建了那麼多功能,實在令人印象深刻。但多年以來,Kraken取得了長足發展,而PHP代碼庫開始變得難以擴展,很難共享知識並安全地做出較大的更改。這些核心服務處理的是分佈式數據存儲、加密和信息安全方面的事宜,這類技能組合在PHP開發人員中並不常見,他們通常更專注於在現有的Web和電商框架上構建內容。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"總體而言,Kraken已進入了爆發式增長階段,代碼庫和工具都需要跟上腳步。考慮到這一點,動態類型的編程語言非常適合早期的構建階段,但隨着代碼庫的擴張和工程師人數的增加,代碼維護起來愈加困難。強類型提供了保證(和格式化的文檔),從而加快了開發速度,讓單個代碼庫可以支持更多開發人員。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"我們重寫核心服務的主要目標是:"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"numberedlist","attrs":{"start":1,"normalizeStart":1},"content":[{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":1,"align":null,"origin":null},"content":[{"type":"text","text":"儘可能保持系統安全性"}]}]},{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":2,"align":null,"origin":null},"content":[{"type":"text","text":"即使系統變得越來越大,也讓系統更易維護、更加健壯"}]}]},{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":3,"align":null,"origin":null},"content":[{"type":"text","text":"獲得更好的性能"}]}]}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"早在2018年初,我們就已經意識到,繼續使用PHP並不是實現這些目標的最佳長期解決方案。"}]},{"type":"heading","attrs":{"align":null,"level":2},"content":[{"type":"text","text":"爲什麼選擇Rust?"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"2018年初,Kraken已經有了用Go和C++編寫的生產服務。儘管Rust提供了出色的性能、安全性和現代語言結構,但將其作爲重寫核心服務的語言選項還是一種賭注。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"Kraken非常注重安全性。因此,我們不想讓C++代碼參與用戶輸入。即使是世界上最好的C++團隊(如構建Windows™或Chrome™的團隊),做出來的代碼中也有約70%的CVE來自於內存安全性問題——諸如釋放後使用、緩衝區溢出、兩次釋放等,這可能會導致內存訪問控制和特權升級攻擊。可是在Java、Go或Rust等語言中,這些漏洞是被徹底堵死的。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"儘管Go可以抵禦這類漏洞,但它不提供諸如泛型或求和類型之類的現代編程特性,結果會導致數據建模或重複問題。Kotlin提供了一個更復雜的類型系統,並且像Go一樣,它簡化了異步編程,但是帶有一個承載諸多遺產的Java生態系統。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"再來看Rust。它的可靠性和性能讓它在加密貨幣和區塊鏈項目中取得了成功。一些Kraken工程師開始拿它做實驗,並視其爲構建可以長期滿足Kraken後端需求的系統的一種選項:性能匹敵C++、現代語言構造有助於準確地建模業務邏輯和錯誤用例、對異步編程有着一流支持、編譯時線程安全,還有充滿活力的生態系統。Rust的價值主張和社區取得的成功促使Kraken在2018年中開始用Rust來重寫核心服務。"}]},{"type":"heading","attrs":{"align":null,"level":2},"content":[{"type":"text","text":"兩年後"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"Core Backend團隊成績斐然,如今同時負責現代化的Rust核心服務和仍在重寫中的舊版PHP服務。同時,其他一些團隊已經成功應用了Rust:Kraken的期貨團隊加入了我們的行列,他們獨立地將所有後端堆棧遷移到了Rust上;Cryptowatch選擇了Rust用於桌面應用程序;Kraken將冷存儲系統遷移到Rust;Kraken Digital Asset Bank也在用Rust構建。這種語言本身也有了顯著改進,讓異步網絡服務編寫起來更容易了。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"總的來說,我們一直很忙:Core Backend團隊的Rust git存儲庫保存了約500000行代碼,比PHP更多,儘管許多特性仍是在PHP中實現的。部分原因是我們用Rust編寫了更多的基礎代碼、測試和全新的特性,另一個因素是PHP與其他動態類型化的編程語言一樣,不需要類型化結構定義(包括錯誤),而Rust代碼中這種定義佔據了很大一部分。在PHP中沒有那些顯式結構,這讓重寫過程幾乎成了一次逆向工程的演練。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"從策略上講,我們決定在Rust中重寫完全相同的功能:由於所有PHP服務都是無狀態的,因此可以輕鬆地將邏輯(逐個端點地)移植到Rust。這樣一來,新招募的團隊就可以獲取更多有關底層系統的知識,並可以進行增量部署或輕鬆回滾。我們已經構建了一個全面的集成測試套件,PHP和Rust服務都需要通過它的測試以確保行爲是相似的。將功能移植到Rust後,可以更輕鬆、更安全地擴展。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"儘管性能提升不是重寫的主要目標,但我們很高興看到Rust提供了開箱即用的驚人速度。我們Tokio驅動的RPC服務器並未做過特別優化(儘管我們通常對內存使用模式非常謹慎),結果每個實例可以支持150k請求\/秒的吞吐量,同時將p99.9延遲保持在3ms以下。系統的運行速度取決於最慢的部分,雖然我們的PHP核心服務不是Kraken的唯一瓶頸,但它們的IO性能要比Rust的低一些,並且對負載更敏感。在將整個端到端路徑遷移到Rust並消除瓶頸之後,我們的客戶應該能看到巨大的性能提升。同時,我們會將端點遷移至Rust、重新設計數據庫和擴展服務,盡一切努力來提高性能和可靠性。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"image","attrs":{"src":"https:\/\/static001.geekbang.org\/infoq\/46\/46bb477ace4794877f5bab5c12f1ff6b.webp","alt":null,"title":null,"style":[{"key":"width","value":"75%"},{"key":"bordertype","value":"none"}],"href":null,"fromPaste":true,"pastePass":true}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":"center","origin":null},"content":[{"type":"text","text":"這是將一個端點移植到Rust時響應時間的變化"}]},{"type":"heading","attrs":{"align":null,"level":2},"content":[{"type":"text","text":"用於應用程序服務的Rust"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"Rust通常被宣傳爲一種出色的系統編程語言,非常適合底層任務、命令行實用程序和網絡服務(例如負載均衡器)。許多人認爲Rust的複雜性對於一般的業務邏輯來說是很大的劣勢,Rust的就業市場也太小了,以至於公司很難使用這種語言來完成諸如構建用戶管理系統或REST API之類的常見任務。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"Rust 非常適合系統編程,但我們也一直用它來做一些通常用更高級別語言(例如Java、Ruby或TypeScript)實現的應用程序服務。正確性在Kraken中絕對至關重要,而Rust的現代語言結構讓我們更容易編寫正確而健壯的代碼。Rust缺少垃圾收集的特性在編寫不需要“關心”內存管理的通用邏輯時往往被認爲是一種劣勢,但在實踐中這並不是問題,因爲我們正在構建的是無狀態服務,而存儲循環數據從來都不是問題。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"但Rust需要精確度,我想說的是這是這種語言最大的好處:它的顯式性(受其強大的類型系統支持)帶來了容易審查且運行時可靠的表達性代碼。在這方面,我認爲Rust與Java和其他同類語言比起來既有更低級別的優勢,也有更高級別的好處。Core Backend團隊還開發了其他一些技術服務,例如負載均衡器或服務監視流,它們需要良好的性能,而且使用Rust讓我們不必在系統和應用程序邏輯語言之間來回切換,還可以重用庫和模式,實踐中這非常方便。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"隨着團隊和代碼庫的成長,有效審查代碼的能力變得至關重要。Rust可以讓行爲清晰且隔離地表現出來,這意味着我們無需過多考慮系統的其他部分——只研究當前函數往往就足夠了。在審查代碼時,我們會看到一個diff(更改的行和周圍的上下文),雖然可能需要更多時間來深入研究更改,但更快的審覈可以讓開發人員迅速獲得反饋,這是很好的驅動力。在Rust中可以肯定的是,編譯後的更改不會出現數據爭用(併發錯誤的主要來源之一)和內存安全問題(我們的大多數代碼都用的是safe Rust)。我可以很容易地發現可能導致問題的函數(當沒有其他選擇時,Rust會中止執行)、發現無用的內存副本,並收集開發人員的意圖。Rust的linter、Clippy有助於統一代碼樣式,帶來了更符合習慣、更一致的代碼庫。最近兩年來我審查了成千上萬的合併請求,Rust爲我帶來了比其他主流編程語言都更高的信心。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"Rust是一種大型而複雜的語言,開發人員很容易在細節上迷失方向。還好我們沒必要爲了保持效率而瞭解所有的細節。根據我們的經驗,Rust是一種非常有生產力的語言:它具有出色的工具鏈,可以迫使我們徹底建模問題、節省寶貴的調試時間、解決潛在的生產問題,並且非常便於代碼重用(這是生產力的倍增器)。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"最後,我覺得有必要澄清“fighting the borrow checker”這種說法,它把Rust編譯器說成了一種怪物:以我的經驗,這種情況主要發生在初學者中,另外就是很少一部分人試圖對代碼進行細節優化或探索極限情況時容易碰到它。大多數有經驗的Rust開發人員很清楚怎樣建模代碼可以避免在編譯器上浪費時間處理各種問題,並且一眼就能發現那些反模式,就像大多數人都知道如何正確地駕駛汽車來避免事故一樣。"}]},{"type":"heading","attrs":{"align":null,"level":2},"content":[{"type":"text","text":"建立一個Rust團隊"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"在這兩年中,我們已經構建了現代化的Kraken後端技術棧的基礎、將現有功能重寫爲Rust、構建了新的Rust服務和功能,還組建了一支由30多名工程師組成的Core Backend團隊。一些開發人員一開始應聘的是PHP開發,但加入團隊後學會了Rust。值得一提的是,Kraken是一家全球化的遠程優先公司,Core Backend團隊的工程師來自15個國家,工作地點分佈在12國境內。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"Rust吸引了很多熱情的開發人員,他們通常對系統編程、分佈式系統或加密技術感興趣。我們目前的Core Backend工程師中有很大一部分是Rust愛好者,他們通過各種Rust在線資源發現了我們的招聘機會,包括Reddit和This Week In Rust(它們多次推薦了我們的招聘信息,謝謝!)。因爲這些社區,人們很久以前就知道Kraken在招聘Rust開發人員了。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"我們的Core Backend團隊成員需要在競爭激烈的市場中應對具有挑戰性的技術和業務問題,在世界各地進行遠程工作,而我們提供了與地理位置無關的高額基本薪酬和慷慨的期權。此外,團隊成員幾乎所有時間都在編寫Rust。這兩年來應聘的衆多候選人很滿意這樣的條件,使我們得以組建世界一流的工程團隊。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"我們一開始也接納對Rust感興趣但缺乏上手經驗的開發人員,但我們很快意識到這並不總是可行的,並且學習曲線因人而異。有趣的是,Rust吸引了來自各種語言的開發人員,這些語言差異巨大,有的是靜態類型,有的是動態類型。很難說來自哪些背景的人們學習起來會更困難,但有些人在幾周內就可以入門,而另一些在幾個月後仍然難以上手。習慣依賴文檔並且對語義有系統理解的人們最有可能快速成長。像許多快速發展的公司一樣,我們需要新員工迅速投入實際問題的工作中。因此,我們要求應聘者提供可證明的Rust經驗,並且需要通過測試,檢驗他們是否全面瞭解Rust的類型系統以及標準庫和常見板條箱的實用知識。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"我相信使用Rust可以幫助人們成爲更好的開發人員,因爲它推動人們重視簡潔的設計和精確度。但光是瞭解Rust並不能讓我們成爲出色的工程師。我們看到許多候選人對Rust都很滿意,但他們在構建後端系統方面經驗有限。我們僱用了許多有着巨大潛力的初級開發人員,因爲在組建團隊時,平衡是成功的關鍵。經驗豐富的開發人員往往是出色的導師:他們通常擁有簡化事物的智慧,知道不應該過於信任自己,也明白該如何最大限度地發揮自身對業務線的影響。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"考慮到這種語言可以解決C++、Java或Go的許多痛點,我希望有更多經驗豐富的開發人員進入Rust的世界。我之前從事Java開發工作有十多年的經驗,向來對過度炒作的新技術保持合理的懷疑態度。但現在我並不想回去用一種素質不及Rust的語言——特別是Rust讓我專注於手頭的模塊,而無需不斷考慮許多隱式不變式,例如某個代碼段是否是從另一個線程調用的,而我需要讓它保持線程安全之類的問題。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"我們希望隨着越來越多的公司(從Discord和Deliveroo到亞馬遜和微軟)在Rust上加大籌碼,我們可以幫助業界發出一個信號,告訴大家Rust的工作機會有很多,並且花時間學習這種語言不會浪費精力。許多經驗豐富的開發人員更願意留在他們擅長的技術棧中,但是有些人可能還是喜歡嘗試擺脫自己的舒適區並挑戰自我。"}]},{"type":"heading","attrs":{"align":null,"level":2},"content":[{"type":"text","text":"Rust很偉大,但不是完美的!"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"Rust讓我們能夠構建許多運行良好的高性能生產代碼。我們有一個龐大的團隊,成員分別負責後端中各種差異巨大的部分。大部分代碼都非常健壯:我們還沒有經歷過Rust核心服務的崩潰或恐慌(大致相當於運行時異常)。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"總體而言,我可以說我們只遇到過業務邏輯問題、配置錯誤問題,並且遇到了一個一般性的性能問題,其與在musl libc上運行的,具有特定內核配置的Tokio相關,不過我們用perf工具定位後就輕鬆修復了。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"儘管這種語言的確很棒,但也有一些衆所周知的侷限困擾着我們。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"bulletedlist","content":[{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"理想情況下,每個易錯函數將具有自己的錯誤枚舉來精確捕獲其錯誤並處理,但實際上它過於冗長,結果導致了不太精確的錯誤特徵(trait)或每個模塊使用一個枚舉。Rust語言在這方面可以做得更好:有一些倡議和宏對此做了探索。"}]}]},{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"在設計庫箱時,缺乏 specialization 和通用關聯類型(generic associated types,GAT)可能會帶來很大限制。"}]}]}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"我們一直在搭配使用async Rust與Future組合器,並在async\/await支持進入nightly版本後立刻開始使用它。這項功能非常棒,使我們能夠使用Tokio構建大規模的併發應用程序。我們並不需要花費太多時間來讓我們的服務器處理超過10K的併發連接或實現背壓。但它還是有一些改進餘地:"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"bulletedlist","content":[{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"與Rust的大多數部分不同,async函數看起來有點像無害的常規函數,但它們可能不會完全執行(更確切地說,它們返回的Future可能不會被輪詢完成)。處理清理邏輯時要格外注意,因爲邏輯本身目前不能異步。支持異步drop的提案有望提供一個解決方案。如何讓這種問題更清晰可見仍然懸而未決;可以讓屬性清楚地表明Future可以安全地取消,否則就讓一個lint警告提醒我們嗎?"}]}]},{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"儘管現在的情況有所好轉,但異步框架的分裂嚴重損害了生態系統。如果Rust能夠提供一種構造,允許任務調度子系統被抽象出來而無需額外開銷,那會是很大的改進。這樣人們就可以選擇自己喜歡的執行器,並將任務執行器傳遞給庫,或者自行驅動Future。"}]}]},{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"靜態初始化任務執行器的當前設計使開發人員簡單地拉出一個依賴項就能錯誤地運行多個執行器。線程局部變量的普遍使用加大了調試的困難。"}]}]},{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"如果能夠在特徵中設計異步函數而無需裝箱,並能引用結果類型,肯定會成爲一項重大的性能改進。"}]}]},{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"我們也希望看到圍繞io-uring的工作帶來巨大的性能改進,同時不至於造成生態系統的進一步分裂。"}]}]}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"在工具鏈方面,Cargo和Rustup大大簡化了設置和編譯項目的工作。RustAnalyzer帶來了顯著的改進,並提供了很棒的IDE體驗。編譯時間總體變短了:想要更短也是可以的,但考慮到增量構建和sccache,現在這樣也不錯了。優化構建確實速度很慢,但總體來說爲了性能和安全性這是很小的代價。具有許可支持的私有Cargo註冊表顯然會助力Rust的企業應用。我們一直在使用git依賴項,但缺乏語義版本控制的支持讓更新過程變得很痛苦。市面上有一些開源的Cargo註冊表可用,但Cargo本身不支持訪問令牌或憑證。我們很樂意贊助這項工作。"}]},{"type":"heading","attrs":{"align":null,"level":2},"content":[{"type":"text","text":"Kraken熱愛Rust"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"總的來說,Rust非常成熟,並且它的大多數痛點在其他主流語言也多多少少會存在。Rust讓代碼重用起來非常輕鬆,並使我們能夠在不犧牲性能的情況下安全地應對快速變化的大型代碼庫。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"對我們而言,使用Rust不再是一項實驗或賭注。這是我們正在構建的可靠技術,並且Core Backend團隊正在尋找熟練的工程師。不得不提的是我們團隊在Rust之外的價值觀:Core Backend團隊利用Rust的工程價值和受Netflix影響的高性能團隊文化,進一步擴展了Kraken的文化,以及對我們使命的承諾。我們相信超越代碼的工程文化,相信自主權。我們拒絕傲慢自大。我們不斷相互學習。不在一個辦公室工作讓我們面臨更大的挑戰,而積極進取的人們可以成爲優秀的工程師,能夠自我驅動、技術精湛,能夠在需求和技術解決方案之間架起橋樑,從而自主前行。我們既看重天賦也看重努力,同時在工作與生活之間保持了良好的平衡,維持健康的體魄。我們關心自己在構建的事物,並全力幫助我們的隊友取得成功。我們意識到完美是出色成果的敵人(衆所周知,Rust開發人員都是完美主義者!😉)。最後,我們相信團隊會不斷自我完善:如果技術或組織方面出現問題,我們會解決它們。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"我們的Core Backend團隊目前在招募中級和高級後端工程師以及站點可靠性工程師,這些人員可幫助支持和改善我們的運營、工具鏈和CI。我們還在聘請測試工程師來幫助我們使用Rust和Cucumber測試API。"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"Kraken的其他團隊也一直在尋找優秀的工程師,他們選擇Rust作爲構建強大和快速響應系統的首選工具:"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"bulletedlist","content":[{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"KrakenDigitalAssetBank是一家特殊用途的託管機構,使用Rust建立現代銀行和支付系統,正在尋找高級工程師;"}]}]},{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"Kraken期貨團隊兩年來一直使用Rust作爲主要語言來構建衍生品交易服務,他們以前用的是Java和Kotlin,正在尋找後端工程師;"}]}]},{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"我們的交易技術團隊在建立現貨交易的同時,還使用C++和Rust構建大量服務,並正在招聘後端工程師;"}]}]},{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"Cryptowatch構建了一個輕量級的桌面交易應用程序,他們也在僱用RustGUI開發人員。"}]}]},{"type":"listitem","attrs":{"listStyle":null},"content":[{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"請務必檢查我們的其他開放職位!"}]}]}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"最後,我們想幫助Rust成長。我們已經通過Kraken Grants計劃贊助了一些開源工作(例如iced GUI框架)。我們很樂意贊助Rust項目或相關關鍵項目的個人貢獻者。如果你正在爲Rust生態系統做出重要貢獻並需要資金,請與我們聯繫!同時,RustAnalyzer團隊所做的出色工作給我們留下了深刻的印象,這些工作直接讓整個社區受益,我們將爲該項目捐款5萬歐元!"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"原文鏈接:"}]},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null}},{"type":"paragraph","attrs":{"indent":0,"number":0,"align":null,"origin":null},"content":[{"type":"text","text":"https:\/\/blog.kraken.com\/post\/7964\/oxidizing-kraken-improving-kraken-infrastructure-using-rust\/?fileGuid=C3XtwPgtGkgvxpKj"}]}]}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章