CyStack logo
  • Sản phẩm & Dịch vụ
  • Giải pháp
  • Bảng giá
  • Công ty
  • Tài liệu
Vi

vi

Trang chủHướng dẫnTạo chứng chỉ SSL tự ký cho Nginx trên Centos 7

Tạo chứng chỉ SSL tự ký cho Nginx trên Centos 7

CyStack blog 10 phút để đọc
CyStack blog06/09/2025
Locker Avatar

Chris Pham

Technical Writer

Locker logo social
Reading Time: 10 minutes

TLS (Transport Layer Security) và tiền nhiệm của nó là SSL (Secure Sockets Layer) là các giao thức web được sử dụng để bao bọc lưu lượng thông thường trong một lớp bảo mật được mã hóa.

Với công nghệ này, máy chủ có thể gửi dữ liệu an toàn giữa máy chủ và các máy khách, ngăn chặn khả năng các thông điệp bị chặn từ bên thứ ba. Hệ thống chứng chỉ cũng giúp người dùng xác minh danh tính của các trang web mà họ kết nối.

Trong hướng dẫn này, chúng ta tạo chứng chỉ SSL tự ký cho Nginx trên Centos 7.

tạo chứng chỉ SSL tự ký cho Nginx trên CentOS 7

Lưu ý, chứng chỉ tự ký sẽ mã hóa dữ liệu trao đổi giữa máy chủ và máy khách. Tuy nhiên, do không được ký bởi các tổ chức chứng thực (CA) tin cậy được tích hợp sẵn trong trình duyệt web nên người dùng sẽ không thể tự động xác minh danh tính của máy chủ. Kết quả là, khi truy cập trang web, họ sẽ thấy cảnh báo bảo mật.

Vì hạn chế này, chứng chỉ tự ký không phù hợp để sử dụng trong môi trường production phục vụ công chúng. Chúng thường được dùng cho mục đích kiểm thử hoặc bảo mật các dịch vụ không quan trọng, phục vụ cho một người dùng hoặc một nhóm nhỏ có thể xác lập niềm tin vào chứng chỉ thông qua các kênh liên lạc khác.

Để có giải pháp chứng chỉ phù hợp cho môi trường sản xuất, bạn hãy tham khảo Let’s Encrypt, một tổ chức chứng thực miễn phí. Bạn có thể tìm hiểu cách tải và cấu hình chứng chỉ Let’s Encrypt trong hướng dẫn thiết lập Nginx với chứng chỉ Let’s Encrypt trên CentOS 7.

Yêu cầu

Để hoàn thành hướng dẫn này, bạn cần chuẩn bị:

  • Một máy chủ CentOS với người dùng không phải root được cấp quyền sudo, như đã mô tả trong hướng dẫn cài đặt máy chủ CentOS 7 ban đầu.
  • Nginx đã được cài đặt trên máy chủ, như trong hướng dẫn Cài đặt Nginx trên CentOS 7.

Khi đã sẵn sàng, hãy đăng nhập vào máy chủ với tài khoản sudo.

Bước 1: Tạo chứng chỉ SSL

TLS/SSL hoạt động bằng cách kết hợp chứng chỉ công khai và khóa bí mật.

  • Khóa SSL được lưu kín trên máy chủ và dùng để mã hóa dữ liệu gửi tới máy khách.
  • Chứng chỉ SSL được chia sẻ công khai cho bất kỳ ai yêu cầu nội dung và có thể được dùng để giải mã dữ liệu được ký từ khóa tương ứng.

Thư mục /etc/ssl/certs, dùng để lưu chứng chỉ công khai, thường đã tồn tại trên máy chủ. Bạn sẽ cần tạo thêm thư mục /etc/ssl/private để lưu khóa bí mật. Vì khóa này cần được bảo mật tuyệt đối nên bạn phải giới hạn quyền truy cập để tránh bị rò rỉ:

sudo mkdir /etc/ssl/private
sudo chmod 700 /etc/ssl/private

Tiếp theo, tạo cặp khóachứng chỉ tự ký bằng OpenSSL chỉ với một lệnh:

sudo openssl req -x509 -nodes -days 365 -newkey rsa:2048 \\
-keyout /etc/ssl/private/nginx-selfsigned.key \\
-out /etc/ssl/certs/nginx-selfsigned.crt

Bạn sẽ được yêu cầu trả lời một loạt câu hỏi. Trước khi đi vào phần đó, chúng ta hãy xem lệnh trên đang thực hiện những gì:

  • openssl: Đây là công cụ dòng lệnh cơ bản để tạo và quản lý chứng chỉ, khóa và các tệp khác của OpenSSL.
  • req: Tiểu lệnh này chỉ định rằng bạn muốn sử dụng chức năng quản lý yêu cầu ký chứng chỉ (CSR) theo chuẩn X.509. “X.509” là một tiêu chuẩn hạ tầng khóa công khai (PKI) mà SSL và TLS tuân theo để quản lý khóa và chứng chỉ. Khi muốn tạo một chứng chỉ X.509 mới, bạn sẽ cần dùng tiểu lệnh này.
  • x509: Tùy chọn này bổ sung cho tiểu lệnh trước bằng cách thông báo cho tiện ích rằng bạn muốn tạo một chứng chỉ tự ký thay vì tạo yêu cầu ký chứng chỉ như thông thường.
  • nodes: Tùy chọn này yêu cầu OpenSSL bỏ qua bước bảo vệ chứng chỉ bằng cụm mật khẩu (passphrase). Bạn cần làm vậy để Nginx có thể đọc tệp này mà không cần sự can thiệp của người dùng khi máy chủ khởi động. Nếu chứng chỉ có cụm mật khẩu, mỗi lần khởi động lại bạn sẽ phải nhập nó, điều này sẽ ngăn quá trình tự động khởi động hoạt động trơn tru.
  • days 365: Tùy chọn này đặt thời hạn hiệu lực của chứng chỉ. Ở đây, bạn đặt là 1 năm.
  • newkey rsa:2048: Tùy chọn này chỉ định rằng bạn muốn tạo mới cả chứng chỉ và khóa cùng lúc. Bạn chưa tạo khóa cần để ký chứng chỉ ở bước trước, vì vậy bạn cần tạo nó cùng với chứng chỉ. Phần rsa:2048 yêu cầu tạo khóa RSA có độ dài 2048 bit.
  • keyout: Tùy chọn này cho OpenSSL biết vị trí lưu tệp khóa riêng tư được tạo.
  • out: Tùy chọn này cho OpenSSL biết vị trí lưu chứng chỉ được tạo.

Như đã đề cập ở trên, các tùy chọn này sẽ tạo cả tệp khóa và chứng chỉ. Bạn sẽ được hỏi một số thông tin về máy chủ để nhúng chính xác thông tin này vào chứng chỉ.

Hãy điền thông tin phù hợp vào các yêu cầ. Dòng quan trọng nhất là dòng yêu cầu Common Name (ví dụ: tên miền đầy đủ của máy chủ hoặc tên của bạn). Bạn cần nhập tên miền gắn với máy chủ hoặc địa chỉ IP công khai của máy chủ.

Toàn bộ phần câu hỏi sẽ trông như sau:

