Cách dùng nginx để thiết lập cơ chế Trao đổi HTTP đã ký (APNS)

Cách tạo chứng chỉ TLS bằng tiện ích SXG, cài đặt công cụ để tạo tệp SXG và định cấu hình nginx để phân phát các tệp SXG.

Hiroki Kumazaki
Hiroki Kumazaki

Signed HTTP Exchanges (SXG) là một công nghệ web mới giúp người dùng dễ dàng phân biệt nhà sáng tạo nội dung với nhà phân phối nội dung. Hướng dẫn này cho bạn biết cách thiết lập SXG.

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

Một số trình duyệt dựa trên Chromium hỗ trợ SXG, bao gồm Google Chrome, Samsung Internet và Microsoft Edge. Hãy xem phần Đồng thuận và chuẩn hoá của bài viết Trao đổi HTTP do nguồn gốc ký để biết thêm thông tin mới nhất.

Điều kiện tiên quyết

Để triển khai SXG trên trang web của bạn, bạn phải:

  • Có quyền kiểm soát miền của bạn, bao gồm cả các mục nhập DNS.
  • Nhận chứng chỉ. SXG yêu cầu phải phát hành một chứng chỉ chuyên dụng. Cụ thể, bạn không thể sử dụng lại khoá hoặc chứng chỉ TLS.
  • Có một máy chủ HTTP có thể tạo và phân phát SXG qua HTTPS.

Các giả định

Hướng dẫn này giả định rằng bạn:

  • Có môi trường OpenSSL 1.1.1. Hướng dẫn này được viết bằng Ubuntu 18.04 LTS trên amd64 ISA.
  • Có khả năng chạy sudo để cài đặt các tệp thực thi.
  • Sử dụng nginx làm máy chủ HTTP.
  • Đang dùng DigiCert để tạo những chứng chỉ có chứa tiện ích liên quan đến SXG, vì có vẻ như đây là nhà cung cấp duy nhất hỗ trợ những tiện ích này.

Ngoài ra, các lệnh mẫu trong bài viết này giả định miền của bạn là website.test, vì vậy, bạn cần thay thế website.test bằng miền thực tế của mình.

Bước 1: Nhận chứng chỉ cho SXG

Để tạo SXG, bạn cần có chứng chỉ TLS có đuôi CanSignHttpExchanges, cũng như một loại khoá cụ thể. DigiCert cung cấp các chứng chỉ có tiện ích này. Bạn cần tệp CSR để cấp chứng chỉ, do đó hãy tạo tệp bằng các lệnh sau:

openssl ecparam -genkey -name prime256v1 -out mySxg.key
openssl req -new -key mySxg.key -nodes -out mySxg.csr -subj "/O=Test/C=US/CN=website.test"

Bạn sẽ nhận được một tệp CSR có dạng như sau:

-----BEGIN CERTIFICATE REQUEST-----
MIHuMIGVAgEAMDMxDTALBgNVBAoMBFRlc3QxCzAJBgNVBAYTAlVTMRUwEwYDVQQD
DAx3ZWJzaXRlLnRlc3QwWTATBgcqhkjOPQIBBggqhkjOPQMBBwNCAAS7IVaeMvid
S5UO7BspzSe5eqT5Qk6X6dCggUiV/vyqQaFDjA/ALyTofgXpbCaksorPaDhdA+f9
APdHWkTbbdv1oAAwCgYIKoZIzj0EAwIDSAAwRQIhAIb7n7Kcc6Y6pU3vFr8SDNkB
kEadlVKNA24SVZ/hn3fjAiAS2tWXhYdJX6xjf2+DL/smB36MKbXg7VWy0K1tWmFi
Sg==
-----END CERTIFICATE REQUEST-----

Hãy chắc chắn rằng:

  • Thời hạn hiệu lực không được vượt quá 90 ngày.
  • Hộp đánh dấu Include the CanSignHttpExchanges extension in the certificate (Thêm tiện ích CanSignHttpExchanges vào chứng chỉ) được bật trong phần Additional Certificate Options (Tuỳ chọn chứng chỉ bổ sung).
Hộp đánh dấu Thêm tiện ích CanSignHttpExchanges vào chứng chỉ.

Nếu chứng chỉ của bạn không phù hợp với các điều kiện này, thì trình duyệt và nhà phân phối sẽ từ chối SXG của bạn vì lý do bảo mật. Hướng dẫn này giả định rằng tên tệp của chứng chỉ bạn nhận được từ DigiCert là mySxg.pem.

