WordPress ã®ã€ã³ã¹ããŒã«æ¹æ³ã«é¢ãããã¥ãŒããªã¢ã«ã¯æ°å€ããããGoogle ã§ãWordPress ã€ã³ã¹ããŒã«ããæ€çŽ¢ãããšãçŽ XNUMX äžä»¶ã®çµæã衚瀺ãããŸãã ããããå®éã«ã¯ãWordPress ãšãã®åºç€ãšãªããªãã¬ãŒãã£ã³ã° ã·ã¹ãã ãã€ã³ã¹ããŒã«ããŠæ§æããé·æéãµããŒãã§ããããã«ããããã®åªããã¬ã€ãã¯ã»ãšãã©ãããŸããã ãããããæ£ããèšå®ã¯ç¹å®ã®ããŒãºã«å€§ããäŸåããŠãããã詳现ãªèª¬æãèšäºãèªã¿ã«ããããŠããããã§ãã
ãã®èšäºã§ã¯ãUbuntu ã« WordPress ãèªåçã«ã€ã³ã¹ããŒã«ãã bash ã¹ã¯ãªãããæäŸããããšã§ãäž¡æ¹ã®é·æãçµã¿åãããããšãè©Šã¿ãŸãããŸãããããå®éã«å®è¡ããåéšåã®æ©èœãšéçºæã«è¡ã£ã劥åç¹ã«ã€ããŠèª¬æããŸãã ã äžçŽãŠãŒã¶ãŒã®å Žåã¯ãèšäºã®ããã¹ããã¹ãããããŠã
NGINX ãŠãããã䜿çšã㊠WordPress ããããã€ããããã«éçºãããã¢ãŒããã¯ãã£ã«ã€ããŠã¯ã次ã®ã»ã¯ã·ã§ã³ã§èª¬æãããŠããŸãã
- WordPress CLI
- Let's Encrypt ãš TLSSSL 蚌ææž
- 蚌ææžã®èªåæŽæ°
- NGINX ãã£ãã·ã¥
- NGINX å§çž®
- HTTPS ããã³ HTTP/2 ã®ãµããŒã
- ããã»ã¹ã®èªåå
ãã®èšäºã§ã¯ãéçåŠçãµãŒããŒãPHP åŠçãµãŒããŒãããã³ããŒã¿ããŒã¹ãåæã«ãã¹ããã XNUMX å°ã®ãµãŒããŒãžã®ã€ã³ã¹ããŒã«ã«ã€ããŠèª¬æããŸãã è€æ°ã®ä»®æ³ãã¹ããšãµãŒãã¹ããµããŒãããã€ã³ã¹ããŒã«ã¯ãå°æ¥ã®æœåšçãªãããã¯ã§ãã ãããã®èšäºã«ãªãããšã«ã€ããŠæžããŠã»ããå Žåã¯ãã³ã¡ã³ãã«æžããŠãã ããã
å¿ èŠæ¡ä»¶
- ã³ã³ãããµãŒã㌠(
LXC ãŸãã¯Lxd ïŒãä»®æ³ãã·ã³ããŸãã¯å°ãªããšã 512MB ã® RAM ãš Ubuntu 18.04 以éãã€ã³ã¹ããŒã«ãããŠããéåžžã® Iron ãµãŒããŒã - ã€ã³ã¿ãŒãããã«ã¢ã¯ã»ã¹å¯èœãªããŒã 80 ããã³ 443
- ãã®ãµãŒããŒã®ãããªã㯠IP ã¢ãã¬ã¹ã«é¢é£ä»ãããããã¡ã€ã³å
- ã«ãŒãã¢ã¯ã»ã¹ (sudo)ã
ã¢ãŒããã¯ãã£ã®æŠèŠ
ã¢ãŒããã¯ãã£ã¯èª¬æãããã®ãšåãã§ã
äžè¬åå
- ã¹ã¯ãªããå ã®å€ãã®æ§æã³ãã³ãã¯ãåªçæ§ã® if æ¡ä»¶ã§ã©ãããããŠããŸããã¹ã¯ãªããã¯ããã§ã«èšå®ãããŠããèšå®ãå€æŽãããªã¹ã¯ãªãã«è€æ°åå®è¡ã§ããŸãã
- ã¹ã¯ãªããã¯ãªããžããªãããœãããŠã§ã¢ãã€ã³ã¹ããŒã«ããããšãããããXNUMX ã€ã®ã³ãã³ãã§ã·ã¹ãã ã¢ããããŒããé©çšã§ããŸã (
apt upgrade
Ubuntuã®å ŽåïŒã - ã³ãã³ãã¯ã³ã³ããå ã§å®è¡ãããŠããããšãæ€åºããŠãããã«å¿ããŠèšå®ãå€æŽã§ããããã«ããŸãã
- èšå®ã§éå§ããã¹ã¬ãã ããã»ã¹ã®æ°ãèšå®ããããã«ãã¹ã¯ãªããã¯ã³ã³ãããŒãä»®æ³ãã·ã³ãããã³ããŒããŠã§ã¢ ãµãŒããŒã§åäœããããã®èªåèšå®ãæšæž¬ããããšããŸãã
- èšå®ã説æãããšããç§ãã¡ã¯åžžã«èªååã«ã€ããŠæåã«èããŸãããããã³ãŒããšããŠç¬èªã®ã€ã³ãã©ã¹ãã©ã¯ãã£ãäœæããããã®åºç€ãšãªãããšãé¡ã£ãŠããŸãã
- ãã¹ãŠã®ã³ãã³ãã¯ãŠãŒã¶ãŒãšããŠå®è¡ãããŸã ã«ãŒããåºæ¬çãªã·ã¹ãã èšå®ãå€æŽããŸãããWordPress ã¯çŽæ¥éåžžã®ãŠãŒã¶ãŒãšããŠå®è¡ãããããã§ãã
ç°å¢å€æ°ã®èšå®
ã¹ã¯ãªãããå®è¡ããåã«ã次ã®ç°å¢å€æ°ãèšå®ããŸãã
WORDPRESS_DB_PASSWORD
- WordPress ããŒã¿ããŒã¹ã®ãã¹ã¯ãŒãWORDPRESS_ADMIN_USER
- WordPress 管çè åWORDPRESS_ADMIN_PASSWORD
- WordPress 管çè ãã¹ã¯ãŒãWORDPRESS_ADMIN_EMAIL
- WordPress 管çè ã®ã¡ãŒã«ã¢ãã¬ã¹WORDPRESS_URL
ã¯ãWordPress ãµã€ãã®å®å šãª URL ã§ããhttps://
.LETS_ENCRYPT_STAGING
- ããã©ã«ãã§ã¯ç©ºã§ãããå€ã 1 ã«èšå®ãããšãLet's Encrypt ã¹ããŒãžã³ã° ãµãŒããŒã䜿çšãããŸããããã¯ãèšå®ããã¹ããããšãã«é »ç¹ã«èšŒææžãèŠæ±ããããã«å¿ èŠã§ããããããªããšã倧éã®èŠæ±ã«ãã Let's Encrypt ãäžæçã« IP ã¢ãã¬ã¹ããããã¯ããå¯èœæ§ããããŸãã ã
ã¹ã¯ãªããã¯ããããã® WordPress é¢é£ã®å€æ°ãèšå®ãããŠãããã©ããã確èªããèšå®ãããŠããªãå Žåã¯çµäºããŸãã
ã¹ã¯ãªããè¡ 572 ïœ 576 ã§å€ã確èªããŸã LETS_ENCRYPT_STAGING
.
掟çç°å¢å€æ°ã®èšå®
55 ïœ 61 è¡ç®ã®ã¹ã¯ãªããã¯ãããŒãã³ãŒãã£ã³ã°ãããå€ããŸãã¯åã®ã»ã¯ã·ã§ã³ã§èšå®ããå€æ°ããååŸããå€ã䜿çšããŠã次ã®ç°å¢å€æ°ãèšå®ããŸãã
DEBIAN_FRONTEND="noninteractive"
- ã¢ããªã±ãŒã·ã§ã³ãã¹ã¯ãªããã§å®è¡ãããŠããããšãããã³ãŠãŒã¶ãŒå¯Ÿè©±ã®å¯èœæ§ããªãããšãã¢ããªã±ãŒã·ã§ã³ã«äŒããŸããWORDPRESS_CLI_VERSION="2.4.0"
WordPress CLI ã¢ããªã±ãŒã·ã§ã³ã®ããŒãžã§ã³ã§ããWORDPRESS_CLI_MD5= "dedd5a662b80cda66e9e25d44c23b25c"
â WordPress CLI 2.4.0 å®è¡å¯èœãã¡ã€ã«ã®ãã§ãã¯ãµã (ããŒãžã§ã³ã¯å€æ°ã§æå®ãããŸã)WORDPRESS_CLI_VERSION
ïŒã 162 è¡ç®ã®ã¹ã¯ãªããã¯ããã®å€ã䜿çšããŠãæ£ãã WordPress CLI ãã¡ã€ã«ãããŠã³ããŒããããããšã確èªããŸããUPLOAD_MAX_FILESIZE="16M"
- WordPress ã«ã¢ããããŒãã§ããæ倧ãã¡ã€ã« ãµã€ãºã ãã®èšå®ã¯è€æ°ã®å Žæã§äœ¿çšããããããXNUMX ãæã«èšå®ããæ¹ãç°¡åã§ããTLS_HOSTNAME= "$(echo ${WORDPRESS_URL} | cut -d'/' -f3)"
- ã·ã¹ãã ã®ãã¹ãåãWORDPRESS_URL å€æ°ããååŸãããŸãã Let's Encrypt ããé©å㪠TLS/SSL 蚌ææžãååŸããããWordPress ã®å éšæ€èšŒãååŸãããããããã«äœ¿çšãããŸããNGINX_CONF_DIR="/etc/nginx"
- ã¡ã€ã³ãã¡ã€ã«ãå«ãNGINXèšå®ãå«ãŸãããã£ã¬ã¯ããªãžã®ãã¹nginx.conf
.CERT_DIR="/etc/letsencrypt/live/${TLS_HOSTNAME}"
â å€æ°ããååŸããããWordPress ãµã€ãã® Let's Encrypt 蚌ææžãžã®ãã¹TLS_HOSTNAME
.
WordPress ãµãŒããŒã«ãã¹ãåãå²ãåœãŠã
ã¹ã¯ãªããã¯ããµã€ãã®ãã¡ã€ã³åãšäžèŽããããã«ãµãŒããŒã®ãã¹ãåãèšå®ããŸãã ããã¯å¿ é ã§ã¯ãããŸããããåäžãµãŒããŒãã»ããã¢ããããå Žåã¯ãã¹ã¯ãªããã®æ§æã«åŸã£ãŠ SMTP çµç±ã§éä¿¡ã¡ãŒã«ãéä¿¡ãããšäŸ¿å©ã§ãã
ã¹ã¯ãªããã³ãŒã
# Change the hostname to be the same as the WordPress hostname
if [ ! "$(hostname)" == "${TLS_HOSTNAME}" ]; then
echo " Changing hostname to ${TLS_HOSTNAME}"
hostnamectl set-hostname "${TLS_HOSTNAME}"
fi
/etc/hosts ã«ãã¹ãåãè¿œå ãã
è£è¶³
ã¹ã¯ãªããã³ãŒã
# Add the hostname to /etc/hosts
if [ "$(grep -m1 "${TLS_HOSTNAME}" /etc/hosts)" = "" ]; then
echo " Adding hostname ${TLS_HOSTNAME} to /etc/hosts so that WordPress can ping itself"
printf "::1 %sn127.0.0.1 %sn" "${TLS_HOSTNAME}" "${TLS_HOSTNAME}" >> /etc/hosts
fi
次ã®ã¹ãããã«å¿ èŠãªããŒã«ãã€ã³ã¹ããŒã«ãã
ã¹ã¯ãªããã®æ®ãã®éšåã«ã¯ããã€ãã®ããã°ã©ã ãå¿ èŠã§ããããªããžããªãææ°ã§ããããšãåæãšããŠããŸãã ãªããžããªã®ãªã¹ããæŽæ°ããåŸãå¿ èŠãªããŒã«ãã€ã³ã¹ããŒã«ããŸãã
ã¹ã¯ãªããã³ãŒã
# Make sure tools needed for install are present
echo " Installing prerequisite tools"
apt-get -qq update
apt-get -qq install -y
bc
ca-certificates
coreutils
curl
gnupg2
lsb-release
NGINX ãŠããããš NGINX ãªããžããªã®è¿œå
ãã®ã¹ã¯ãªããã¯ãå ¬åŒ NGINX ãªããžããªãã NGINX ãŠããããšãªãŒãã³ ãœãŒã¹ NGINX ãã€ã³ã¹ããŒã«ããææ°ã®ã»ãã¥ãªã㣠ã¢ããããŒããšãã°ä¿®æ£ãé©çšãããããŒãžã§ã³ã䜿çšãããŠããããšã確èªããŸãã
ã¹ã¯ãªããã¯ãNGINX Unit ãªããžããªãè¿œå ãã次㫠NGINX ãªããžããªãè¿œå ããŠããªããžã㪠ããŒãšæ§æãã¡ã€ã«ãè¿œå ããŸãã apt
ãã€ã³ã¿ãŒãããçµç±ã®ãªããžããªãžã®ã¢ã¯ã»ã¹ãå®çŸ©ããŸãã
NGINX ãŠããããš NGINX ã®å®éã®ã€ã³ã¹ããŒã«ã¯æ¬¡ã®ã»ã¯ã·ã§ã³ã§è¡ãããŸãã ãªããžããªãäºåã«è¿œå ãããŠãããããã¡ã¿ããŒã¿ãè€æ°åæŽæ°ããå¿ èŠããªããã€ã³ã¹ããŒã«ãé«éåãããŸãã
ã¹ã¯ãªããã³ãŒã
# Install the NGINX Unit repository
if [ ! -f /etc/apt/sources.list.d/unit.list ]; then
echo " Installing NGINX Unit repository"
curl -fsSL https://nginx.org/keys/nginx_signing.key | apt-key add -
echo "deb https://packages.nginx.org/unit/ubuntu/ $(lsb_release -cs) unit" > /etc/apt/sources.list.d/unit.list
fi
# Install the NGINX repository
if [ ! -f /etc/apt/sources.list.d/nginx.list ]; then
echo " Installing NGINX repository"
curl -fsSL https://nginx.org/keys/nginx_signing.key | apt-key add -
echo "deb https://nginx.org/packages/mainline/ubuntu $(lsb_release -cs) nginx" > /etc/apt/sources.list.d/nginx.list
fi
NGINXãNGINX UnitãPHP MariaDBãCertbot (Let's Encrypt) ãšãã®äŸåé¢ä¿ã®ã€ã³ã¹ããŒã«
ãã¹ãŠã®ãªããžããªãè¿œå ããããã¡ã¿ããŒã¿ãæŽæ°ããã¢ããªã±ãŒã·ã§ã³ãã€ã³ã¹ããŒã«ããŸãã ã¹ã¯ãªããã«ãã£ãŠã€ã³ã¹ããŒã«ãããããã±ãŒãžã«ã¯ãWordPress.org ã®å®è¡æã«æšå¥šããã PHP æ¡åŒµæ©èœãå«ãŸããŠããŸã
ã¹ã¯ãªããã³ãŒã
echo " Updating repository metadata"
apt-get -qq update
# Install PHP with dependencies and NGINX Unit
echo " Installing PHP, NGINX Unit, NGINX, Certbot, and MariaDB"
apt-get -qq install -y --no-install-recommends
certbot
python3-certbot-nginx
php-cli
php-common
php-bcmath
php-curl
php-gd
php-imagick
php-mbstring
php-mysql
php-opcache
php-xml
php-zip
ghostscript
nginx
unit
unit-php
mariadb-server
NGINX ãŠãããããã³ WordPress ã§äœ¿çšããããã® PHP ã®ã»ããã¢ãã
ã¹ã¯ãªããã¯ãã£ã¬ã¯ããªã«èšå®ãã¡ã€ã«ãäœæããŸã conf.dã ããã«ãããPHP ã¢ããããŒãã®æ倧ãã¡ã€ã« ãµã€ãºãèšå®ãããSTDERR ãžã® PHP ãšã©ãŒåºåããªã³ã«ãªããNGINX ãŠãããã®ãã°ã«æžã蟌ãŸããããã«ãªããNGINX ãŠããããåèµ·åãããŸãã
ã¹ã¯ãªããã³ãŒã
# Find the major and minor PHP version so that we can write to its conf.d directory
PHP_MAJOR_MINOR_VERSION="$(php -v | head -n1 | cut -d' ' -f2 | cut -d'.' -f1,2)"
if [ ! -f "/etc/php/${PHP_MAJOR_MINOR_VERSION}/embed/conf.d/30-wordpress-overrides.ini" ]; then
echo " Configuring PHP for use with NGINX Unit and WordPress"
# Add PHP configuration overrides
cat > "/etc/php/${PHP_MAJOR_MINOR_VERSION}/embed/conf.d/30-wordpress-overrides.ini" << EOM
; Set a larger maximum upload size so that WordPress can handle
; bigger media files.
upload_max_filesize=${UPLOAD_MAX_FILESIZE}
post_max_size=${UPLOAD_MAX_FILESIZE}
; Write error log to STDERR so that error messages show up in the NGINX Unit log
error_log=/dev/stderr
EOM
fi
# Restart NGINX Unit because we have reconfigured PHP
echo " Restarting NGINX Unit"
service unit restart
WordPress ã® MariaDB ããŒã¿ããŒã¹èšå®ã®æå®
MySQL ã§ã¯ãªã MariaDB ãéžæããã®ã¯ãã³ãã¥ããã£æŽ»åãããå€ãããŸãã
ã¹ã¯ãªããã¯æ°ããããŒã¿ããŒã¹ãäœæããã«ãŒããã㯠ã€ã³ã¿ãŒãã§ã€ã¹çµç±ã§ WordPress ã«ã¢ã¯ã»ã¹ããããã®èªèšŒæ å ±ãäœæããŸãã
ã¹ã¯ãªããã³ãŒã
# Set up the WordPress database
echo " Configuring MariaDB for WordPress"
mysqladmin create wordpress || echo "Ignoring above error because database may already exist"
mysql -e "GRANT ALL PRIVILEGES ON wordpress.* TO "wordpress"@"localhost" IDENTIFIED BY "$WORDPRESS_DB_PASSWORD"; FLUSH PRIVILEGES;"
WordPress CLI ããã°ã©ã ã®ã€ã³ã¹ããŒã«
ãã®ã¹ãããã§ã¯ãã¹ã¯ãªããã«ãã£ãŠããã°ã©ã ãã€ã³ã¹ããŒã«ãããŸãã
ã¹ã¯ãªããã³ãŒã
if [ ! -f /usr/local/bin/wp ]; then
# Install the WordPress CLI
echo " Installing the WordPress CLI tool"
curl --retry 6 -Ls "https://github.com/wp-cli/wp-cli/releases/download/v${WORDPRESS_CLI_VERSION}/wp-cli-${WORDPRESS_CLI_VERSION}.phar" > /usr/local/bin/wp
echo "$WORDPRESS_CLI_MD5 /usr/local/bin/wp" | md5sum -c -
chmod +x /usr/local/bin/wp
fi
WordPress ã®ã€ã³ã¹ããŒã«ãšèšå®
ã¹ã¯ãªããã¯ãWordPress ã®ææ°ããŒãžã§ã³ããã£ã¬ã¯ããªã«ã€ã³ã¹ããŒã«ããŸãã /var/www/wordpress
ãŸããèšå®ãå€æŽããŸãã
- ããŒã¿ããŒã¹æ¥ç¶ã¯ãTCP ãã©ãã£ãã¯ãåæžããããã«ãã«ãŒãããã¯äžã® TCP ã§ã¯ãªã Unix ãã¡ã€ã³ ãœã±ããäžã§åäœããŸãã
- WordPress ã¯ãã¬ãã£ãã¯ã¹ãè¿œå ããŸã https:// ã¯ã©ã€ã¢ã³ãã HTTPS çµç±ã§ NGINX ã«æ¥ç¶ããå Žå㯠URL ã«éä¿¡ãããªã¢ãŒã ãã¹ãå (NGINX ã«ãã£ãŠæäŸããã) ã PHP ã«éä¿¡ããŸãã ãããèšå®ããã«ã¯ã³ãŒãã䜿çšããŸãã
- WordPress ã®ãã°ã€ã³ã«ã¯ HTTPS ãå¿ èŠã§ã
- ããã©ã«ãã® URL æ§é ã¯ãªãœãŒã¹ã«åºã¥ããŠããŸã
- WordPress ãã£ã¬ã¯ããªã®ãã¡ã€ã« ã·ã¹ãã ã«æ£ããã¢ã¯ã»ã¹èš±å¯ãèšå®ããŸãã
ã¹ã¯ãªããã³ãŒã
if [ ! -d /var/www/wordpress ]; then
# Create WordPress directories
mkdir -p /var/www/wordpress
chown -R www-data:www-data /var/www
# Download WordPress using the WordPress CLI
echo " Installing WordPress"
su -s /bin/sh -c 'wp --path=/var/www/wordpress core download' www-data
WP_CONFIG_CREATE_CMD="wp --path=/var/www/wordpress config create --extra-php --dbname=wordpress --dbuser=wordpress --dbhost="localhost:/var/run/mysqld/mysqld.sock" --dbpass="${WORDPRESS_DB_PASSWORD}""
# This snippet is injected into the wp-config.php file when it is created;
# it informs WordPress that we are behind a reverse proxy and as such
# allows it to generate links using HTTPS
cat > /tmp/wp_forwarded_for.php << 'EOM'
/* Turn HTTPS 'on' if HTTP_X_FORWARDED_PROTO matches 'https' */
if (isset($_SERVER['HTTP_X_FORWARDED_PROTO']) && strpos($_SERVER['HTTP_X_FORWARDED_PROTO'], 'https') !== false) {
$_SERVER['HTTPS'] = 'on';
}
if (isset($_SERVER['HTTP_X_FORWARDED_HOST'])) {
$_SERVER['HTTP_HOST'] = $_SERVER['HTTP_X_FORWARDED_HOST'];
}
EOM
# Create WordPress configuration
su -s /bin/sh -p -c "cat /tmp/wp_forwarded_for.php | ${WP_CONFIG_CREATE_CMD}" www-data
rm /tmp/wp_forwarded_for.php
su -s /bin/sh -p -c "wp --path=/var/www/wordpress config set 'FORCE_SSL_ADMIN' 'true'" www-data
# Install WordPress
WP_SITE_INSTALL_CMD="wp --path=/var/www/wordpress core install --url="${WORDPRESS_URL}" --title="${WORDPRESS_SITE_TITLE}" --admin_user="${WORDPRESS_ADMIN_USER}" --admin_password="${WORDPRESS_ADMIN_PASSWORD}" --admin_email="${WORDPRESS_ADMIN_EMAIL}" --skip-email"
su -s /bin/sh -p -c "${WP_SITE_INSTALL_CMD}" www-data
# Set permalink structure to a sensible default that isn't in the UI
su -s /bin/sh -p -c "wp --path=/var/www/wordpress option update permalink_structure '/%year%/%monthnum%/%postname%/'" www-data
# Remove sample file because it is cruft and could be a security problem
rm /var/www/wordpress/wp-config-sample.php
# Ensure that WordPress permissions are correct
find /var/www/wordpress -type d -exec chmod g+s {} ;
chmod g+w /var/www/wordpress/wp-content
chmod -R g+w /var/www/wordpress/wp-content/themes
chmod -R g+w /var/www/wordpress/wp-content/plugins
fi
NGINX ãŠãããã®ã»ããã¢ãã
ãã®ã¹ã¯ãªããã¯ãPHP ãå®è¡ã㊠WordPress ãã¹ãåŠçããããã« NGINX ãŠããããæ§æããPHP ããã»ã¹ã®åå空éãåé¢ããããã©ãŒãã³ã¹èšå®ãæé©åããŸãã ããã§æ³šç®ãã¹ã XNUMX ã€ã®æ©èœããããŸãã
- åå空éã®ãµããŒãã¯ãã¹ã¯ãªãããã³ã³ããå ã§å®è¡ãããŠãããã©ããã®ãã§ãã¯ã«åºã¥ããŠãæ¡ä»¶ã«ãã£ãŠæ±ºå®ãããŸãã ã»ãšãã©ã®ã³ã³ãããŒèšå®ã§ã¯ã³ã³ãããŒã®ãã¹ããããèµ·åããµããŒããããŠããªãããããããå¿ èŠã«ãªããŸãã
- ããŒã ã¹ããŒã¹ããµããŒããããŠããå Žåã¯ãããŒã ã¹ããŒã¹ãç¡å¹ã«ããŸãã ãããã¯ãŒã¯ã ããã¯ãWordPress ãäž¡æ¹ã®ãšã³ããã€ã³ãã«æ¥ç¶ããåæã« Web äžã§å©çšã§ããããã«ããããã§ãã
- ããã»ã¹ã®æ倧æ°ã¯æ¬¡ã®ããã«å®çŸ©ãããŸãã (MariaDB ããã³ NGINX Uniy ã®å®è¡ã«äœ¿çšå¯èœãªã¡ã¢ãª)/(PHP ã® RAM å¶é + 5)
ãã®å€ã¯ NGINX ãŠãããèšå®ã§èšå®ãããŸãã
ãã®å€ã¯ãåžžã«å°ãªããšã 10 ã€ã® PHP ããã»ã¹ãå®è¡ãããŠããããšãæå³ããŸããããã¯éèŠã§ãããªããªããWordPress ã¯ããèªäœã«å¯ŸããŠå€ãã®éåæãªã¯ãšã¹ããäœæããè¿œå ã®ããã»ã¹ããªããšãWP-Cron ãªã©ã®å®è¡ãäžæããŠããŸãããã§ãã ããã§äœæãããèšå®ã¯ä¿å®çã§ãããããããŒã«ã«èšå®ã«åºã¥ããŠãããã®å¶éãå¢æžããããšãã§ããŸãã ã»ãšãã©ã®å®çšŒåã·ã¹ãã ã§ã¯ãèšå®ã¯ 100 ïœ XNUMX ã§ãã
ã¹ã¯ãªããã³ãŒã
if [ "${container:-unknown}" != "lxc" ] && [ "$(grep -m1 -a container=lxc /proc/1/environ | tr -d '')" == "" ]; then
NAMESPACES='"namespaces": {
"cgroup": true,
"credential": true,
"mount": true,
"network": false,
"pid": true,
"uname": true
}'
else
NAMESPACES='"namespaces": {}'
fi
PHP_MEM_LIMIT="$(grep 'memory_limit' /etc/php/7.4/embed/php.ini | tr -d ' ' | cut -f2 -d= | numfmt --from=iec)"
AVAIL_MEM="$(grep MemAvailable /proc/meminfo | tr -d ' kB' | cut -f2 -d: | numfmt --from-unit=K)"
MAX_PHP_PROCESSES="$(echo "${AVAIL_MEM}/${PHP_MEM_LIMIT}+5" | bc)"
echo " Calculated the maximum number of PHP processes as ${MAX_PHP_PROCESSES}. You may want to tune this value due to variations in your configuration. It is not unusual to see values between 10-100 in production configurations."
echo " Configuring NGINX Unit to use PHP and WordPress"
cat > /tmp/wordpress.json << EOM
{
"settings": {
"http": {
"header_read_timeout": 30,
"body_read_timeout": 30,
"send_timeout": 30,
"idle_timeout": 180,
"max_body_size": $(numfmt --from=iec ${UPLOAD_MAX_FILESIZE})
}
},
"listeners": {
"127.0.0.1:8080": {
"pass": "routes/wordpress"
}
},
"routes": {
"wordpress": [
{
"match": {
"uri": [
"*.php",
"*.php/*",
"/wp-admin/"
]
},
"action": {
"pass": "applications/wordpress/direct"
}
},
{
"action": {
"share": "/var/www/wordpress",
"fallback": {
"pass": "applications/wordpress/index"
}
}
}
]
},
"applications": {
"wordpress": {
"type": "php",
"user": "www-data",
"group": "www-data",
"processes": {
"max": ${MAX_PHP_PROCESSES},
"spare": 1
},
"isolation": {
${NAMESPACES}
},
"targets": {
"direct": {
"root": "/var/www/wordpress/"
},
"index": {
"root": "/var/www/wordpress/",
"script": "index.php"
}
}
}
}
}
EOM
curl -X PUT --data-binary @/tmp/wordpress.json --unix-socket /run/control.unit.sock http://localhost/config
NGINXã®ã»ããã¢ãã
åºæ¬ç㪠NGINX èšå®ã®æ§æ
ã¹ã¯ãªãã㯠NGINX ãã£ãã·ã¥çšã®ãã£ã¬ã¯ããªãäœæããã¡ã€ã³ã®æ§æãã¡ã€ã«ãäœæããŸãã nginx.conf
ã ãã³ãã©ããã»ã¹æ°ãšã¢ããããŒãæã®æ倧ãã¡ã€ã«ãµã€ãºã®èšå®ã«æ³šæããŠãã ããã 次ã®ã»ã¯ã·ã§ã³ã§å®çŸ©ããå§çž®èšå®ãã¡ã€ã«ãå«ãè¡ãšããã®åŸã«ãã£ãã·ã¥èšå®ãç¶ãè¡ããããŸãã
ã¹ã¯ãªããã³ãŒã
# Make directory for NGINX cache
mkdir -p /var/cache/nginx/proxy
echo " Configuring NGINX"
cat > ${NGINX_CONF_DIR}/nginx.conf << EOM
user nginx;
worker_processes auto;
error_log /var/log/nginx/error.log warn;
pid /var/run/nginx.pid;
events {
worker_connections 1024;
}
http {
include ${NGINX_CONF_DIR}/mime.types;
default_type application/octet-stream;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /var/log/nginx/access.log main;
sendfile on;
client_max_body_size ${UPLOAD_MAX_FILESIZE};
keepalive_timeout 65;
# gzip settings
include ${NGINX_CONF_DIR}/gzip_compression.conf;
# Cache settings
proxy_cache_path /var/cache/nginx/proxy
levels=1:2
keys_zone=wp_cache:10m
max_size=10g
inactive=60m
use_temp_path=off;
include ${NGINX_CONF_DIR}/conf.d/*.conf;
}
EOM
NGINX å§çž®ã®ã»ããã¢ãã
ã¯ã©ã€ã¢ã³ãã«éä¿¡ããåã«ã³ã³ãã³ãããã®å Žã§å§çž®ããããšã¯ããµã€ãã®ããã©ãŒãã³ã¹ãåäžãããåªããæ¹æ³ã§ãããããã¯å§çž®ãæ£ããæ§æãããŠããå Žåã«éããŸãã ã¹ã¯ãªããã®ãã®ã»ã¯ã·ã§ã³ã¯èšå®ã«åºã¥ããŠããŸã
ã¹ã¯ãªããã³ãŒã
cat > ${NGINX_CONF_DIR}/gzip_compression.conf << 'EOM'
# Credit: https://github.com/h5bp/server-configs-nginx/
# ----------------------------------------------------------------------
# | Compression |
# ----------------------------------------------------------------------
# https://nginx.org/en/docs/http/ngx_http_gzip_module.html
# Enable gzip compression.
# Default: off
gzip on;
# Compression level (1-9).
# 5 is a perfect compromise between size and CPU usage, offering about 75%
# reduction for most ASCII files (almost identical to level 9).
# Default: 1
gzip_comp_level 6;
# Don't compress anything that's already small and unlikely to shrink much if at
# all (the default is 20 bytes, which is bad as that usually leads to larger
# files after gzipping).
# Default: 20
gzip_min_length 256;
# Compress data even for clients that are connecting to us via proxies,
# identified by the "Via" header (required for CloudFront).
# Default: off
gzip_proxied any;
# Tell proxies to cache both the gzipped and regular version of a resource
# whenever the client's Accept-Encoding capabilities header varies;
# Avoids the issue where a non-gzip capable client (which is extremely rare
# today) would display gibberish if their proxy gave them the gzipped version.
# Default: off
gzip_vary on;
# Compress all output labeled with one of the following MIME-types.
# `text/html` is always compressed by gzip module.
# Default: text/html
gzip_types
application/atom+xml
application/geo+json
application/javascript
application/x-javascript
application/json
application/ld+json
application/manifest+json
application/rdf+xml
application/rss+xml
application/vnd.ms-fontobject
application/wasm
application/x-web-app-manifest+json
application/xhtml+xml
application/xml
font/eot
font/otf
font/ttf
image/bmp
image/svg+xml
text/cache-manifest
text/calendar
text/css
text/javascript
text/markdown
text/plain
text/xml
text/vcard
text/vnd.rim.location.xloc
text/vtt
text/x-component
text/x-cross-domain-policy;
EOM
WordPress çšã® NGINX ã®ã»ããã¢ãã
次ã«ãã¹ã¯ãªãã㯠WordPress ã®æ§æãã¡ã€ã«ãäœæããŸãã ããã©ã«ã.conf ã«ã¿ãã°ã«ãã conf.dã ããã§èšå®ãããŸã:
- Certbot çµç±ã§ Let's Encrypt ããåä¿¡ãã TLS 蚌ææžãã¢ã¯ãã£ãåããŸã (ã»ããã¢ããã«ã€ããŠã¯æ¬¡ã®ã»ã¯ã·ã§ã³ã§èª¬æããŸã)ã
- Let's Encrypt ã®æšå¥šäºé ã«åºã¥ã㊠TLS ã»ãã¥ãªãã£èšå®ãæ§æãã
- ããã©ã«ã㧠1 æéã®ãã£ãã·ã¥ ã¹ããã ãªã¯ãšã¹ããæå¹ã«ãã
- XNUMX ã€ã®äžè¬çãªèŠæ±ãã¡ã€ã« (favicon.ico ããã³ robots.txt) ã«ã€ããŠãã¢ã¯ã»ã¹ ãã°ãç¡å¹ã«ãããã¡ã€ã«ãèŠã€ãããªãå Žåã®ãšã©ãŒ ãã°ãç¡å¹ã«ããŸãã
- é ããã¡ã€ã«ããã³äžéšã®ãã¡ã€ã«ãžã®ã¢ã¯ã»ã¹ãçŠæ¢ãã ãPHPã®äžæ£ã¢ã¯ã»ã¹ãæå³ããªãèµ·åãé²ããã
- éçãã¡ã€ã«ãšãã©ã³ã ãã¡ã€ã«ã®ã¢ã¯ã»ã¹ ãã°ãç¡å¹ã«ãã
- ããããŒèšå®
ã¢ã¯ã»ã¹å¶åŸ¡èš±å¯ãªãªãžã³ ãã©ã³ããã¡ã€ã«çš - Index.php ããã³ãã®ä»ã®éçãã¡ã€ã«ã®ã«ãŒãã£ã³ã°ãè¿œå ããŸãã
ã¹ã¯ãªããã³ãŒã
cat > ${NGINX_CONF_DIR}/conf.d/default.conf << EOM
upstream unit_php_upstream {
server 127.0.0.1:8080;
keepalive 32;
}
server {
listen 80;
listen [::]:80;
# ACME-challenge used by Certbot for Let's Encrypt
location ^~ /.well-known/acme-challenge/ {
root /var/www/certbot;
}
location / {
return 301 https://${TLS_HOSTNAME}$request_uri;
}
}
server {
listen 443 ssl http2;
listen [::]:443 ssl http2;
server_name ${TLS_HOSTNAME};
root /var/www/wordpress/;
# Let's Encrypt configuration
ssl_certificate ${CERT_DIR}/fullchain.pem;
ssl_certificate_key ${CERT_DIR}/privkey.pem;
ssl_trusted_certificate ${CERT_DIR}/chain.pem;
include ${NGINX_CONF_DIR}/options-ssl-nginx.conf;
ssl_dhparam ${NGINX_CONF_DIR}/ssl-dhparams.pem;
# OCSP stapling
ssl_stapling on;
ssl_stapling_verify on;
# Proxy caching
proxy_cache wp_cache;
proxy_cache_valid 200 302 1h;
proxy_cache_valid 404 1m;
proxy_cache_revalidate on;
proxy_cache_background_update on;
proxy_cache_lock on;
proxy_cache_use_stale error timeout http_500 http_502 http_503 http_504;
location = /favicon.ico {
log_not_found off;
access_log off;
}
location = /robots.txt {
allow all;
log_not_found off;
access_log off;
}
# Deny all attempts to access hidden files such as .htaccess, .htpasswd,
# .DS_Store (Mac)
# Keep logging the requests to parse later (or to pass to firewall utilities
# such as fail2ban)
location ~ /. {
deny all;
}
# Deny access to any files with a .php extension in the uploads directory;
# works in subdirectory installs and also in multi-site network.
# Keep logging the requests to parse later (or to pass to firewall utilities
# such as fail2ban).
location ~* /(?:uploads|files)/.*.php$ {
deny all;
}
# WordPress: deny access to wp-content, wp-includes PHP files
location ~* ^/(?:wp-content|wp-includes)/.*.php$ {
deny all;
}
# Deny public access to wp-config.php
location ~* wp-config.php {
deny all;
}
# Do not log access for static assets, media
location ~* .(?:css(.map)?|js(.map)?|jpe?g|png|gif|ico|cur|heic|webp|tiff?|mp3|m4a|aac|ogg|midi?|wav|mp4|mov|webm|mpe?g|avi|ogv|flv|wmv)$ {
access_log off;
}
location ~* .(?:svgz?|ttf|ttc|otf|eot|woff2?)$ {
add_header Access-Control-Allow-Origin "*";
access_log off;
}
location / {
try_files $uri @index_php;
}
location @index_php {
proxy_socket_keepalive on;
proxy_http_version 1.1;
proxy_set_header Connection "";
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header Host $host;
proxy_pass http://unit_php_upstream;
}
location ~* .php$ {
proxy_socket_keepalive on;
proxy_http_version 1.1;
proxy_set_header Connection "";
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header Host $host;
try_files $uri =404;
proxy_pass http://unit_php_upstream;
}
}
EOM
Let's Encrypt ããã®èšŒææžçšã® Certbot ã®ã»ããã¢ãããšèªåæŽæ°
- NGINXãåæ¢ããŸã
- æšå¥šããã TLS èšå®ãããŠã³ããŒãããŸã
- Certbot ãå®è¡ããŠãµã€ãã®èšŒææžãååŸããŸã
- 蚌ææžã䜿çšããããã« NGINX ãåèµ·åããŸã
- Certbot ãæ¯æ¥åå 3 æ 24 åã«å®è¡ããŠèšŒææžãæŽæ°ããå¿ èŠããããã©ããã確èªããå¿ èŠã«å¿ããŠæ°ãã蚌ææžãããŠã³ããŒãã㊠NGINX ãåèµ·åããããã«æ§æããŸãã
ã¹ã¯ãªããã³ãŒã
echo " Stopping NGINX in order to set up Let's Encrypt"
service nginx stop
mkdir -p /var/www/certbot
chown www-data:www-data /var/www/certbot
chmod g+s /var/www/certbot
if [ ! -f ${NGINX_CONF_DIR}/options-ssl-nginx.conf ]; then
echo " Downloading recommended TLS parameters"
curl --retry 6 -Ls -z "Tue, 14 Apr 2020 16:36:07 GMT"
-o "${NGINX_CONF_DIR}/options-ssl-nginx.conf"
"https://raw.githubusercontent.com/certbot/certbot/master/certbot-nginx/certbot_nginx/_internal/tls_configs/options-ssl-nginx.conf"
|| echo "Couldn't download latest options-ssl-nginx.conf"
fi
if [ ! -f ${NGINX_CONF_DIR}/ssl-dhparams.pem ]; then
echo " Downloading recommended TLS DH parameters"
curl --retry 6 -Ls -z "Tue, 14 Apr 2020 16:49:18 GMT"
-o "${NGINX_CONF_DIR}/ssl-dhparams.pem"
"https://raw.githubusercontent.com/certbot/certbot/master/certbot/certbot/ssl-dhparams.pem"
|| echo "Couldn't download latest ssl-dhparams.pem"
fi
# If tls_certs_init.sh hasn't been run before, remove the self-signed certs
if [ ! -d "/etc/letsencrypt/accounts" ]; then
echo " Removing self-signed certificates"
rm -rf "${CERT_DIR}"
fi
if [ "" = "${LETS_ENCRYPT_STAGING:-}" ] || [ "0" = "${LETS_ENCRYPT_STAGING}" ]; then
CERTBOT_STAGING_FLAG=""
else
CERTBOT_STAGING_FLAG="--staging"
fi
if [ ! -f "${CERT_DIR}/fullchain.pem" ]; then
echo " Generating certificates with Let's Encrypt"
certbot certonly --standalone
-m "${WORDPRESS_ADMIN_EMAIL}"
${CERTBOT_STAGING_FLAG}
--agree-tos --force-renewal --non-interactive
-d "${TLS_HOSTNAME}"
fi
echo " Starting NGINX in order to use new configuration"
service nginx start
# Write crontab for periodic Let's Encrypt cert renewal
if [ "$(crontab -l | grep -m1 'certbot renew')" == "" ]; then
echo " Adding certbot to crontab for automatic Let's Encrypt renewal"
(crontab -l 2>/dev/null; echo "24 3 * * * certbot renew --nginx --post-hook 'service nginx reload'") | crontab -
fi
ãµã€ãã®è¿œå ã®ã«ã¹ã¿ãã€ãº
äžã§ã¯ãTLSSSL ãæå¹ã«ãªã£ãŠããæ¬çªç°å¢ã«å¯Ÿå¿ãããµã€ããæäŸããããã«ãã¹ã¯ãªããã NGINX ãš NGINX Unit ãæ§æããæ¹æ³ã«ã€ããŠèª¬æããŸããã å¿ èŠã«å¿ããŠãå°æ¥çã«ä»¥äžãè¿œå ããããšãã§ããŸãã
- ãµããŒã
ããã㪠ãHTTPS ãä»ãããªã³ã¶ãã©ã€å§çž®ã®æ¹å ModSecurity㯠Ñã¯ãŒããã¬ã¹ã®ã«ãŒã« ãµã€ããžã®èªåæ»æãé²ãããããã¯ã¢ãããã ããªãã«åã£ãWordPressãä¿è· çµç±AppArmor (Ubuntu äž)- Postfix ãŸã㯠msmtp (WordPress ãã¡ãŒã«ãéä¿¡ã§ããããã«ãã)
- ãµã€ãããã§ãã¯ããŠãåŠçã§ãããã©ãã£ãã¯éãææ¡ãã
ãµã€ãã®ããã©ãŒãã³ã¹ãããã«åäžãããã«ã¯ã次ã®ããã«ã¢ããã°ã¬ãŒãããããšããå§ãããŸãã
N.B. é«è² è·ã®ãµã€ãã®ãµããŒãã«ã€ããŠã¯ãå°é家ã«ãåãåãããã ããã
ãµãŠã¹ããªããž ã ããããè² è·ã®äžã§ããã客æ§ã® Web ãµã€ãããµãŒãã¹ã®é«éãã€ä¿¡é Œæ§ã®é«ãåäœãä¿èšŒããŸãã
åºæïŒ habr.com