Skip to content

Instantly share code, notes, and snippets.

@vivianspencer
Last active August 29, 2015 14:15
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save vivianspencer/9a33187d8b6470d9fe99 to your computer and use it in GitHub Desktop.
Save vivianspencer/9a33187d8b6470d9fe99 to your computer and use it in GitHub Desktop.
Server setup - Linode, Debian, Apache, PHP, MariaDB

sudo echo "johnsmith" > /etc/hostname

sudo hostname -F /etc/hostname

sudo nano /etc/hosts

127.0.0.1       localhost.localdomain localhost 
12.34.56.78     johnsmith.example.com johnsmith 
2600:3c01::a123:b456:c789:d012      johnsmith.example.com johnsmith

sudo dpkg-reconfigure tzdata

date

sudo nano /etc/apt/sources.list

deb http://mirrors.linode.com/debian/ wheezy main contrib non-free
deb-src http://mirrors.linode.com/debian/ wheezy main contrib non-free

deb http://mirrors.linode.com/debian-security/ wheezy/updates main contrib non-free
deb-src http://mirrors.linode.com/debian-security/ wheezy/updates main contrib non-free

# wheezy-updates, previously known as 'volatile'
deb http://mirrors.linode.com/debian/ wheezy-updates main
deb-src http://mirrors.linode.com/debian/ wheezy-updates main

sudo apt-get update && sudo apt-get upgrade --show-upgraded

sudo apt-get install python-software-properties

sudo apt-key adv --recv-keys --keyserver keyserver.ubuntu.com 0xcbcb082a1bb943db

sudo add-apt-repository 'deb http://mirrors.coreix.net/mariadb/repo/10.0/debian wheezy main'

sudo apt-get update && sudo apt-get upgrade --show-upgraded

sudo apt-get install git fail2ban apache2 apache2-doc apache2-utils php5 php-apc php5-curl php5-gd php5-cli libapache2-mod-fastcgi php5-fpm php5-mysqlnd mariadb-server mysqltuner zsh unattended-upgrades bsd-mailx

sudo nano /etc/apache2/conf.d/security

ServerTokens Prod
ServerSignature Off

curl -sS https://getcomposer.org/installer | php

sudo mv composer.phar /usr/local/bin/composer

sudo adduser exampleuser

sudo usermod -a -G sudo,www-data exampleuser

su exampleuser

cd ~

curl -L http://install.ohmyz.sh | sh

chsh -s /usr/bin/zsh

mkdir ~/.ssh

from desktop scp ~/.ssh/id_rsa.pub exampleuser@123.456.78.90:

mv ~/id_rsa.pub ~/.ssh/authorized_keys

chown -R exampleuser:exampleuser .ssh

chmod 700 .ssh

chmod 600 .ssh/authorized_keys

sudo nano /etc/ssh/sshd_config

PasswordAuthentication no
PubkeyAuthentication yes
AuthorizedKeysFile     %h/.ssh/authorized_keys
PermitRootLogin no

sudo service ssh restart

ssh-keygen -t rsa -C "info@example.com"

eval "$(ssh-agent -s)"

ssh-add ~/.ssh/id_rsa

sudo iptables -L

sudo nano /etc/iptables.firewall.rules

*filter

#  Allow all loopback (lo0) traffic and drop all traffic to 127/8 that doesn't use lo0
-A INPUT -i lo -j ACCEPT
-A INPUT -d 127.0.0.0/8 -j REJECT

#  Accept all established inbound connections
-A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT

#  Allow all outbound traffic - you can modify this to only allow certain traffic
-A OUTPUT -j ACCEPT

#  Allow HTTP and HTTPS connections from anywhere (the normal ports for websites and SSL).
-A INPUT -p tcp --dport 80 -j ACCEPT
-A INPUT -p tcp --dport 443 -j ACCEPT

#  Allow SSH connections
#  The -dport number should be the same port number you set in sshd_config
-A INPUT -p tcp -m state --state NEW --dport 22 -j ACCEPT

#  Allow ping
-A INPUT -p icmp --icmp-type echo-request -j ACCEPT

#  Allow incoming Longview connections
-A INPUT -s longview.linode.com -j ACCEPT

# Allow metrics to be provided Longview
-A OUTPUT -d longview.linode.com -j ACCEPT

# Prevent DoS Attacks
-A INPUT -p tcp --dport 80 -m limit --limit 25/minute --limit-burst 100 -j ACCEPT

#  Log iptables denied calls
-A INPUT -m limit --limit 5/min -j LOG --log-prefix "iptables denied: " --log-level 7

#  Drop all other inbound - default deny unless explicitly allowed policy
-A INPUT -j DROP
-A FORWARD -j DROP

COMMIT

sudo iptables-restore < /etc/iptables.firewall.rules

sudo iptables -L

sudo nano /etc/network/if-pre-up.d/firewall

