# Setting up Nginx-Apache Reverse Proxy, PHP, & MariaDB with SSL on EC2/Lightsail with Amazon Linux Final setup should consists of: 1. NGINX (reverse proxy & static contents) - Supports SSL ([Let's Encrypt](https://letsencrypt.org)). - Supports multiple domains, 1 IP. 1. Apache 2.4 (Dynamic content: PHP) 1. PHP 7.1 1. MariaDB 10.1 You can skip certain parts if you don't need it. ## Preparations 1. Create www directory if not exists yet: `sudo mkdir -p /var/www` 1. Give write permission: `sudo chmod -R 755 /var/www` 1. Create new directory for your subdomain: `sudo mkdir -p /var/www/domain.com/sub1/public` 1. Give ownership to current logged in user: `sudo chown $USER:$USER -R /var/www/domain.com/sub1/` ## NGINX 1. Install: `sudo yum install nginx -y` - If no package available, refer https://aws.amazon.com/premiumsupport/knowledge-center/ec2-enable-epel/ 1. Configure this file: `/etc/nginx/conf.d/default.conf` to something like this: ```nginx.conf server { listen 80; server_name sub1.domain.com; root /var/www/domain.com/sub1/public/; index index.php index.html index.htm; location / { try_files $uri $uri/ /index.php$uri$is_args$args; } location ~ \.php { proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header Host $host; proxy_set_header X-Forwarded-Proto $scheme; proxy_set_header X-Forwarded-Port 443; proxy_pass http://127.0.0.1:8080; } location ~ /\.ht { deny all; } } ``` 1. Auto-start NGINX on system start: `sudo chkconfig nginx on` ## Apache 1. Install: `sudo yum install httpd24 -y` - If no package available, refer https://stackoverflow.com/questions/37940661/aws-rhel7-missing-packages 1. Configure `/etc/httpd/conf/httpd.conf` as follows: ```httpd.conf Listen 8080 ``` 1. Configure virtual hosts at `/etc/httpd/conf.d/vhosts.conf`: ``` ServerAdmin email@sub1.domain.com DocumentRoot /var/www/domain.com/sub1/public/ ServerName sub1.domain.com ErrorLog logs/sub1.domain.com-error_log CustomLog logs/sub1.domain.com-access_log common ``` 1. Auto-start Apache on system start: `sudo chkconfig httpd on` ## SSL (Let's Encrypt) ### EC2 - Amazon Linux 2 Follow: https://certbot.eff.org/lets-encrypt/centosrhel7-nginx 1. Enable optional channel: ``` sudo yum -y install yum-utils sudo yum-config-manager --enable rhui-REGION-rhel-server-extras rhui-REGION-rhel-server-optional ``` 1. Install certbot: ``` sudo yum install certbot-nginx ``` 1. Request cert: ``` sudo certbot --nginx ``` - Go through the wizard carefully. 1. If all went well, your certs will be at `/etc/letsencrypt/live/sub1.domain.com/` and your `/etc/nginx/conf.d/default.conf` has been updated by cerbot automatically. * In the future, to renew: ``` certbot renew ``` ### Lightsail 1. Install Certbot: ``` sudo yum install python27-devel git -y sudo git clone https://github.com/letsencrypt/letsencrypt /opt/letsencrypt sudo /opt/letsencrypt/letsencrypt-auto --debug ``` 1. Request cert: ``` sudo /opt/letsencrypt/letsencrypt-auto --authenticator standalone --installer nginx --pre-hook "nginx -s stop" --post-hook "nginx" ``` - Go through the wizard carefully. 1. If all went well, your certs will be at `/etc/letsencrypt/live/sub1.domain.com/` and your `/etc/nginx/conf.d/default.conf` has been updated by cerbot automatically. * In the future, to renew: ``` sudo /opt/letsencrypt/letsencrypt-auto --authenticator standalone --installer nginx --pre-hook "nginx -s stop" --post-hook "nginx" renew ``` ## MariaDB 1. Add yum repository. Create this file: `/etc/yum.repos.d/mariadb.repo`: - Refer https://mariadb.com/kb/en/library/yum/ - Repo Generator: https://downloads.mariadb.org/mariadb/repositories/ 1. Install: ``` sudo yum makecache sudo yum install MariaDB-server MariaDB-client -y ``` 1. If you install version `10.2` and above, the service name is `mariadb`, otherwise it's `mysql` 1. Start service: ``` sudo service mysql(or mariadb) start ``` 1. Secure your MariaDB installation: `sudo mysql_secure_installation` 1. Auto-start MariaDB on system start: `sudo chkconfig mysql(or mariadb) on` ## PHP 7.1 1. Install: `sudo yum install php71 -y` - If no package available, try remi: https://rpms.remirepo.net/wizard/ 1. Install PHP Modules - Run `yum search php71-` to search for available modules and just yum install it. ## Start All Services 1. `sudo service nginx start` 1. `sudo service httpd start` 1. `sudo service mysql(or mariadb) start` ## Add More (Sub)Domains Once everything is working, you can start adding more (sub)domains. 1. Create new directory for your subdomain: `sudo mkdir -p /var/www/domain.com/sub2/public` 1. Give ownership to current logged in user: `sudo chown $USER:$USER -R /var/www/domain.com/sub2/` 1. Edit `/etc/nginx/conf.d/default.conf` to add more domains, but without the ssl settings: ``` # 1st domain settings are up here, don't remove server { ... } # 1st domain settings are up here, don't remove server { listen 80; server_name sub2.domain.com; root /var/www/domain.com/sub2/public/; index index.php index.html index.htm; location / { try_files $uri $uri/ /index.php$uri$is_args$args; } location ~ \.php { proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header Host $host; proxy_set_header X-Forwarded-Proto $scheme; proxy_set_header X-Forwarded-Port 443; proxy_pass http://127.0.0.1:8080; } location ~ /\.ht { deny all; } } ``` 1. Edit Apache virtual hosts at `/etc/httpd/conf.d/vhosts.conf` to add more virtual host: ``` # 1st domain settings are up here, don't remove ... # 1st domain settings are up here, don't remove ServerAdmin email@sub2.domain.com DocumentRoot /var/www/domain.com/sub2/public/ ServerName sub2.domain.com ErrorLog logs/sub2.domain.com-error_log CustomLog logs/sub2.domain.com-access_log common ``` 1. Request SSL cert using certbot again, but this time pick the new domain: - EC2 - With Amazon Linux 2 ``` sudo certbot --nginx ``` - Lightsail ``` sudo /opt/letsencrypt/letsencrypt-auto --authenticator standalone --installer nginx --pre-hook "nginx -s stop" --post-hook "nginx" ``` - If all went well, your certs will be at `/etc/letsencrypt/live/sub2.domain.com/` and your `/etc/nginx/conf.d/default.conf` has been updated by cerbot automatically. 1. Restart NGINX & Apache: ``` sudo service nginx restart sudo service httpd restart ``` 1. ??? 1. Profit. :D ## Final Files for References You can view the final files down below. - [/etc/nginx/conf.d/default.conf](#file-default-conf) - [/etc/httpd/conf.d/vhosts.conf](#file-vhosts-conf) ## References: - https://gist.github.com/nrollr/56e933e6040820aae84f82621be16670 - https://www.digitalocean.com/community/tutorials/how-to-configure-nginx-as-a-reverse-proxy-for-apache - https://stackoverflow.com/questions/14434120/nginx-set-multiple-server-name-with-ssl-support - https://www.digitalocean.com/community/tutorials/how-to-install-linux-apache-mysql-php-lamp-stack-on-centos-7 - https://certbot.eff.org/#centosrhel7-nginx - https://community.letsencrypt.org/t/solution-client-with-the-currently-selected-authenticator-does-not-support-any-combination-of-challenges-that-will-satisfy-the-ca/49983 - https://coderwall.com/p/e7gzbq/https-with-certbot-for-nginx-on-amazon-linux - https://mariadb.com/kb/en/library/yum/