Fluid是一個開源的Kubernetes原生的分布式資料集編排和加速引擎,主要服務於雲原生情境下的資料密集型應用。Fluid支援管理和調度EFCRuntime,實現資料集的可見度、Auto Scaling和資料訪問加速等能力。本文介紹如何使用Fluid EFCRuntime加速NAS檔案訪問。
前提條件
已確保ECS的作業系統為Alibaba Cloud Linux 2,核心版本為v4.19.91-23及以上版本。
已建立ACK Pro版叢集,且叢集的Kubernetes版本不低於1.18。具體操作,請參見建立ACK Pro版叢集。
已開通阿里雲Apsara File Storage NAS服務,並在已建立的ACK Pro叢集節點可正常掛載訪問的通用容量型、通用效能型NAS執行個體。
說明對於AI訓練情境,建議您根據吞吐效能選擇檔案儲存體規格。更多資訊,請參見選型指導。
已配置kubectl,並可以正常串連ACK Pro版叢集。具體操作,請參見擷取叢集KubeConfig並通過kubectl工具串連叢集。
EFC介紹
EFC彈性檔案用戶端(Elastic File Client)是阿里雲檔案儲存體團隊開發的基於FUSE的使用者態POSIX用戶端。它可以替代傳統的核心態NFS用戶端,提供多連結訪問、中繼資料快取、分布式資料緩衝等加速能力,並結合阿里雲Prometheus監控提供端側效能監控能力。相比於核心態NFS v3、v4.x用戶端和其他基於開源FUSE的用戶端,EFC有以下優勢:
強一致的語義:EFC通過強一致的分布式鎖機制實現檔案和目錄的強一致;檔案寫入可以立即被其他用戶端讀取;新檔案建立出來後,就可以立即讓所有的其他用戶端同步訪問到,便於您在多節點間管理資料。
端上單機讀寫緩衝能力:最佳化了FUSE的緩衝邏輯,利用計算節點上的少量記憶體,提供了更好的小檔案讀寫效能。相比於傳統的NFS用戶端,效能提升了50%以上。
分布式唯讀緩衝能力:除了端上讀寫緩衝,EFC提供分布式唯讀緩衝的能力,利用多節點的記憶體建立緩衝池,並隨計算規模免營運自動擴充。
小檔案預取能力:EFC會針對性地預取熱目錄下的熱資料,節省拉取資料的開銷。
熱升級和Failover能力:EFC支援秒級Failover特性,實現了對業務無影響的用戶端版本的熱升級能力。
使用Fluid EFCRuntime加速NAS檔案訪問
Fluid通過EFCRuntime的Kubernetes自訂資源對接EFC,協助使用者實現資料集的可見度、Auto Scaling等能力。
使用限制
EFCRuntime具有以下限制:
暫不支援DataLoad緩衝預熱功能,只支援第一次讀取資料時放入緩衝的功能。
暫不支援Dataset資來源物件上的緩衝狀態資訊透出。
僅支援在華北3(張家口)、華北2(北京)、華南3(廣州)、華南1(深圳)、華東2(上海)地區使用。
原理介紹
如下圖所示,通過將NAS中的資料緩衝到本地,實現對檔案訪問速度的提升。其工作原理如下:
您可以通過定義Dataset CRD資來源物件和EFCRuntime CRD資來源物件,分別指定NAS的資料來源資訊。
Fluid Controllers組件根據資料來源資訊,在叢集中建立EFC Cache Worker組件和EFC FUSE組件。
使用者建立應用Pod時,可以通過指定PVC(PersistentVolumeClaim)的方式掛載到EFC FUSE用戶端暴露的檔案系統掛載點。
當使用者訪問檔案時,EFC FUSE用戶端會將請求轉寄給EFC Cache Worker,後者會判斷資料是否已經被緩衝到本地,如果有緩衝就直接返回;否則從NAS中擷取資料,並緩衝到本地,即通過EFC緩衝訪問NAS檔案儲存體中的資料,獲得緩衝加速效果。
Dataset:由Fluid定義的一種Kubernetes CRD。它描述了邏輯上相關的一組資料的集合,會被上層運算引擎使用。
EFCRuntime:支撐Dataset訪問加速能力的一種Runtime類型實現,其背後使用的緩衝引擎為EFC。EFC緩衝引擎包括EFC Cache Worker組件和EFC FUSE組件。
EFC Cache Worker組件:通過一致性雜湊提供緩衝能力的服務端組件,根據不同的資料訪問需求可選擇關閉該組件。關閉該組件後,EFC將關閉分布式唯讀緩衝功能。其他特性不受影響。
EFC FUSE組件:以POSIX協議標準暴露資料提供者的EFC用戶端組件。
操作流程
步驟一:安裝ack-fluid組件
安裝雲原生AI套件和ack-fluid組件,且確保組件為0.9.10及以上版本。
若您已安裝開源Fluid,請卸載後再部署ack-fluid組件。
未安裝雲原生AI套件
您可以在安裝雲原生AI套件時開啟Fluid資料加速。具體操作,請參見安裝雲原生AI套件。
已安裝雲原生AI套件
登入Container Service管理主控台,在左側導覽列選擇叢集。
在叢集列表頁面,單擊目的地組群名稱,然後在左側導覽列,選擇 。
在雲原生AI套件頁面,單擊ack-fluid右側操作列下的部署。
在安裝組件對話方塊,單擊確定。
ack-fluid組件版本較低
登入Container Service管理主控台,在左側導覽列選擇叢集。
在叢集列表頁面,單擊目的地組群名稱,然後在左側導覽列,選擇 。
在雲原生AI套件頁面,單擊ack-fluid右側操作列下的升級。
在升級組件對話方塊,單擊確定。
步驟二:在NAS中建立待訪問的資料
如果您的NAS中已有合適的資料檔案,可以跳過此步驟。
掛載NAS檔案系統至任意一台ECS。具體操作,請參見一鍵掛載NAS NFS協議檔案系統。
執行以下命令,尋找檔案掛載點。
findmnt /mnt
預期輸出:
TARGET SOURCE FSTYPE OPTIONS /mnt/nfs xxxxxxxxxxx-xxxxx.cn-beijing.nas.aliyuncs.com:/ nfs rw,relatime,vers=3,rsize=1048576,wsize=1048576,namlen=255,hard,nolock,no
執行以下命令,在NAS檔案儲存體掛載點目錄下建立一個大小為10G的檔案。
dd if=/dev/zero of=/mnt/nfs/allzero-demo count=1024 bs=10M
預期輸出:
1024+0 records in 1024+0 records out 10737418240 bytes (11 GB) copied, 50.9437 s, 211 MB/s
步驟三:建立Fluid Dataset和EFCRuntime
建立dataset.yaml檔案,程式碼範例如下。
NAS程式碼範例
apiVersion: data.fluid.io/v1alpha1 kind: Dataset metadata: name: efc-demo spec: mounts: - mountPoint: "nfs://<nas_url>:<nas_dir>" name: efc path: "/" --- apiVersion: data.fluid.io/v1alpha1 kind: EFCRuntime metadata: name: efc-demo spec: replicas: 3 master: networkMode: ContainerNetwork worker: networkMode: ContainerNetwork fuse: networkMode: ContainerNetwork tieredstore: levels: - mediumtype: MEM path: /dev/shm quota: 15Gi
dataset.yaml檔案中包含Dataset和EFCRuntime。
Dataset:描述NAS檔案儲存體的相關資訊,例如NAS檔案儲存體URL,需掛載的子目錄等。
EFCRuntime:啟動一個EFC緩衝系統來提供快取服務。在EFCRuntime中描述EFC緩衝系統Worker組件副本數,以及每個Worker組件最大的緩衝容量等。
參數
說明
mountPoint
NAS的格式為
nfs://<nas_url>:<nas_dir>
,欄位解析如下。replicas
建立EFC緩衝系統的Worker組件副本數。可以根據計算節點記憶體配置和資料集大小進行調整。建議quota和replicas乘積大於所需緩衝的資料集總大小。
networkMode
取值ContainerNetwork和HostNetwork。在ACK環境中建議設定為ContainerNetwork,使用容器網路不會有額外的效能損失。
mediumtype
緩衝類型。只支援HDD、SSD和MEM。其中MEM代表記憶體。在AI訓練情境中,建議使用MEM。當使用MEM時,path所指定的快取資料儲存目錄需要設定為記憶體檔案系統(例如tmpfs)。
path
EFC緩衝系統Worker的快取資料儲存目錄。建議使用/dev/shm。
quota
單個Worker組件提供的最大緩衝容量。可以根據計算節點記憶體配置和資料集大小進行調整。建議quota和replicas乘積大於所需緩衝的資料集總大小。
執行以下命令,建立EFCRuntime和Dataset。
kubectl create -f dataset.yaml
執行以下命令,查看Dataset的部署情況。
kubectl get dataset efc-demo
預期輸出:
NAME UFS TOTAL SIZE CACHED CACHE CAPACITY CACHED PERCENTAGE PHASE AGE efc-demo Bound 24m
Dataset處於Bound狀態,表明EFC緩衝系統已在叢集內正常啟動,應用Pod可正常訪問Dataset中定義的資料。
執行以下命令,查看EFCRuntime的部署情況。
kubectl get efcruntime
預期輸出:
NAME MASTER PHASE WORKER PHASE FUSE PHASE AGE efc-demo Ready Ready Ready 27m
預期輸出表明EFC緩衝系統的Master組件、Worker組件以及FUSE組件都處於就緒狀態。
執行以下命令,查看PVC和PV的建立情況。
在Dataset以及對應的EFC緩衝系統準備就緒後,Fluid將會自動建立PVC和PV。
kubectl get pv,pvc
預期輸出:
NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE persistentvolume/default-efc-demo 100Gi ROX Retain Bound default/efc-demo fluid 94m NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE persistentvolumeclaim/efc-demo Bound default-efc-demo 100Gi ROX fluid 94m
步驟四:建立應用程式容器訪問資料
您可以通過建立應用程式容器來使用EFC加速服務。下述樣本將建立兩個應用程式容器,在兩個不同的節點上多次訪問同一儲存於NAS檔案系統中的資料,通過比較訪問時間來展示EFCRuntime的加速效果。
建立app.yaml,程式碼範例如下。
以下內容描述了一個名為efc-app的StatefulSet資來源物件,它包含兩個Pod,每個Pod都將使用Fluid自動建立的efc-demo PVC掛載到容器內的/data目錄。
apiVersion: apps/v1 kind: StatefulSet metadata: name: efc-app labels: app: nginx spec: serviceName: nginx replicas: 2 selector: matchLabels: app: nginx template: metadata: labels: app: nginx spec: containers: - name: nginx image: registry.openanolis.cn/openanolis/nginx:1.14.1-8.6 command: ["/bin/bash"] args: ["-c", "sleep inf"] volumeMounts: - mountPath: "/data" name: data-vol volumes: - name: data-vol persistentVolumeClaim: claimName: efc-demo
執行以下命令,建立名為efc-app的StatefulSet資來源物件。
kubectl create -f app.yaml
執行以下命令,查看檔案大小。
kubectl exec -it efc-app-0 -- du -h /data/allzero-demo
預期輸出:
10G /data/allzero-demo
查看應用程式容器檔案的讀取時間。
說明讀取檔案耗時和輸送量可能隨運行環境和測量方式而變化。本文是在一個有著三個ECS節點且節點執行個體規格均為ecs.g7ne.8xlarge的ACK叢集中擷取的資料結果。其中,efc-demo的3個分布式緩衝Worker Pod均運行於一個ECS節點上,並且efc-app StatefulSet的兩個Pod分別運行在另外兩個不同的節點上。資料結果不受FUSE端kernel cache影響。
執行以下命令,查看第一個應用程式容器中檔案的讀取時間。
說明如果您使用自己的真實資料檔案,您需要使用真實檔案路徑替代以下命令中的/data/allzero-demo。
kubectl exec -it efc-app-0 -- bash -c "time cat /data/allzero-demo > /dev/null"
預期輸出:
real 0m15.792s user 0m0.023s sys 0m2.404s
預期輸出表明讀取10G檔案需要15.792s,讀取速度為648 MiB/s。
執行以下命令,在另一應用程式容器中,讀取相同的10G大小檔案的耗時。
說明如果您使用自己的真實資料檔案,您需要使用真實檔案路徑替代以下命令中的
/data/allzero-demo
。kubectl exec -it efc-app-1 -- bash -c "time cat /data/allzero-demo > /dev/null"
預期輸出:
real 0m9.970s user 0m0.012s sys 0m2.283s
預期輸出表明讀取10G檔案需要9.970s,讀取速度為1034.3 MiB/s。
可以看到,沒有使用緩衝時,資料讀取速度為648 MiB/s;使用EFCRuntime緩衝後,資料讀取速度為1034.3 MiB/s。對於相同檔案,EFCRuntime提升了約2倍讀取效率。