Cách cài đặt WordPress với Docker Compose
WordPress là một Hệ thống Quản lý Nội dung (CMS) open-souce và miễn phí được xây dựng trên cơ sở dữ liệu MySQL với xử lý PHP . Nhờ kiến trúc plugin có thể mở rộng và hệ thống tạo mẫu, và thực tế là hầu hết việc quản trị của nó có thể được thực hiện thông qua giao diện web, WordPress là một lựa chọn phổ biến khi tạo các loại trang web khác nhau, từ blog đến các trang sản phẩm đến các trang Thương mại điện tử.Chạy WordPress thường liên quan đến việc cài đặt ngăn xếp LAMP (Linux, Apache, MySQL và PHP) hoặc LEMP (Linux, Nginx, MySQL và PHP), điều này có thể tốn nhiều thời gian. Tuy nhiên, bằng cách sử dụng các công cụ như Docker và Docker Compose , bạn có thể đơn giản hóa quá trình cài đặt ngăn xếp ưa thích của bạn và cài đặt WordPress. Thay vì cài đặt các thành phần riêng lẻ bằng tay, bạn có thể sử dụng hình ảnh để chuẩn hóa những thứ như thư viện, file cấu hình và biến môi trường và chạy những hình ảnh này trong các containers , các quy trình riêng biệt chạy trên hệ điều hành dùng chung. Ngoài ra, bằng cách sử dụng Soạn thư, bạn có thể phối hợp nhiều containers - ví dụ: một ứng dụng và database - để giao tiếp với nhau.
Trong hướng dẫn này, bạn sẽ xây dựng một cài đặt WordPress nhiều containers . Vùng chứa của bạn sẽ bao gồm database MySQL, web server Nginx và chính WordPress. Bạn cũng sẽ bảo mật cài đặt của bạn bằng cách lấy certificate TLS / SSL với Let's Encrypt cho domain bạn muốn liên kết với trang web của bạn . Cuối cùng, bạn sẽ cài đặt một cron
việc cron
để gia hạn certificate của bạn để domain của bạn vẫn an toàn.
Yêu cầu
Để làm theo hướng dẫn này, bạn cần :
- Server chạy Ubuntu 18.04, cùng với user không phải root có quyền
sudo
và firewall đang hoạt động. Để được hướng dẫn về cách cài đặt những điều này, vui lòng xem hướng dẫn Cài đặt Server Ban đầu này. - Docker được cài đặt trên server của bạn, làm theo các Bước 1 và 2 của Cách cài đặt và sử dụng Docker trên Ubuntu 18.04 .
- Docker Compose được cài đặt trên server của bạn, làm theo Bước 1 của Cách cài đặt Docker Compose trên Ubuntu 18.04 .
- Tên domain đã đăng ký. Hướng dẫn này sẽ sử dụng example.com xuyên suốt. Bạn có thể nhận một miễn phí tại Freenom hoặc sử dụng công ty đăng ký domain mà bạn chọn.
Cả hai bản ghi DNS sau được cài đặt cho server của bạn. Bạn có thể theo dõi phần giới thiệu này về DigitalOcean DNS để biết chi tiết về cách thêm chúng vào account DigitalOcean, nếu đó là những gì bạn đang sử dụng:
- Bản ghi A với
example.com
trỏ đến địa chỉ IP công cộng của server của bạn. - Một bản ghi A với
www. example.com
trỏ đến địa chỉ IP công cộng của server của bạn.
- Bản ghi A với
Bước 1 - Xác cấu hình web server
Trước khi chạy bất kỳ containers nào, bước đầu tiên của ta sẽ là xác cấu hình cho web server Nginx của ta . Tệp cấu hình của ta sẽ bao gồm một số khối vị trí dành riêng cho WordPress, cùng với khối vị trí để hướng các yêu cầu xác minh Let's Encrypt đến ứng dụng client Certbot để gia hạn certificate tự động.
Đầu tiên, hãy tạo một folder dự án cho cài đặt WordPress của bạn có tên là wordpress
và chuyển đến nó:
- mkdir wordpress && cd wordpress
Tiếp theo, tạo một folder cho file cấu hình:
- mkdir nginx-conf
Mở file bằng nano
hoặc editor bạn quen dùng :
- nano nginx-conf/nginx.conf
Trong file này, ta sẽ thêm một khối server với các lệnh cho tên server và root tài liệu của ta cũng như các khối vị trí để định hướng yêu cầu của ứng dụng client Certbot đối với certificate , PHP processor và các yêu cầu nội dung tĩnh.
Dán đoạn mã sau vào file . Đảm bảo thay thế example.com
bằng domain của bạn :
server { listen 80; listen [::]:80; server_name example.com www.example.com; index index.php index.html index.htm; root /var/www/html; location ~ /.well-known/acme-challenge { allow all; root /var/www/html; } location / { try_files $uri $uri/ /index.php$is_args$args; } location ~ \.php$ { try_files $uri =404; fastcgi_split_path_info ^(.+\.php)(/.+)$; fastcgi_pass wordpress:9000; fastcgi_index index.php; include fastcgi_params; fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name; fastcgi_param PATH_INFO $fastcgi_path_info; } location ~ /\.ht { deny all; } location = /favicon.ico { log_not_found off; access_log off; } location = /robots.txt { log_not_found off; access_log off; allow all; } location ~* \.(css|gif|ico|jpeg|jpg|js|png)$ { expires max; log_not_found off; } }
Khối server của ta bao gồm các thông tin sau:
Chỉ thị:
-
listen
: Đây nói với Nginx để lắng nghe trên cổng80
, mà sẽ cho phép ta sử dụng Certbot của Plugin webroot cho các yêu cầu giấy chứng nhận của ta . Lưu ý ta chưa bao gồm cổng443
- ta sẽ cập nhật cấu hình của bạn để bao gồm SSL khi ta đã lấy được certificate thành công. -
server_name
: Điều này xác định tên server của bạn và khối server sẽ được sử dụng cho các yêu cầu tới server của bạn. Đảm bảo thay thếexample.com
trong dòng này bằng domain của bạn . -
index
:index
thịindex
xác định các file sẽ được sử dụng làm index khi xử lý các yêu cầu đến server của bạn. Ta đã sửa đổi thứ tự ưu tiên mặc định ở đây, di chuyểnindex.php
trướcindex.html
để Nginx ưu tiên các file được gọi làindex.php
khi có thể. -
root
: Chỉ thịroot
của ta đặt tên cho folder root cho các yêu cầu tới server của ta . Thư mục này,/var/www/html
, được tạo như một điểm mount tại thời điểm xây dựng theo hướng dẫn trong WordPress Dockerfile của ta . Các hướng dẫn Dockerfile này cũng đảm bảo các file từ bản phát hành WordPress được gắn vào ổ đĩa này.
Khối vị trí:
-
location ~ /.well-known/acme-challenge
: Khối vị trí này sẽ xử lý các yêu cầu.well-known
folder .well.well-known
, nơi Certbot sẽ đặt một file tạm thời để xác thực rằng DNS cho domain của ta phân giải tới server của ta . Với cấu hình này, ta sẽ có thể sử dụng plugin webroot của Certbot để lấy certificate cho domain của ta . -
location /
: Trong khối vị trí này, ta sẽ sử dụng lệnhtry_files
để kiểm tra các file phù hợp với các yêu cầu URI riêng lẻ. Tuy nhiên, thay vì trả về trạng thái 404Not Found
làm mặc định, ta sẽ chuyển quyền kiểm soát đếnindex.php
của WordPress với các đối số yêu cầu. -
location ~ \.php$
: Khối vị trí này sẽ xử lý quá trình PHP processor và ủy quyền các yêu cầu này tới containerswordpress
của ta . Vì Docker image WordPress của ta sẽ dựa trên hình ảnhphp:fpm
, ta cũng sẽ bao gồm các tùy chọn cấu hình dành riêng cho giao thức FastCGI trong khối này. Nginx yêu cầu một PHP processor độc lập cho các yêu cầu PHP: trong trường hợp của ta , các yêu cầu này sẽ được xử lý bởi bộ xử lýphp-fpm
bao gồm trong hình ảnhphp:fpm
. Ngoài ra, khối vị trí này bao gồm các chỉ thị, biến và tùy chọn dành riêng cho FastCGI sẽ ủy quyền các yêu cầu đến ứng dụng WordPress đang chạy trong containerswordpress
của ta , đặt index ưu tiên cho URI yêu cầu được phân tích cú pháp và phân tích cú pháp các yêu cầu URI. -
location ~ /\.ht
: Khối này sẽ xử lý các.htaccess
vì Nginx sẽ không phân phát chúng. Chỉ thịdeny_all
đảm bảo các.htaccess
sẽ không bao giờ được cung cấp cho user . -
location = /favicon.ico
,location = /robots.txt
: Các khối này đảm bảo các yêu cầu đến/favicon.ico
và/robots.txt
sẽ không được ghi lại. -
location ~* \.(css|gif|ico|jpeg|jpg|js|png)$
: Khối này tắt ghi log cho các yêu cầu nội dung tĩnh và đảm bảo những nội dung này có khả năng lưu vào bộ nhớ cache cao, vì chúng thường đắt tiền để phân phát.
Để biết thêm thông tin về FastCGI proxy, hãy xem Hiểu và triển khai FastCGI Proxying trong Nginx . Để biết thông tin về khối server và vị trí, hãy xem Tìm hiểu về server Nginx và các thuật toán lựa chọn khối vị trí .
Lưu file khi bạn hoàn tất chỉnh sửa.Nếu bạn sử dụng nano
, hãy làm như vậy bằng cách nhấn CTRL+X
, Y
, sau đó ENTER
.
Với cấu hình Nginx của bạn tại chỗ, bạn có thể chuyển sang tạo các biến môi trường để chuyển đến ứng dụng và containers database của bạn trong thời gian chạy.
Bước 2 - Xác định các biến môi trường
Database và containers ứng dụng WordPress của bạn cần quyền truy cập vào các biến môi trường nhất định trong thời gian chạy để dữ liệu ứng dụng của bạn tồn tại và có thể truy cập vào ứng dụng của bạn. Các biến này bao gồm cả thông tin nhạy cảm và không nhạy cảm: giá trị nhạy cảm cho password gốc MySQL và password user và database ứng dụng của bạn và thông tin không nhạy cảm cho tên và server database ứng dụng của bạn.
Thay vì đặt tất cả các giá trị này trong file Docker Compose của ta - file chính chứa thông tin về cách các containers của ta sẽ chạy - ta có thể đặt các giá trị nhạy cảm trong file .env
và hạn chế lưu thông của nó. Điều này sẽ ngăn các giá trị này sao chép vào kho dự án của ta và bị lộ công khai.
Trong folder dự án chính của bạn, ~/ wordpress
, hãy mở một file có tên .env
:
- nano .env
Các giá trị bí mật mà ta sẽ đặt trong file này bao gồm password cho user gốc MySQL của ta , tên user và password mà WordPress sẽ sử dụng để truy cập database .
Thêm các tên và giá trị biến sau vào file . Hãy nhớ cung cấp các giá trị của bạn tại đây cho mỗi biến:
MYSQL_ROOT_PASSWORD=your_root_password MYSQL_USER=your_wordpress_database_user MYSQL_PASSWORD=your_wordpress_database_password
Ta đã bao gồm password cho account quản trị gốc , cũng như tên user và password ưa thích cho database ứng dụng của ta .
Lưu file khi bạn hoàn tất chỉnh sửa.
Bởi vì file .env
của bạn chứa thông tin nhạy cảm, bạn cần đảm bảo nó có trong các file .gitignore
và .dockerignore
của dự án .gitignore
.dockerignore
file này sẽ cho Git và Docker biết những file nào không được sao chép vào repository Git và Docker image của bạn.
Nếu bạn định làm việc với Git để kiểm soát version , hãy khởi tạo folder làm việc hiện tại của bạn dưới dạng repository với git init
:
- git init
Sau đó, mở file .gitignore
:
- nano .gitignore
Thêm .env
vào file :
.env
Lưu file khi bạn hoàn tất chỉnh sửa.
Tương tự như vậy, bạn nên thận trọng khi thêm .env
vào file .dockerignore
, để nó không kết thúc trên containers của bạn khi bạn đang sử dụng folder này làm ngữ cảnh xây dựng của bạn .
Mở tập tin:
- nano .dockerignore
Thêm .env
vào file :
.env
Dưới đây, bạn có thể tùy chọn thêm các file và folder được liên kết với sự phát triển ứng dụng của bạn :
.env .git docker-compose.yml .dockerignore
Lưu file khi bạn hoàn tất.
Với thông tin nhạy cảm của bạn đã có sẵn, giờ đây bạn có thể chuyển sang xác định các dịch vụ của bạn trong file docker-compose.yml
.
Bước 3 - Xác định Dịch vụ với Docker Compose
Tệp docker-compose.yml
của bạn sẽ chứa các định nghĩa dịch vụ cho cài đặt của bạn. Dịch vụ trong Soạn là một containers đang chạy và các định nghĩa dịch vụ chỉ định thông tin về cách mỗi containers sẽ chạy.
Sử dụng tính năng Soạn thư, bạn có thể xác định các dịch vụ khác nhau để chạy các ứng dụng nhiều containers , vì tính năng Soạn thư cho phép bạn liên kết các dịch vụ này với nhau với các mạng và dung lượng chia sẻ. Điều này sẽ hữu ích cho cài đặt hiện tại của ta vì ta sẽ tạo các containers khác nhau cho database , ứng dụng WordPress và web server của ta . Ta cũng sẽ tạo một containers để chạy ứng dụng client Certbot nhằm lấy certificate cho web server của ta .
Để bắt đầu, hãy mở file docker-compose.yml
:
- nano docker-compose.yml
Thêm mã sau để xác định version file Soạn và dịch vụ database db
:
version: '3' services: db: image: mysql:8.0 container_name: db restart: unless-stopped env_file: .env environment: - MYSQL_DATABASE=wordpress volumes: - dbdata:/var/lib/mysql command: '--default-authentication-plugin=mysql_native_password' networks: - app-network
Định nghĩa dịch vụ db
chứa các tùy chọn sau:
-
image
: Điều này cho biết Soạn hình ảnh nào cần kéo để tạo containers . Ta đang ghim hình ảnhmysql: 8.0
ở đây để tránh xung đột trong tương lai vì hình ảnhmysql:latest
tiếp tục được cập nhật. Để biết thêm thông tin về ghim version và tránh xung đột phụ thuộc, hãy xem tài liệu Docker về các phương pháp hay nhất của Dockerfile . -
container_name
: Điều này chỉ định tên cho containers . -
restart
: Điều này xác định policy khởi động lại containers . Mặc định làno
, nhưng ta đã đặt containers khởi động lại trừ khi nó bị dừng theo cách thủ công. -
env_file
: Tùy chọn này cho Soạn biết rằng ta muốn thêm các biến môi trường từ một file có tên.env
, nằm trong ngữ cảnh xây dựng của ta . Trong trường hợp này, bối cảnh xây dựng là folder hiện tại của ta . -
environment
: Tùy chọn này cho phép bạn thêm các biến môi trường bổ sung, ngoài những biến số được xác định trong file.env
của bạn. Ta sẽ đặt biếnMYSQL_DATABASE
bằng vớiwordpress
để cung cấp tên cho database ứng dụng của ta . Vì đây là thông tin không nhạy cảm nên ta có thể đưa trực tiếp thông tin đó vào filedocker-compose.yml
. -
volumes
: Ở đây, ta đang gắn một volume có tên làdbdata
vào folder/var/lib/mysql
trên containers . Đây là folder dữ liệu tiêu chuẩn cho MySQL trên hầu hết các bản phân phối. -
command
: Tùy chọn này chỉ định một lệnh để overrides lệnh CMD mặc định cho hình ảnh. Trong trường hợp của ta , ta sẽ thêm một tùy chọn vào lệnhmysqld
chuẩn của Docker image , lệnh này khởi động server MySQL trên containers . Tùy chọn này,--default-authentication-plugin=mysql_native_password
, đặt biến hệ thốngmysql_native_password
--default-authentication-plugin
thànhmysql_native_password
, chỉ định cơ chế xác thực nào sẽ chi phối các yêu cầu xác thực mới tới server . Vì PHP và do đó hình ảnh WordPress của ta sẽ không hỗ trợ mặc định xác thực mới hơn của MySQL , ta phải thực hiện điều chỉnh này để xác thực user database ứng dụng của ta . -
networks
: Điều này chỉ định rằng dịch vụ ứng dụng của ta sẽ tham giaapp-network
mà ta sẽ xác định ở cuối file .
Tiếp theo, bên dưới định nghĩa dịch vụ db
của bạn, hãy thêm định nghĩa cho dịch vụ ứng dụng wordpress
của bạn:
... wordpress: depends_on: - db image: wordpress:5.1.1-fpm-alpine container_name: wordpress restart: unless-stopped env_file: .env environment: - WORDPRESS_DB_HOST=db:3306 - WORDPRESS_DB_USER=$MYSQL_USER - WORDPRESS_DB_PASSWORD=$MYSQL_PASSWORD - WORDPRESS_DB_NAME=wordpress volumes: - wordpress:/var/www/html networks: - app-network
Trong định nghĩa dịch vụ này, ta đang đặt tên containers của bạn và xác định policy khởi động lại, như ta đã làm với dịch vụ db
. Ta cũng đang thêm một số tùy chọn cụ thể cho containers này:
-
depends_on
: Tùy chọn này đảm bảo các containers của ta sẽ bắt đầu theo thứ tự phụ thuộc, với containerswordpress
bắt đầu sau containersdb
. Ứng dụng WordPress của ta dựa trên sự tồn tại của database ứng dụng và user của ta , vì vậy việc thể hiện thứ tự phụ thuộc này sẽ cho phép ứng dụng của ta khởi động đúng cách. -
image
: Đối với cài đặt này, ta đang sử dụng hình ảnh WordPress5.1.1 -fpm-alpine
. Như đã thảo luận trong Bước 1 , việc sử dụng hình ảnh này đảm bảo ứng dụng của ta sẽ có bộ xử lýphp-fpm
mà Nginx yêu cầu để xử lý quá trình PHP processor . Đây cũng là một hình ảnhalpine
, có nguồn root từ dự án Alpine Linux , sẽ giúp giảm kích thước hình ảnh tổng thể của ta . Để biết thêm thông tin về lợi ích và hạn chế của việc sử dụng hình ảnhalpine
và liệu điều này có phù hợp với ứng dụng của bạn hay không, hãy xem toàn bộ cuộc thảo luận trong phần Biến thể hình ảnh của trang Docker image Hub WordPress . -
env_file
: , ta chỉ định rằng ta muốn lấy các giá trị từ file.env
, vì đây là nơi ta xác định user và password database ứng dụng của bạn . -
environment
: Ở đây, ta đang sử dụng các giá trị mà ta đã xác định trong file.env
của.env
, nhưng ta đang gán chúng cho các tên biến mà hình ảnh WordPress mong đợi:WORDPRESS_DB_USER
vàWORDPRESS_DB_PASSWORD
. Ta cũng đang định nghĩaWORDPRESS_DB_HOST
, sẽ là server MySQL chạy trên containersdb
có thể truy cập trên cổng mặc định của MySQL,3306
.WORDPRESS_DB_NAME
của ta sẽ có cùng giá trị mà ta đã chỉ định trong định nghĩa dịch vụ MySQL choMYSQL_DATABASE
:wordpress
của ta . -
volumes
: Ta đang gắn một volume có tên làwordpress
vào mountpoint/var/www/html
được tạo bởi hình ảnh WordPress . Sử dụng một ổ đĩa được đặt tên theo cách này sẽ cho phép ta chia sẻ mã ứng dụng của bạn với các containers khác. -
networks
: Ta cũng đang thêm containerswordpress
vàoapp-network
mạng.
Tiếp theo, bên dưới định nghĩa dịch vụ ứng dụng wordpress
, hãy thêm định nghĩa sau cho dịch vụ webserver
Nginx của bạn:
... webserver: depends_on: - wordpress image: nginx:1.15.12-alpine container_name: webserver restart: unless-stopped ports: - "80:80" volumes: - wordpress:/var/www/html - ./nginx-conf:/etc/nginx/conf.d - certbot-etc:/etc/letsencrypt networks: - app-network
, ta đặt tên cho containers của bạn và làm cho nó phụ thuộc vào containers wordpress
theo thứ tự bắt đầu. Ta cũng đang sử dụng một alpine
hình ảnh - những 1.15.12 -alpine
Nginx hình ảnh .
Định nghĩa dịch vụ này cũng bao gồm các tùy chọn sau:
-
ports
: Điều này cho thấy cổng80
để kích hoạt các tùy chọn cấu hình mà ta đã xác định trong filenginx.conf
của ta ở Bước 1 . -
volumes
: Ở đây, ta đang xác định sự kết hợp của các volume được đặt tên và các mount liên kết :-
wordpress:/var/www/html
: Thao tác này sẽ gắn mã ứng dụng WordPress của ta vào folder/var/www/html
, folder mà ta đặt làm folderroot
trong khối server Nginx của ta . -
./nginx-conf:/etc/nginx/conf.d
: Thao tác này sẽ mount folder cấu hình Nginx trên server lưu trữ với folder liên quan trên containers , đảm bảo bất kỳ thay đổi nào ta thực hiện đối với file trên server lưu trữ sẽ được phản ánh trong thùng đựng hàng. -
certbot-etc:/etc/letsencrypt
: Điều này sẽ gắn các certificate và khóa Let's Encrypt có liên quan cho domain của ta vào folder thích hợp trên containers .
-
Và , ta đã thêm containers này vào app-network
mạng.
Cuối cùng, bên dưới định nghĩa webserver
của bạn, hãy thêm định nghĩa dịch vụ cuối cùng của bạn cho dịch vụ certbot
. Đảm bảo thay thế địa chỉ email và domain được liệt kê ở đây bằng thông tin của bạn :
certbot: depends_on: - webserver image: certbot/certbot container_name: certbot volumes: - certbot-etc:/etc/letsencrypt - wordpress:/var/www/html command: certonly --webroot --webroot-path=/var/www/html --email sammy@example.com --agree-tos --no-eff-email --staging -d example.com -d www.example.com
Định nghĩa này yêu cầu Soạn thảo kéo hình ảnh certbot/certbot
từ Docker Hub. Nó cũng sử dụng dung lượng được đặt tên để chia sẻ tài nguyên với containers Nginx, bao gồm certificate domain và khóa trong certbot-etc
và mã ứng dụng trong wordpress
.
, ta đã sử dụng depends_on
để chỉ định rằng containers certbot
sẽ được khởi động khi dịch vụ webserver
đang chạy.
Ta cũng đã bao gồm một tùy chọn command
định một lệnh con để chạy với lệnh certbot
mặc định của containers . Lệnh con certonly
sẽ nhận được certificate với các tùy chọn sau:
-
--webroot
: Điều này yêu cầu Certbot sử dụng plugin webroot để đặt các file trong folder webroot để xác thực. Plugin này phụ thuộc vào phương thức xác thực HTTP-01 , phương thức này sử dụng yêu cầu HTTP để chứng minh rằng Certbot có thể truy cập tài nguyên từ server phản hồi với một domain nhất định. -
--webroot-path
: Điều này chỉ định đường dẫn của folder webroot. -
--email
: Email bạn muốn để đăng ký và khôi phục. -
--agree-tos
: Điều này chỉ rõ rằng bạn đồng ý với Thỏa thuận người đăng ký của ACME . -
--no-eff-email
: Điều này cho Certbot biết rằng bạn không muốn chia sẻ email của bạn với Electronic Frontier Foundation (EFF). Hãy bỏ qua điều này nếu bạn muốn. -
--staging
: Điều này cho Certbot biết rằng bạn muốn sử dụng môi trường staging của Let's Encrypt để lấy certificate thử nghiệm. Sử dụng tùy chọn này cho phép bạn kiểm tra các tùy chọn cấu hình của bạn và tránh các giới hạn yêu cầu domain có thể xảy ra. Để biết thêm thông tin về các giới hạn này, vui lòng xem tài liệu giới hạn tỷ lệ của Let's Encrypt. -
-d
: Điều này cho phép bạn chỉ định domain mà bạn muốn áp dụng cho yêu cầu của bạn . Trong trường hợp này, ta đã bao gồmexample.com
vàwww. example.com
. Đảm bảo thay thế các domain này bằng domain của bạn .
Bên dưới định nghĩa dịch vụ certbot
, hãy thêm định nghĩa mạng và dung lượng của bạn:
... volumes: certbot-etc: wordpress: dbdata: networks: app-network: driver: bridge
Khóa volumes
cấp cao nhất của ta xác định các dung lượng certbot-etc
, wordpress
và dbdata
. Khi Docker tạo tập, nội dung của tập được lưu trữ trong một folder trên hệ thống file server , /var/lib/docker/volumes/
, được quản lý bởi Docker. Nội dung của mỗi tập sau đó được mount từ folder này vào bất kỳ containers nào sử dụng tập. Bằng cách này, có thể chia sẻ mã và dữ liệu giữa các containers .
Mạng app-network
mạng cầu nối do user xác định cho phép giao tiếp giữa các containers của ta vì chúng nằm trên cùng một server Docker daemon. Điều này hợp lý hóa lưu lượng truy cập và giao tiếp trong ứng dụng, vì nó mở tất cả các cổng giữa các container trên cùng một mạng cầu nối mà không để lộ bất kỳ cổng nào ra thế giới bên ngoài. Do đó, các containers db
, wordpress
và webserver
của ta có thể giao tiếp với nhau và ta chỉ cần để lộ cổng 80
để truy cập front-end vào ứng dụng.
Tệp docker-compose.yml
đã hoàn thành sẽ giống như sau:
version: '3' services: db: image: mysql:8.0 container_name: db restart: unless-stopped env_file: .env environment: - MYSQL_DATABASE=wordpress volumes: - dbdata:/var/lib/mysql command: '--default-authentication-plugin=mysql_native_password' networks: - app-network wordpress: depends_on: - db image: wordpress:5.1.1-fpm-alpine container_name: wordpress restart: unless-stopped env_file: .env environment: - WORDPRESS_DB_HOST=db:3306 - WORDPRESS_DB_USER=$MYSQL_USER - WORDPRESS_DB_PASSWORD=$MYSQL_PASSWORD - WORDPRESS_DB_NAME=wordpress volumes: - wordpress:/var/www/html networks: - app-network webserver: depends_on: - wordpress image: nginx:1.15.12-alpine container_name: webserver restart: unless-stopped ports: - "80:80" volumes: - wordpress:/var/www/html - ./nginx-conf:/etc/nginx/conf.d - certbot-etc:/etc/letsencrypt networks: - app-network certbot: depends_on: - webserver image: certbot/certbot container_name: certbot volumes: - certbot-etc:/etc/letsencrypt - wordpress:/var/www/html command: certonly --webroot --webroot-path=/var/www/html --email sammy@example.com --agree-tos --no-eff-email --staging -d example.com -d www.example.com volumes: certbot-etc: wordpress: dbdata: networks: app-network: driver: bridge
Lưu file khi bạn hoàn tất chỉnh sửa.
Với các định nghĩa dịch vụ của bạn, bạn đã sẵn sàng khởi động các containers và kiểm tra các certificate request của bạn .
Bước 4 - Lấy certificate SSL và thông tin đăng nhập
Ta có thể bắt đầu các containers của bạn bằng lệnh docker-compose up
, lệnh này sẽ tạo và chạy các containers của ta theo thứ tự mà ta đã chỉ định. Nếu yêu cầu domain của ta thành công, ta sẽ thấy trạng thái thoát chính xác trong kết quả của ta và các certificate phù hợp được gắn trong folder /etc/letsencrypt/live
trên containers webserver
.
Tạo các containers với docker-compose up
và cờ -d
, sẽ chạy các containers db
, wordpress
và webserver
trong nền:
- docker-compose up -d
Bạn sẽ thấy kết quả xác nhận các dịch vụ của bạn đã được tạo:
OutputCreating db ... done Creating wordpress ... done Creating webserver ... done Creating certbot ... done
Sử dụng docker-compose ps
, kiểm tra trạng thái dịch vụ của bạn:
- docker-compose ps
Nếu mọi thứ thành công, các dịch vụ db
, wordpress
và webserver
bạn sẽ được Up
và containers certbot
sẽ thoát với thông báo trạng thái 0
:
Output Name Command State Ports ------------------------------------------------------------------------- certbot certbot certonly --webroot ... Exit 0 db docker-entrypoint.sh --def ... Up 3306/tcp, 33060/tcp webserver nginx -g daemon off; Up 0.0.0.0:80->80/tcp wordpress docker-entrypoint.sh php-fpm Up 9000/tcp
Nếu bạn thấy bất cứ điều gì khác hơn Up
trong State
cột cho db
, wordpress
, hoặc webserver
dịch vụ, hoặc một trạng thái thoát khác hơn 0
cho certbot
container, hãy chắc chắn để kiểm tra các bản ghi dịch vụ với các docker-compose logs
lệnh:
- docker-compose logs service_name
Bây giờ, bạn có thể kiểm tra xem các certificate của bạn đã được gắn vào containers webserver
bằng docker-compose exec
:
- docker-compose exec webserver ls -la /etc/letsencrypt/live
Nếu certificate request của bạn thành công, bạn sẽ thấy kết quả như sau:
Outputtotal 16 drwx------ 3 root root 4096 May 10 15:45 . drwxr-xr-x 9 root root 4096 May 10 15:45 .. -rw-r--r-- 1 root root 740 May 10 15:45 README drwxr-xr-x 2 root root 4096 May 10 15:45 example.com
Đến đây bạn biết rằng yêu cầu của bạn sẽ thành công, bạn có thể chỉnh sửa định nghĩa dịch vụ certbot
để xóa cờ --staging
.
Mở docker-compose.yml
:
- nano docker-compose.yml
Tìm phần của file có định nghĩa dịch vụ certbot
và thay thế cờ --staging
trong tùy chọn command
bằng cờ --force-renewal
, cờ này sẽ cho Certbot biết rằng bạn muốn certificate request mới với các domain giống như một certificate hiện có. Định nghĩa dịch vụ certbot
bây giờ sẽ giống như sau:
... certbot: depends_on: - webserver image: certbot/certbot container_name: certbot volumes: - certbot-etc:/etc/letsencrypt - certbot-var:/var/lib/letsencrypt - wordpress:/var/www/html command: certonly --webroot --webroot-path=/var/www/html --email sammy@example.com --agree-tos --no-eff-email --force-renewal -d example.com -d www.example.com ...
Đến đây bạn có thể chạy certbot
docker-compose up
để tạo lại containers certbot
. Ta cũng sẽ bao gồm tùy chọn --no-deps
để cho Soạn biết rằng nó có thể bỏ qua việc khởi động dịch vụ webserver
, vì nó đã chạy:
- docker-compose up --force-recreate --no-deps certbot
Bạn sẽ thấy kết quả cho biết rằng certificate request của bạn đã thành công:
OutputRecreating certbot ... done Attaching to certbot certbot | Saving debug log to /var/log/letsencrypt/letsencrypt.log certbot | Plugins selected: Authenticator webroot, Installer None certbot | Renewing an existing certificate certbot | Performing the following challenges: certbot | http-01 challenge for example.com certbot | http-01 challenge for www.example.com certbot | Using the webroot path /var/www/html for all unmatched domains. certbot | Waiting for verification... certbot | Cleaning up challenges certbot | IMPORTANT NOTES: certbot | - Congratulations! Your certificate and chain have been saved at: certbot | /etc/letsencrypt/live/example.com/fullchain.pem certbot | Your key file has been saved at: certbot | /etc/letsencrypt/live/example.com/privkey.pem certbot | Your cert will expire on 2019-08-08. To obtain a new or tweaked certbot | version of this certificate in the future, simply run certbot certbot | again. To non-interactively renew *all* of your certificates, run certbot | "certbot renew" certbot | - Your account credentials have been saved in your Certbot certbot | configuration directory at /etc/letsencrypt. You should make a certbot | secure backup of this folder now. This configuration directory will certbot | also contain certificates and private keys obtained by Certbot so certbot | making regular backups of this folder is ideal. certbot | - If you like Certbot, please consider supporting our work by: certbot | certbot | Donating to ISRG / Let's Encrypt: https://letsencrypt.org/donate certbot | Donating to EFF: https://eff.org/donate-le certbot | certbot exited with code 0
Với các certificate của bạn, bạn có thể chuyển sang sửa đổi cấu hình Nginx của bạn để bao gồm SSL.
Bước 5 - Sửa đổi cấu hình web server và định nghĩa dịch vụ
Bật SSL trong cấu hình Nginx của ta sẽ liên quan đến việc thêm chuyển hướng HTTP đến HTTPS, chỉ định certificate SSL và các vị trí chính của ta , đồng thời thêm các thông số bảo mật và tiêu đề.
Vì bạn sẽ tạo lại dịch vụ webserver
để bao gồm những bổ sung này, bạn có thể dừng nó ngay bây giờ:
- docker-compose stop webserver
Trước khi ta sửa đổi chính file cấu hình, trước tiên hãy lấy các thông số bảo mật Nginx được đề xuất từ Certbot bằng cách sử dụng curl
:
- curl -sSLo nginx-conf/options-ssl-nginx.conf https://raw.githubusercontent.com/certbot/certbot/master/certbot-nginx/certbot_nginx/_internal/tls_configs/options-ssl-nginx.conf
Lệnh này sẽ lưu các tham số này trong một file có tên là options-ssl-nginx.conf
, nằm trong folder nginx-conf
.
Tiếp theo, xóa file cấu hình Nginx bạn đã tạo trước đó:
- rm nginx-conf/nginx.conf
Mở một version khác của file :
- nano nginx-conf/nginx.conf
Thêm mã sau vào file để chuyển hướng HTTP sang HTTPS và thêm thông tin đăng nhập SSL, giao thức và tiêu đề bảo mật. Hãy nhớ thay thế example.com
bằng domain của bạn :
server { listen 80; listen [::]:80; server_name example.com www.example.com; location ~ /.well-known/acme-challenge { allow all; root /var/www/html; } location / { rewrite ^ https://$host$request_uri? permanent; } } server { listen 443 ssl http2; listen [::]:443 ssl http2; server_name example.com www.example.com; index index.php index.html index.htm; root /var/www/html; server_tokens off; ssl_certificate /etc/letsencrypt/live/example.com/fullchain.pem; ssl_certificate_key /etc/letsencrypt/live/example.com/privkey.pem; include /etc/nginx/conf.d/options-ssl-nginx.conf; add_header X-Frame-Options "SAMEORIGIN" always; add_header X-XSS-Protection "1; mode=block" always; add_header X-Content-Type-Options "nosniff" always; add_header Referrer-Policy "no-referrer-when-downgrade" always; add_header Content-Security-Policy "default-src * data: 'unsafe-eval' 'unsafe-inline'" always; # add_header Strict-Transport-Security "max-age=31536000; includeSubDomains; preload" always; # enable strict transport security only if you understand the implications location / { try_files $uri $uri/ /index.php$is_args$args; } location ~ \.php$ { try_files $uri =404; fastcgi_split_path_info ^(.+\.php)(/.+)$; fastcgi_pass wordpress:9000; fastcgi_index index.php; include fastcgi_params; fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name; fastcgi_param PATH_INFO $fastcgi_path_info; } location ~ /\.ht { deny all; } location = /favicon.ico { log_not_found off; access_log off; } location = /robots.txt { log_not_found off; access_log off; allow all; } location ~* \.(css|gif|ico|jpeg|jpg|js|png)$ { expires max; log_not_found off; } }
Khối server HTTP chỉ định webroot cho các yêu cầu gia hạn Certbot tới folder .well .well-known/acme-challenge
. Nó cũng bao gồm một chỉ thị viết lại hướng các yêu cầu HTTP đến folder root tới HTTPS.
Khối server HTTPS cho phép ssl
và http2
. Để đọc thêm về cách HTTP / 2 lặp lại trên các giao thức HTTP và những lợi ích mà nó có thể có đối với hiệu suất trang web, vui lòng xem phần giới thiệu về Cách Cài đặt Nginx với Hỗ trợ HTTP / 2 trên Ubuntu 18.04 .
Khối này cũng bao gồm certificate SSL và các vị trí chính của ta , cùng với các thông số bảo mật Certbot được đề xuất mà ta đã lưu vào nginx-conf/options-ssl-nginx.conf
.
Ngoài ra, ta đã bao gồm một số tiêu đề bảo mật sẽ cho phép ta nhận được xếp hạng A trên những thứ như Phòng thí nghiệm SSL và các trang web kiểm tra server Tiêu đề bảo mật . Các tiêu đề này bao gồm X-Frame-Options
, X-Content-Type-Options
, Referrer Policy
, Content-Security-Policy
và X-XSS-Protection
. Tiêu đề Strict Transport Security
HTTP (HSTS) được comment - chỉ bật tính năng này nếu bạn hiểu ý nghĩa và đã đánh giá chức năng “tải trước” của nó .
Các index
thị root
và index
của ta cũng nằm trong khối này, cũng như phần còn lại của các khối vị trí dành riêng cho WordPress được thảo luận trong Bước 1 .
Khi bạn đã chỉnh sửa xong, hãy lưu file .
Trước khi tạo lại dịch vụ webserver
, bạn cần thêm ánh xạ cổng 443
vào định nghĩa dịch vụ webserver
của bạn .
Mở file docker-compose.yml
của bạn:
- nano docker-compose.yml
Trong định nghĩa dịch vụ webserver
, hãy thêm ánh xạ cổng sau:
... webserver: depends_on: - wordpress image: nginx:1.15.12-alpine container_name: webserver restart: unless-stopped ports: - "80:80" - "443:443" volumes: - wordpress:/var/www/html - ./nginx-conf:/etc/nginx/conf.d - certbot-etc:/etc/letsencrypt networks: - app-network
Tệp docker-compose.yml
sẽ trông như thế này khi hoàn tất:
version: '3' services: db: image: mysql:8.0 container_name: db restart: unless-stopped env_file: .env environment: - MYSQL_DATABASE=wordpress volumes: - dbdata:/var/lib/mysql command: '--default-authentication-plugin=mysql_native_password' networks: - app-network wordpress: depends_on: - db image: wordpress:5.1.1-fpm-alpine container_name: wordpress restart: unless-stopped env_file: .env environment: - WORDPRESS_DB_HOST=db:3306 - WORDPRESS_DB_USER=$MYSQL_USER - WORDPRESS_DB_PASSWORD=$MYSQL_PASSWORD - WORDPRESS_DB_NAME=wordpress volumes: - wordpress:/var/www/html networks: - app-network webserver: depends_on: - wordpress image: nginx:1.15.12-alpine container_name: webserver restart: unless-stopped ports: - "80:80" - "443:443" volumes: - wordpress:/var/www/html - ./nginx-conf:/etc/nginx/conf.d - certbot-etc:/etc/letsencrypt networks: - app-network certbot: depends_on: - webserver image: certbot/certbot container_name: certbot volumes: - certbot-etc:/etc/letsencrypt - wordpress:/var/www/html command: certonly --webroot --webroot-path=/var/www/html --email sammy@example.com --agree-tos --no-eff-email --force-renewal -d example.com -d www.example.com volumes: certbot-etc: wordpress: dbdata: networks: app-network: driver: bridge
Lưu file khi bạn hoàn tất chỉnh sửa.
Tạo lại dịch vụ webserver
:
- docker-compose up -d --force-recreate --no-deps webserver
Kiểm tra các dịch vụ của bạn bằng docker-compose ps
:
- docker-compose ps
Bạn sẽ thấy kết quả cho biết rằng các dịch vụ db
, wordpress
và webserver
đang chạy:
Output Name Command State Ports ---------------------------------------------------------------------------------------------- certbot certbot certonly --webroot ... Exit 0 db docker-entrypoint.sh --def ... Up 3306/tcp, 33060/tcp webserver nginx -g daemon off; Up 0.0.0.0:443->443/tcp, 0.0.0.0:80->80/tcp wordpress docker-entrypoint.sh php-fpm Up 9000/tcp
Với các containers của bạn đang chạy, bây giờ bạn có thể hoàn tất cài đặt WordPress của bạn thông qua giao diện web.
Bước 6 - Hoàn tất cài đặt thông qua giao diện web
Với các containers của ta đang chạy, ta có thể hoàn tất cài đặt thông qua giao diện web WordPress.
Trong trình duyệt web , chuyển đến domain server của bạn. Hãy nhớ thay thế example.com
tại đây bằng domain của bạn :
https://example.com
Chọn ngôn ngữ bạn muốn sử dụng:
Sau khi nhấp vào Tiếp tục , bạn sẽ đến trang cài đặt chính, nơi bạn cần chọn tên cho trang web của bạn và tên user . Bạn nên chọn một tên user dễ nhớ ở đây (thay vì "admin" ) và một password mạnh. Bạn có thể sử dụng password mà WordPress tạo tự động hoặc tạo password của bạn .
Cuối cùng, bạn cần nhập địa chỉ email của bạn và quyết định xem bạn có muốn ngăn cản các công cụ tìm kiếm lập index trang web hay không:
Nhấp vào Cài đặt WordPress ở cuối trang sẽ đưa bạn đến dấu nhắc đăng nhập:
Sau khi đăng nhập, bạn sẽ có quyền truy cập vào console quản trị WordPress:
Với việc cài đặt WordPress của bạn hoàn tất, bây giờ bạn có thể thực hiện các bước đảm bảo rằng certificate SSL của bạn sẽ tự động gia hạn.
Bước 7 - Gia hạn certificate
Chứng chỉ Let's Encrypt có giá trị trong 90 ngày, vì vậy bạn cần cài đặt quy trình gia hạn tự động đảm bảo rằng chúng không mất hiệu lực. Một cách để làm điều này là tạo một công việc với tiện ích lập lịch cron
. Trong trường hợp này, ta sẽ tạo một cron
việc cron
để chạy định kỳ một tập lệnh sẽ gia hạn certificate của ta và reload cấu hình Nginx của ta .
Đầu tiên, hãy mở một tập lệnh có tên ssl_renew.sh
:
- nano ssl_renew.sh
Thêm mã sau vào tập lệnh để gia hạn certificate và reload cấu hình web server của bạn. Hãy nhớ thay thế tên user mẫu ở đây bằng tên user không phải root của bạn :
#!/bin/bash COMPOSE="/usr/local/bin/docker-compose --no-ansi" DOCKER="/usr/bin/docker" cd /home/sammy/wordpress/ $COMPOSE run certbot renew --dry-run && $COMPOSE kill -s SIGHUP webserver $DOCKER system prune -af
Đầu tiên, tập lệnh này sẽ gán mã binary docker-compose
cho một biến có tên là COMPOSE
và chỉ định tùy chọn --no-ansi
, tùy chọn này sẽ chạy các lệnh docker-compose
mà không có ký tự điều khiển ANSI . Sau đó, nó thực hiện tương tự với mã binary docker
. Cuối cùng, nó thay đổi thành folder dự án ~/wordpress
và chạy các lệnh docker-compose
sau:
-
certbot
docker-compose run
: Thao tác này sẽ khởi độngcertbot
chứacertbot
và overridescommand
được cung cấp trong định nghĩa dịch vụcertbot
của ta . Thay vì sử dụng lệnhcertonly
, ta đang sử dụng lệnh conrenew
ở đây, lệnh này sẽ gia hạn các certificate sắp hết hạn. Ta đã bao gồm tùy chọn--dry-run
ở đây để kiểm tra tập lệnh của ta . -
docker-compose kill
: Thao tác này sẽ gửiSIGHUP
hiệuSIGHUP
tới containerswebserver
để reload cấu hình Nginx. Để biết thêm thông tin về cách sử dụng quy trình này để reload cấu hình Nginx của bạn, vui lòng xem bài đăng trên blog Docker này về việc triển khai hình ảnh Nginx chính thức với Docker .
Sau đó, nó chạy sơ lược docker system prune
để loại bỏ tất cả các containers và hình ảnh không sử dụng.
Đóng file khi bạn hoàn tất chỉnh sửa. Làm cho nó có thể thực thi:
- chmod +x ssl_renew.sh
Tiếp theo, mở file crontab
gốc của bạn để chạy tập lệnh gia hạn tại một khoảng thời gian cụ thể:
- sudo crontab -e
Nếu đây là lần đầu tiên bạn chỉnh sửa file này, bạn cần chọn một editor :
Outputno crontab for root - using an empty one Select an editor. To change later, run 'select-editor'. 1. /bin/nano <---- easiest 2. /usr/bin/vim.basic 3. /usr/bin/vim.tiny 4. /bin/ed Choose 1-4 [1]: ...
Ở cuối file , thêm dòng sau:
... */5 * * * * /home/sammy/wordpress/ssl_renew.sh >> /var/log/cron.log 2>&1
Điều này sẽ đặt khoảng thời gian công việc thành năm phút một lần, vì vậy bạn có thể kiểm tra xem yêu cầu gia hạn của bạn có hoạt động như dự định hay không. Ta cũng đã tạo một file log , cron.log
, để ghi lại kết quả có liên quan từ công việc.
Sau năm phút, hãy kiểm tra cron.log
để xem liệu yêu cầu gia hạn đã thành công hay chưa:
- tail -f /var/log/cron.log
Bạn sẽ thấy kết quả xác nhận gia hạn thành công:
Output- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - ** DRY RUN: simulating 'certbot renew' close to cert expiry ** (The test certificates below have not been saved.) Congratulations, all renewals succeeded. The following certs have been renewed: /etc/letsencrypt/live/example.com/fullchain.pem (success) ** DRY RUN: simulating 'certbot renew' close to cert expiry ** (The test certificates above have not been saved.) - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Đến đây bạn có thể sửa đổi file crontab
để đặt khoảng thời gian hàng ngày. Ví dụ: để chạy tập lệnh hàng ngày vào buổi trưa, bạn sẽ sửa đổi dòng cuối cùng của file để trông giống như sau:
... 0 12 * * * /home/sammy/wordpress/ssl_renew.sh >> /var/log/cron.log 2>&1
Bạn cũng cần xóa tùy chọn --dry-run
khỏi tập lệnh ssl_renew.sh
của bạn :
#!/bin/bash COMPOSE="/usr/local/bin/docker-compose --no-ansi" DOCKER="/usr/bin/docker" cd /home/sammy/wordpress/ $COMPOSE run certbot renew && $COMPOSE kill -s SIGHUP webserver $DOCKER system prune -af
Công việc cron
của bạn sẽ đảm bảo các certificate Let's Encrypt của bạn không mất hiệu lực bằng cách gia hạn chúng khi chúng đủ điều kiện. Bạn cũng có thể cài đặt xoay log với tiện ích Logrotate để xoay và nén các file log của bạn .
Kết luận
Trong hướng dẫn này, bạn đã sử dụng Docker Compose để tạo cài đặt WordPress với web server Nginx. Là một phần của quy trình làm việc này, bạn đã nhận được certificate TLS / SSL cho domain bạn muốn liên kết với trang web WordPress của bạn . Ngoài ra, bạn đã tạo một cron
việc cron
để gia hạn các certificate này khi cần thiết.
Là các bước bổ sung để cải thiện hiệu suất và dự phòng của trang web, bạn có thể tham khảo các bài viết sau về phân phối và backup nội dung WordPress:
- Cách tăng tốc độ phân phối tài sản WordPress bằng CDN DigitalOcean Spaces .
- Cách backup trang web WordPress lên không gian .
- Cách lưu trữ tài sản WordPress trên DigitalOcean .
Nếu bạn quan tâm đến việc khám phá quy trình làm việc được tích hợp với Kubernetes, bạn cũng có thể xem:
Các tin liên quan
Cách di chuyển Docker compose workflow sang Kubernetes2019-04-03
Cách tối ưu hóa image Docker cho sản xuất
2019-03-25
Giữ lại một ứng dụng Node.js để phát triển với Docker Compose
2019-03-05
Cách cài đặt và sử dụng Docker Compose trên CentOS 7
2019-01-23
Cách sử dụng Traefik làm reverse-proxy cho container Docker trên Debian 9
2019-01-08
Cách thiết lập registry Docker riêng trên Ubuntu 18.04
2019-01-07
Cách thiết lập triển khai nhiều node với Rancher 2.1, Kubernetes và Docker Machine trên Ubuntu 18.04
2019-01-03
Cách tạo ứng dụng Node.js với Docker
2018-11-29
Cách quản lý triển khai nhiều node với Máy Rancher và Docker trên Ubuntu 16.04
2018-10-30
Cách cài đặt và sử dụng Docker trên Ubuntu 16.04
2018-10-19