Überspringen zu Hauptinhalt

In diesem Tutorial möchte ich euch zeigen wir ihr einen HAProxy als Load Balancer mit SSL und zwei Nginx Webserver im GlusterFS aufsetzen könnt.

Zu aller erst ein kleines Bild, welches verdeutlichen soll wie unsere Infrastruktur aussehen soll:

haproxy load balancer mit GlusterFS webservern

Wie ihr seht verwende ich dazu 3 x Debian 9 Server. Ein Server fungiert als Lasten-Server mit HAProxy und verteilt anfragen auf die beiden Nginx Webserver. Die beiden Webserver sind mit Hilfe eines Glusters verbunden. In meinem konkreten Fall teilen sich dabei die beiden Server den gesamten Application Code (var/www Ordner) und synchronisieren sich.

GlusterFS oder Rsync?

In meinem vorherigen Tutorial habe ich Rsync benutzt um beide Server zu synchronisieren. Warum jetzt GlusterFS?  

Traditionell verwenden viele Webhoster rsync, indem sie eine eventuell konsistente Methode (z.B. rsync bei einem Cron-Job) verwendet haben, um eine Kopie des gesamten Dateibaums auf dem lokalen Speicher für jeden Server zu behalten. Obwohl dies eine gültige Option ist, hat sie einige Einschränkungen. Verschwendeter Speicherplatz wird zu einem zunehmenden Problem, da immer mehr Daten gesammelt und analysiert werden. Synchronisationsfehler werden manchmal nicht überprüft, vom Benutzer bereitgestellte Inhalte werden nicht sofort verfügbar, etc. Außerdem ist das Problem mit aktivem rsync, dass dieses das I/O der Festplatten aufgrund von Dateisperren blockiert.

Standard Server-Konfigurationen einrichten

Bevor wir anfangen müssen wir folgende Standard-Konfigs bei jedem Server eingerichtet sein:

  1. Alle Server müssen über eine interne IP verfügen und erreichbar sein
  2. Sie sollten alle auf dem neusten Stand sein

Da wir in unserem Beispiel VServer von Vultr verwenden, müssen wir hier zu erst die interne IP konfigurieren. Die interne IP findet ihr in den Einstellungen eures Servers.

nano /etc/network/interfaces

# folgenden eintragen und speichern
auto ens7
iface ens7 inet static
address INTERNE_IP_HIER
netmask 255.255.240.0
mtu 1450

# danach folgenden Befehl ausführen
ifup ens7

Dann noch die Server-Repositories updaten:

apt-get update
apt-get upgrade

Wichtig: Das Ganze für alle 3 Server machen!

Webserver Übersicht

HAProxy Load Balancer und Let’s Encrypt aufsetzen

Heutzutage nutzen viele Webseiten https (SSL) und das solltet ihr auch. Nicht nur für Google (SEO), sondern auch für die Datensicherheit, ist dies immer ein richtiger Schritt.

Loggt euch dafür auf euren Load Balancer Server über SSH ein.

Let’s Encrypt (SSL) installieren

Zuerst müssen wir den certification bot installieren. Da Let’s Encrypt im Normalfall immer über port 80 geht um die Zertifikate upzudaten müssen wir dazu später einen anderen Port konfigurieren. Dazu später mehr.

certbot installieren

apt-get install certbot

Zertifikat holen:

certbot certonly --standalone --preferred-challenges http --http-01-port 80 -d example.com -d www.example.com

Nun müssen wir den fullchain.pem und privkey.pem zusammenführen. Dazu erstellen wir zuerst einen Order:

mkdir -p /etc/haproxy/certs

Danach die Dateien zusammenführen

DOMAIN='example.com' bash -c 'cat /etc/letsencrypt/live/$DOMAIN/fullchain.pem /etc/letsencrypt/live/$DOMAIN/privkey.pem > /etc/haproxy/certs/$DOMAIN.pem'

Und den Zugriff ändern:

chmod -R go-rwx /etc/haproxy/certs

Damit ist euer Zertifikat erstellt.

HAProxy installieren

Nun können wir weitermachen indem wir den HAProxy Load Balancer aufsetzen. Wichtig: falls mal der HAProxy nicht starten sollte, benutzt folgenden Debug Befehl um Fehler in der HAProxy-Konfiguration zu erkennen:

haproxy -c -f /etc/haproxy/haproxy.cfg
# haproxy installieren
apt-get install haproxy

Die Konfiguration des HAProxy passiert immer in der folgenden Datei: /etc/haproxy/haproxy.cfg

