Les grands modèles de langage (LLM) peuvent facilement atteindre plusieurs dizaines de gigaoctets, ce qui entraîne des démarrages à froid lents et une latence élevée au redémarrage lorsque les fichiers de modèle sont extraits depuis Object Storage Service. Fluid résout ce problème en mettant en cache les fichiers de modèle localement sur les nœuds du cluster via JindoRuntime. Après le premier chargement, le service d'inférence lit les fichiers de modèle depuis le cache mémoire local de JindoFS au lieu de les télécharger depuis OSS, ce qui accélère considérablement les redémarrages suivants. Cette rubrique explique comment configurer la mise en cache basée sur Fluid pour un modèle Qwen-7B-Chat-Int8 et le déployer en tant que service d'inférence KServe pris en charge par vLLM sur des GPU NVIDIA V100.
Prérequis
Avant de commencer, assurez-vous de disposer des éléments suivants :
Un cluster ACK Pro n'exécutant pas ContainerOS, fonctionnant sous Kubernetes 1.22 ou version ultérieure, avec au moins 3 nœuds et 3 Go de mémoire libre par nœud. Consultez la section Créer un cluster ACK Pro.
La suite AI cloud-native installée avec le composant ack-fluid déployé. Consultez la section Déployer la suite AI cloud-native.
Arena 0.9.15 ou version ultérieure installé. Consultez la section Configurer le client Arena.
Le composant ack-kserve installé. Consultez la section Installer ack-kserve.
OSS activé. Consultez la section Activer OSS.
Fonctionnement
Fluid introduit deux ressources personnalisées Kubernetes qui fonctionnent conjointement :
Dataset : déclare le chemin de stockage distant à exposer ; dans ce cas, un chemin de compartiment OSS contenant les fichiers de modèle.
JindoRuntime : démarre un cluster JindoFS qui met en cache le contenu du jeu de données en mémoire sur les nœuds du cluster, de sorte que les lectures suivantes soient servies localement plutôt que depuis OSS.
Lorsque le service d'inférence KServe monte le jeu de données, le serveur vLLM lit les fichiers de modèle depuis le cache JindoFS local au lieu de les télécharger depuis OSS à chaque démarrage.
Étape 1 : Préparer les données du modèle et les télécharger vers OSS
Télécharger le modèle Qwen-7B-Chat-Int8
-
Installez Git et le plug-in Large File Support (LFS) :
sudo yum install git sudo yum install git-lfs -
Clonez le dépôt Qwen-7B-Chat-Int8 depuis ModelScope, en ignorant les téléchargements LFS pendant le clonage :
GIT_LFS_SKIP_SMUDGE=1 git clone https://www.modelscope.cn/qwen/Qwen-7B-Chat-Int8.git -
Accédez au répertoire cloné, puis récupérez les fichiers de modèle gérés par LFS :
cd Qwen-7B-Chat-Int8 git lfs pull
Télécharger le modèle vers OSS
Connectez-vous à la console OSS et notez le nom de votre compartiment OSS. Pour créer un compartiment, consultez la page Créer un compartiment.
Installez et configurez ossutil. Consultez la page Installer ossutil.
-
Créez un répertoire dans le compartiment et téléchargez les fichiers de modèle :
ossutil mkdir oss://<your-bucket-name>/Qwen-7B-Chat-Int8 ossutil cp -r ./Qwen-7B-Chat-Int8 oss://<your-bucket-name>/Qwen-7B-Chat-Int8
Étape 2 : Créer un jeu de données et un JindoRuntime
Créer un Secret pour les identifiants OSS
Créez un Secret Kubernetes pour stocker la paire AccessKey utilisée afin d'accéder au compartiment OSS :
kubectl apply -f - <<EOF
apiVersion: v1
kind: Secret
metadata:
name: oss-secret
stringData:
fs.oss.accessKeyId: <your-access-key-id>
fs.oss.accessKeySecret: <your-access-key-secret>
EOF
Remplacez <your-access-key-id> et <your-access-key-secret> par vos identifiants réels. Pour obtenir une paire AccessKey, consultez la section Obtenir une paire AccessKey.
Résultat attendu :
secret/oss-secret created
Créer le jeu de données et JindoRuntime
Créez un fichier nommé resource.yaml avec le contenu suivant. Pour plus de détails sur la configuration, consultez la section Utiliser JindoFS pour accélérer l'accès à OSS.
apiVersion: data.fluid.io/v1alpha1
kind: Dataset
metadata:
name: qwen-7b-chat-int8
spec:
mounts:
- mountPoint: oss://<oss_bucket>/Qwen-7b-chat-Int8 # Replace with your actual OSS path
options:
fs.oss.endpoint: <oss_endpoint> # Replace with your OSS bucket endpoint
name: models
path: "/"
encryptOptions:
- name: fs.oss.accessKeyId
valueFrom:
secretKeyRef:
name: oss-secret
key: fs.oss.accessKeyId
- name: fs.oss.accessKeySecret
valueFrom:
secretKeyRef:
name: oss-secret
key: fs.oss.accessKeySecret
---
apiVersion: data.fluid.io/v1alpha1
kind: JindoRuntime
metadata:
name: qwen-7b-chat-int8 # Must match the dataset name
spec:
replicas: 3
tieredstore:
levels:
- mediumtype: MEM # Cache in memory
volumeType: emptyDir
path: /dev/shm
quota: 3Gi # Cache capacity per replica
high: "0.95"
low: "0.7"
fuse:
resources:
requests:
memory: 2Gi
properties:
fs.oss.download.thread.concurrency: "200"
fs.oss.read.buffer.size: "8388608"
fs.oss.read.readahead.max.buffer.count: "200"
fs.oss.read.sequence.ambiguity.range: "2147483647"
Appliquez la configuration :
kubectl apply -f resource.yaml
Résultat attendu :
dataset.data.fluid.io/qwen-7b-chat-int8 created
jindoruntime.data.fluid.io/qwen-7b-chat-int8 created
Étape 3 : Déployer un service d'inférence vLLM
Déployez le modèle Qwen-7B-Chat-Int8 en tant que service d'inférence KServe à l'aide de vLLM. L'option --data monte le jeu de données Fluid dans le conteneur, permettant ainsi au modèle d'être lu depuis le cache JindoFS.
arena serve kserve \
--name=qwen-fluid \
--image=kube-ai-registry.cn-shanghai.cr.aliyuncs.com/kube-ai/vllm:0.4.1 \
--gpus=1 \
--cpu=4 \
--memory=12Gi \
--data="qwen-7b-chat-int8:/mnt/models/Qwen-7B-Chat-Int8" \
"python3 -m vllm.entrypoints.openai.api_server --port 8080 --trust-remote-code --served-model-name qwen --model /mnt/models/Qwen-7B-Chat-Int8 --gpu-memory-utilization 0.95 --quantization gptq --max-model-len=6144"
Résultat attendu :
inferenceservice.serving.kserve.io/qwen-fluid created
INFO[0002] The Job qwen-fluid has been submitted successfully
INFO[0002] You can run `arena serve get qwen-fluid --type kserve -n default` to check the job status
Étape 4 : Vérifier les résultats d'accélération
Vérifier l'état du cache du jeu de données
kubectl get dataset qwen-7b-chat-int8
Résultat attendu :
NAME UFS TOTAL SIZE CACHED CACHE CAPACITY CACHED PERCENTAGE PHASE AGE
qwen-7b-chat-int8 17.01GiB 10.46MiB 18.00GiB 0.1% Bound 23h
Le statut PHASE: Bound confirme que le jeu de données est lié et que JindoRuntime est actif. Le pourcentage mis en cache augmente à mesure que le service d'inférence lit les fichiers de modèle.
Vérifier le temps de démarrage du serveur
Exécutez les commandes suivantes pour mesurer le temps nécessaire au serveur pour devenir prêt :
# Get the Pod name for the inference service
POD_NAME=$(kubectl get po | grep qwen-fluid | awk -F " " '{print $1}')
# Check how long the server took to become ready
kubectl logs $POD_NAME | grep -i "server ready takes"
Résultat attendu :
server ready takes 25.875763 s
Avec la mise en cache Fluid activée, les fichiers de modèle sont servis depuis la mémoire locale lors des redémarrages suivants au lieu d'être téléchargés depuis OSS, ce qui réduit le temps de démarrage. L'accélération réelle varie en fonction de la taille du jeu de données, de la mémoire du nœud et des conditions réseau.
Pour obtenir des données de référence comparant les temps d'accès avec et sans cache, consultez la section Étape 3 : Créer des applications pour tester l'accélération des données de la rubrique « Utiliser JindoFS pour accélérer l'accès à OSS ».
Dépannage
JindoRuntime n'est pas prêt
Symptôme : Le jeu de données reste dans un état autre que Bound après l'application de resource.yaml.
Cause : Les workers JindoRuntime peuvent être en attente en raison d'une mémoire insuffisante. Chaque réplica demande 3 Go de mémoire de cache plus 2 Go pour le sidecar Fuse.
Solution : Vérifiez les événements sur JindoRuntime :
kubectl describe jindoruntime qwen-7b-chat-int8
Si les nœuds manquent de mémoire libre, réduisez la valeur de quota dans tieredstore ou ajoutez des nœuds disposant de plus de mémoire disponible.
Erreurs d'accès OSS
Symptôme : Le jeu de données affiche des erreurs ou les pods JindoRuntime signalent un accès refusé.
Cause : L'AccessKey ID ou l'AccessKey secret dans le Secret oss-secret est incorrect, ou l'AccessKey ne dispose pas de l'autorisation de lecture sur le compartiment OSS.
Solution : Vérifiez les identifiants dans le Secret :
kubectl get secret oss-secret -o yaml
Re-créez le Secret avec les valeurs correctes si nécessaire, puis redémarrez JindoRuntime.
Pod du service d'inférence bloqué en init
Symptôme : Le pod qwen-fluid reste dans l'état Init.
Cause : Le sidecar Fuse n'a peut-être pas encore monté le jeu de données, ou le jeu de données n'est pas dans l'état Bound.
Solution : Vérifiez d'abord l'état du jeu de données :
kubectl get dataset qwen-7b-chat-int8
Attendez que l'état PHASE: Bound soit atteint avant que le pod du service d'inférence ne puisse continuer. Si le jeu de données est lié mais que le pod est toujours bloqué, vérifiez les événements du pod :
kubectl describe pod $POD_NAME
Étapes suivantes
En savoir plus sur l'accélération des données Fluid : Présentation de Fluid
Explorer les configurations avancées du cache JindoRuntime : Utiliser JindoFS pour accélérer l'accès à OSS