How to setup a VPS (or Dedicated Server) with Nginx from scratch
In this tutorial we are going to go through the steps of securing the server and configuring Nginx, PHP, Phpmyadmin and MySql.
Step 1. Basic Security
Assuming you have already logged into your server we start by changing the root password to something more secure.
passwd
This will prompt you to change the root password, It is recommended to choose something extremely complex as it is your most crucial line of defence against the outside world.
Next, open up the ssh config
vim /etc/ssh/sshd_config
and change the port from 22 to anything between 1025 to 65536, this will prevent our server from being easily spotted by malicious eyes
Port 22
We can now restart the ssh service to apply our changes
service ssh restart
Now that these basic tasks are done we need to update our server to the latest stable LTS. We can do this with
apt-get update apt-get upgrade
Step 2. Even more Security – Denyhosts
To make it even harder for those malicious individuals to compromise our server we are going to install denyhosts. This is a program that basically scans your log files an auto-bans anyone who seems a bit too suspicous.
apt-get install denyhosts
The default options are fine but I like to edit the configuration file and tweak the settings below
vim /etc/denyhosts.conf
BLOCK_SERVICE = sshd # Change to ALL DENY_THRESHOLD_INVALID = 5 # Change to 3 DENY_THRESHOLD_VALID = 10 # Change to 3 DENY_THRESHOLD_ROOT = 1 # Change to 3 #RESET_ON_SUCCESS = yes # Uncomment this line
What we have basically done is to make it easier to block individuals who try random attacks and give ourselves more chances to get it right.. I live in a country with ever changing IP Addresses and it’s annoying to get blocked from your own server when you enter the wrong password once.
If you have a static ip, then follow the step below, if not, please ignore
vim /etc/hosts.allow
tell denyhosts to ignore your IP by adding it to a whitelist in the format
ALL: 177.636.375.433 # Replace this with your static IP
When you are done, start denyhosts with
service denyhosts restart
(ps, if your ever want to see who is currently banned, check the /etc/hosts.deny file.)
Step 3. PHP 5.5
Ubuntu comes with 5.3 (maybe 5.4 now) in its repository but we much prefer Php 5.5 as it has more features, is faster and well… is 0.2 better 🙂 . To get this we need to use an external repo.
apt-get install python-software-properties add-apt-repository ppa:ondrej/php5
Repository added, now to update and install with some common modules
apt-get update apt-get install php5-common php5-mysqlnd php5-xmlrpc php5-curl php5-gd php5-cli php5-fpm php-pear php5-dev php5-imap php5-mcrypt
I have found that sometimes mcrypt requires a restart of the server to work properly, so if you get any ‘mcrypt’ errors, please ‘shutdown -r now’
if you wish to check your php modules and version info you can do so with
php -v # version php -i # Similar to running phpinfo()
Step 4. MySQL
When it comes to Mysql we have two options (actually, there are many but these are my favorite)
- Install percona server (A better, but heavier drop-in replacement for MySQL [suggested for hosts with at least 1GB of ram] )
- Install the default Oracle MySQL server (Machines with less than 1GB ram)
To install percona, we need to add the repo and then install. To do this..
apt-key adv --keyserver keys.gnupg.net --recv-keys 1C4CBDCDCD2EFD2A echo "deb http://repo.percona.com/apt `lsb_release -cs` main" >> /etc/apt/sources.list.d/percona.list echo "deb-src http://repo.percona.com/apt `lsb_release -cs` main" >> /etc/apt/sources.list.d/percona.list apt-get update apt-get install percona-server-server-5.6 percona-server-client-5.6
For Oracle, as it is already in our repo… we just need to
apt-get install mysql-client mysql-server
Cool, almost here.. lets start the mysql server and secure it for production use
service mysql restart /usr/bin/mysql_secure_installation
Step 5. Installing Nginx
The normal Nginx Package tends to ignore a few packages I’ve grown to know and love and so I recommend you use either nginx-full or brian mercers nginx-custom. My preference is the custom because It has a few third party modules that even nginx-full does not (such as fcgi cache purge). To install, use
add-apt-repository ppa:brianmercer/nginx apt-get update apt-get install nginx-custom
If you wish to use nginx-full then you can just run
apt-get install nginx-full
NOTE. Please don’t try to install both at the same time..
Step 6. Configure, configure, configure
PHP
We first going to configure the php config file and make a few changes
- Prevent php from ‘guessing’ where users want to go (horrible security risk)
- Increase upload limit
vim /etc/php5/fpm/php.ini
find
#cgi.fix_pathinfo=1
replace with
cgi.fix_pathinfo=0
Also, find and set the the following values as shown below
upload_max_filesize = 10M
post_max_size = 12M
NGINX
vim /etc/nginx/nginx.conf
we are going to make a bunch of changes here, try to make your config look like the following
user www-data; worker_processes 2; #should be equal to the number of cpu cores you have pid /var/run/nginx.pid;
events { worker_connections 1024; # Nginx can take alot of stress so we upped this }
http {
sendfile on; tcp_nopush on; tcp_nodelay on; keepalive_timeout 65; types_hash_max_size 2048; # server_tokens off;
server_names_hash_bucket_size 64; #to prevent errors with multiple Vhosts
include /etc/nginx/mime.types; default_type application/octet-stream;
fastcgi_buffers 8 16k; #also to prevent erros fastcgi_buffer_size 32k; # this too
client_max_body_size 12m; # we also want to increase upload limit
access_log /var/log/nginx/access.log; error_log /var/log/nginx/error.log;
# We enable all the gzip options because google loves gzip gzip on; gzip_disable "msie6";
gzip_vary on; gzip_proxied any; gzip_comp_level 6; gzip_buffers 16 8k; gzip_http_version 1.1; gzip_types text/plain text/css application/json application/x-javascript text/xml application/xml application/xml+rss text/javascript;
include /etc/nginx/conf.d/*.conf; include /etc/nginx/sites-enabled/*; }
Now thats over with lets configure our Server Blocks (or Virtual Hosts)… we can either use the default file as a template for each seperate site or if you only have one site/you wish to use the ip directly feel free to simply edit the default file that is already there… In this example we are just going to edit he default
cd /etc/nginx/sites-availiable vim default
Edit the host to resemble the following
server { listen 80;
root /usr/share/nginx/www; index index.php index.html index.htm;
server_name localhost mydomain.com domain2.com;
location / { try_files $uri $uri/ /index.html; }
error_page 404 /404.html;
error_page 500 502 503 504 /50x.html; location = /50x.html { root /usr/share/nginx/www; }
location ~ .php$ { try_files $uri =404; fastcgi_pass unix:/var/run/php5-fpm.sock; fastcgi_index index.php; fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name; include fastcgi_params; }
location ~ /.ht { deny all; }
}
Restart nginx
service nginx restart
and go your domain (or ip) in your browser… Voilia!! A working nginx server.
IF you want another block to serve a different directory, copy the previous template but make the following changes
cp default myhost vim myhost server_name mynewdomain.com www.mynewdomain.com root /usr/share/nginx/www/mynewhostdir;
Now that that’s done, lets make a link to it in our sites-availiable dir to activate it
ln -s /etc/nginx/sites-availiable/myhost /etc/nginx/sites-enables/myhost
Lets restart nginx again
service nginx restart
Aaaand done 🙂 (ps. your html/php files should be in the location specified by root option in the corresponding block.
Step 7. Phpmyadmin
What is sql without phpmyadmin? Luckily this last step is the easiest of them all
apt-get install phpmyadmin ln -s /usr/share/phpmyadmin/ /usr/share/nginx/www
Now go to http://myipaddress/phpmyadmin
Questions? Comments? Fixes? Just leave em in the comments section?
END
Recent Comments