Bước 2: Cài đặt libsxg

Định dạng SXG phức tạp và khó tạo nếu không sử dụng công cụ. Bạn có thể sử dụng một trong các tuỳ chọn sau để tạo SXG:

Hướng dẫn này sử dụng libsxg.

Cách 1: Cài đặt libsxg từ gói Debian

Bạn có thể cài đặt gói theo cách thông thường của Debian, miễn là phiên bản OpenSSL (libssl-dev) khớp.

sudo apt install -y libssl-dev
wget https://github.com/google/libsxg/releases/download/v0.2/libsxg0_0.2-1_amd64.deb
wget https://github.com/google/libsxg/releases/download/v0.2/libsxg-dev_0.2-1_amd64.deb
sudo dpkg -i libsxg0_0.2-1_amd64.deb
sudo dpkg -i libsxg-dev_0.2-1_amd64.deb

Lựa chọn 2: Tạo libsxg theo cách thủ công

Nếu không sử dụng một môi trường tương thích với tệp .deb, bạn có thể tự tạo libsxg. Trước tiên, bạn cần cài đặt git, cmake, opensslgcc.

git clone https://github.com/google/libsxg
mkdir libsxg/build
cd libsxg/build
cmake .. -DRUN_TEST=false -DCMAKE_BUILD_TYPE=Release
make
sudo make install

Bước 3: Cài đặt trình bổ trợ nginx

Trình bổ trợ nginx cho phép bạn tạo SXG một cách linh động thay vì tạo SXG một cách tĩnh trước khi phân phát.

Cách 1: Cài đặt trình bổ trợ từ một gói Debian

Mô-đun SXG cho nginx được phân phối trên GitHub. Trên các hệ thống dựa trên Debian, bạn có thể cài đặt gói này dưới dạng gói nhị phân:

sudo apt install -y nginx=1.15.9-0
wget https://github.com/google/nginx-sxg-module/releases/download/v0.1/libnginx-mod-http-sxg-filter_1.15.9-0ubuntu1.1_amd64.deb
sudo dpkg -i libnginx-mod-http-sxg-filter_1.15.9-0ubuntu1.1_amd64.deb

Cách 2: Tạo trình bổ trợ theo cách thủ công

Bạn cần có mã nguồn nginx để tạo mô-đun nginx. Bạn có thể tải tệp tarball và tạo tệp đó cùng với mô-đun động SXG bằng các lệnh dưới đây:

git clone https://github.com/google/nginx-sxg-module
wget https://nginx.org/download/nginx-1.17.5.tar.gz
tar xvf nginx-1.17.5.tar.gz
cd nginx-1.17.5
./configure --prefix=/opt/nginx --add-dynamic-module=../nginx-sxg-module --without-http_rewrite_module --with-http_ssl_module
make
sudo make install

Cấu hình nginx có tính linh hoạt tuyệt vời. Cài đặt nginx ở bất kỳ vị trí nào trong hệ thống, sau đó chỉ định đường dẫn tương ứng của module/config/log/pidfile. Hướng dẫn này giả định rằng bạn đã cài đặt ứng dụng vào /opt/nginx.

Bước 4: Định cấu hình trình bổ trợ nginx để hoạt động với SXG

Cách 1: Định cấu hình mô-đun nginx được cài đặt từ Debian

Hãy làm theo hướng dẫn này nếu trước đó bạn đã sử dụng Bước 3, Lựa chọn 1.

Bạn cần sử dụng HTTPS để phân phối nội dung SXG. Bạn có thể lấy chứng chỉ SSL/TLS từ DigiCert, Let's Encrypt và các dịch vụ khác. Xin lưu ý rằng bạn KHÔNG THỂ sử dụng chứng chỉ SXG cho SSL hoặc ngược lại. Do đó, bạn sẽ cần 2 chứng chỉ. Tệp cấu hình trong /etc/nginx/nginx.conf sẽ có dạng như sau, giả sử bạn đặt cặp khoá/chứng chỉ SSL trong /path/to/ssl/ và cặp khoá/chứng chỉ SXG trong /path/to/sxg/:

user www-data;
include /etc/nginx/modules-enabled/*.conf;

events {
     worker_connections 768;
}

http {
    include       mime.types;
    default_type  application/octet-stream;
    add_header  X-Content-Type-Options nosniff;

    server {
        listen 443 ssl;
        ssl_certificate     /path/to/ssl/fullchain.pem;
        ssl_certificate_key /path/to/ssl/privkey.pem;
        server_name  website.test;

        sxg on;
        sxg_certificate     /path/to/sxg/mySxg.pem;
        sxg_certificate_key /path/to/sxg/mySxg.key;
        sxg_cert_url        https://website.test/certs/cert.cbor;
        sxg_validity_url    https://website.test/validity/resource.msg;
        sxg_cert_path       /certs/cert.cbor;

        root /var/www/html;
    }
}
  • sxg_cert_url là yếu tố cần thiết để trình duyệt tải SXG đúng cách vì nó xác định vị trí chuỗi chứng chỉ. Chuỗi chứng chỉ chứa chứng chỉ và thông tin ghim OCSP ở định dạng cbor. Xin lưu ý rằng bạn không phải phân phát tệp cert.cbor từ cùng một nguồn gốc. Bạn có thể phân phát tệp này thông qua bất kỳ CDN nào hoặc dịch vụ phân phát tệp tĩnh khác, miễn là dịch vụ đó hỗ trợ HTTPS.
  • sxg_validitiy_url dự kiến sẽ phân phát thông tin liên quan đến tiêu đề chữ ký SXG. Nếu một trang chưa được sửa đổi sau lần sử dụng SXG gần đây nhất, thì bạn không cần phải tải toàn bộ tệp SXG xuống về mặt kỹ thuật. Vì vậy, việc chỉ cập nhật thông tin tiêu đề chữ ký có thể sẽ làm giảm lưu lượng truy cập mạng. Nhưng thông tin chi tiết vẫn chưa được triển khai.

Khởi động nginx để bạn có thể phân phát SXG!

sudo systemctl start nginx.service
curl -H"Accept: application/signed-exchange;v=b3" https://website.test/ > index.html.sxg
cat index.html.sxg
sxg1-b3...https://website.test/...(omit)

Cách 2: Định cấu hình mô-đun nginx được tạo từ nguồn

Hãy làm theo các hướng dẫn này nếu trước đó bạn đã sử dụng Bước 3, Tùy chọn 2.

Định cấu hình hệ thống nginx được cài đặt trong /opt/nginx sao cho tương tự như ví dụ sau:

load_module "/opt/nginx/modules/ngx_http_sxg_filter_module.so";

events {
    worker_connections 768;
}

http {
    include       mime.types;
    default_type  application/octet-stream;
    add_header X-Content-Type-Options nosniff;

    server {
        listen 443 ssl;
        ssl_certificate     /path/to/ssl/fullchain.pem;
        ssl_certificate_key /path/to/ssl/privkey.pem;
        server_name  example.com;

        sxg on;
        sxg_certificate     /path/to/sxg/mySxg.pem;
        sxg_certificate_key /path/to/sxg/mySxg.key;
        sxg_cert_url        https://website.test/certs/cert.cbor;
        sxg_validity_url    https://website.test/validity/resource.msg;
        sxg_cert_path       /certs/cert.cbor;

        root /opt/nginx/html;
    }
}

Sau đó, hãy bắt đầu nginx. Giờ đây, bạn có thể nhận SXG!

cd /opt/nginx/sbin
sudo ./nginx
curl -H "Accept: application/signed-exchange;v=b3" https://website.test/ > index.html.sxg
less index.html.sxg
sxg1-b3...https://website.test/...(omit)

Bước 5: Phân phát phần phụ trợ ứng dụng

Trong các ví dụ trên, nginx phân phát các tệp tĩnh trong thư mục gốc, nhưng bạn có thể sử dụng các lệnh ngược dòng cho ứng dụng của mình để tạo SXG cho phần phụ trợ ứng dụng web tuỳ ý (chẳng hạn như Ruby on Rails, Django hoặc Express) miễn là nginx hoạt động như một máy chủ HTTP(S) phía trước.

upstream app {
    server 127.0.0.1:8080;
}

server {
    location / {
        proxy_pass http://app;
    }
}

Bước 6: Kiểm thử

Sử dụng công cụ trao đổi đã ký tệp báo lỗi để kiểm tra xem các SXG đang được phân phát có chính xác hay không, đảm bảo không có lỗi nào được báo cáo và xác minh rằng tiêu đề và nội dung là như dự kiến.

go get -u github.com/WICG/webpackage/go/signedexchange/cmd/dump-signedexchange
export PATH=$PATH:~/go/bin
dump-signedexchange -verify -uri https://website.test/ | less

Gửi phản hồi

Các kỹ sư Chromium đang làm việc trên SXG rất mong nhận được ý kiến phản hồi của bạn 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!