LY Corporation Tech Blog

支持 LY Corporation 和 LY Corporation Group (LINE Plus, LINE Taiwan and LINE Vietnam) 服務,宣傳技術和開發文化。

Terraform for Verda - A journey of Infrastructure as Code for our private cloud

哈囉,我是來自Verda可靠性工程團隊的山下慶将(keke)。在這篇文章中,我想跟各位分享Verda是如何一步步邁向Infrastructure as Code的道路,以及我們對Verda平台的資源(例如虛擬機,負載均衡以及Redis集群)創建與管理上的願景。本文中還會涵蓋一些在使用Terraform作為平台規模程度下,資源創建與管理上所需的工具準備。

本文翻譯自 Terraform for Verda - A journey of Infrastructure as Code for our private cloud (譯者: Eric Huang)

什麼是Verda?

Verda是LINE基於OpenStack的私有雲,這個專案起始於2016年,類似於 Amazon Web Services (AWS) 或 Google Cloud Platform (GCP),這平台提供了開發者各種必要的服務,例如虛擬機,MySQL與CDN:同時,Verda也支援各類包含Kubernetes的Verda Kubernetes Service (VKS)以及Functions的Verda Functions Service (VFS),響應在使用Verda服務上的許多需求。在如此提供的眾多服務之下,留給開發者決定哪些Verda上的服務該被使用,以及該如何構建它們。

並不是每一個LINE提供的產品都部署在Verda之上,但有各項的服務現正託管於Verda平台之上。Verda上已經有超過10萬台虛擬機和超過7萬台實體機正被使用,而且數量每一天都在增加。因為LINE提供的是全球化的服務,Verda當然也提供了在各個區域上的所需功能。

在LINE中,開發者可以不管何時何地,在所支援的區域上,創建及更新他們在開發上所需的各種資源。這使得開發者可以專注在開發本質上,而不用浪費多餘的時間成本去從頭開始租用虛擬機,特地前去資料中心維護機櫃,或者採行基本的監控功能。多虧有了Verda,我們可以在同時兼顧可擴充性下,快速回應當今社會下的習習變遷,並高速地開發我們的產品。

資源是如何被創建與管理的?

相對而言,Verda是一個相當大的私有雲。在我們採行Infrastructure as Code之前,所有Verda平台上的開發者,在創建這些資源時都是百分百純手工,也就是在稱作Verda Dashboard的網頁介面上手動點擊,就如同以下的截圖所示。

在一個LINE典型的專案中,開發者會使用虛擬機或是VKS集群來託管他們的應用服務,並使用Verda object storage (VOS) buckets及CDNs去分佈他們的靜態資源。這些全部的資源都曾經需要手動創建。每一天,開發者都需要登入Verda dashboard,透過手動的方式在介面上執行各種操作,來管理他們開發時所需的資源。當然與公有雲一樣,在Verda上有認證以及權限控管的功能,開發者可以依據權限去管理Verda的專案。

遇到的問題與Infrastructure as Code

我們已經用上述的方式創建Verda上的資源長達六年,而如果包含非Verda資源的話,更超過十年。我們已經這樣做了很長一段時間,而許多的同仁並不認為這會有什麼問題或有任何疏漏。

在雲原生的時代,每個資源的生命週期變得更短,而對資源的需求也更加及時,任何的設定改動也會更加頻繁。所以,如何掌握基礎設施的異動變成軟體開發領域上十分重要的因素。對LINE來說也是如此。這是因為像Verda這樣的私有雲,將會被創建並不斷擴大規模,也將會有指數型成長的資源操作。在此之下,透過互動型的工具例如Verda dashboard一個個創建及管理資源將會造成一些問題及風險發生。當有更多的資源在每一天被生成,修改及刪除時,網頁上的按鈕操作將會是高度沒效率且不安全的方法。而且在網頁上的操作可能不會經過任何的審核流程,也不會有任何資料紀錄資源創建的原因,方式及用途。與團隊成員一同跑安全的軟體開發週期(safe development cycle)時,將會有機會導致多個成員引起的衝突發生。這些操作將不可重現,也存在著人為錯誤的風險。

Infrastructure as Code(IaC)的出現幫助我們解決這些問題,針對傳統的資源創建與管理上的種種問題都能迎刃而解,更幫助開發者僅需要跑一段腳本,就能快速生成一個高度文件化且支援版本控管的資源。由於這些原始碼被存放在版本控制系統中,允許我們能在GitHub上審核任何異動,也因為這些原始碼是一切真相的來源(source-of-truth),更能幫助我們團隊協作。