nano /etc/haproxy/haproxy.cfg

# in dieses Detei kommt
frontend www-http
	bind HAPROXY_PUBLIC_IP:80
	reqadd X-Forwarded-Proto:\ http
	default_backend www-backend

frontend www-https
	bind HAPROXY_PUBLIC_IP:443 ssl crt /etc/haproxy/certs/example.com.pem
	reqadd X-Forwarded-Proto:\ https
	acl letsencrypt-acl path_beg /.well-known/acme-challenge/
	use_backend letsencrypt-backend if letsencrypt-acl
	default_backend www-backend

backend www-backend
	redirect scheme https if !{ ssl_fc }
	server www-1 WEBSERVER_INTERN_IP_1:80 check
	server www-2 WEBSERVER_INTERN_IP_2:80 check

backend letsencrypt-backend
	server letsencrypt 127.0.0.1:54321

Falls ihr zusätzlich noch die HAProxy Stats zum Monitoring benötigt, fügt folgenden Code in die Config ein. Denkt dran den Username & Passwort unter Auth zu ändern:

listen stats
	bind :1936
	mode http
	log global

	maxconn 10

	clitimeout 100s
	srvtimeout 100s
	contimeout 100s
	timeout queue 100s

	stats enable
	stats hide-version
	stats refresh 30s
	stats show-node
	stats auth admin:password
	stats uri /haproxy?stats

Load Balancer neustarten:

service haproxy restart

Ihr könnt nun die folgende Seite der Stats aufrufen: http://HAPROXY_PUBLIC_IP:1936/haproxy?stats

HAProxy Stats & Monitoring

Zertifikate automatisch erneuern

Damit ihr die Let’s Encrypt Zertifikate nicht automatisch erneuern müsst, könnt ihr diese automatisch über euren Server erneuern lassen. Dazu erstellen wir uns ein BASH-Skript, dass die Key chains zusammenfügt und einen Cronjob, der die Zertifikate erneuert:

# Bash skript erstellen
nano /usr/local/bin/renew.sh

# folgendes einfügen

#!/bin/sh

SITE=example.com

# move to the correct let's encrypt directory
cd /etc/letsencrypt/live/$SITE

# cat files to make combined .pem for haproxy
cat fullchain.pem privkey.pem > /etc/haproxy/certs/$SITE.pem

# reload haproxy
service haproxy reload

#### Danach Rechte setzen
chmod u+x /usr/local/bin/renew.sh

Testet das Skript wie folgt:

sudo /usr/local/bin/renew.sh

Es sollte ohne Fehler durchlaufen.

Nun müssen wir noch den Renewal-Prozess konfigurieren, da wir über einen anderen Port als 80 gehen müssen (in diesem Fall 54321).

nano /etc/letsencrypt/renewal/example.com.conf

Hier den Port ändern:

http01_port = 54321

Speichern und testen (es wird nichts erneuert):

certbot renew --dry-run

Wenn alles gut gelaufen ist, können wir nun für diesen Prozess einen Cronjob einrichten:

crontab -e
30 2 * * * /usr/bin/certbot renew --renew-hook "/usr/local/bin/renew.sh" >> /var/log/le-renewal.log

Sichern und beenden. Dadurch wird ein neuer Cron-Job erzeugt, der den Befehl certbot renew jeden Tag um 2:30 Uhr ausführt. Die durch den Befehl erzeugte Ausgabe wird in eine Protokolldatei geleitet, die sich unter /var/log/le-renewal.log befindet. Wenn das Zertifikat tatsächlich erneuert wird, wird das Skript –renew-hook ausgeführt, um die kombinierte PEM-Datei zu erstellen und Haproxy neu zu laden.

Mehr zu lesen: How To Secure HAProxy with Let’s Encrypt

Webserver mit GlusterFS aufsetzen

Nun setzen wir die beiden Webserver mit GlusterFS auf. Da GlusterFS voraussetzt, dass die beiden Server untereinander kommunizieren können müssen wir die Host Datei anpacken. Auch hier wichtig: auf beiden Servern!

nano /etc/hosts
WEBSERVER_INTERN_IP_1 web-gfs-1
WEBSERVER_INTERN_IP_2 web-gfs-2

Danach können wir den GlusterFS-Server installieren:

apt-get install glusterfs-server

Sobald dies auf beiden Servern installiert ist, können wir mit der Einrichtung unseres Speichervolumens beginnen.

Wir müssen die Server peeren. Es spielt keine Rolle, welchen Server wir verwenden:

#auf dem server web-gfs-1 folgendes ausführen
gluster peer probe web-gfs-2

gluster peer status

www-Volume erstellen und starten:

gluster volume create www replica 2 transport tcp web-gfs-1:/var/data web-gfs-2:/var/data force
gluster volume start www

fstab editieren und die volumes mounten:

nano /etc/fstab

# auf web-gfs-1
web-gfs-1:/www /var/www glusterfs _netdev,fetch-attempts=10 0 0

# auf wen-gfs-2
web-gfs-2:/www /var/www glusterfs _netdev,fetch-attempts=10 0 0

mount auf beiden server ausführen:

mount -a

Gluster testen: Erstellt eine index.php auf einem server, ich nehme web-gfs-1 dafür.

nano /var/www/html/index.php

# folgenden reinschreiben:
<?php
phpinfo();

Schaut nun mit Hilfe von ls -l auf dem anderen Server web-gfs-2 nach ob sich im Order /var/www/html/ eine index.php befindet. Wenn ja, dann wurde GlusterFS erfolgreich aufgesetzt! Glückwunsch!

Nginx und PHP installieren

Ich mache es kurz un knapp, da ich dieses schon in meinem vorherigen Tutorial beschrieben habe: Nginx und PHP aufsetzen.

apt-get install nginx
apt-get install php-fpm
apt-get -y install php7.0-mysql php7.0-curl php7.0-gd php7.0-intl php-pear php-imagick php7.0-imap php7.0-mcrypt php-memcache php7.0-pspell php7.0-recode php7.0-sqlite3 php7.0-tidy php7.0-xmlrpc php7.0-xsl php7.0-mbstring php-gettext

nano /etc/nginx/sites-available/default
...

# Add index.php to the list if you are using PHP
index index.php index.html index.htm index.nginx-debian.html;

...

# pass PHP scripts to FastCGI server
#
location ~ \.php$ {
       include snippets/fastcgi-php.conf;

       # With php-fpm (or other unix sockets):
       fastcgi_pass unix:/var/run/php/php7.0-fpm.sock;
       # With php-cgi (or other tcp sockets):
       # fastcgi_pass 127.0.0.1:9000;
}

Nun können wir die public IP unseres HAProxys aufrufen. Wenn eine Hallo Welt Seite erscheint habt ihr alles richtig gemacht! Sonst macht einen Kommentar hier 🙂

Mehr lesen:

Stresstest mit Hilfe von Apache Benchmark

Ich wollte wissen wie schnell mein Server-Setup denn jetzt ist. Also habe ich Apache Benchmark auf dem Proxy server installiert und ein paar Stress-Tests gemacht:

# ab -n <num_requests> -c <concurrency> <addr>:<port><path>
ab -n 1000 -c 100 https://www.example.com/

AB-Resultat deuten:

Server Software: nginx/1.10.3
Server Hostname: welaunch.io
Server Port: 443
SSL/TLS Protocol: TLSv1.2,ECDHE-RSA-AES256-GCM-SHA384,2048,256
TLS Server Name: welaunch.io

Document Path: /
Document Length: 96313 bytes

Concurrency Level: 100
Time taken for tests: 3.085 seconds
Complete requests: 1000
Failed requests: 965
(Connect: 0, Receive: 0, Length: 965, Exceptions: 0)
Total transferred: 96451661 bytes
HTML transferred: 96314661 bytes
Requests per second: 324.17 [#/sec] (mean)
Time per request: 308.476 [ms] (mean)
Time per request: 3.085 [ms] (mean, across all concurrent requests)
Transfer rate: 30534.31 [Kbytes/sec] received

Connection Times (ms)
min mean[+/-sd] median max
Connect: 2 31 39.6 19 223
Processing: 46 274 50.5 285 436
Waiting: 38 130 39.3 118 303
Total: 82 305 61.5 305 562

Percentage of the requests served within a certain time (ms)
50% 305
66% 309
75% 311
80% 312
90% 341
95% 429
98% 504
99% 510
100% 562 (longest request)

Nach dem Test ist mir aufgefallen, dass ich 965 fehlerhafte Requests hatte. Diese waren aber nicht einem Serverausfall sondern lediglich der Content-Length geschuldet (Length: 965). Das ist nicht schlimm, denn der Befehlt phpinfo() gibt je nach load balanced webserver eine etwas andere Ausgabe aus (z.B. die IP ist anders).

Daniel Barenkamp

Founder and Creator of WeLaunch (formerly DB-Dzine).

Dieser Beitrag hat 0 Kommentare

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert.

×Suche schließen
Suche