Country Name (2 letter code) [XX]:US
State or Province Name (full name) []:Example
Locality Name (eg, city) [Default City]:Example
Organization Name (eg, company) [Default Company Ltd]:Example Inc
Organizational Unit Name (eg, section) []:Example Dept
Common Name (eg, your name or your server's hostname) []:your_domain_or_ip
Email Address []:webmaster@example.com

Cả hai tệp bạn vừa tạo sẽ được đặt trong các thư mục con tương ứng của thư mục /etc/ssl.

Vì bạn đang sử dụng OpenSSL nên hãy tạo một nhóm Diffie-Hellman mạnh, nhóm này được dùng để đàm phán Bảo mật chuyển tiếp hoàn hảo (Perfect Forward Secrecy) với các client.

Bạn có thể thực hiện việc này bằng cách nhập lệnh:

sudo openssl dhparam -out /etc/ssl/certs/dhparam.pem 2048

Có thể phải mất vài phút để hoàn thành lệnh này nhưng sau khi hoàn tất bạn sẽ có một nhóm DH mạnh tại /etc/ssl/certs/dhparam.pem để dùng trong cấu hình.

Bước 2: Cấu hình Nginx sử dụng SSL

Cấu hình mặc định của Nginx trong CentOS khá đơn giản, với khối máy chủ HTTP mặc định nằm trong tệp cấu hình chính. Nginx sẽ kiểm tra các tệp kết thúc bằng .conf trong thư mục /etc/nginx/conf.d để nạp thêm cấu hình.

Bạn sẽ tạo một tệp mới trong thư mục này để cấu hình một server block phục vụ nội dung bằng các tệp chứng chỉ mà bạn đã tạo. Sau đó, bạn có thể tùy chọn cấu hình khối máy chủ mặc định để chuyển hướng các yêu cầu HTTP sang HTTPS.

Tạo server block TLS/SSL

Tạo và mở tệp ssl.conf trong thư mục /etc/nginx/conf.d:

sudo vi /etc/nginx/conf.d/ssl.conf

Bên trong, bắt đầu bằng việc mở một server block. Theo mặc định, kết nối TLS/SSL sử dụng cổng 443, vì vậy đây sẽ là cổng listen. Bạn nên đặt server_name là tên miền hoặc địa chỉ IP của máy chủ mà bạn đã dùng làm Common Name khi tạo chứng chỉ. Tiếp theo, dùng các chỉ thị ssl_certificate, ssl_certificate_keyssl_dhparam để chỉ vị trí của các tệp SSL mà bạn đã tạo:

/etc/nginx/conf.d/ssl.conf
server {
    listen 443 http2 ssl;
    listen [::]:443 http2 ssl;

    server_name your_server_ip;

    ssl_certificate /etc/ssl/certs/nginx-selfsigned.crt;
    ssl_certificate_key /etc/ssl/private/nginx-selfsigned.key;
    ssl_dhparam /etc/ssl/certs/dhparam.pem;
}

Tiếp theo, bạn sẽ thêm một số tùy chọn SSL bổ sung để tăng cường bảo mật cho trang web. Các tùy chọn này được lấy từ khuyến nghị của Cipherlist.eu, trang cung cấp các thiết lập mã hóa dễ áp dụng cho phần mềm phổ biến.

Lưu ý: Cấu hình mặc định được gợi ý trên Cipherlist.eu cung cấp mức bảo mật cao, đôi khi điều này làm giảm khả năng tương thích với các client cũ. Nếu cần hỗ trợ các client cũ, bạn có thể dùng danh sách tương thích thay thế bằng cách nhấn vào liên kết “Yes, give me a ciphersuite that works with legacy/old software”.

Danh sách cấu hình tương thích có thể được sử dụng thay cho các gợi ý mặc định trong phần cấu hình ở trên, nằm giữa hai khối chú thích. Việc lựa chọn cấu hình nào sẽ phụ thuộc chủ yếu vào những gì bạn cần hỗ trợ.

Bạn có thể tùy chỉnh một số phần trong cấu hình. Trước hết, hãy thêm DNS resolver mà bạn muốn sử dụng cho các yêu cầu upstream vào chỉ thị resolver. Trong hướng dẫn này, chúng ta dùng DNS của Google, nhưng bạn có thể thay đổi nếu muốn sử dụng một tùy chọn khác.

Ngoài ra, bạn nên tìm hiểu về HTTP Strict Transport Security (HSTS), đặc biệt là tính năng preload. Tính năng này giúp tăng cường bảo mật nhưng có thể gây hậu quả nghiêm trọng nếu kích hoạt nhầm hoặc cấu hình sai. Trong hướng dẫn này, chúng ta sẽ không bật preload, nhưng bạn có thể tự kích hoạt nếu nắm rõ tác động của nó.

/etc/nginx/conf.d/ssl.conf
server {
    listen 443 http2 ssl;
    listen [::]:443 http2 ssl;

    server_name your_server_ip;

    ssl_certificate /etc/ssl/certs/nginx-selfsigned.crt;
    ssl_certificate_key /etc/ssl/private/nginx-selfsigned.key;
    ssl_dhparam /etc/ssl/certs/dhparam.pem;

    ########################################################################
    # from <https://cipherlist.eu/>                                          #
    ########################################################################

    ssl_protocols TLSv1.3; # Requires nginx >= 1.13.0 else use TLSv1.2
    ssl_prefer_server_ciphers on;
    ssl_ciphers EECDH+AESGCM:EDH+AESGCM;
    ssl_ecdh_curve secp384r1; # Requires nginx >= 1.1.0
    ssl_session_timeout  10m;
    ssl_session_cache shared:SSL:10m;
    ssl_session_tickets off; # Requires nginx >= 1.5.9
    ssl_stapling on; # Requires nginx >= 1.3.7
    ssl_stapling_verify on; # Requires nginx >= 1.3.7
    resolver 8.8.8.8 8.8.4.4 valid=300s;
    resolver_timeout 5s;
    # Disable preloading HSTS for now. Uncomment the following line if you understand the implications.
    #add_header Strict-Transport-Security "max-age=63072000; includeSubDomains; preload";
    add_header X-Frame-Options DENY;
    add_header X-Content-Type-Options nosniff;
    add_header X-XSS-Protection "1; mode=block";
    ##################################
    # END <https://cipherlist.eu/> BLOCK #
    ##################################
}

Vì bạn đang sử dụng chứng chỉ tự ký nên SSL stapling sẽ không được dùng trong trường hợp này. Nginx sẽ chỉ hiển thị cảnh báo, tắt stapling cho chứng chỉ tự ký và vẫn hoạt động bình thường.

Cuối cùng, bạn hãy thêm phần cấu hình Nginx còn lại cho trang web của bạn. Phần này sẽ khác nhau tùy theo nhu cầu của mỗi người. Trong ví dụ này, bạn chỉ cần sao chép một số chỉ thị được sử dụng trong khối location mặc định, phần này sẽ thiết lập thư mục gốc tài liệu và một số trang lỗi.

/etc/nginx/conf.d/ssl.conf
server {
    listen 443 http2 ssl;
    listen [::]:443 http2 ssl;

    server_name your_server_ip;

    ssl_certificate /etc/ssl/certs/nginx-selfsigned.crt;
    ssl_certificate_key /etc/ssl/private/nginx-selfsigned.key;
    ssl_dhparam /etc/ssl/certs/dhparam.pem;

    ########################################################################
    # from <https://cipherlist.eu/>                                          #
    ########################################################################

    . . .

    ##################################
    # END <https://cipherlist.eu/> BLOCK #
    ##################################

    root /usr/share/nginx/html;

    location / {
    }

    error_page 404 /404.html;
    location = /404.html {
    }

    error_page 500 502 503 504 /50x.html;
    location = /50x.html {
    }
}

Khi hoàn tất, lưu và thoát. Cấu hình này giúp Nginx dùng chứng chỉ SSL bạn tạo để mã hóa lưu lượng, đảm bảo chỉ các giao thức và bộ mã hóa an toàn nhất mới được sử dụng. Lưu ý, cấu hình ví dụ này chỉ phục vụ trang mặc định của Nginx, vì vậy bạn có thể chỉnh sửa để phù hợp với nhu cầu của mình (nếu muốn

Tạo chuyển hướng từ HTTP sang HTTPS (Tùy chọn)

Với cấu hình hiện tại, Nginx phản hồi nội dung mã hóa cho các yêu cầu trên cổng 443, còn nội dung không mã hóa sẽ được phản hồi cho các yêu cầu trên cổng 80. Cách cấu hình này có nghĩa là trang web của bạn hỗ trợ mã hóa nhưng không bắt buộc sử dụng. Trong một số trường hợp, lựa chọn này có thể chấp nhận được nhưng thông thường bạn nên yêu cầu mã hóa, đặc biệt khi có dữ liệu nhạy cảm như mật khẩu được truyền giữa trình duyệt và máy chủ.

May mắn là tệp cấu hình mặc định của Nginx cho phép chúng ta dễ dàng thêm chỉ thị vào khối máy chủ mặc định trên cổng 80. Bạn có thể thực hiện việc này bằng cách chèn đoạn sau vào đầu tệp ssl.conf:

/etc/nginx/conf.d/ssl.conf
server {
    listen 80;
    listen [::]:80;
    server_name your_server_ip;
    return 301 https://$host$request_uri;
}
...

Khi hoàn tất, lưu và đóng tệp. Cấu hình này sẽ khiến khối máy chủ HTTP trên cổng 80 (mặc định) chuyển hướng các yêu cầu đến khối máy chủ HTTPS mà bạn đã cấu hình.

Bước 3: Áp dụng thay đổi trong Nginx

Sau khi bạn đã thực hiện các thay đổi, hãy khởi động lại Nginx để áp dụng cấu hình mới.

Trước tiên, bạn nên kiểm tra để đảm bảo không còn lỗi cú pháp nào trong các tệp cấu hình. Bạn có thể thực hiện bằng lệnh:

sudo nginx -t

Nếu mọi thứ đều phù hợp, bạn sẽ nhận được kết quả như sau:

nginx: [warn] "ssl_stapling" ignored, issuer certificate not found
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful

Hãy chú ý đến cảnh báo ở đầu. Như đã đề cập trước đó, thiết lập này tạo ra cảnh báo vì chứng chỉ tự ký không thể sử dụng SSL stapling. Điều này là bình thường và máy chủ của bạn vẫn có thể mã hóa kết nối chính xác.

Nếu kết quả của bạn giống như trên, tức là tệp cấu hình không có lỗi cú pháp, bạn có thể khởi động lại Nginx để áp dụng thay đổi:

sudo systemctl restart nginx

Tiến trình Nginx sẽ được khởi động lại và áp dụng các thiết lập SSL mà bạn đã cấu hình.

Bước 4: Kiểm tra mã hóa

Bây giờ, bạn đã sẵn sàng để kiểm tra máy chủ SSL.

Mở trình duyệt web và nhập https:// theo sau là tên miền hoặc địa chỉ IP của máy chủ vào thanh địa chỉ:

https://server_domain_or_IP

Vì chứng chỉ bạn tạo không được ký bởi một trong các tổ chức chứng chỉ (CA) đáng tin cậy của trình duyệt, nên bạn sẽ thấy một cảnh báo trông “đáng sợ” giống như hình bên dưới:

Tạo chứng chỉ SSL tự ký cho Nginx trên Centos 7

Cảnh báo chứng chỉ tự ký của Nginx

Đây là hiện tượng bình thường và đã được dự đoán trước. Bạn chỉ cần quan tâm đến khả năng mã hóa của chứng chỉ, không phải việc xác thực tính hợp lệ của máy chủ từ bên thứ ba. Nhấn “ADVANCED” rồi chọn liên kết được cung cấp để tiếp tục truy cập máy chủ:

Tạo chứng chỉ SSL tự ký cho Nginx trên Centos 7

Bỏ qua cảnh báo chứng chỉ tự ký của Nginx

Bạn sẽ được chuyển đến trang web của mình. Nếu nhìn vào thanh địa chỉ của trình duyệt, bạn sẽ thấy dấu hiệu về mức bảo mật một phần, có thể là biểu tượng ổ khóa có dấu “x” hoặc hình tam giác có dấu chấm than. Trong trường hợp này, điều đó chỉ có nghĩa là chứng chỉ không thể được xác thực, nhưng kết nối của bạn vẫn đang được mã hóa.

Nếu bạn đã cấu hình Nginx để chuyển hướng các yêu cầu HTTP sang HTTPS, bạn cũng có thể kiểm tra xem chuyển hướng có hoạt động đúng không:

http://server_domain_or_IP

Nếu kết quả hiển thị cùng biểu tượng như trên, điều đó nghĩa là chuyển hướng của bạn hoạt động đúng như mong đợi.

Kết luận

Bạn đã cấu hình Nginx để sử dụng mã hóa mạnh cho các kết nối từ client. Nhờ đó, máy chủ có thể xử lý các yêu cầu một cách an toàn và ngăn chặn bên thứ ba đọc được lưu lượng truyền giữa client và máy chủ.

0 Bình luận

Đăng nhập để thảo luận

Chuyên mục Hướng dẫn

Tổng hợp các bài viết hướng dẫn, nghiên cứu và phân tích chi tiết về kỹ thuật, các xu hướng công nghệ mới nhất dành cho lập trình viên.

Đăng ký nhận bản tin của chúng tôi

Hãy trở thành người nhận được các nội dung hữu ích của CyStack sớm nhất

Xem chính sách của chúng tôi Chính sách bảo mật.

Đăng ký nhận Newsletter

Nhận các nội dung hữu ích mới nhất