事實上,關鍵在於如何實現Infrastructure as Code,我們採用的是Hahicorp開發的Terraform。Terraform是業界針對Infrastructure as Code上被廣泛使用的工具之一,更儼然成為業界標準。它通用化的Hashicorp Configuration Language能透過聲明宣告的方式,在不管供應商情況下,管理任何的資源。Terraform能透過它可插拔的插件功能,讓平台提供商向任何的平台添加功能。這使得我們能為了Verda開發與Terraform相容的插件。

該如何開始

在過去,我們已經透過demo,實務教學以及報告等方式,付出許多的心力去呈現Infrastructure as Code的價值以及該如何在我們的專案上被運用。然而,在私有雲上使用Terraform之前(或任何其他Infrastructure as Code的工具),我們必須先做一些事前準備。如果你使用公有雲的話,你不必擔心這些東西因為他們往往都會提供。但如果你採用私有雲的話,你需要額外花時間設計與實作它們。

私有的Terraform registry

即便你使用的是公有雲,在使用Terraform作為內部API或類似用途時,你不會想把這些程式對外公開。同樣地,你不會想對外曝光這些私有的Terraform provider。通常這些provider都可以在Hashicorp'官方的Terraform registry被任何人存取。如果你使用Terraform Cloud,他們也同樣提供registry的功能。然而,這一次我們需要自己託管這些服務,所以我們必須自己實作相容於Terraform的Module Registry ProtocolProvider Registry Protocol registry 伺服器,並部署在Verda的VKS集群上。

後端使用相容於Amazon S3的VOS,provider的程式以及其他資料的內容將會被存放在那。當Verda平台上的開發者在執行Terraform時,他們將會向我們內部的Terraform registry取得provider的程式,以便跟Verda溝通。開發者僅需要指定內部Terraform registry的URL,就可以在Verda上實現Infrastructure as Code。

使用Terraform鎖作為更安全且一致化的操作

預設情況下,當Terraform在執行寫入操作時,它會將目前稱作Terraform state的狀態上鎖。不同的後端,也就是Terraform state會有著不同的鎖。在GCS(Google Cloud Storage)上,鎖是內建的並獨立存在,而在S3上時,鎖需要搭配Amazon DynamoDB使用。在私有雲世界裡,這些選項將會變得不可用,要改採用例如Kubernetes或是HTTP的後端儲存機制。這使得Verda的那些開發者需要各自託管這些後端儲存系統,在Terraform使用上將會變得非常麻煩。所以這個後端系統必須以平台的方式提供給Terraform使用者。

慶幸的是,Verda上有與S3介面相符且支援版本控制的物件儲存系統: VOS。所以我們決定採用S3當作我們的後端儲存,並提供與DynamoDB相容的鎖。現在已有開源且與DynamoDB兼容的資料庫,例如ScallyDB。但是因為它不滿足我們的最低要求,也就是認證與權限控管功能(除非使用商業版),最後並沒有採用。我們的小型團隊嘗試去想辦法提供一個不需要資料庫的鎖功能,我們曾參照MINIO's dsyncHashicorp Serf使用的Gossip協定去設計與實作鎖的機制。在實現與DynamoDB相容的API與配置狀態鎖集群之後,這些鎖將會具備可擴展與高度可用的特性。這些設計的細節是一段漫長的故事,待下次呈現給各位。

這些組成狀態鎖集群的節點在與彼此溝通時使用Connect協定(Buf公司所提供相容於gRPC協定的HTTP API),減低了會造成效能瓶頸的流量負擔。題外話,Connect兼容於HTTP/1.1,可以像使用RESTful API一樣被呼叫,也使我們在開發上能更輕鬆。

整個狀態鎖的系統是託管於VKS上,也因為有了多租戶的架構,可以被多位開發者直接利用。

Provider與文件入口

因為我們需要這些客製化的provider,當然也是要花時間實現它們。Verda上的服務都是由每個團隊各自開發及營運他們各自的產品,所以某種程度上,資訊是分散的。因此API端點由每個服務各自擁有,形成類似於微服務的架構。而provider需要正確地呼叫每個服務的API,所以使用了OpenStack的Catalog功能作為服務發現的來源,去參照這些端點並呼叫API。這讓我們可以正確的取得不同區域上,不同服務的端點,進而去呼叫與開發者相關的資源API。另外,由於我們使用私有的registry,所以並不存在像Hashicorp官方提供的文件入口。

