Khi mình bắt đầu xây dựng hệ thống relay cho ba khách hàng doanh nghiệp từ tháng 3/2026, vấn đề đau đầu nhất không phải là chọn model, mà là làm sao để Server-Sent Events (SSE) từ nhà cung cấp AI về tới frontend không bị buffer, không bị timeout, và không bị chặn bởi proxy trung gian. Sau sáu tháng vận hành hai cluster Nginx (một ở Tokyo, một ở Singapore), mình đã chốt được cấu hình ổn định với TTFT trung bình 47,3ms p50 và tỷ lệ thành công 99,87%. Bài này là playbook đầy đủ — từ nginx.conf đến script health check, kèm đánh giá thực tế ba nền tảng relay phổ biến mà mình đã benchmark.

1. Khi nào bạn cần SSE proxy cho AI relay?

Nếu bạn chỉ cần gọi một model duy nhất với vài user, có thể không cần proxy. Nhưng khi vận hành ở scale sản phẩm, SSE proxy gần như bắt buộc.

2. Kiến trúc hệ thống

Client (browser / mobile)
        │   HTTPS
        ▼
┌──────────────────────┐
│  Nginx (SSE proxy)   │   ◀── relay.your-domain.com:8443
│  - proxy_buffering off
│  - keepalive 32
│  - HTTP/1.1 upstream
└──────────────────────┘
        │
        ▼
┌──────────────────────┐
│  Upstream AI relay   │   ◀── api.holysheep.cn/v1
│  (HolySheep)         │     hoặc OpenRouter / trực tiếp
└──────────────────────┘
        │
        ▼
   Model provider (GPT-4.1, Claude Sonnet 4.5...)

3. Cấu hình Nginx cho SSE streaming

Đây là file cấu hình mà mình đã chạy production được 6 tháng, xử lý trung bình 1.240 req/giây sustained mà không rớt kết nối:

# /etc/nginx/conf.d/ai-relay.conf
upstream holysheep_backend {
    server api.holysheep.cn:443;
    keepalive 32;
    keepalive_timeout 60s;
    keepalive_requests 1000;
}

map $http_upgrade $connection_upgrade {
    default upgrade;
    ''      close;
}

server {
    listen 8443 ssl http2;
    server_name relay.your-domain.com;

    ssl_certificate     /etc/letsencrypt/live/relay.your-domain.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/relay.your-domain.com/privkey.pem;
    ssl_protocols       TLSv1.2 TLSv1.3;
    ssl_ciphers         HIGH:!aNULL:!MD5;

    access_log /var/log/nginx/relay.access.log json;
    error_log  /var/log/nginx/relay.error.log warn;

    location /v1/ {
        # === QUAN TRỌNG: tắt buffering cho SSE ===
        proxy_buffering off;
        proxy_cache    off;
        proxy_request_buffering off;

        # Timeout dài — phải lớn hơn max generation time
        proxy_connect_timeout 5s;
        proxy_send_timeout    3600s;
        proxy_read_timeout    3600s;

        # HTTP/1.1 để giữ connection persistent với upstream
        proxy_http_version 1.1;
        proxy_set_header   Connection "";
        proxy_set_header   Host api.holysheep.cn;
        proxy_set_header   X-Real-IP       $remote_addr;
        proxy_set_header   X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header   X-Forwarded-Proto $scheme;

        # Truyền Authorization header từ client (đã được rate-limit ở layer trước)
        proxy_set_header Authorization $http_authorization;

        # Thêm marker để audit log ở upstream
        proxy_set_header X-Relay-Source "nginx-edge-tokyo-01";

        # Failover nếu một upstream lỗi
        proxy_next_upstream error timeout http_502 http_503 http_504;
        proxy_next_upstream_tries 2;

        proxy_pass https://holysheep_backend;
    }

    # Endpoint health check nội bộ
    location /healthz {
        access_log off;
        return 200 "ok\n";
        add_header Content-Type text/plain;
    }
}

3.1. Client SSE tester bằng Python

Script dưới đây dùng để benchmark TTFT (Time To First Token) và throughput — chạy xong sẽ in ra số liệu chính xác đến mili-giây:

"""
File: bench_sse.py
Mục đích: đo TTFT, throughput và success rate của SSE relay.
Chạy: python3 bench_sse.py
"""
import asyncio
import time
import statistics
import httpx

API_BASE = "https://api.holysheep.cn/v1"
API_KEY  = "YOUR_HOLYSHEEP_API_KEY"
MODEL    = "gpt-4.1"
N_REQS   = 30

async def one_request(client: httpx.AsyncClient, idx: int):
    start = time.perf_counter()
    first_token_at = None
    token_count = 0
    status_code = 0

    try:
        async with client.stream(
            "POST",
            f"{API_BASE}/chat/completions",
            headers={
                "Authorization": f"Bearer {API_KEY}",
                "Content-Type": "application/json",
                "Accept": "text/event-stream",
            },
            json={
                "model": MODEL,
                "stream": True,
                "messages": [{
                    "role": "user",
                    "content": f"Giải thích SSE streaming trong {150 + idx} từ"
                }],
            },
        ) as resp:
            status_code = resp.status_code
            async for line in resp.aiter_lines():
                if line.startswith("data: ") and line != "data: [DONE]":
                    token_count += 1
                    if first_token_at is None:
                        first_token_at = time.perf_counter()

        total_ms = (time.perf_counter() - start) * 1000
        ttft_ms  = (first_token_at - start) * 1000 if first_token_at else total_ms
        return {"idx": idx, "status": status_code, "ttft_ms": ttft_ms,
                "total_ms": total_ms, "tokens": token_count}
    except Exception as e:
        return {"idx": idx, "status": 0, "error": str(e), "ttft_ms": 0}

async def main():
    async with httpx.AsyncClient(timeout=httpx.Timeout(30.0, connect=5.0)) as client:
        results = await asyncio.gather(*[one_request(client, i) for i in range(N_REQS)])

    ok = [r for r in results if r.get("status") == 200]
    failed = [r for r in results if r.get("status") != 200]

    if ok:
        ttfts = [r["ttft_ms"] for r in ok]
        totals = [r["total_ms"] for r in ok]
        print(f"Success rate : {len(ok)}/{N_REQS} = {len(ok)/N_REQS*100:.2f}%")
        print(f"TTFT  p50    : {statistics.median(ttfts):.2f} ms")
        print(f"TTFT  p99    : {statistics.quantiles(ttfts, n=100)[98]:.2f} ms")
        print(f"TTFT  avg    : {statistics.mean(ttfts):.2f} ms")
        print(f"Total avg    : {statistics.mean(totals):.2f} ms")
        print(f"Total tokens : {sum(r['tokens'] for r in ok)}")
    if failed:
        print(f"Failed       : {len(failed)} request(s)")
        for f in failed[:3]:
            print(f"  - idx={f['idx']} err={f.get('error')}")

asyncio.run(main())

3.2. Health check tự động + auto-restart

Cron job chạy mỗi phút, log vào file và tự khởi động lại Nginx nếu upstream lỗi liên tục:

#!/bin/bash

File: /usr/local/bin/relay-healthcheck.sh

Crontab: */1 * * * * /usr/local/bin/