Programmierung
Zufällige MySQL Abfrage
Ab und an möchte man eine bestimmte zufällige Anzahl von Ergebnissen aus einer MySQL Tabelle Abfragen.
Hier die entsprechende Syntax:
SELECT * from meine_tabelle ORDER BY RAND() LIMIT 25
OpenKM vergisst Einstellungen
Wir nutzen schon seit einiger Zeit OpenKM als Dokumentenmanagement. Am Anfang gab es ein sehr interessantes Phänomen, das nach einem Neustart des Dienstes alle Einstellungen verloren waren.
Die Lösung ist relativ einfach, wenn man weiß wie. OpenKM speichert die Einstellungen in einer HSQL Datenbank. Standardmäßig wird diese bei jedem Start neu erstellt. Das kann man ändern in dem man folgende Datei anpasst:
/opt/jboss-4.2.3.GA/OpenKM.cfg
#hibernate.hbm2ddl=create
hibernate.hbm2ddl=none
Cakephp 2.0 erschienen
Mittlerweile ist die offizielle Version 2.0 von Cakephp erschienen.
Ein paar kurze Eckdaten:
- Performance ca. 50% schneller gegenüber Cakephp 1.3 (liegt stark am neuen lazy-loading und das der PHP4 Support weggefallen ist)
- PHPUnit als Testframework
- Download: https://github.com/cakephp/cakephp/tarball/2.0.0
- Dokumentation: http://caky.de
Eigene Git Modul (Submodul) Strategie - Cakephp Plugins
Wenn man mit Git arbeitet möchte man irgendwann einmal Code von anderen importieren.
Zum Beispiel um ein Plugin in seine Cakephp Applikation zu importieren. Oder man hat selbst verschiedene Projekte und möchte bestimmten Code wiederverwenden. Bei uns haben wir zum Beispiel das Frontend für unsere Kunden und das Backend für die Administratoren komplett von einander getrennt. Aber z.B. der CSS Code ist in beiden Projekten nahezu gleich. Und auch bestimmte Plugins kommen in beiden vor. Es wäre ein fast unmöglicher Aufwand in beiden Projekten immer den identischen Code zu haben.
Daher haben wir ein Konzept gefunden wie man mit solchen Abhängigkeiten flexibel umgehen kann.
$ cd mein-projekt $ git clone <url-anderes-projekt> mein-unterprojekt $ git add mein-unterprojekt/
Wichtig ist hierbei das beim letzten Befehl auch ein / am Ende steht. Andernfalls versucht Git den eigenen viel komplexeren Submodul-Modus zu benutzen.
Jetzt hat man praktisch zwei verschachtelte Git Repositorys. Wenn man nun das Unterprojekt updaten will, geht man wie folgt vor:
$ cd mein-unterprojekt $ git pull
Das funktioniert weil immer das näherliegende .git Verzeichnis benutzt wird. Ein weiterer großer Vorteil ist das wir das Unterprojekt an unsere Projektbedürfnisse anpassen können.
Ein kleiner Wermutstropfen tritt auf wenn ein anderes Projektmitglied den Code vom Hauptprojekt "cloned". Der Code vom Unterprojekt ist zwar enthalten, aber nicht die direkte Abhängigkeit zum Unterrepository. Das lässt sich aber relativ einfach lösen in dem man bei Änderungen dann einfach den Ordner löscht mit "rm -Rf mein-unterprojekt" und wie oben gezeigt wieder neu cloned. Daher packen wir in jedem von uns angelegten Unterprojekt auch eine Readme mit den nötigen URL Infos hinein.
MySQL und Backticks `FELDNAME`
Ich denke viele sind schon über MySQL Queries gestolpert die so aussehen:
SELECT user_id, xyz FROM ...
Was ist daran falsch? Nunja richtig sollte die Anweisung so lauten:
SELECT `user_id`, `xyz` FROM ...
Das Problem ist das ohne Backticks die Abfrage zwar funktioniert, aber wenn man ausversehen ein MySQL Schlüsselwort erwischt es sehr merkwürdige Fehler erzeugt. Zum Beispiel wenn plötzlich der Query nach einem MySQL Update nicht mehr funktioniert, weil ein neues Schlüsselwort eingeführt wurde.
Die reservierten Wörter findet man übrigens hier: http://dev.mysql.com/doc/refman/5.5/en/reserved-words.html
Selenium und Firefox 7
Diesmal gibts für Firefox 7 von Selenium wieder das offizielle Plugin:
http://release.seleniumhq.org/selenium-ide/1.3.0/selenium-ide-1.3.0.xpi
Die Datei installiert man über Extras -> Addons -> Werkzeug Symbol -> Add-on aus Datei installieren
Anwendungsoptimierung
Eine unserer Aufgaben im Linux Server Support ist es Kunden beim Optimieren Ihrer Seite(n)/Server zu unterstützen. Meistens betrifft dieses Servereinstellungen zu verfeinern. Manchmal müssen wir uns aber auch auf die Anwendungsebene begeben um zu analyisieren wo Performance verloren geht.
In dem jetztigen Fall ging es um ein VB Forum mit über 200.000 Seiten. MySQL und Apache waren schon wunderbar eingestimmt. Trotz der fast 200 Onlineuser waren die Seitenwerte unter 1 Sekunde. Eigentlich alles optimal. Aber der Betreiber merkte das der Googlebot immer länger zum Spidern brauchte.
Nach einer Analyse mit Jmeter viel mir auf das Beitragsseiten zum Vergleich zu anderen ca. 400ms länger also im Schnitt 800ms zum Laden brauchten. Im Schnitt hatte die Seite einen Wert von 319ms (nur dynamischer Content).
Ich denke viele wären über solche Werte schon sehr froh. Aber da die Googlebewertung einer Seite auch davon abhängt wie schnell Sie sich Spidern lässt und 400ms * 200.000 Seiten = ca. 22h schnellers crawlen bedeutet, hatten wir eine neue Herausforderung vor uns.
Mit der zur Hilfenahme von xdebug gelang es uns relativ schnell den Übeltäter mittels Profiling ausfindig zu machen. Und zwar setzt der Kunde zur Seo Optimierung VBSEO ein. Diese Extension machte in der vorhandenen Version sehr viel Gebrauch von preg_replace() (über 80.000 Aufrufe pro Seite). Des Weiteren viel uns auf das sich im APC Usercache gerade einmal 80 KByte an Daten befanden. Jetzt hätte man natürlich den Source Code durchforsten können, aber das ist für mich bei komplexeren Anwendungen immer nur die letzte Wahl.
Denn man kann so schnell die Updatefähigkeit verlieren und man sollte zunächst versuchen bei den Entwicklern nachzufragen. Offiziell gab es zwar noch kein Update aber eine inoffizielle Entwicklerversion. Diese sollte eigentlich das Cache Problem lösen, was leider nicht wirklich klappte, dafür aber waren die Beitragsseiten nun genauso schnell wie alle anderen.
