TensorFlow Serving คืออะไร
TensorFlow Serving เป็นระบบ High-performance Serving สำหรับ Machine Learning Models ที่ Google พัฒนา ออกแบบมาสำหรับ Production Environment รองรับทั้ง TensorFlow SavedModel และ TensorFlow Lite Models ให้บริการผ่าน gRPC และ REST API
จุดเด่นคือ Performance สูง (C++ Backend), Model Versioning อัตโนมัติ, Batching ที่ Optimize สำหรับ GPU, Hot-reload Models ใหม่โดยไม่ต้อง Restart Service และรองรับ Multiple Models พร้อมกัน
Installation และ Configuration
# === TensorFlow Serving Setup ===
# 1. Docker (วิธีที่ง่ายที่สุด)
docker pull tensorflow/serving:latest
docker pull tensorflow/serving:latest-gpu # สำหรับ GPU
# 2. โครงสร้าง Model Directory
# /models/
# ├── text_classifier/
# │ ├── 1/ # Version 1
# │ │ ├── saved_model.pb
# │ │ └── variables/
# │ ├── 2/ # Version 2
# │ │ ├── saved_model.pb
# │ │ └── variables/
# │ └── 3/ # Version 3 (latest)
# │ ├── saved_model.pb
# │ └── variables/
# ├── image_classifier/
# │ └── 1/
# │ ├── saved_model.pb
# │ └── variables/
# └── recommender/
# └── 1/
# ├── saved_model.pb
# └── variables/
# 3. รันด้วย Docker (Single Model)
docker run -d --name tf-serving \
-p 8501:8501 \
-p 8500:8500 \
-v /path/to/models/text_classifier:/models/text_classifier \
-e MODEL_NAME=text_classifier \
tensorflow/serving
# 4. รันด้วย Docker (Multiple Models + Config)
docker run -d --name tf-serving-multi \
-p 8501:8501 \
-p 8500:8500 \
-v /path/to/models:/models \
-v /path/to/model_config.txt:/config/model_config.txt \
tensorflow/serving \
--model_config_file=/config/model_config.txt \
--model_config_file_poll_wait_seconds=60
# 5. Model Config File (model_config.txt)
# model_config_list {
# config {
# name: "text_classifier"
# base_path: "/models/text_classifier"
# model_platform: "tensorflow"
# model_version_policy {
# specific {
# versions: 2
# versions: 3
# }
# }
# }
# config {
# name: "image_classifier"
# base_path: "/models/image_classifier"
# model_platform: "tensorflow"
# }
# config {
# name: "recommender"
# base_path: "/models/recommender"
# model_platform: "tensorflow"
# }
# }
# 6. Batching Config (batching_parameters.txt)
# max_batch_size { value: 32 }
# batch_timeout_micros { value: 5000 }
# max_enqueued_batches { value: 100 }
# num_batch_threads { value: 4 }
# pad_variable_length_inputs: true
# 7. รันพร้อม Batching
docker run -d --name tf-serving-batch \
-p 8501:8501 \
-p 8500:8500 \
-v /path/to/models:/models \
-v /path/to/model_config.txt:/config/model_config.txt \
-v /path/to/batching_parameters.txt:/config/batching.txt \
tensorflow/serving \
--model_config_file=/config/model_config.txt \
--enable_batching=true \
--batching_parameters_file=/config/batching.txt
# 8. GPU Support
docker run -d --name tf-serving-gpu \
--gpus all \
-p 8501:8501 \
-p 8500:8500 \
-v /path/to/models:/models \
-e MODEL_NAME=text_classifier \
tensorflow/serving:latest-gpu \
--per_process_gpu_memory_fraction=0.5
# 9. ตรวจสอบ Model Status
curl http://localhost:8501/v1/models/text_classifier
curl http://localhost:8501/v1/models/text_classifier/versions/3
Python Client สำหรับ TensorFlow Serving
# tf_serving_client.py — Client สำหรับ TensorFlow Serving
# pip install tensorflow-serving-api grpcio requests numpy
import requests
import numpy as np
import json
import time
import grpc
from concurrent import futures
import logging
logging.basicConfig(level=logging.INFO)
logger = logging.getLogger(__name__)
class TFServingClient:
"""Client สำหรับ TensorFlow Serving"""
def __init__(self, host="localhost", rest_port=8501, grpc_port=8500):
self.rest_url = f"http://{host}:{rest_port}"
self.grpc_target = f"{host}:{grpc_port}"
# === REST API ===
def predict_rest(self, model_name, instances, version=None):
"""Predict ผ่าน REST API"""
url = f"{self.rest_url}/v1/models/{model_name}"
if version:
url += f"/versions/{version}"
url += ":predict"
payload = {"instances": instances}
start = time.perf_counter()
resp = requests.post(url, json=payload, timeout=30)
latency = (time.perf_counter() - start) * 1000
if resp.status_code != 200:
logger.error(f"REST Error: {resp.status_code} {resp.text}")
raise Exception(f"Prediction failed: {resp.text}")
result = resp.json()
result["_latency_ms"] = round(latency, 2)
return result
# === gRPC API (faster) ===
def predict_grpc(self, model_name, input_data, input_name="input",
version=None):
"""Predict ผ่าน gRPC (เร็วกว่า REST)"""
from tensorflow_serving.apis import predict_pb2
from tensorflow_serving.apis import prediction_service_pb2_grpc
import tensorflow as tf
channel = grpc.insecure_channel(self.grpc_target)
stub = prediction_service_pb2_grpc.PredictionServiceStub(channel)
request = predict_pb2.PredictRequest()
request.model_spec.name = model_name
if version:
request.model_spec.version.value = version
request.inputs[input_name].CopyFrom(
tf.make_tensor_proto(input_data)
)
start = time.perf_counter()
response = stub.Predict(request, timeout=30)
latency = (time.perf_counter() - start) * 1000
output = {}
for key, tensor in response.outputs.items():
output[key] = tf.make_ndarray(tensor).tolist()
output["_latency_ms"] = round(latency, 2)
return output
def get_model_status(self, model_name):
"""ดูสถานะ Model"""
url = f"{self.rest_url}/v1/models/{model_name}"
resp = requests.get(url)
return resp.json()
def get_model_metadata(self, model_name):
"""ดู Model Metadata (input/output signature)"""
url = f"{self.rest_url}/v1/models/{model_name}/metadata"
resp = requests.get(url)
return resp.json()
def benchmark(self, model_name, instances, n_requests=100):
"""Benchmark Prediction Performance"""
latencies = []
# Warmup
for _ in range(5):
self.predict_rest(model_name, instances)
# Benchmark
for i in range(n_requests):
result = self.predict_rest(model_name, instances)
latencies.append(result["_latency_ms"])
avg = np.mean(latencies)
p50 = np.percentile(latencies, 50)
p95 = np.percentile(latencies, 95)
p99 = np.percentile(latencies, 99)
qps = 1000 / avg * len(instances)
print(f"\n{'='*50}")
print(f"TF Serving Benchmark: {model_name}")
print(f"{'='*50}")
print(f" Requests: {n_requests}")
print(f" Batch: {len(instances)}")
print(f" Avg: {avg:.1f}ms")
print(f" P50: {p50:.1f}ms")
print(f" P95: {p95:.1f}ms")
print(f" P99: {p99:.1f}ms")
print(f" QPS: {qps:.0f}")
return {"avg": avg, "p50": p50, "p95": p95, "p99": p99, "qps": qps}
# === ตัวอย่าง ===
# client = TFServingClient("localhost", 8501, 8500)
#
# # REST Prediction
# result = client.predict_rest("text_classifier", [
# {"input_text": "This is a great product"},
# {"input_text": "Terrible service"},
# ])
# print(result)
#
# # Model Status
# status = client.get_model_status("text_classifier")
# print(status)
#
# # Benchmark
# client.benchmark("text_classifier", [{"input_text": "test"}], n_requests=100)
Kubernetes Deployment
# === Kubernetes Deployment สำหรับ TensorFlow Serving ===
# tf-serving-deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: tf-serving
namespace: ml-serving
spec:
replicas: 3
selector:
matchLabels:
app: tf-serving
template:
metadata:
labels:
app: tf-serving
spec:
affinity:
podAntiAffinity:
preferredDuringSchedulingIgnoredDuringExecution:
- weight: 100
podAffinityTerm:
labelSelector:
matchExpressions:
- key: app
operator: In
values: ["tf-serving"]
topologyKey: kubernetes.io/hostname
containers:
- name: tf-serving
image: tensorflow/serving:latest
ports:
- containerPort: 8501
name: rest
- containerPort: 8500
name: grpc
args:
- --model_config_file=/config/model_config.txt
- --enable_batching=true
- --batching_parameters_file=/config/batching.txt
- --monitoring_config_file=/config/monitoring.txt
- --rest_api_num_threads=16
resources:
requests:
cpu: "2"
memory: 4Gi
limits:
cpu: "4"
memory: 8Gi
volumeMounts:
- name: models
mountPath: /models
readOnly: true
- name: config
mountPath: /config
readinessProbe:
httpGet:
path: /v1/models/text_classifier
port: 8501
initialDelaySeconds: 30
periodSeconds: 10
livenessProbe:
httpGet:
path: /v1/models/text_classifier
port: 8501
initialDelaySeconds: 60
periodSeconds: 30
volumes:
- name: models
persistentVolumeClaim:
claimName: model-storage
- name: config
configMap:
name: tf-serving-config
---
apiVersion: v1
kind: Service
metadata:
name: tf-serving
namespace: ml-serving
spec:
selector:
app: tf-serving
ports:
- name: rest
port: 8501
targetPort: 8501
- name: grpc
port: 8500
targetPort: 8500
---
apiVersion: autoscaling/v2
kind: HorizontalPodAutoscaler
metadata:
name: tf-serving-hpa
namespace: ml-serving
spec:
scaleTargetRef:
apiVersion: apps/v1
kind: Deployment
name: tf-serving
minReplicas: 3
maxReplicas: 20
metrics:
- type: Resource
resource:
name: cpu
target:
type: Utilization
averageUtilization: 60
Best Practices
- ใช้ gRPC สำหรับ Low Latency: gRPC เร็วกว่า REST 2-3 เท่า เหมาะกับ Internal Services
- เปิด Batching: รวม Requests เป็น Batch ลด GPU Overhead เพิ่ม Throughput
- Model Versioning: ใช้ Version Directories Auto-detect Version ใหม่ ทำ Canary Deployment
- Resource Limits: ตั้ง CPU/Memory Limits เหมาะสม ใช้ per_process_gpu_memory_fraction สำหรับ GPU
- Health Checks: ใช้ /v1/models/MODEL_NAME สำหรับ Readiness Probe
- Monitoring: ติดตาม Latency, Throughput, Error Rate, GPU Utilization ตั้ง Alert
- Warm-up: ใช้ TF Serving Warmup Feature ส่ง Sample Requests ตอน Start ลด Cold Start
TensorFlow Serving คืออะไร
ระบบ High-performance Serving สำหรับ ML Models จาก Google รองรับ gRPC REST API Model Versioning Batching GPU Acceleration Hot-reload Models ไม่ต้อง Restart
TensorFlow Serving ต่างจาก Flask/FastAPI อย่างไร
TF Serving ออกแบบเฉพาะ ML Serving มี C++ Backend Performance สูงกว่า Batching อัตโนมัติ Model Versioning gRPC Protocol GPU Memory Management Flask/FastAPI เป็น General-purpose ต้องจัดการเอง
วิธี Optimize Performance ทำอย่างไร
เปิด Batching รวม Requests ลด GPU Overhead ใช้ TensorRT/XLA ตั้ง num_load_threads ใช้ gRPC แทน REST ตั้ง Resource Limits เหมาะสม ใช้ Warm-up ลด Cold Start
Model Versioning ทำอย่างไร
จัดโครงสร้าง /models/model_name/version_number/ TF Serving Auto-detect Version ใหม่ Load อัตโนมัติ ใช้ Model Config File กำหนด Serve Version ไหน รองรับ A/B Testing ด้วย Traffic Splitting
สรุป
TensorFlow Serving เป็นตัวเลือกที่ดีที่สุดสำหรับ Deploy TensorFlow Models ใน Production ใช้ Docker สำหรับ Setup ง่าย Kubernetes สำหรับ Scale เปิด Batching เพิ่ม Throughput ใช้ gRPC สำหรับ Low Latency Model Versioning สำหรับ Safe Deployment ตั้ง Health Checks และ Monitoring ติดตาม Performance
