CDN Deep Dive 2026 — Kiến trúc Edge, Cache Invalidation và Cloudflare vs CloudFront vs Azure Front Door

Posted on: 4/21/2026 5:13:36 PM

Khi một website phục vụ người dùng từ Hà Nội đến São Paulo, từ Tokyo đến Berlin, khoảng cách vật lý giữa server gốc và trình duyệt trở thành bottleneck lớn nhất. Content Delivery Network (CDN) giải quyết vấn đề này bằng cách đặt bản sao nội dung tại hàng trăm điểm hiện diện (PoP) trên toàn cầu. Năm 2026, CDN không còn chỉ cache file tĩnh — chúng đã trở thành nền tảng edge computing với khả năng chạy code, xử lý hình ảnh, chặn DDoS và tối ưu routing theo thời gian thực. Bài viết này sẽ phân tích kiến trúc CDN hiện đại, so sánh ba nền tảng lớn nhất (Cloudflare, AWS CloudFront, Azure Front Door) và đi sâu vào các chiến lược cache invalidation cho production.

1. Kiến trúc CDN hiện đại — Từ Reverse Proxy đến Edge Platform

CDN hoạt động dựa trên nguyên tắc đơn giản: đưa nội dung đến gần người dùng nhất có thể. Nhưng cách triển khai nguyên tắc này đã thay đổi hoàn toàn trong 5 năm qua.

1.1. Two-Tier vs Single-Tier Architecture

Có hai trường phái kiến trúc CDN chính trong năm 2026, mỗi trường phái có triết lý thiết kế khác biệt:

graph TB
    subgraph "Two-Tier (CloudFront)"
        U1["User"] --> E1["Edge PoP
(600+ locations)"] E1 -->|"Cache Miss"| R1["Regional Edge Cache
(13 regions)"] R1 -->|"Cache Miss"| OS1["Origin Shield
(1 region)"] OS1 -->|"Cache Miss"| O1["Origin Server"] end subgraph "Single-Tier (Cloudflare)" U2["User"] --> E2["Edge PoP
(310+ cities)"] E2 -->|"Cache Miss"| TC["Upper-Tier PoP
(Tiered Cache)"] TC -->|"Cache Miss"| O2["Origin Server"] end style E1 fill:#f8f9fa,stroke:#e94560,color:#2c3e50 style R1 fill:#e94560,stroke:#fff,color:#fff style OS1 fill:#2c3e50,stroke:#e94560,color:#fff style O1 fill:#16213e,stroke:#e94560,color:#fff style E2 fill:#f8f9fa,stroke:#e94560,color:#2c3e50 style TC fill:#e94560,stroke:#fff,color:#fff style O2 fill:#16213e,stroke:#e94560,color:#fff

Hình 1: So sánh kiến trúc Two-Tier (CloudFront) và Single-Tier (Cloudflare)

CloudFront sử dụng kiến trúc ba lớp: Edge Location → Regional Edge Cache → Origin Shield → Origin. Mỗi lớp có chức năng riêng, tạo ra nhiều cơ hội cache hit nhưng cũng tăng latency khi miss.

Cloudflare áp dụng mô hình anycast đơn giản hơn: mỗi server tại mỗi PoP chạy toàn bộ software stack — caching, WAF, DDoS mitigation, SSL termination, Workers compute — trong một lượt xử lý duy nhất. Với Tiered Cache, Cloudflare thêm một lớp upper-tier PoP để giảm request về origin.

1.2. Vòng đời của một Request qua CDN

sequenceDiagram
    participant B as Browser
    participant DNS as DNS Resolver
    participant E as Edge PoP
    participant O as Origin Server
    B->>DNS: Resolve cdn.example.com
    DNS-->>B: Anycast IP (nearest PoP)
    B->>E: GET /api/products (TLS 1.3)
    Note over E: Check Cache Key
(URL + headers + query) alt Cache HIT E-->>B: 200 OK (X-Cache: HIT, ~28ms) else Cache MISS E->>O: Forward request O-->>E: 200 OK + Cache-Control headers Note over E: Store in cache
Apply TTL + tags E-->>B: 200 OK (X-Cache: MISS, ~120ms) end

Hình 2: Vòng đời request qua CDN — từ DNS resolution đến cache response

28ms Median TTFB — Cloudflare (cached)
35ms Median TTFB — CloudFront (cached)
310+ Cities — Cloudflare PoPs
600+ PoPs — CloudFront Edge Locations

2. Cache-Control — Ngôn ngữ giao tiếp giữa Origin và CDN

Header Cache-Control là cơ chế chính để origin server chỉ thị CDN cách cache nội dung. Hiểu sai header này là nguyên nhân phổ biến nhất của các vấn đề caching trong production.

2.1. Các Directive quan trọng

DirectiveÝ nghĩaVí dụ sử dụng
max-age=NCache trong N giây kể từ response timeStatic assets: max-age=31536000 (1 năm)
s-maxage=NTTL riêng cho shared cache (CDN), override max-ageAPI response: s-maxage=60, max-age=0
stale-while-revalidate=NCho phép serve stale content trong N giây khi đang revalidates-maxage=300, stale-while-revalidate=60
stale-if-error=NServe stale nếu origin trả error trong N giâyFallback khi origin down
no-storeKhông cache ở bất kỳ đâuResponse chứa thông tin nhạy cảm
no-cacheCache nhưng phải revalidate mỗi lần dùngNội dung cần luôn fresh
privateChỉ browser cache, CDN không được cacheResponse chứa dữ liệu user-specific
# Nginx — Cấu hình Cache-Control cho các loại nội dung khác nhau

# Static assets (CSS, JS, images) — cache 1 năm, immutable
location ~* \.(css|js|woff2|webp|avif|svg)$ {
    add_header Cache-Control "public, max-age=31536000, immutable";
}

# HTML pages — CDN cache 5 phút, browser không cache
location ~* \.html$ {
    add_header Cache-Control "public, s-maxage=300, max-age=0, must-revalidate";
}

# API responses — CDN cache 1 phút, serve stale 30s khi revalidate
location /api/ {
    add_header Cache-Control "public, s-maxage=60, stale-while-revalidate=30, stale-if-error=300";
}

# User-specific data — không cache trên CDN
location /api/me/ {
    add_header Cache-Control "private, no-cache";
}

2.2. CDN-Cache-Control — Header riêng cho CDN

Cloudflare hỗ trợ header CDN-Cache-Control (theo chuẩn RFC 9213) cho phép origin chỉ thị caching riêng cho CDN mà không ảnh hưởng đến browser cache. Đây là giải pháp khi bạn muốn CDN cache lâu hơn browser:

// ASP.NET Core — set CDN-Cache-Control riêng biệt với browser Cache-Control
app.MapGet("/api/products", async (ProductService service) =>
{
    var products = await service.GetAllAsync();
    return Results.Ok(products);
})
.WithMetadata(new EndpointMetadataCollection(
    // Browser: không cache
    // CDN: cache 5 phút, serve stale 30s khi revalidate
    new ResponseCacheAttribute
    {
        Duration = 0,
        Location = ResponseCacheLocation.None,
        NoStore = false
    }
));

// Middleware thêm CDN-Cache-Control header
app.Use(async (context, next) =>
{
    await next();
    if (context.Request.Path.StartsWithSegments("/api/products"))
    {
        context.Response.Headers["CDN-Cache-Control"] = "max-age=300, stale-while-revalidate=30";
        context.Response.Headers["Cache-Control"] = "no-cache";
    }
});

3. Cache Invalidation — Bài toán khó nhất của CDN

Phil Karlton từng nói: "There are only two hard things in Computer Science: cache invalidation and naming things." Với CDN phân tán trên hàng trăm PoP, invalidation trở thành thách thức thực sự cho production.

3.1. Bốn chiến lược Invalidation

graph LR
    subgraph "TTL-Based"
        A1["Set TTL
max-age=300"] --> A2["Auto expire
sau 5 phút"] end subgraph "Purge by URL" B1["Content thay đổi"] --> B2["API: purge
/path/to/page"] end subgraph "Tag-Based Purge" C1["Tag responses
Cache-Tag: product-123"] --> C2["Purge tag
→ invalidate tất cả"] end subgraph "Versioned URLs" D1["style.v3.css"] --> D2["Deploy mới:
style.v4.css"] end style A1 fill:#f8f9fa,stroke:#4CAF50,color:#2c3e50 style A2 fill:#f8f9fa,stroke:#4CAF50,color:#2c3e50 style B1 fill:#f8f9fa,stroke:#e94560,color:#2c3e50 style B2 fill:#f8f9fa,stroke:#e94560,color:#2c3e50 style C1 fill:#f8f9fa,stroke:#2196F3,color:#2c3e50 style C2 fill:#f8f9fa,stroke:#2196F3,color:#2c3e50 style D1 fill:#f8f9fa,stroke:#ff9800,color:#2c3e50 style D2 fill:#f8f9fa,stroke:#ff9800,color:#2c3e50

Hình 3: Bốn chiến lược Cache Invalidation phổ biến

Chiến lượcTốc độĐộ chính xácPhù hợp
TTL-BasedTự động, không cần actionThấp — stale trong TTL windowNội dung ít thay đổi, chấp nhận eventual consistency
Purge by URLNhanh (< 1s trên Cloudflare)Cao — chính xác từng URLBiết rõ URL nào cần invalidate
Tag-Based PurgeNhanh — 1 lệnh purge nhiều URLsRất cao — nhóm theo logicKhông thể enumerate tất cả URL bị ảnh hưởng
Versioned URLsTức thì — URL mới = cache missTuyệt đối — không bao giờ staleStatic assets (CSS, JS, images)

3.2. Tag-Based Purge — Chiến lược cho Production

Tag-based purge (hay Surrogate Keys) là phương pháp mạnh mẽ nhất cho các hệ thống phức tạp. Ý tưởng: mỗi response được gắn một hoặc nhiều cache tag, khi dữ liệu thay đổi, bạn purge theo tag thay vì liệt kê từng URL.

// ASP.NET Core — Gắn Cache-Tag cho response
app.MapGet("/api/products/{id}", async (int id, ProductService service) =>
{
    var product = await service.GetByIdAsync(id);
    return Results.Ok(product);
})
.AddEndpointFilter(async (context, next) =>
{
    var result = await next(context);
    var id = context.GetArgument<int>(0);
    var httpContext = context.HttpContext;

    // Gắn nhiều tags cho một response
    httpContext.Response.Headers["Cache-Tag"] =
        $"product-{id},category-{product.CategoryId},all-products";
    httpContext.Response.Headers["Cache-Control"] =
        "public, s-maxage=3600, stale-while-revalidate=60";

    return result;
});

// Khi product thay đổi → purge tag
app.MapPut("/api/products/{id}", async (int id, Product updated,
    ProductService service, ICdnPurgeService cdn) =>
{
    await service.UpdateAsync(id, updated);

    // Purge tất cả response có tag "product-123" hoặc "all-products"
    await cdn.PurgeTagsAsync($"product-{id}", "all-products");

    return Results.Ok(updated);
});
// Cloudflare Tag-Based Purge via API
public class CloudflarePurgeService : ICdnPurgeService
{
    private readonly HttpClient _http;
    private readonly string _zoneId;

    public async Task PurgeTagsAsync(params string[] tags)
    {
        var request = new HttpRequestMessage(HttpMethod.Post,
            $"https://api.cloudflare.com/client/v4/zones/{_zoneId}/purge_cache");

        request.Content = JsonContent.Create(new { tags });
        request.Headers.Add("Authorization", "Bearer {API_TOKEN}");

        var response = await _http.SendAsync(request);
        response.EnsureSuccessStatusCode();
    }

    public async Task PurgeUrlsAsync(params string[] urls)
    {
        var request = new HttpRequestMessage(HttpMethod.Post,
            $"https://api.cloudflare.com/client/v4/zones/{_zoneId}/purge_cache");

        request.Content = JsonContent.Create(new { files = urls });
        request.Headers.Add("Authorization", "Bearer {API_TOKEN}");

        await _http.SendAsync(request);
    }
}

3.3. Stale-While-Revalidate — Không bao giờ chờ Origin

Directive stale-while-revalidate là vũ khí bí mật để loại bỏ latency spike khi cache expire. Sau khi TTL hết hạn, CDN vẫn trả response cũ (stale) cho user ngay lập tức, đồng thời fetch bản mới từ origin ở background.

sequenceDiagram
    participant U as User
    participant CDN as CDN Edge
    participant O as Origin
    Note over CDN: Cache TTL expired
stale-while-revalidate=60 U->>CDN: GET /api/data CDN-->>U: 200 OK (stale data, ~30ms) CDN->>O: Background revalidate O-->>CDN: 200 OK (fresh data) Note over CDN: Cache updated
New TTL starts U->>CDN: GET /api/data (next request) CDN-->>U: 200 OK (fresh data, ~30ms)

Hình 4: Stale-While-Revalidate — user luôn nhận response nhanh, revalidation chạy background

Khi nào dùng stale-while-revalidate?

Pattern này lý tưởng cho nội dung chấp nhận stale trong vài chục giây: product listings, blog posts, config data, dashboard metrics. Không phù hợp cho dữ liệu tài chính, inventory count, hoặc bất kỳ thứ gì yêu cầu strong consistency.

4. Cloudflare CDN — Zero Bandwidth Cost, Full-Stack Edge

Cloudflare là lựa chọn mặc định cho 80% websites trong năm 2026, nhờ mô hình pricing phá vỡ thị trường: $0 bandwidth cost ở mọi plan, kể cả Free.

4.1. Kiến trúc Anycast toàn cầu

Mỗi server tại mỗi PoP của Cloudflare chạy toàn bộ stack: caching, WAF, DDoS protection, bot management, SSL/TLS termination, và Workers runtime. Không có phân biệt "edge server" và "origin shield" — mọi node đều là full-function.

4.2. Cache Rules 2026 — Tính năng mới

Tháng 3/2026, Cloudflare giới thiệu Cache Response Rules với ba khả năng mới:

Tính năngMô tảUse case
Independent Browser TTLSet browser Cache-Control khác với edge cache TTLEdge cache 1 giờ, browser cache 5 phút
Cache Tag ManagementThêm/sửa/xoá cache tags trên responseChuyển đổi tag format từ CDN khác sang Cloudflare
Strip Caching BlockersXoá Set-Cookie, ETag từ origin response trước khi cacheCache response mà origin gắn cookie không cần thiết
// Cloudflare Worker — Advanced caching logic tại edge
export default {
  async fetch(request, env) {
    const url = new URL(request.url);

    // Cache API responses tại edge với custom key
    const cacheKey = new Request(url.toString(), request);
    const cache = caches.default;

    let response = await cache.match(cacheKey);
    if (response) {
      return new Response(response.body, {
        ...response,
        headers: {
          ...Object.fromEntries(response.headers),
          'X-Cache': 'HIT',
          'X-Cache-Age': response.headers.get('Age') || '0'
        }
      });
    }

    // Cache miss → fetch from origin
    response = await fetch(request);

    // Clone response để cache
    const responseToCache = new Response(response.body, response);
    responseToCache.headers.set('Cache-Control', 's-maxage=300');
    responseToCache.headers.set('Cache-Tag', `api,path-${url.pathname}`);

    // Không await — cache ở background
    caches.default.put(cacheKey, responseToCache.clone());

    return responseToCache;
  }
};

4.3. Tiered Cache — Giảm tải Origin

Cloudflare Tiered Cache (miễn phí từ plan Free) tạo thêm một lớp cache giữa edge PoP và origin. Thay vì 310+ PoP đều fetch origin khi miss, chỉ một số upper-tier PoP được chọn mới liên hệ origin. Kết quả: giảm 60-90% request đến origin.

graph TB
    U["Users worldwide"] --> E1["Edge PoP
Hà Nội"] U --> E2["Edge PoP
HCM"] U --> E3["Edge PoP
Bangkok"] U --> E4["Edge PoP
Tokyo"] E1 -->|"Miss"| T1["Upper-Tier
Singapore"] E2 -->|"Miss"| T1 E3 -->|"Miss"| T1 E4 -->|"Miss"| T2["Upper-Tier
Tokyo"] T1 -->|"Miss"| O["Origin Server
US-East"] T2 -->|"Miss"| O style E1 fill:#f8f9fa,stroke:#e94560,color:#2c3e50 style E2 fill:#f8f9fa,stroke:#e94560,color:#2c3e50 style E3 fill:#f8f9fa,stroke:#e94560,color:#2c3e50 style E4 fill:#f8f9fa,stroke:#e94560,color:#2c3e50 style T1 fill:#e94560,stroke:#fff,color:#fff style T2 fill:#e94560,stroke:#fff,color:#fff style O fill:#2c3e50,stroke:#e94560,color:#fff

Hình 5: Cloudflare Tiered Cache — chỉ upper-tier PoPs mới liên hệ origin

5. AWS CloudFront — Sức mạnh của hệ sinh thái AWS

5.1. Origin Shield — Lớp cache thứ ba

CloudFront Origin Shield là tính năng trả phí (~$0.0035/10K requests) tạo thêm một lớp cache tập trung. Tất cả request miss từ Regional Edge Cache đều đi qua Origin Shield trước khi đến origin, giúp:

  • Tăng cache hit ratio: nhiều Regional Edge Cache share cùng một Origin Shield
  • Request coalescing: nhiều request cùng object được gộp thành 1 request đến origin
  • Giảm chi phí origin: đặc biệt hữu ích khi origin phải xử lý nặng (image transformation, video transcoding)
# AWS CDK (TypeScript) — CloudFront với Origin Shield
import * as cloudfront from 'aws-cdk-lib/aws-cloudfront';
import * as origins from 'aws-cdk-lib/aws-cloudfront-origins';

const distribution = new cloudfront.Distribution(this, 'CDN', {
  defaultBehavior: {
    origin: new origins.HttpOrigin('api.example.com', {
      // Bật Origin Shield tại region gần origin nhất
      originShieldEnabled: true,
      originShieldRegion: 'us-east-1',
      protocolPolicy: cloudfront.OriginProtocolPolicy.HTTPS_ONLY,
    }),
    // Cache Policy: cache theo URL + Accept header + query strings
    cachePolicy: new cloudfront.CachePolicy(this, 'ApiCachePolicy', {
      cachePolicyName: 'api-cache-1h',
      defaultTtl: Duration.hours(1),
      maxTtl: Duration.days(1),
      minTtl: Duration.seconds(0),
      headerBehavior: cloudfront.CacheHeaderBehavior.allowList('Accept', 'Accept-Language'),
      queryStringBehavior: cloudfront.CacheQueryStringBehavior.all(),
      enableAcceptEncodingGzip: true,
      enableAcceptEncodingBrotli: true,
    }),
    viewerProtocolPolicy: cloudfront.ViewerProtocolPolicy.REDIRECT_TO_HTTPS,
  },
});

5.2. Lambda@Edge vs CloudFront Functions

Tiêu chíCloudFront FunctionsLambda@Edge
RuntimeJavaScript (ECMAScript 5.1)Node.js, Python
Execution time< 1msĐến 30s (origin events)
Memory2 MBĐến 10 GB
Network accessKhông
Pricing$0.10/triệu invocations$0.60/triệu + duration
Use caseURL rewrite, header manipulation, cache key normalizationA/B testing, auth check, image optimization, SSR
// CloudFront Function — Normalize cache key
function handler(event) {
    var request = event.request;

    // Normalize query string order → tăng cache hit ratio
    if (request.querystring) {
        var params = Object.keys(request.querystring).sort();
        var normalized = params.map(function(key) {
            return key + '=' + request.querystring[key].value;
        }).join('&');
        request.querystring = {};
        normalized.split('&').forEach(function(pair) {
            var parts = pair.split('=');
            request.querystring[parts[0]] = { value: parts[1] };
        });
    }

    // Strip marketing parameters từ cache key
    delete request.querystring['utm_source'];
    delete request.querystring['utm_medium'];
    delete request.querystring['utm_campaign'];
    delete request.querystring['fbclid'];

    return request;
}

6. Azure Front Door — CDN tích hợp Load Balancing

Azure Front Door kết hợp CDN, global load balancing, WAF, và SSL offloading trong một dịch vụ duy nhất. Điểm mạnh lớn nhất: tích hợp sâu với hệ sinh thái Azure (App Service, Container Apps, Static Web Apps).

6.1. Caching Rules

// Azure Bicep — Front Door với caching rules
resource frontDoor 'Microsoft.Cdn/profiles@2024-09-01' = {
  name: 'myFrontDoor'
  location: 'global'
  sku: {
    name: 'Standard_AzureFrontDoor'
  }
}

resource route 'Microsoft.Cdn/profiles/afdEndpoints/routes@2024-09-01' = {
  name: 'defaultRoute'
  parent: endpoint
  properties: {
    originGroup: { id: originGroup.id }
    patternsToMatch: ['/*']
    cacheConfiguration: {
      // Cache 1 giờ, query string là một phần cache key
      cacheBehavior: 'OverrideAlways'
      cacheDuration: '01:00:00'
      queryStringCachingBehavior: 'IncludeSpecifiedQueryStrings'
      queryParameters: 'page,sort,filter'
      compressionSettings: {
        isCompressionEnabled: true
        contentTypesToCompress: [
          'text/html'
          'application/json'
          'text/css'
          'application/javascript'
        ]
      }
    }
  }
}

Azure Front Door Cache Purge Latency

Tính đến tháng 4/2026, Azure Front Door cache purge có thể mất đến 20 phút để propagate toàn cầu. Microsoft chưa cam kết SLA cho purge latency. Nếu bạn cần instant invalidation, hãy kết hợp versioned URLs cho static assets hoặc cân nhắc Cloudflare (purge < 1 giây).

7. So sánh toàn diện — Cloudflare vs CloudFront vs Azure Front Door

Tiêu chíCloudflareAWS CloudFrontAzure Front Door
PoPs310+ cities, 120+ quốc gia600+ edge, 13 regional192+ PoPs
Median TTFB (cached)28ms35ms~40ms
Bandwidth cost$0 (mọi plan)$0.085/GB (US), giảm theo volume~$0.08/GB (varies)
Free tierUnlimited bandwidth, 100K Workers/day1TB/tháng (12 tháng đầu)Không có free tier CDN
Edge computeWorkers (V8 isolates, 0ms cold start)Lambda@Edge + CF FunctionsRules Engine (limited logic)
DDoS protectionUnlimited, miễn phí mọi planShield Standard free, Advanced $3K/thángStandard miễn phí, Premium trả phí
WAFCó từ Free plan (managed rules)WAF v2 trả phí riêng (~$5/rule)Tích hợp sẵn (Standard/Premium)
Cache purge speed< 1 giây globally< 60 giâyĐến 20 phút
Tag-based purgeEnterprise planKhông hỗ trợ nativeKhông hỗ trợ
Tốt nhất choĐa số websites, cost-sensitive, edge-firstAWS-native workloads, S3 originsAzure-native, multi-region apps

8. Thiết kế CDN Layer cho Production

Dưới đây là kiến trúc CDN production kết hợp nhiều chiến lược caching và invalidation:

graph TB
    U["Users"] --> CDN["CDN Edge
(Cloudflare/CloudFront)"] CDN -->|"Static assets
Cache 1 năm"| S3["Object Storage
(S3/R2)"] CDN -->|"API responses
Cache 5 min"| API["API Server
(.NET / Node.js)"] CDN -->|"HTML pages
SWR 60s"| SSR["SSR Server
(Nuxt/Next)"] API --> DB["Database"] DB -->|"Change Event"| WH["Webhook Handler"] WH -->|"Purge tags"| CDN CI["CI/CD Pipeline"] -->|"Purge on deploy"| CDN CMS["CMS / Admin"] -->|"Purge on publish"| CDN style CDN fill:#e94560,stroke:#fff,color:#fff style S3 fill:#f8f9fa,stroke:#e94560,color:#2c3e50 style API fill:#f8f9fa,stroke:#e94560,color:#2c3e50 style SSR fill:#f8f9fa,stroke:#e94560,color:#2c3e50 style WH fill:#2c3e50,stroke:#e94560,color:#fff style DB fill:#16213e,stroke:#e94560,color:#fff

Hình 6: Kiến trúc CDN production với multiple invalidation triggers

8.1. Best Practices cho CDN Production

Nguyên tắc vàng

TTL cho day-to-day, purge cho emergencies. Đặt TTL hợp lý (5-60 phút cho API, 1 năm cho static assets với versioned URLs) là chiến lược chính. Chỉ dùng purge khi cần invalidation tức thì — purge trên mọi request là anti-pattern vì nó đánh bại mục đích của CDN.

// ASP.NET Core — CDN Caching Middleware hoàn chỉnh
public class CdnCachingMiddleware
{
    private readonly RequestDelegate _next;

    public async Task InvokeAsync(HttpContext context)
    {
        await _next(context);

        var path = context.Request.Path.Value ?? "";

        // Static assets: cache vĩnh viễn với fingerprinted URLs
        if (path.StartsWith("/assets/") || path.StartsWith("/_next/static/"))
        {
            context.Response.Headers["Cache-Control"] =
                "public, max-age=31536000, immutable";
            return;
        }

        // API: CDN cache 5 phút, browser không cache, SWR 30s
        if (path.StartsWith("/api/") && context.Request.Method == "GET")
        {
            context.Response.Headers["Cache-Control"] = "no-cache";
            context.Response.Headers["CDN-Cache-Control"] =
                "max-age=300, stale-while-revalidate=30, stale-if-error=600";
            return;
        }

        // HTML: CDN cache 1 phút, SWR 30s
        if (context.Response.ContentType?.Contains("text/html") == true)
        {
            context.Response.Headers["Cache-Control"] =
                "public, s-maxage=60, stale-while-revalidate=30, max-age=0";
        }
    }
}

9. Chi phí thực tế — CDN có thể miễn phí?

Với Cloudflare Free plan, câu trả lời là cho đa số websites:

$0 Cloudflare Free — Unlimited bandwidth
$25K+ CloudFront — 500TB/tháng bandwidth
$20 Cloudflare Pro — WAF + Advanced DDoS
$3K+ AWS Shield Advanced + WAF

Khi nào CloudFront/Azure Front Door vẫn là lựa chọn đúng?

Khi hệ thống của bạn đã nằm hoàn toàn trong AWS hoặc Azure. Data transfer giữa CloudFront và S3/ALB/API Gateway trong cùng region có giá ưu đãi hoặc miễn phí. Chi phí CDN bandwidth lúc này được bù đắp bởi việc giảm egress cost từ origin. Tương tự, Azure Front Door kết hợp với Azure Static Web Apps (miễn phí) tạo thành stack rất hiệu quả về chi phí.

10. Kết luận

CDN năm 2026 không còn là "thêm vào thì tốt" — nó là thành phần bắt buộc của mọi kiến trúc web production. Với Cloudflare cung cấp CDN + WAF + DDoS miễn phí, không có lý do gì để một website chạy mà không có CDN.

Về chiến lược caching: versioned URLs cho static assets (cache vĩnh viễn, không bao giờ stale), s-maxage + stale-while-revalidate cho API responses (fast, eventually consistent), và tag-based purge cho nội dung cần invalidation chính xác. Đây là công thức đã được chứng minh ở quy mô production.

Cuối cùng, việc chọn CDN provider phụ thuộc vào hệ sinh thái hiện tại. Nếu bắt đầu mới hoặc cost-sensitive, Cloudflare là lựa chọn mặc định. Nếu đã deep trong AWS, CloudFront + Origin Shield cho integration tốt nhất. Azure Front Door phù hợp khi bạn cần CDN + global load balancer + WAF trong một dịch vụ Azure-native duy nhất.

Nguồn tham khảo