Ưu và nhược điểm của việc sử dụng logic hết hạn nhất quán hoặc khác nhau trên các lớp bộ nhớ đệm của trình chạy dịch vụ và bộ nhớ đệm HTTP.
Mặc dù các service worker và PWA đang trở thành tiêu chuẩn của các ứng dụng web hiện đại, nhưng việc lưu vào bộ nhớ đệm tài nguyên đã trở nên phức tạp hơn bao giờ hết. Bài viết này đề cập đến bức tranh tổng thể về việc lưu vào bộ nhớ đệm của trình duyệt, bao gồm:
- Các trường hợp sử dụng và sự khác biệt giữa tính năng lưu vào bộ nhớ đệm của trình chạy dịch vụ và tính năng lưu vào bộ nhớ đệm HTTP.
- Ưu và nhược điểm của các chiến lược hết hạn lưu vào bộ nhớ đệm của trình chạy dịch vụ so với các chiến lược lưu vào bộ nhớ đệm HTTP thông thường.
Tổng quan về quy trình lưu vào bộ nhớ đệm
Nhìn chung, trình duyệt sẽ tuân theo thứ tự lưu vào bộ nhớ đệm dưới đây khi yêu cầu một tài nguyên:
- Bộ nhớ đệm của trình chạy dịch vụ: Trình chạy dịch vụ kiểm tra xem tài nguyên có nằm trong bộ nhớ đệm của nó hay không và quyết định có trả về chính tài nguyên đó hay không dựa trên các chiến lược lưu vào bộ nhớ đệm đã được lập trình. Xin lưu ý rằng quá trình này không diễn ra tự động. Bạn cần tạo một trình xử lý sự kiện tìm nạp trong trình chạy dịch vụ và chặn các yêu cầu mạng để các yêu cầu được phân phát từ bộ nhớ đệm của trình chạy dịch vụ thay vì mạng.
- Bộ nhớ đệm HTTP (còn gọi là bộ nhớ đệm của trình duyệt): Nếu tìm thấy tài nguyên trong Bộ nhớ đệm HTTP và tài nguyên đó chưa hết hạn, thì trình duyệt sẽ tự động sử dụng tài nguyên trong bộ nhớ đệm HTTP.
- Phía máy chủ: Nếu không tìm thấy nội dung nào trong bộ nhớ đệm của trình chạy dịch vụ hoặc bộ nhớ đệm HTTP, thì trình duyệt sẽ chuyển đến mạng để yêu cầu tài nguyên. Nếu tài nguyên không được lưu vào bộ nhớ đệm trong CDN, thì yêu cầu phải quay lại máy chủ gốc.

Lớp lưu vào bộ nhớ đệm
Lưu vào bộ nhớ đệm của trình chạy dịch vụ
Một trình chạy dịch vụ sẽ chặn các yêu cầu HTTP thuộc loại mạng và sử dụng chiến lược lưu vào bộ nhớ đệm để xác định những tài nguyên cần trả về cho trình duyệt. Bộ nhớ đệm của trình chạy dịch vụ và bộ nhớ đệm HTTP có cùng mục đích chung, nhưng bộ nhớ đệm của trình chạy dịch vụ cung cấp nhiều khả năng lưu vào bộ nhớ đệm hơn, chẳng hạn như khả năng kiểm soát chi tiết đối với chính xác những gì được lưu vào bộ nhớ đệm và cách lưu vào bộ nhớ đệm.
Kiểm soát bộ nhớ đệm của trình chạy dịch vụ
Một trình chạy dịch vụ chặn các yêu cầu HTTP bằng trình nghe sự kiện (thường là sự kiện fetch). Đoạn mã này minh hoạ logic của chiến lược lưu vào bộ nhớ đệm Ưu tiên bộ nhớ đệm.

Bạn nên dùng Workbox để tránh mất thời gian tạo lại. Ví dụ: bạn có thể đăng ký đường dẫn URL tài nguyên bằng một dòng mã biểu thức chính quy.
import {registerRoute} from 'workbox-routing';
registerRoute(new RegExp('styles/.*\\.css'), callbackHandler);
Các chiến lược lưu vào bộ nhớ đệm và trường hợp sử dụng của trình chạy dịch vụ
Bảng tiếp theo trình bày các chiến lược lưu vào bộ nhớ đệm phổ biến của trình chạy dịch vụ và thời điểm mỗi chiến lược hữu ích.
| Chiến lược | Lý do về độ mới | Trường hợp sử dụng |
|---|---|---|
| Chỉ mạng | Nội dung phải luôn được cập nhật. |
|
| Mạng chuyển về bộ nhớ đệm | Bạn nên phân phát nội dung mới. Tuy nhiên, nếu mạng gặp sự cố hoặc không ổn định, thì việc phân phát nội dung cũ hơn một chút là chấp nhận được. |
|
| Stale-while-revalidate | Bạn có thể phân phát nội dung trong bộ nhớ đệm ngay lập tức, nhưng nên sử dụng nội dung đã cập nhật trong bộ nhớ đệm sau này. |
|
| Ưu tiên bộ nhớ đệm, chuyển về mạng | Nội dung không quan trọng và có thể được phân phát từ bộ nhớ đệm để tăng hiệu suất, nhưng trình chạy dịch vụ thỉnh thoảng nên kiểm tra các bản cập nhật. |
|
| Chỉ bộ nhớ đệm | Nội dung hiếm khi thay đổi. |
|
Các lợi ích bổ sung của tính năng lưu vào bộ nhớ đệm của trình chạy dịch vụ
Ngoài khả năng kiểm soát chi tiết logic lưu vào bộ nhớ đệm, tính năng lưu vào bộ nhớ đệm của trình chạy dịch vụ còn cung cấp:
- Thêm bộ nhớ và không gian lưu trữ cho nguồn gốc của bạn: Trình duyệt phân bổ tài nguyên bộ nhớ đệm HTTP trên cơ sở mỗi nguồn gốc. Nói cách khác, nếu bạn có nhiều miền con, thì tất cả các miền con đó đều dùng chung bộ nhớ đệm HTTP. Không có gì đảm bảo rằng nội dung của nguồn/miền của bạn sẽ nằm trong bộ nhớ đệm HTTP trong thời gian dài. Ví dụ: người dùng có thể xoá bộ nhớ đệm bằng cách dọn dẹp theo cách thủ công trong giao diện người dùng cài đặt của trình duyệt hoặc kích hoạt quá trình tải lại hoàn toàn trên một trang. Với bộ nhớ đệm của trình chạy dịch vụ, nội dung được lưu vào bộ nhớ đệm của bạn có khả năng cao hơn nhiều là vẫn được lưu vào bộ nhớ đệm. Hãy xem phần Bộ nhớ liên tục để tìm hiểu thêm.
- Tính linh hoạt cao hơn với các mạng không ổn định hoặc trải nghiệm ngoại tuyến: Với bộ nhớ đệm HTTP, bạn chỉ có lựa chọn nhị phân: tài nguyên được lưu vào bộ nhớ đệm hoặc không. Với tính năng lưu vào bộ nhớ đệm của trình chạy dịch vụ, bạn có thể giảm thiểu các "trục trặc" nhỏ một cách dễ dàng hơn nhiều (với chiến lược "stale-while-revalidate"), cung cấp trải nghiệm hoàn chỉnh khi không có mạng (với chiến lược "Chỉ bộ nhớ đệm") hoặc thậm chí là một trải nghiệm ở giữa, chẳng hạn như giao diện người dùng tuỳ chỉnh với các phần của trang đến từ bộ nhớ đệm của trình chạy dịch vụ và một số phần bị loại trừ (với chiến lược "Đặt trình xử lý bắt") khi thích hợp.
Hoạt động lưu vào bộ nhớ đệm HTTP
Lần đầu tiên trình duyệt tải một trang web và các tài nguyên liên quan, trình duyệt sẽ lưu trữ các tài nguyên này trong bộ nhớ đệm HTTP. Bộ nhớ đệm HTTP thường được trình duyệt tự động bật, trừ phi người dùng cuối đã tắt bộ nhớ đệm này một cách rõ ràng.
Sử dụng tính năng lưu vào bộ nhớ đệm HTTP có nghĩa là dựa vào máy chủ để xác định thời điểm lưu một tài nguyên vào bộ nhớ đệm và thời gian lưu là bao lâu.
Kiểm soát thời gian hết hạn của bộ nhớ đệm HTTP bằng tiêu đề phản hồi HTTP
Khi phản hồi yêu cầu của trình duyệt về một tài nguyên, máy chủ sẽ sử dụng tiêu đề phản hồi HTTP để cho trình duyệt biết thời gian lưu tài nguyên vào bộ nhớ đệm. Hãy xem phần Tiêu đề phản hồi: định cấu hình máy chủ web để tìm hiểu thêm.
Các chiến lược lưu vào bộ nhớ đệm HTTP và trường hợp sử dụng
Tính năng lưu vào bộ nhớ đệm HTTP đơn giản hơn nhiều so với tính năng lưu vào bộ nhớ đệm của trình chạy dịch vụ, vì tính năng lưu vào bộ nhớ đệm HTTP chỉ xử lý logic hết hạn tài nguyên dựa trên thời gian (TTL). Hãy xem phần Bạn nên sử dụng giá trị nào cho tiêu đề phản hồi? và Tránh những yêu cầu không cần thiết về mạng nhờ Bộ nhớ đệm HTTP (Tóm tắt) để tìm hiểu thêm về các chiến lược lưu vào bộ nhớ đệm HTTP.
Thiết kế logic hết hạn của bộ nhớ đệm
Phần này giải thích những ưu và nhược điểm của việc sử dụng logic hết hạn nhất quán trên các lớp bộ nhớ đệm của trình chạy dịch vụ và bộ nhớ đệm HTTP, cũng như ưu và nhược điểm của logic hết hạn riêng biệt trên các lớp này.
Logic nhất quán về thời gian hết hạn cho tất cả các lớp bộ nhớ đệm
Để minh hoạ ưu và nhược điểm, chúng ta sẽ xem xét 3 trường hợp: dài hạn, trung hạn và ngắn hạn.
| Tình huống | Lưu vào bộ nhớ đệm trong thời gian dài | Lưu vào bộ nhớ đệm trong trung hạn | Lưu vào bộ nhớ đệm trong thời gian ngắn |
|---|---|---|---|
| Chiến lược lưu vào bộ nhớ đệm của trình chạy dịch vụ | Bộ nhớ đệm, dự phòng cho mạng | Stale-while-revalidate | Mạng chuyển về bộ nhớ đệm |
| Thời gian tồn tại (TTL) của bộ nhớ đệm trình chạy dịch vụ | 30 ngày | 1 ngày | 10 phút |
| Tuổi tối đa của bộ nhớ đệm HTTP | 30 ngày | 1 ngày | 10 phút |
Tình huống: Lưu vào bộ nhớ đệm dài hạn (Bộ nhớ đệm, dự phòng cho mạng)
- Khi tài nguyên được lưu vào bộ nhớ đệm là hợp lệ (<= 30 ngày): Trình chạy dịch vụ sẽ trả về tài nguyên được lưu vào bộ nhớ đệm ngay lập tức mà không cần truy cập vào mạng.
- Khi một tài nguyên được lưu vào bộ nhớ đệm đã hết hạn (> 30 ngày): Trình chạy dịch vụ sẽ truy cập vào mạng để tìm nạp tài nguyên. Trình duyệt không có bản sao của tài nguyên trong bộ nhớ đệm HTTP, vì vậy, trình duyệt sẽ truy cập phía máy chủ để lấy tài nguyên.
Nhược điểm: Trong trường hợp này, tính năng lưu vào bộ nhớ đệm HTTP mang lại ít giá trị hơn vì trình duyệt sẽ luôn truyền yêu cầu đến phía máy chủ khi bộ nhớ đệm hết hạn trong trình chạy dịch vụ.
Tình huống: Lưu vào bộ nhớ đệm trong thời gian trung bình (Stale-while-revalidate)
- Khi một tài nguyên được lưu vào bộ nhớ đệm là hợp lệ (≤ 1 ngày): Trình chạy dịch vụ sẽ trả về tài nguyên được lưu vào bộ nhớ đệm ngay lập tức và chuyển đến mạng để tìm nạp tài nguyên. Trình duyệt có một bản sao của tài nguyên trong bộ nhớ đệm HTTP, vì vậy, trình duyệt sẽ trả về bản sao đó cho trình chạy dịch vụ.
- Khi một tài nguyên được lưu vào bộ nhớ đệm đã hết hạn (> 1 ngày): Trình chạy dịch vụ sẽ trả về tài nguyên được lưu vào bộ nhớ đệm ngay lập tức và chuyển đến mạng để tìm nạp tài nguyên. Trình duyệt không có bản sao của tài nguyên trong bộ nhớ đệm HTTP, vì vậy, trình duyệt sẽ truy cập phía máy chủ để tìm nạp tài nguyên.
Nhược điểm: Trình chạy dịch vụ yêu cầu thêm tính năng xoá bộ nhớ đệm để ghi đè bộ nhớ đệm HTTP nhằm tận dụng tối đa bước "xác thực lại".
Tình huống: Lưu vào bộ nhớ đệm trong thời gian ngắn (Mạng dự phòng cho bộ nhớ đệm)
- Khi một tài nguyên được lưu vào bộ nhớ đệm là hợp lệ (≤ 10 phút): Trình chạy dịch vụ sẽ truy cập vào mạng để tìm nạp tài nguyên. Trình duyệt có một bản sao của tài nguyên trong bộ nhớ đệm HTTP nên trình duyệt sẽ trả về bản sao đó cho trình chạy dịch vụ mà không cần truy cập vào phía máy chủ.
- Khi một tài nguyên được lưu vào bộ nhớ đệm đã hết hạn (> 10 phút): Trình chạy dịch vụ sẽ trả về tài nguyên được lưu vào bộ nhớ đệm ngay lập tức và chuyển đến mạng để tìm nạp tài nguyên. Trình duyệt không có bản sao của tài nguyên trong bộ nhớ đệm HTTP, vì vậy, trình duyệt sẽ truy cập phía máy chủ để tìm nạp tài nguyên.
Nhược điểm: Tương tự như trường hợp lưu vào bộ nhớ đệm trong trung hạn, trình chạy dịch vụ yêu cầu logic xoá bộ nhớ đệm bổ sung để ghi đè bộ nhớ đệm HTTP nhằm tìm nạp tài nguyên mới nhất từ phía máy chủ.
Trình chạy dịch vụ trong mọi trường hợp
Trong mọi trường hợp, bộ nhớ đệm của trình chạy dịch vụ vẫn có thể trả về các tài nguyên được lưu vào bộ nhớ đệm khi mạng không ổn định. Mặt khác, bộ nhớ đệm HTTP không đáng tin cậy khi mạng không ổn định hoặc bị gián đoạn.
Logic hết hạn bộ nhớ đệm khác nhau tại bộ nhớ đệm của trình chạy dịch vụ và các lớp HTTP
Để minh hoạ ưu và nhược điểm, chúng ta sẽ xem xét lại các trường hợp dài hạn, trung hạn và ngắn hạn.
| Tình huống | Lưu vào bộ nhớ đệm trong thời gian dài | Lưu vào bộ nhớ đệm trong trung hạn | Lưu vào bộ nhớ đệm trong thời gian ngắn |
|---|---|---|---|
| Chiến lược lưu vào bộ nhớ đệm của trình chạy dịch vụ | Bộ nhớ đệm, dự phòng cho mạng | Stale-while-revalidate | Mạng chuyển về bộ nhớ đệm |
| Thời gian tồn tại (TTL) của bộ nhớ đệm trình chạy dịch vụ | 90 ngày | 30 ngày | 1 ngày |
| Tuổi tối đa của bộ nhớ đệm HTTP | 30 ngày | 1 ngày | 10 phút |
Tình huống: Lưu vào bộ nhớ đệm dài hạn (Bộ nhớ đệm, dự phòng cho mạng)
- Khi một tài nguyên được lưu vào bộ nhớ đệm có hiệu lực trong bộ nhớ đệm của trình chạy dịch vụ (tối đa 90 ngày): Trình chạy dịch vụ sẽ trả về tài nguyên được lưu vào bộ nhớ đệm ngay lập tức.
- Khi một tài nguyên được lưu vào bộ nhớ đệm đã hết hạn trong bộ nhớ đệm của trình chạy dịch vụ (> 90 ngày): Trình chạy dịch vụ sẽ truy cập vào mạng để tìm nạp tài nguyên. Trình duyệt không có bản sao của tài nguyên trong bộ nhớ đệm HTTP, vì vậy, trình duyệt sẽ chuyển sang phía máy chủ.
Ưu và nhược điểm:
- Ưu điểm: Người dùng trải nghiệm phản hồi tức thì vì trình chạy dịch vụ trả về các tài nguyên được lưu vào bộ nhớ đệm ngay lập tức.
- Ưu điểm: Trình chạy dịch vụ có quyền kiểm soát chi tiết hơn về thời điểm sử dụng bộ nhớ đệm và thời điểm yêu cầu các phiên bản tài nguyên mới.
- Nhược điểm: Bạn phải có một chiến lược lưu vào bộ nhớ đệm của trình chạy dịch vụ được xác định rõ ràng.
Tình huống: Lưu vào bộ nhớ đệm trong thời gian vừa phải (Stale-while-revalidate)
- Khi một tài nguyên được lưu vào bộ nhớ đệm có hiệu lực trong bộ nhớ đệm của trình chạy dịch vụ (tối đa 30 ngày): Trình chạy dịch vụ sẽ trả về tài nguyên được lưu vào bộ nhớ đệm ngay lập tức.
- Khi một tài nguyên được lưu vào bộ nhớ đệm hết hạn trong bộ nhớ đệm của trình chạy dịch vụ (> 30 ngày): Trình chạy dịch vụ sẽ truy cập vào mạng để lấy tài nguyên. Trình duyệt không có bản sao của tài nguyên trong bộ nhớ đệm HTTP, vì vậy, trình duyệt sẽ chuyển sang phía máy chủ.
Ưu và nhược điểm:
- Ưu điểm: Người dùng trải nghiệm phản hồi tức thì vì trình chạy dịch vụ trả về các tài nguyên được lưu vào bộ nhớ đệm ngay lập tức.
- Ưu điểm: Trình chạy dịch vụ có thể đảm bảo rằng yêu cầu tiếp theo cho một URL nhất định sẽ sử dụng phản hồi mới từ mạng, nhờ quá trình xác thực lại diễn ra "trong nền".
- Nhược điểm: Bạn phải có một chiến lược lưu vào bộ nhớ đệm của trình chạy dịch vụ được xác định rõ ràng.
Tình huống: Lưu vào bộ nhớ đệm trong thời gian ngắn (Mạng dự phòng cho bộ nhớ đệm)
- Khi một tài nguyên được lưu vào bộ nhớ đệm có hiệu lực trong bộ nhớ đệm của trình chạy dịch vụ (<= 1 ngày): Trình chạy dịch vụ sẽ truy cập vào mạng để lấy tài nguyên. Trình duyệt sẽ trả về tài nguyên từ bộ nhớ đệm HTTP nếu có. Nếu mạng bị ngừng hoạt động, trình chạy dịch vụ sẽ trả về tài nguyên từ bộ nhớ đệm của trình chạy dịch vụ
- Khi một tài nguyên được lưu vào bộ nhớ đệm hết hạn trong bộ nhớ đệm của trình chạy dịch vụ (> 1 ngày): Trình chạy dịch vụ sẽ truy cập vào mạng để tìm nạp tài nguyên. Trình duyệt tìm nạp các tài nguyên qua mạng khi phiên bản được lưu vào bộ nhớ đệm trong bộ nhớ đệm HTTP đã hết hạn.
Ưu và nhược điểm:
- Ưu điểm: Khi mạng không ổn định hoặc ngừng hoạt động, trình chạy dịch vụ sẽ trả về ngay các tài nguyên được lưu vào bộ nhớ đệm.
- Nhược điểm: Trình chạy dịch vụ yêu cầu thêm tính năng xoá bộ nhớ đệm để ghi đè Bộ nhớ đệm HTTP và đưa ra các yêu cầu "Ưu tiên mạng".
Kết luận
Do sự phức tạp của việc kết hợp các trường hợp lưu vào bộ nhớ đệm, nên không thể thiết kế một quy tắc bao gồm tất cả các trường hợp. Tuy nhiên, dựa trên những phát hiện trong các phần trước, bạn nên xem xét một số đề xuất khi thiết kế chiến lược lưu vào bộ nhớ đệm:
- Logic lưu vào bộ nhớ đệm của trình chạy dịch vụ không cần phải nhất quán với logic hết hạn lưu vào bộ nhớ đệm HTTP. Nếu có thể, hãy sử dụng logic hết hạn dài hơn trong trình chạy dịch vụ để cấp cho trình chạy dịch vụ nhiều quyền kiểm soát hơn.
- Tính năng lưu vào bộ nhớ đệm HTTP vẫn đóng một vai trò quan trọng, nhưng không đáng tin cậy khi mạng không ổn định hoặc bị gián đoạn.
- Xem xét lại các chiến lược lưu vào bộ nhớ đệm cho từng tài nguyên để đảm bảo chiến lược lưu vào bộ nhớ đệm của trình chạy dịch vụ mang lại giá trị mà không xung đột với bộ nhớ đệm HTTP.