====== Modul 5: Containerisering och orkestrering av ML-applikationer ======
===== Översikt =====
I denna modul fokuserar vi på hur containerteknologier och orkestreringsplattformar kan användas för att paketera, driftsätta och skala ML-modeller i produktionsmiljöer. Vi utforskar hur man kan bygga portabla, reproducerbara och skalbara ML-applikationer med hjälp av Docker och Kubernetes. Modulen behandlar även hur man kan hantera resursbehov, skalning och lastbalansering för prediktions-API:er och batchprocessering.
===== Lärandemål =====
Efter denna modul kommer du att:
* Förstå fördelarna med containerisering för ML-system
* Kunna bygga optimerade Docker-images för ML-modeller
* Behärska driftsättning av ML-modeller i Kubernetes
* Implementera skalningsstrategier för varierande belastning
* Hantera GPU-resurser i containeriserade miljöer
* Designa lösningar för både realtidsprediktioner och batchinferens
===== 5.1 Introduktion till containerisering för ML =====
==== Varför containerisering för ML? ====
* **Miljöisolering**: Löser "fungerar på min maskin"-problem
* **Reproduktion**: Säkerställer att modeller körs i identiska miljöer
* **Portabilitet**: Enkel förflyttning mellan utveckling, test och produktion
* **Skalbarhet**: Enkel skalning upp och ner baserat på belastning
* **Versionering**: Tydlig spårning av miljö och modellversioner
* **Resurseffektivitet**: Bättre resursutnyttjande än virtuella maskiner
==== Containerteknologier för ML ====
* **Docker**: De facto-standard för containerisering
* **Singularity**: Populärt för HPC (High-Performance Computing) och GPU-arbetslaster
* **Containerd**: Lättviktig container runtime
* **Podman**: Daemonless containerhantering
==== Grundläggande Docker-koncept för ML ====
* **Images**: Paketerad miljö för ML-modeller
* **Containers**: Körande instanser av images
* **Dockerfile**: Definition av en Docker-image
* **Registry**: Lagring och distribution av images (Docker Hub, ECR, etc.)
* **Nätverk**: Kommunikation mellan containers
* **Volymer**: Persistent datalagring
===== 5.2 Containerisering av ML-modeller med Docker =====
==== Optimala Dockerfile-strategier för ML ====
* **Base images**: Val av lämpliga bas-images (TensorFlow, PyTorch, etc.)
* **Multi-stage builds**: Separera träning från inferens
* **Layer-optimering**: Minimera antalet lager och storleken
* **Dependency management**: Hantering av biblioteksberoenden
* **Caching**: Effektiv caching för snabbare byggen
==== Exempel på Dockerfile för ML-modell ====
# Multi-stage build för en ML-modell
# Byggfas - använd officiell TensorFlow-image med GPU-stöd
FROM tensorflow/tensorflow:2.9.0-gpu AS builder
# Installera byggberoenden
RUN apt-get update && apt-get install -y --no-install-recommends \
git \
&& rm -rf /var/lib/apt/lists/*
# Sätt arbetskatalog
WORKDIR /build
# Kopiera requirements först för bättre caching
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt
# Kopiera källkod
COPY src/ ./src/
COPY models/ ./models/
COPY config.yaml .
# Pakagera modellen för optimerad inferens
RUN python src/optimize_model.py --model models/model.h5 --output models/optimized_model
# Inferensfas - använd lightweight image för runtime
FROM tensorflow/tensorflow:2.9.0 AS runtime
# Installera produktionsberoenden
COPY --from=builder /build/requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt
# Kopiera optimerad modell och kod
WORKDIR /app
COPY --from=builder /build/models/optimized_model ./models/
COPY --from=builder /build/src/inference.py ./
COPY --from=builder /build/config.yaml ./
# Exponera port för API
EXPOSE 8501
# Definiera standardkommando
CMD ["python", "inference.py", "--port", "8501"]
==== Optimering av Docker-images för ML ====
* **Image-storlek**: Minimera storleken genom att ta bort utvecklingsverktyg
* **Startid**: Optimera för snabb startup av containers
* **Caching**: Strukturera Dockerfile för optimal caching
* **Lagerstruktur**: Gruppera relaterade kommandon för att minimera antal lager
* **Alpine-baserade images**: För minimala produktionsimages
==== Best practices för containerisering av ML-modeller ====
* **Separering av träning och inferens**: Olika containers för olika ändamål
* **Externalisera konfiguration**: Använd environment-variabler eller config-filer
* **Preload-modeller**: Ladda modeller vid container-uppstart för att minimera kallstarttid
* **Health checks**: Implementera hälsokontroller för containerövervakning
* **Lämplig loggning**: Konfigurera loggning för effektiv felsökning
* **Säkerhetsoptimering**: Kör som non-root-användare, scanna för sårbarheter
===== 5.3 Orkestrering med Kubernetes för ML-arbetsbelastningar =====
==== Introduktion till Kubernetes för ML ====
* **Kubernetes-komponenter**: Noder, Pods, Services, Deployments
* **Kubernetes-arkitektur**: Control plane och worker nodes
* **Namespace-organisering**: Logisk separation av miljöer och team
* **ML-specifika överväganden**: Resursbehov, specialiserad hårdvara
==== Kubernetes-resurser för ML-driftsättning ====
* **Deployments**: För stateless prediktions-API:er
* **StatefulSets**: För tillståndsbaserade ML-system
* **Services**: Exponera ML-endpoints
* **ConfigMaps och Secrets**: Hantera konfiguration och hemligheter
* **Jobs och CronJobs**: För batchträning och -inferens
* **HPA (Horizontal Pod Autoscaler)**: Automatisk skalning baserat på belastning
==== Exempel på Kubernetes-manifest för ML-modellserving ====
# deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: ml-model-service
labels:
app: ml-model-service
spec:
replicas: 3
selector:
matchLabels:
app: ml-model-service
template:
metadata:
labels:
app: ml-model-service
spec:
containers:
- name: model-server
image: my-registry/ml-model:latest
ports:
- containerPort: 8501
resources:
limits:
cpu: "2"
memory: "4Gi"
nvidia.com/gpu: 1
requests:
cpu: "1"
memory: "2Gi"
readinessProbe:
httpGet:
path: /health
port: 8501
initialDelaySeconds: 10
periodSeconds: 5
livenessProbe:
httpGet:
path: /health
port: 8501
initialDelaySeconds: 30
periodSeconds: 15
env:
- name: MODEL_PATH
value: "/app/models/optimized_model"
- name: PREDICTION_TIMEOUT
value: "5"
volumeMounts:
- name: model-storage
mountPath: /app/models
volumes:
- name: model-storage
persistentVolumeClaim:
claimName: model-pvc
---
# service.yaml
apiVersion: v1
kind: Service
metadata:
name: ml-model-service
spec:
selector:
app: ml-model-service
ports:
- port: 80
targetPort: 8501
type: ClusterIP
---
# autoscaler.yaml
apiVersion: autoscaling/v2
kind: HorizontalPodAutoscaler
metadata:
name: ml-model-service-hpa
spec:
scaleTargetRef:
apiVersion: apps/v1
kind: Deployment
name: ml-model-service
minReplicas: 3
maxReplicas: 10
metrics:
- type: Resource
resource:
name: cpu
target:
type: Utilization
averageUtilization: 70
==== Kubernetes-operatörer för ML ====
* **KubeFlow Operator**: Hantering av ML-arbetsflöden
* **Seldon Core**: Driftsättning av ML-modeller med komplex routning
* **Feast Operator**: Feature Store-hantering
* **NVIDIA GPU Operator**: GPU-resurshantering
===== 5.4 Hantering av GPU-resurser i containeriserade miljöer =====
==== GPU-runtime för containers ====
* **NVIDIA Docker**: Docker med GPU-stöd
* **Kubernetes Device Plugins**: GPU-allokering i Kubernetes
* **Multi-GPU-konfigurationer**: Parallellisering över flera GPUs
==== GPU-specifika optimeringar ====
* **Memory management**: Optimalt utnyttjande av GPU-minne
* **Batch sizing**: Anpassade batchstorlekar för GPU
* **Mixed precision**: Användning av FP16 för snabbare inferens
* **Kernel tuning**: Optimering av CUDA-kernels
* **GPU-delning**: Dela en GPU mellan flera containers
==== Exempel på GPU-konfiguration i Kubernetes ====
# nvidia-device-plugin.yaml
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: nvidia-device-plugin-daemonset
namespace: kube-system
spec:
selector:
matchLabels:
name: nvidia-device-plugin-ds
template:
metadata:
labels:
name: nvidia-device-plugin-ds
spec:
tolerations:
- key: nvidia.com/gpu
operator: Exists
effect: NoSchedule
containers:
- name: nvidia-device-plugin-ctr
image: nvidia/k8s-device-plugin:v0.12.2
securityContext:
allowPrivilegeEscalation: false
capabilities:
drop: ["ALL"]
volumeMounts:
- name: device-plugin
mountPath: /var/lib/kubelet/device-plugins
volumes:
- name: device-plugin
hostPath:
path: /var/lib/kubelet/device-plugins
===== 5.5 Skalning och lastbalansering av ML-modeller =====
==== Skalningsstrategier för ML-tjänster ====
* **Horisontell skalning**: Öka antalet poddar baserat på belastning
* **Vertikal skalning**: Öka resurser per podd
* **Autoskalning**: Automatisk anpassning baserat på metrics
* **Prediktiv skalning**: Förutsägbara skalning baserat på historiska mönster
==== Lastbalanseringsmetoder ====
* **Round-robin**: Jämn fördelning av förfrågningar
* **Sessionsstickyness**: Håll användare till samma instans
* **Modellshard**: Dela upp modellen över flera instanser
* **Specialisering**: Olika modeller för olika typer av förfrågningar
==== Implementering av optimal inferens i en distribuerad miljö ====
* **Modellparallellism**: Dela upp stora modeller över flera GPUs/noder
* **Batchprediktioner**: Gruppera förfrågningar för bättre genomströmning
* **Dataparallelism**: Samma modell på flera noder för bättre genomströmning
* **Adaptive batching**: Dynamisk batchstorlek baserat på belastning
* **Caching**: Cacha vanliga förfrågningar för snabbare respons
==== Exempel på adaptive batching med TensorFlow Serving ====
import tensorflow as tf
from tensorflow_serving.apis import predict_pb2
from tensorflow_serving.apis import prediction_service_pb2_grpc
import grpc
import numpy as np
import time
from concurrent import futures
# Konfigurera gRPC-klient
channel = grpc.insecure_channel('localhost:8500')
stub = prediction_service_pb2_grpc.PredictionServiceStub(channel)
# Batchsamlare
class BatchCollector:
def __init__(self, max_batch_size=32, timeout=0.1):
self.max_batch_size = max_batch_size
self.timeout = timeout
self.batch = []
self.executor = futures.ThreadPoolExecutor(max_workers=1)
self.future = None
def add_request(self, image):
# Skapa ett Future-object för resultatet
result_future = futures.Future()
# Lägg till request i batch
self.batch.append((image, result_future))
# Starta batch-process om det är den första i batchen
if len(self.batch) == 1:
self.future = self.executor.submit(self._process_batch)
# Processa omedelbart om batch är full
if len(self.batch) >= self.max_batch_size:
self.future.result()
return result_future
def _process_batch(self):
# Vänta tills timeout eller maximal batchstorlek
start_time = time.time()
while len(self.batch) < self.max_batch_size and time.time() - start_time < self.timeout:
time.sleep(0.001)
# Skapa batch-request
batch_size = len(self.batch)
images = np.zeros((batch_size, 224, 224, 3), dtype=np.float32)
futures = []
# Samla in data och futures
for i, (image, future) in enumerate(self.batch):
images[i] = image
futures.append(future)
# Töm batchen
self.batch = []
# Skapa TF Serving-request
request = predict_pb2.PredictRequest()
request.model_spec.name = 'image_classifier'
request.model_spec.signature_name = 'serving_default'
request.inputs['input'].CopyFrom(
tf.make_tensor_proto(images)
)
# Gör prediktionen
try:
result = stub.Predict(request, timeout=5.0)
predictions = tf.make_ndarray(result.outputs['output'])
# Sätt resultat för varje future
for i, future in enumerate(futures):
future.set_result(predictions[i])
except Exception as e:
# Sätt undantag för alla futures
for future in futures:
future.set_exception(e)
===== 5.6 Design av ML-tjänster för olika användningsfall =====
==== Realtidsprediktioner ====
* **API-design**: RESTful eller gRPC-API för snabb inferens
* **Latensoptimering**: Minimera svarstid för realtidsapplikationer
* **Stateless design**: Stateless design för enkel skalning
* **Caching-strategier**: Cacha vanliga förfrågningar
* **Felhantering**: Robusta strategier för hantering av fel och timeout
==== Batchprediktioner ====
* **Arbetsköer**: Använd köer för att hantera stora batchjobb
* **Schemaläggning**: Schemalägg batchjobb under låg belastning
* **Checkpointing**: Spara tillstånd för att återuppta vid fel
* **Parallellisering**: Dela upp stora jobb i parallella arbetare
* **Dataflödesoptimering**: Optimera dataflöde för hög genomströmning
==== Online learning ====
* **Inkrementell träning**: Uppdatera modeller med nya data i realtid
* **A/B-testmiljö**: Testa modelluppdateringar i produktion
* **Shadow deployment**: Validera nya modeller utan att påverka användare
* **Feedback loops**: Samla in feedback för kontinuerlig förbättring
==== Exempel på ML-tjänstarkitektur för realtid- och batchprediktioner ====
# Real-time API service
apiVersion: apps/v1
kind: Deployment
metadata:
name: realtime-prediction-api
spec:
replicas: 5
selector:
matchLabels:
app: realtime-prediction-api
template:
metadata:
labels:
app: realtime-prediction-api
spec:
containers:
- name: api-server
image: my-registry/ml-api:latest
ports:
- containerPort: 8000
resources:
limits:
nvidia.com/gpu: 1
---
# Batch prediction job
apiVersion: batch/v1
kind: CronJob
metadata:
name: batch-prediction-job
spec:
schedule: "0 2 * * *" # Kör kl 02:00 varje dag
jobTemplate:
spec:
parallelism: 5 # 5 parallella pods
completions: 1
template:
spec:
containers:
- name: batch-processor
image: my-registry/ml-batch:latest
resources:
limits:
nvidia.com/gpu: 1
volumeMounts:
- name: data-volume
mountPath: /data
- name: output-volume
mountPath: /output
volumes:
- name: data-volume
persistentVolumeClaim:
claimName: input-data-pvc
- name: output-volume
persistentVolumeClaim:
claimName: output-data-pvc
restartPolicy: Never
===== Praktiska övningar =====
1. **Docker containerisering**: Bygg en Docker-container för en tränad ML-modell
2. **Kubernetes-driftsättning**: Driftsätt en ML-modell på Kubernetes-kluster
3. **Autoskalningskonfiguration**: Implementera automatisk skalning baserat på trafikbelastning
4. **GPU-optimering**: Optimera en GPU-baserad inferensmiljö för maximal prestanda
===== Verktygsintroduktion =====
* **Docker**: Byggande och hantering av containers
* **Kubernetes**: Orkestrering av containers
* **KubeFlow**: ML-specifika tjänster för Kubernetes
* **Seldon Core**: Driftsättningsplattform för ML på Kubernetes
* **TensorRT**: NVIDIA SDK för optimerad inferens
===== Läsresurser =====
* "Containerization of Machine Learning Models" - NVIDIA Developer Blog
* "Kubernetes Patterns for ML Services" - Kubeflow Documentation
* "Optimizing GPU Usage for Deep Learning Inference" - AWS ML Blog
* "Distributed TensorFlow on Kubernetes" - Google Cloud Documentation
* "High-Performance Inference with TensorRT" - NVIDIA Documentation
===== Nyckelinsikter =====
* Containerisering möjliggör portabel, reproducerbar ML-utveckling och -driftsättning
* Multi-stage Docker-byggen separerar utveckling från produktion för optimal effektivitet
* Kubernetes ger en robust plattform för att orkestreras ML-tjänster med komplex skalning
* GPU-hantering i containeriserade miljöer kräver speciella överväganden för optimal prestanda
* Skalnings- och lastbalanseringsstrategierna bör anpassas efter specifika ML-användningsfall
* Realtids- vs. batchprediktioner kräver olika arkitekturella mönster
===== Nästa steg =====
I nästa modul kommer vi att fokusera på modellövervakning och underhåll, där vi kommer att lära oss hur man övervakar modellprestanda i produktion, detekterar drift och implementerar automatiska omträningsstrategier.