在使用Terraform Plugin Doc生成Markdown之後,我們做些細微的調整並部署到基於Docusaurus的文件網站上。這些處理提供更清楚且易讀的文件,幫助開發者上手使用。

因為Infrastructure as Code的價值還尚未在LINE中被廣為流傳,我們在這入口也提供了各類指引與參考文件等幫助。

Provider是如何改變我們的Verda平台

在正式開始這項專案之後,SRE以及那些想要有更安全,透過程式化定義資源管理的同仁都對這項專案充滿了興趣。我們可以感受到團隊協作的價值正充分被顯現,因為所有的操作,例如創建Verda資源與更改設定等,現在都可以在GitHub上被審核。最重要的是,我感覺到開發者針對Verda資源的思維已經開始轉變。前面曾經提過LINE一直使用互動式的工具,以命令式的方式管理所有資源。因為這樣,大家沒有意識到現在的流程出了什麼問題,而是漸漸地習慣它。然而,有愈來愈多的服務與公有雲提供商,像這樣在網頁上的操作資源不再被推崇,取而代之的是更加流行的Infrastructure as Code。我上一份工作在與GCP客戶支援溝通時,我們就是交換了Terraform檔案。由此可證,這樣的概念已經逐漸被接受。

身為SRE以及平台提供方,同時也是組織中的一份子,我深信這項挑戰將會引領Verda,大大邁進走向下一個階段。

下一步

Infrastructure as Code的概念僅於近年被導入,然而在LINE中有更多手動生成,且現存已久的資源。為了能在LINE中,更加平順的導入這個新的觀念及採用這些工具,我們計畫採行下列幾點行動。

培育Infrastructure as Code的文化

為了讓Infrastructure as Code能更有價值,這個概念必須要深植人心,成為文化的根基。Terraform憑藉它能輕易地透過插件的方式擴充,也能應用在各種各類的資源等因素,而有了許多實際的案例。也因此在HashiCorp的Terraform registry中,現在已有超過1600個公開的provider供開發者使用。

在看過其他公有雲的現況後,我體悟到許多的組織就算有網頁操作介面,也依然遵循著Infrastructure as Code的原則,我認為這在推動Infrastructure as Code上絕對有幫助,並且是一份強大的助力。我覺得IaC所產生的價值是存在的,而我們怎麼將這份價值滲透在組織中,取決於我們傳達人的價值作為一種文化的能力。

我們將積極採取任何措施來改善新手的上手體驗,例如透過來自於試行團隊與其他早期使用者的回饋進行持續改進的工作,提升文件品質以及實踐的支持。

幫助開發者進行移轉

先前提到LINE在Verda使用上有著深遠的歷史,即使我們使用Infrastructure as Code表示那些新創建的資源的話,這僅僅占漫長Verda史中的些微篇幅。而其餘那些現存的資源仍然需要開發者透過手動的方式更新及維護。Terraform雖然有import的功能,但是當有大量的資源已經存在而且Infrastructure as Code的價值還尚未在組織中普及的話,整個移轉的過程是極具挑戰性的。

我們仍希望在移轉上付出心力,因為我們相信提供開發者像dtan4/terraforming以及GoogleCloudPlatform/terraformer的工具能夠一次完成整個移轉程序是十分重要的。

我想當我們能夠將現存資源移轉到Terraform後,才能開始進行公司規模的Infrastructure as Code。

零接觸生產環境

零接觸生產環境(Zero Touch Prod)是其中一個最小權限原則(principle of least privilege) 所要達成的目標,由Google的SRE以及資安團隊所倡議。永久或是臨時的人類權限(包含SRE)都會被移除,目標就是要透過自動化工具等間接的方法,降低更動線上資源的所產生的任何風險。Infrastructure as Code透過原始碼管理資源,就可以與應用程式用同樣的方法,去使用CI異動資源。

因為開發者不再需要直接存取線上資源,任何資源的異動都可以在GitHub上忠實呈現。這一切都歸咎於Terraform能代替人類安全地執行任何操作,也因此我們相信我們將會有更安全,更可靠的平台。