Cách dùng nginx dùng nginx để phân phối cơ chế Trao đổi HTTP đã ký

Cách tải và phân phát các tệp SXG bằng nginx cũng như những thách thức của việc tìm nạp trước tài nguyên phụ.

Hiroki Kumazaki
Hiroki Kumazaki

Là nhà phân phối Signed HTTP Exchanges (SXG) (Cơ quan trao đổi HTTP đã ký), bạn có thể phân phối các tệp SXG thay mặt cho nhà sáng tạo nội dung gốc. Các trình duyệt web hỗ trợ SXG sẽ cho thấy các tệp SXG như thể chúng được phân phối từ nhà sáng tạo nội dung ban đầu. Điều này cho phép bạn triển khai tính năng tải trước trên nhiều trang web mà không vi phạm quyền riêng tư. Hướng dẫn này chỉ cho bạn cách phân phối SXG đúng cách.

Hỗ trợ trên nhiều trình duyệt

Chrome hiện là trình duyệt duy nhất hỗ trợ SXG. Xem phần Đồng thuận và Mục tiêu chuẩn hoá của Origin-Signed HTTP Exchanges (Trao đổi HTTP có chữ ký gốc) để biết thêm thông tin mới nhất.

Tải tệp SXG

Hãy chỉ định trong tiêu đề của yêu cầu Accept rằng bạn muốn máy chủ trả về một tệp SXG cùng với yêu cầu:

Accept: application/signed-exchange;v=b3,*/*;q=0.8

Hướng dẫn này giả định rằng bạn đặt các tệp SXG trong /var/www/sxg.

Phân phát một tệp SXG đơn giản

Đính kèm các tiêu đề sau để phân phối một tệp SXG duy nhất:

Content-Type: application/signed-exchange;v=v3
X-Content-Type-Options: nosniff

Định cấu hình nginx:

http {
    ...
    types {
        application/signed-exchange;v=b3  sxg;
    }
    add_header X-Content-Type-Options nosniff;

    location / {
        more_set_headers "Content-Type: application/signed-exchange;v=b3";
        alias /var/www/sxg/;
        try_files $uri.sxg $uri =404;
        autoindex off;
    }
    ...

Tải cấu hình mới vào nginx:

sudo systemctl restart nginx.service

nginx sẽ bắt đầu phân phát các tệp SXG. Khi Chrome truy cập vào máy chủ của bạn, địa chỉ của nhà xuất bản nội dung ban đầu sẽ xuất hiện trong thanh!

Tìm nạp trước tài nguyên phụ

Hầu hết các trang web đều bao gồm nhiều tài nguyên phụ, chẳng hạn như CSS, JavaScript, phông chữ và hình ảnh. Bạn không thể thay đổi nội dung của SXG nếu không có khoá riêng tư của nhà sáng tạo nội dung. Điều này gây ra sự cố khi trình duyệt cố gắng phân giải các tài nguyên phụ.

Ví dụ: giả sử index.html.sxg từ https://website.test/index.html có một đường liên kết đến https://website.test/app.js. Khi nhận được tệp SXG từ https://distributor.test/example.com/index.html.sxg, trình duyệt của người dùng sẽ tìm thấy đường liên kết đến https://website.test/app.js. Trình duyệt có thể tìm nạp https://website.test/app.js trực tiếp khi truy cập thực tế, nhưng bạn không nên thực hiện việc này trong giai đoạn tải trước để bảo vệ quyền riêng tư. Nếu tài nguyên được tìm nạp trong giai đoạn tải trước, thì nhà sáng tạo nội dung (website.test) có thể phát hiện được nhà phân phối nội dung nào (distributor.test) đang yêu cầu tài nguyên.

Đường liên kết đến app.js trong parse.test/index.html.sxg trỏ đến trang web.test/app.js.

Nếu nhà phân phối muốn phân phát app.js.sxg qua dịch vụ của mình và cố gắng sửa đổi https://website.test/app.js thành phiên bản của tài nguyên phụ đó của nhà phân phối (chẳng hạn như https://distributor.test/website.test/app.js.sxg), thì chữ ký sẽ không khớp và khiến SXG không hợp lệ.

Việc cố gắng liên kết tham chiếu đến app.js trong segments.test/index.html.sxg đến segments.test/app.js gây ra lỗi chữ ký không khớp.

Để giải quyết vấn đề này, hiện đã có tính năng tìm nạp trước tài nguyên phụ SXG thử nghiệm trong Chrome. Bạn có thể bật tính năng này tại: about://flags/#enable-sxg-subresource-prefetching. Để sử dụng tính năng tìm nạp trước tài nguyên phụ, bạn phải đáp ứng các điều kiện sau:

  • Nhà xuất bản phải nhúng một mục tiêu đề phản hồi trong SXG, chẳng hạn như: link: <https://website.test/app.js>;rel="preload";as="script",<https://website.test/app.js>;rel="allowed-alt-sxg";header-integrity="sha256-h6GuCtTXe2nITIHHpJM+xCxcKrYDpOFcIXjihE4asxk=". Thông tin này chỉ định tài nguyên phụ có thể thay thế bằng hàm băm cụ thể về tính toàn vẹn của SXG.
  • Nhà phân phối phải đính kèm một tiêu đề phản hồi khi phân phát SXG, chẳng hạn như: link: <https://distributor.test/website.test/app.js.sxg>;rel="alternate";type="application/signed-exchange;v=b3";anchor="https://website.test/app.js". Mã này chỉ định đường dẫn của app.js và tương ứng với tài nguyên phụ.

liên kết

Cách đầu tiên tương đối dễ dàng vì nginx-sxg-module có thể tính toán hàm băm về tính toàn vẹn và nhúng hàm này vào tiêu đề đường liên kết từ các phản hồi tải lên. Nhưng nguyên tắc thứ hai khó hơn vì nhà phân phối nội dung phải biết về các nguồn phụ được chỉ định trong SXG.

Nếu không có tài nguyên phụ nào khác ngoài https://website.test/app.js, thì bạn chỉ cần thêm vào cấu hình nginx là:

add_header link <https://distributor.test/website.test/app.js.sxg>;rel="alter...

Nhưng những trường hợp như vậy rất hiếm vì các trang web điển hình chứa nhiều tài nguyên phụ. Ngoài ra, nhà phân phối phải đính kèm tiêu đề thích hợp của đường liên kết neo khi phân phát tệp SXG. Hiện tại, không có cách nào dễ dàng để giải quyết vấn đề này, vì vậy hãy chú ý theo dõi thông tin cập nhật!

Gửi phản hồi

Các kỹ sư Chromium muốn nghe ý kiến phản hồi của bạn về việc phân phối SXG tại webpackage-dev@chromium.org. Bạn cũng có thể tham gia cuộc thảo luận về thông số kỹ thuật hoặc báo cáo lỗi cho nhóm. Ý kiến phản hồi của bạn sẽ giúp ích rất nhiều cho quá trình chuẩn hoá, đồng thời giúp giải quyết các vấn đề về việc triển khai. Xin cảm ơn!