#!/bin/sh
/sbin/iptables-restore < /etc/iptables.firewall.rules

sudo chmod +x /etc/network/if-pre-up.d/firewall

sudo a2enmod rewrite

sudo nano /etc/apache2/apache2.conf

Linode 1024

KeepAlive Off

<IfModule mpm_prefork_module>
StartServers 2
MinSpareServers 6
MaxSpareServers 12
MaxClients 80
MaxRequestsPerChild 3000
</IfModule>

Linode 2048

KeepAlive Off

<IfModule mpm_prefork_module>
StartServers 4
MinSpareServers 12
MaxSpareServers 24
MaxClients 160
MaxRequestsPerChild 6000
</IfModule>

Linode 4096

KeepAlive Off

<IfModule mpm_prefork_module>
StartServers 8
MinSpareServers 24
MaxSpareServers 48
MaxClients 320
MaxRequestsPerChild 12000
</IfModule>

sudo a2dissite default

sudo a2enmod actions

sudo nano /etc/php5/fpm/pool.d/www.conf

listen = /var/run/php5-fpm.sock

sudo service php5-fpm restart

sudo apache2 -v

sudo nano /etc/apache2/mods-enabled/fastcgi.conf

Apache version 2.2 or earlier

<IfModule mod_fastcgi.c>
    AddType application/x-httpd-fastphp5 .php
    Action application/x-httpd-fastphp5 /php5-fcgi
    Alias /php5-fcgi /usr/lib/cgi-bin/php5-fcgi
    FastCgiExternalServer /usr/lib/cgi-bin/php5-fcgi -socket /var/run/php5-fpm.sock -pass-header Authorization
</IfModule>

Apache version 2.4 or later

<IfModule mod_fastcgi.c>
    AddType application/x-httpd-fastphp5 .php
    Action application/x-httpd-fastphp5 /php5-fcgi
    Alias /php5-fcgi /usr/lib/cgi-bin/php5-fcgi
    FastCgiExternalServer /usr/lib/cgi-bin/php5-fcgi -socket /var/run/php5-fpm.sock -pass-header Authorization
    <Directory /usr/lib/cgi-bin>
        Require all granted
    </Directory>
</IfModule>

sudo mysql_secure_installation

sudo nano /etc/php5/apache2/php.ini

**if new file, exit, run the following command and reopen sudo mkdir /etc/php5/apache2 sudo cp /etc/php5/fpm/php.ini /etc/php5/apache2/php.ini

short_open_tag = Off
asp_tags = Off
expose_php = Off
max_execution_time = 30
max_input_time = 60
memory_limit = 128M
error_reporting = E_COMPILE_ERROR|E_RECOVERABLE_ERROR|E_ERROR|E_CORE_ERROR
display_errors = Off 
log_errors = On 
register_globals = Off
file_uploads = On
upload_max_filesize = 100M
max_file_uploads = 20
allow_url_include = Off
date.timezone = Europe/London

sudo cp /etc/php5/apache2/php.ini /etc/php5/fpm/php.ini

sudo nano /etc/php5/mods-available/apc.ini

[APC]
extension=apc.so
apc.enabled=1
apc.shm_segments=1

;32M per WordPress install
apc.shm_size=128M

;Relative to the number of cached files (you may need to watch your stats for a day or two to find out a good number)
apc.num_files_hint=7000

;Relative to the size of WordPress
apc.user_entries_hint=4096

;The number of seconds a cache entry is allowed to idle in a slot before APC dumps the cache
apc.ttl=7200
apc.user_ttl=7200
apc.gc_ttl=3600

;Setting this to 0 will give you the best performance, as APC will
;not have to check the IO for changes. However, you must clear
;the APC cache to recompile already cached files. If you are still
;developing, updating your site daily in WP-ADMIN, and running W3TC
;set this to 1
apc.stat=1

;This MUST be 0, WP can have errors otherwise!
apc.include_once_override=0

;Only set to 1 while debugging
apc.enable_cli=0

;Allow 2 seconds after a file is created before it is cached to prevent users from seeing half-written/weird pages
apc.file_update_protection=2

;Leave at 2M or lower. WordPress does't have any file sizes close to 2M
apc.max_file_size=2M

apc.cache_by_default=1
apc.use_request_time=1
apc.slam_defense=0
apc.mmap_file_mask=/tmp/apc.XXXXXX
apc.stat_ctime=0
apc.canonicalize=1
apc.write_lock=1
apc.report_autofilter=0
apc.rfc1867=0
apc.rfc1867_prefix =upload_
apc.rfc1867_name=APC_UPLOAD_PROGRESS
apc.rfc1867_freq=0
apc.rfc1867_ttl=3600
apc.lazy_classes=0
apc.lazy_functions=0

sudo service apache2 restart

sudo updatedb

sudo dpkg-reconfigure -plow unattended-upgrades

sudo nano /etc/apt/apt.conf.d/50unattended-upgrades

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment