Skip to content

Das leidige mit Konfigdateien für PHP und Zugangsdaten für die DB

Immer wieder stolpere ich auf Servern oder in diversen Sourcode-Versionsverwaltungen wie git oder svn über hart eincodierte Zugangsdaten zu Datenbankservern oder sogar zu FTP-Servern. Auch in meinen ersten Projekten hat es sowas gegeben. Aber da hab ich noch keine Versionsverwaltung benutzt. Im Laufe der Jahre mit PHP-Projekten habe ich mir eine Aufteilung der Konfigdateien angewöhnt, die meinen Sicherheitsanforderungen stand hält und gleichzeitig die Passwörter aus irgendwelchen Repositorys raushält. Dies möchte ich hier mal als Anregung für die diversen Frischling-Programierer oder als Denkanstoß für einige alte Hasen vorstellen.

Der Grundgedanke dabei ist folgender. Ich benötige immer wieder Konfigurationseinstellungen, die sich je nach Projekt unterscheiden. Aber es gibt auch immer wieder Files, die ich in jedem Projekt verwende und die auch bei jedem Script eingebunden werden.

Als erstes gibt es da die global.php. Dieser File befindet sich im Web-Hauptverzeichnis des Projekts. Die Datei enthält Definitionen von Konstanten und Includes von PHP-Files, die immer benötigt werden.


<?php
// global.php
define('WEB_ROOT',dirname(__FILE__));

require_once(WEB_ROOT . '/lib/class.DieIchImmerBrauche.php');
require_once(WEB_ROOT . '/lib/class.Database.php');
require_once(WEB_ROOT . '/config.php');
?>


Als erstes definiere ich WEB_ROOT. Damit haben alle anderen Scripte unabhängig davon in welchem Verzeichnis sie sich befinden eine Konstante mit dem Root-Verzeichnis des Projekts. Da __FILE__ sich immer auf das Script "global.php" bezieht, kommt auch der richtige Pfad dabei raus, wenn ich die global.php z.B. aus einem Unterverzeichnis als "../../global.php" includieren muss. Wie zu sehen ist, kann ich diese Datei getrost in ein neues Projekt kopieren, ohne etwas zu ändern.

In der untersten Zeile sieht man den nächsten Step. Es wird eine Datei config.php eingebunden. In jedem Projekt benötige ich Einstellungen, die es in einem anderen nicht gibt. Dies könnte z.B. der Pfad zu einem Datenverzeichnis sein.


<?php
// config.php

$MYSQL_HOST = "127.0.0.1";
$MYSQL_USER = "demo";
$MYSQL_PASS = "demo";
$MYSQL_NAME = "demo";

$DATA_DIR = WEB_ROOT . '/../data/';

$DEFAULT_IMAGE_WIDTH = 170;

if( is_file(WEB_ROOT . '/.htconfig.php') ) {
include_once(WEB_ROOT . '/.htconfig.php');
}

define('CONFIG_OK',1)
?>



In der Datei config.php habe ich ALLE Konfigurationseinstellungen für mein Projekt hinterlegt, die ich benötige. Aber wichtig dabei ist, das es sich dabei um DEFAULT-Einstellungen handelt. Vor allem die DB-Zugangsdaten sind dort ganz deutlich nur ein Beispiel, welches aber funktionieren würde wenn man sich auf so unsichere Zugangsdaten einlassen würde. Mit DATA_DIR definiere ich z.B. eine Defaultkonfig für ein Datenverzeichnis ausserhalb des Projektverzeichnisses. Einige Files will man nunmal nicht im DOCUMENT_ROOT des Webservers liegen haben. Mit DEFAULT_IMAGE_WIDTH ist auch noch ein Beispiel enthalten, welches ich benötige, um Vorschaubilder zu skallieren. Dadurch, dass hier alle notwendigen Konfigvariablen initalisiert werden, hab ich später keinen Ärger mit Fehlermeldungen, weil irgend ein Wert nicht gesetzt ist.

Die Magie der Datei ist die if-Anweisung. Es wird gecheckt, ob sich eine Datei namens .htconfig.php im WEB_ROOT befinden. Wenn dies der Fall ist, wird sie importiert. Der Dateiname ist ganz bewust gewählt. Dateien mit einem "." am Anfang sind unter Linux versteckte Dateien. Aber am wichtigsten ist mir dabei, dass in einem Apache-Webserver per Default Dateien, die mit ".ht" anfangen, nicht ausgeliefert werden. Dies ist ein Schutzmechanismuss, der auch die ".htaccess" Dateien vor dem Download schützt. PHP und Apache haben bei einem unvorsichtigen Admin oder auch unter bestimmten Fehlerbildern leider die Angewohnheit die Scriptdateien ungeparst auszuliefern. Ist der Webserver also nicht sauber konfiguriert, würde ein Angreifer die Zugangsdaten im Klartext sehen. Dies Problem stellt sich nicht, wenn man die Zugangsdaten in der ".htconfig.php" versteckt.


<?php
// .htconfig.php

$MYSQL_USER = "appuser";
$MYSQL_PASS = "realpassword";
$MYSQL_NAME = "appdb";
?>


In der ".htconfig.php" können nun alle Variablen aus der "config.php" mit den richtigen Werten überschrieben werden. Werte, die ich nicht benötige, können einfach übersprungen werden.

Um den Bogen zu git und Subversion wieder zu schliessen, sei jetzt noch erwähnt, dass die Datei ".htconfig.php" nicht mit in die Versionsverwaltung übertragen werden. Bei git steht sie dazu einfach in der Datei ".gitignore" und bei Subversion in der ".svnignore".

Als Goodie kommt dabei auch noch heraus, dass ich eine neue Softwareversion jederzeit im Webverzeichnis entpacken kann. Da in diesen Archiven die ".htconfig.php" auch nicht enthalten ist, wird auch meine Konfig nicht überschrieben.

So. Und wer bis hierhin aufgepasst hat, wird sich jetzt evtl. noch über die Konstante CONFIG_OK wundern. Dies ist ein weiterer Sicherheitsmechanismuss für die Scripte. Habe ich in einer PHP-Datei nur eine Klasse definiert, stört es mich nicht wenn diese Datei von einem Browser aufgerufen wird. Aber es gibt auch Dateien, die nicht ohne bestimmte Vorraussetzungen aufgerufen werden dürfen. Diese schützte ich einfach direkt am dateianfang wie folgt...


<?php
// eine Datei die nicht vom Browser aufgerufen werden soll...

if( ! defined('CONFIG_OK') ) {
die('Du kommst hier nicht rein!');
}

[...]
?>

Der neue Trend: Barfuss laufen

Meinen letzten Sommerurlaub anno 2011 habe ich 300km mit Barfussschuhen absolviert. Auch beim Sport trage ich immer häufiger Barfussschuhwerk. In den letzten Wochen tauchen die Barfussschuhe immer häufiger in den Onlinemedien auf. Deswegen hier mal ein Link zu einem Artikel mit ein paar Hinweisen zum Barfusslaufen...

Der neue Trend: Barfuss laufen

Kleine Basisarbeiten am Server

Die letzten Tage waren die Newsticker voll von einer Schlagzeile: Die Schaltsekunde!

In der Nacht zum 01.07. ist mal wieder eine Schaltsekunde eingefügt worden, um die Verluste auszugleichen. Der Linux-Kernel stolpert dabei leider in einigen Versionen und erzeugt eine Endlosschleife, die die CPU mal kurz auf 100% laufen lässt. Die Mail von Hetzner in meinem Postfach hat dabei den ersten Platz gewonnen. Die haben in den Statistiken einen schönen Stromanstieg im 1 Megawatt zum Zeitpunkt der Einführung der Schaltsekunde gemessen. und da dieser "Peak" auch Tage später noch anhält, wurden alle Kunden aufgefordert ihren Server zu checken und ggf. zu rebooten.

Beim Check haben sich auch gleich ein paar Sachen ergeben, die ich im Themenkreis "Stromsparen" gleich mit gecheckt habe.

Neue CPUs können die Taktfrequenz reduzieren, um Strom zu sparen. Unter Linux kann dieses Verhalten mit der Software "cpufrequtils" erledigt werden. Mit dem gleichnamigen Debian-Packet installiert sich die Konfig-Dateiei /etc/default/cpufrequtils. Der GOVERNOR stellt dabei ein, wie sich die CPU verhalten soll. Bei mir war das per Default "performance", was so viel wie "immer auf max speed" bedeutet. Ein Einfaches Umstellen auf ondemand sorgt dafür, dass die CPU sich in ruhigen Zeiten runtertaktet. Kontrollieren lässt sich das mit dem Befehl cpufreq-info:


# cpufreq-info
cpufrequtils 004: cpufreq-info (C) Dominik Brodowski 2004-2006
Report errors and bugs to cpufreq@lists.linux.org.uk, please.
analyzing CPU 0:
driver: powernow-k8
CPUs which need to switch frequency at the same time: 0 1
hardware limits: 1000 MHz - 2.80 GHz
available frequency steps: 2.80 GHz, 2.60 GHz, 2.40 GHz, 2.20 GHz, 2.00 GHz, 1.80 GHz, 1000 MHz
available cpufreq governors: conservative, powersave, userspace, ondemand, performance
current policy: frequency should be within 1000 MHz and 2.80 GHz.
The governor "ondemand" may decide which speed to use
within this range.
current CPU frequency is 1000 MHz (asserted by call to hardware).
cpufreq stats: 2.80 GHz:99.35%, 2.60 GHz:0.00%, 2.40 GHz:0.00%, 2.20 GHz:0.00%, 2.00 GHz:0.00%, 1.80 GHz:0.02%, 1000 MHz:0.63% (10253)
analyzing CPU 1:
driver: powernow-k8
CPUs which need to switch frequency at the same time: 0 1
hardware limits: 1000 MHz - 2.80 GHz
available frequency steps: 2.80 GHz, 2.60 GHz, 2.40 GHz, 2.20 GHz, 2.00 GHz, 1.80 GHz, 1000 MHz
available cpufreq governors: conservative, powersave, userspace, ondemand, performance
current policy: frequency should be within 1000 MHz and 2.80 GHz.
The governor "ondemand" may decide which speed to use
within this range.
current CPU frequency is 1000 MHz (asserted by call to hardware).
cpufreq stats: 2.80 GHz:99.35%, 2.60 GHz:0.00%, 2.40 GHz:0.00%, 2.20 GHz:0.00%, 2.00 GHz:0.00%, 1.80 GHz:0.02%, 1000 MHz:0.63% (10253)


Wichtig sind dabei die Zeilen "current policy" und "current CPU frequency". Dort ist zu sehen, dass meine CPU aktuell auf 1GHz gelaufen ist. Der Rest verrät mir dann auch gleich noch ein bischen über die Fähigkeiten der CPU.

Eine weitere kleine Vorkehrung, die ich inzwischen immer aktiviere, ist der Parameter "noatime" beim mounten von Dateisystemen. Einmal die /etc/fstab gecheckt und schon war zu sehen, dass dies auf dem Server noch nicht aktiv ist. noatime verhindert, dass die Access-Time einer Datei, also der letzte Zugriff auf diese Datei, in der Inode gespeichert wird. Dieser unscheinbare kleine Schalter macht also aus jeder Lese-Operation auch gleich ein Schreibzugriff auf das rotierende Rost. Das kostet Zeit, drückt auf die Geschwindigkeit und verbraucht (wenn auch nur in geringen Mengen) mehr Strom. Also abschalten...

In der fstab wird dazu die Spalte der Mountoptionen angepasst.

/dev/md2 / ext3 defaults,noatime 0 0

Da die fstab nur beim mounten eingelesen wird, müsste ich den Server rebooten. Will ich aber nicht. Also fix ein remount abgeschickt:


# mount -o remount /


Danach ist die noatime-Einstellung für die Platte gesetzt und ein Lesezugriff bleibt ein Lesezugriff. Checken kann man das ebenfalls mit mount:

# mount
/dev/md2 on / type ext3 (rw,noatime)


Es gibt bestimmt noch mehr kleine Tips zum Energiesparen oder Performance erhöhen. Wenn Ihr welche habt, hinterlasst sie einfach als Kommentar unter diesem Beitrag.

Ich brauch mehr Käffchen...

Dieser Titel entwickelt sich wahrscheinlich zu einem Dauerbrenner, aber diese sprachliche Unqualität wollte ich Euch nicht vorenthalten.
Wer bei dieser Rechtschreibung noch auf den Link klickt, hat selber schuld...


From: WEBMAIL ADMIN
Sent: Tuesday, June 05, 2012 12:01 PM
To: undisclosed-recipients:
Subject: ACHTUNG ACHTUNG (QUOTE ALERT)

Sehr geehrte Benutzer E-Mail,

Ihr Postfach hat es die Quote überschritten. Sie können nicht senden oder empfangen neue E-Mails, bis Sie Ihre account.if revalidate Sie nicht aktualisieren Sie Ihre E-Mail-Konto im Jahr 2012, müssen Sie es jetzt tun. Sie können erweitern 1GB E-Mail-Kontingent, verwenden Sie folgenden Link an:

[URL-AUS-SICHERHEITSGRÜNDEN-GELÖSCHT]

Warnung!
Wenn Sie dies nicht tun, werden in begrenztem Zugang zu Ihrem Postfach zur Folge haben. Scheitern auf Ihr Konto innerhalb von drei Tagen von diesem Update-Benachrichtigung aktualisieren, wird Ihr Konto dauerhaft geschlossen werden.

Danke fuer die Benutzung unserer Web-Mail.

unterzeichnet
Es ist Service!
Copyright © 2012 System Administrator ®

PHP-Syntaxcheck mit vim

Mit PHP ist das so eine Sache. Bei den meisten Einbrüchen auf Webservern, die ich bearbeitet, kreist die Ursache immer wieder um ein und die selbe Programmiersprache. Der Grund dafür liegt zum einen in der großen Beliebtheit von PHP und zum anderen wohl in der noch größeren Anzahl an C&P-Programmierern in diesem Umfeld. Als Webserver-Admin ist das also eine Programmiersprache, um die man häufig nicht herum kommt.

Immer wieder schaue ich dort über den Tellerrand und versuche den "Programmierern" beizubringen, wie man den Code wenigstens einigermaßen sicher bekommt. Dafür will ich mich natürlich nicht mit irgend welchen großen Entwicklungsumgebungen auseinander setzen. Sowas macht man mit vim. Damit ich bei meinen Demos wenigstens ein Grundmaß an Funktionalität habe und vor allem weil das Programmiersprachenhoping bei mir immer mal wieder zu Syntaxfehlern führt, prüfe ich meinen Code vor dem Upload auf Syntaxfehler. Mit einer einzigen Zeile in der ~/.vimrc bringe ich dem vim bei, dies auf den Druck von F9 zu tun:

map <f9> :w<CR>:!php -l %<CR>

... und vorbei ist die Zeit in der man die Syntaxfehler erst nach dem Upload zu sehen bekommt. Lokal muss auf der Workstation dafür allerdings ein php installiert sein...
tweetbackcheck