Quick and Painless AWS Setup


Amazon Web Service is actually a great tool to use for testing before you jump into a tangled mess of twisted command line arguments and snagging the core functionality of your root user’s over zealous freedom of commands. Following the basic steps for a web server, then moving into the detailed intricacies will prevent you from having hair pulling and drama inducing levels of hormonal rage outbursts. In this article, I will give the basic step by step procedures to enable a fully functional PHP 7.x web server running nGinX, MariaDB 10.2.x and smoothing everything out with a FREE SSL from LetsEncrypt. In this example, I am demonstrating this setup on an Ubuntu 16.04 LTS server from Amazon.


Server Configuration

There are several ways to setup and install a server. This method is one of my favorites, it makes things simple to manage, and it allows for scripting by giving the ability to quickly enable and disable the server.

Ubuntu’s Proper Editor

By default, Ubuntu uses Nano for its text editor. Although there are many alternatives available, you can change the default editor by running this command. This will make configuring things much easier if you are familiar with the editor you use.

sudo update-alternatives --config editor
There are 4 choices for the alternative editor (providing /usr/bin/editor).
  Selection          Path        Priority      Status
* 0          /bin/nano        40        auto mode
 1          /bin/ed        -100      manual mode
 2          /bin/nano        40      manual mode
 3          /usr/bin/vim.basic    30      manual mode
 4          /usr/bin/vim.tiny     10      manual mode
Press <enter> to keep the current choice[*], or type selection number:

Change Hostname

First we need to make sure that our domain name on this server is pointing to the localhost.

sudo nano /etc/hosts

Add the following: <name><fqdn>.<tld> to the hosts file, here is an example of using

Finally, add the host to the hostname, with this

sudo hostname <name><fqdn>.<tld>

Installing PHP and other Common Packages

No matter which PHP you wish to install, always make sure your server is up to date. With this setup, I am using the 5.6 PPA which is the current LTS system out at this time.

sudo apt update && sudo apt upgrade -y
sudo add-apt-repository ppa:ondrej/php -y
sudo apt install build-essential nginx auto-apt checkinstall libssl-dev zlib1g-dev python python-dev python-pip mailutils ruby ruby-dev mariadb-client-core-10.0 mariadb-client-10.0 letsencrypt apparmor-utils build-essential checkinstall automake libbz2-1.0 libbz2-dev libbz2-ocaml libbz2-ocaml-dev libreadline-dev clamav -y

Update OpenSSH for PCI Compliance

Check for the new version with "ssh -V" once the follow has been completed.

sudo wget && sudo tar -zxvf openssh-7.3p1.tar.gz && cd openssh-7.3p1 && ./configure && sudo make && sudo checkinstall make install
sudo service ssh restart
sudo reboot

Create a NON ROOT user

If you want to avoid the easiest way to hack a website, then do not use the root to serve all of your files, for this reason we need to create a user with non super user privileges. This user must be part of www-data group so nGinX and PHP will server the files with the non privileged user.

sudo adduser <username>
sudo usermod -a -G www-data <username>

Create the SSH key for the non privileged user

First we need to switch to the new user by sudo’ing into the user. Then by using ssh <some address>, this will automatically create the .ssh folder in the user’s /home/ folder with the correct permissions automatically.

sudo su – <username>
ssh <some address>

Some Setting up PIP, SASS and Compass

sudo -H pip install virtualenv
sudo -H pip install –upgrade pip
sudo su -c "gem install sass"
sudo su -c "gem install compass"

LetsEncrypt Configuration

As a superuser, it is time to start the SSL installation. If you are following this from start to finish, you need to exit the web users account by hitting CTRL-D or typing exit. Now you are back to the superuser "e;ubuntu"e;.

sudo letsencrypt certonly –webroot -w /var/www/html -d $(hostname);

See nginx configuration vis /etc/letsencrypt/live/
**note:** if you are moving servers or otherwise fiddling with an existing set of ssl credentials, it would be in your interest to use
letsencrypt to revoke your existing creds before running the above, otherwise you’ll not be able to renew!

## nginx_ensite/dissite Configuration
Install from git as sudo member

git clone
cd nginx_ensite
sudo checkinstall

### Create Unique DH Group
#### Important! Prevent LogJam SSL Attack!
# requires root permissions

cd /etc/ssl/private
openssl dhparam -out dhparams.pem 2048
chmod 600 dhparams.pem

### Nginx Configuration

Magento 1.x Nginx configuration:

One will most likely be able to replace with the actual subdomain and it will “just work”.

[Production Nginx Configuration](Production-Nginx-Configuration) file differs!

#### Enable gzip compression for CSS, JS and Icons in /etc/nginx/nginx.conf

#### Generate dhparams.pem File

This can take up to 20 minutes depending on your host’s horsepower

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

Add the following under your ssl keys in your enginx config:

ssl_dhparam /etc/ssl/certs/dhparam.pem;
cd /home/<username>
chown -R :www-data .
find ./ -type d -exec chmod 755 {} \;
find ./ -type f -exec chmod 644 {} \;

php-fpm Configuration

TODO production chroot

Create log directory:

sudo mkdir /home/spectrum/spectrum-labs/logs
sudo chown -R spectrum:www-data /home/spectrum/spectrum-labs/logs
sudo chmod -R 775 /home/spectrum/spectrum-labs/html/media/catalog/product

Assure that logrotate is properly configured to use correct file permissions for logging in /etc/logrotate.d/php5.6-fpm.

Up the max_execution_time value in /etc/php/5.6/cgi/php.ini

Change the following in /etc/php/5.6/fpm/pool.d/www.conf
change pm to “ondemand”
everything with a leading “;” is to be commented out.

Note: bumped max_children up from 5 to 8. Getting “server reached max_children setting” errors in log.

mcrypt Configuration

sudo phpenmod mcrypt
sudo service php5.6-fpm restart
sudo service nginx restart

Permissions for <username> User

Use sudo visudo and add the following:
# allow <username> to restart php-fpm and nginx

<username> ALL=(ALL) NOPASSWD: /usr/sbin/service php5.6-fpm restart
<username> ALL=(ALL) NOPASSWD: /usr/sbin/service nginx restart


PCI compliance requires we have anti-virus installed. On our unix system. That does not receive emails. It’s a process, you see.

See for the gory details also
may have good information, for future reference

A quick “paste it in” version is [here](anti-virus-web-server-xenial)

Stupid Server Tricks

If kswapd0 is eating up your processor after a bulk import: # as root!

echo 1 > /proc/sys/vm/drop_caches

Revoke Existing LetsEncrypt Certificate

sudo letsencrypt revoke -d subdomain.domain.tld –cert-path /etc/letsencrypt/live/subdomain.domain.tld/fullchain.pem

LetsEncrypt Auto Update Script

Letsencrypt requires that you have a vanilla http connection for auto-renew script to work. This means that since we redirect **everything** to ssl, that auto-renew will fail. This script switches to the default nginx setup, runs the renewal script, then restarts the service.

Name this script update-ssl and make it executable.

Update your root crontab like so:

@daily /home/ubuntu/update-ssl

Add ip blocking

cd /etc/nginx
cp nginx.conf ./nginx.conf.bak
sudo nano nginx.conf

## Add the following under the http {

include blockips.conf;

Save your file

Create a new blockips.conf file

sudo nano blockips.conf

Save your file

Add the following

Save your file

Test nGinx

sudo nginx -t # if comes back as tests OK then
sudo nginx -s reload # Test your site to make sure it still loads
sudo rm nginx.conf.bak

%d bloggers like this: