Archives For PHP

camera Weekly Snap: Puppet Camp Program, PHP & DRDB25 – 29 March was packed with events and the odd tool or two for sys admins and web devs.

Markus announced the programme for Puppet Camp 2013 on 19 April, while Bernd shared his impressions of the FLOSS UK 2013 conference in Newcastle.

Continuing on events, Eva counted 23 days to the OSDC with Andreas Schmidt’s presentation on implementing the Marionette Collective.

Philipp then introduced two new features in DRBD for high availability clustering, and Marius gave us his thoughts on the latest PHP standards from PSR-0 to PSR-3.

20.thumbnail Weekly Snap: Puppet Camp Program, PHP & DRDB

Autor: Amanda Mailer

Amanda unterstützt das NETWAYS Team im Bereich Marketing und da vor allem bei allen englischen Aktivitäten. Als Australierin mit einem deutschen Mann verheiratet, fällt ihr das auch besonders leicht. Neben NETWAYS arbeitet sie auch im Icinga Team mit.

php PSR 0,1,2, nichts dabei!Mir ist klar dass der Titel dieses Post erstmal Verwirrung stiftet. Denn es hat wieder mit den unmöglichen Tiefen von PHP zu tun, und zwar mit einem Standard. Bis vor einiger Zeit gibt es für PHP aus dem Vendor Team keinen eigenen Standard wie man PHP eigentlich schreibt – also wie man es so schreibt das es lesbar ist und bei jeden gleich aussieht.

Bis zu diesem Zeitpunkt gab es einige Versuche: Zend, Squiz, Pear. Aber das Ergebnis war nie perfekt. Andere Sprachen haben ihren Styleguide bereits dabei, z.B. PEP8 in Python. Auch wurde viel in fremden Welten geklaut, z.B. Code Conventions von Java oder die Entfremdung einiger C Stile brachte so manches Stirnrunzeln vor den Bildschirm. Nun hat die PHP Framework Interop Group mit Ihrem “propose a standards recommendation” einen sehr guten Standard rausgekurbelt der:

  1. Zu PHP passt
  2. Die Aktualität berücksichtigt
  3. Von vielen akzeptiert wird

Die PHP-FIG an sich sich ist eine Gruppe von Personen die versuchen an vielen Ecken und Enden Standards zu schaffen, an die man sich halten kann – aber nicht muss. Herausgekommen ist ein vierteiliges Werk was wiederum auf spezielle Teile von Sprachkonstrukten Einfluss nimmt:

Über PSR-3 lässt sich streiten aber 0-2 sind super umgesetzt  und integriert sich sinnvoll in die Sprache. Nicht zuletzt wird der Standard von vielen Tools bereits unterstützt: PHP CodeSniffer oder PHPStorm, Eclipse. Und viele Projekte sind bereits damit umgesetzt, http://packagist.org feststellen kann.

So schaut es gut aus:

$ phpcs --standard=PSR2 Process.php 
Time: 0 seconds, Memory: 6.25Mb
<?php
/**
 * This file is part of DINGS
 *
 * DINGS is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * DINGS is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with TKMON.  If not, see <http://www.gnu.org/licenses/>.
 *
 * @author Marius Hein <marius.hein@netways.de>
 * @copyright 2012-2013 NETWAYS GmbH <info@netways.de>
 */
 
namespace NETWAYS\IO;
 
/**
 * Specific implementation to FO
 * @package NETWAYS\IO
 * @author Marius Hein <marius.hein@netways.de>
 */
class FileObject extends \SplFileObject
{
    /**
     * Integrate chmod on that file
     * @param int $mode
     * @return bool
     */
    public function chmod($mode)
    {
        return chmod($this->getRealPath(), $mode);
    }
}
10.thumbnail PSR 0,1,2, nichts dabei!

Autor: Marius Hein

Marius Hein ist schon seit 2003 bei NETWAYS. Er hat hier seine Ausbildung zum Fachinformatiker absolviert, dann als Application Developer gearbeitet und ist nun Leiter der Softwareentwicklung. Ausserdem ist er Mitglied im Icinga Team und verantwortet dort das Icinga Web.

(this is a cross-post with my private blog, you will find there the English version of this post)

oder: Frameworking falsch gemacht

Ich bin diese Woche bei einem Kunden auf etwas interessantes gestoßen. Einige Plugins für Icinga verursachten enorme CPU Last, sobald ein paar Checks gleichzeitig gestartet sind waren beide CPUs der VM auf 80-90%.

Als ich mir die Plugins angeschaut habe fand ich seltsamen PHP Code, sah ungefähr so aus:

<?php
require_once('phplib/Framework.php');
if(!FRAMEWORK_LOADED) Framework::initialize();
CheckLicenseManager::run();

So auf den ersten Blick wirkt es ja nicht mal schlecht, da wird halt ein Framework geladen, dass die jeweiligen Klassen bereitstellt und dann wird die jeweilige Klasse “ausführt”. Das Framework selbst bestand aus mehreren PEAR Klassen und selbst geschriebenen Klassen die die jeweiligen Checks implementieren.

Das faszinierende an der Geschichte war jedoch dass das Plugin knapp 6 Sekunden dafür gebraucht hat die “–help” Ausgabe zu liefern, die eigentliche Funktion des Plugins ist in unter einer Sekunde fertig.

Ein strace des Skripts brachte dann das Problem recht schnell ans Tageslicht: das Framework tut nichts anderes als per PHP-Autoloadfunktion sämtliche PHP Dateien und Klassen im Verzeichnis zu laden, was ca. 90 Stück waren.

Ich erklärte dem Kunden das Problem, und dass ich wohl keine direkte Lösung anbieten könnte, außer eben die paar Plugins neu zu schreiben. Das machte ich dann auch und dem Server war wieder langweilig.

Ein paar Regeln für Icinga Plugins (die ich für mich gesetzt habe):

  • Keep it simple ™
  • Ordentlich kommentieren
  • eine verständliche –help Ausgabe mit Beispielen
  • bei komplexen Plugins: Verbose und Debug Funktionen für spätere Probleme und Tests
  • Möglichst in Perl oder Shell schreiben um weniger Abhängigkeitsprobleme zu haben
  • und last but not least:
    Wenn möglich veröffentlichen, denn dafür gibt’s monitoringexchange.org, denn irgendjemand kann es sicher auch gebrauchen!  icon wink Wie man ein Icinga Plugin nicht schreiben sollte
56.thumbnail Wie man ein Icinga Plugin nicht schreiben sollte

Autor: Markus Frosch

Markus arbeitet bei NETWAYS als Senior Consultant und unterstützt Kunden bei der Implementierung von Nagios, Icinga und anderen Open Source Systems Management Tools. Neben seiner beruflichen Tätigkeit ist Markus aktiver Mitarbeiter im Debian Projekt.

Über Doctrine schreibe ich ja gerne mal was, so auch heute. Da Doctrine 2.2 die letzte aktuelle Version ist, hoffe ich, dass es noch andere gibt, die ältere Versionen einsetzen und folgende Informationen vielleicht nützlich finden.

Kindknoten hinzufügen
Ein Nested Set zu speichern, bei dem die Sortierung der Knoten der Reihenfolge entspricht, wie sie hinzugefügt werden, sieht auf den ersten Blick ganz einfach aus:


$node->getNode()->insertAsLastChildOf($parent);

Aber: Doctrine ändert bei diesem Funktionsaufruf automatisch die Grenzen der Teilmenge (links und rechts), ausgehend von $parent, in der Datenbank. Die Grenzen vom Objekt $parent werden aber nicht aktualisiert. Das führt dazu, dass neue Knoten nicht als letztes, sondern als erstes Kind hinzugefügt werden. Ein simples


$parent->refresh();

nach jeder Änderung, löst das Problem.

Teilbäume
Zum Abschluss, stell ich noch Code zur Verfügung, der einen Teilbaum aus einem Nested Set, mit dem Namen Tree, selektiert:


$table = Doctrine_Core::getTable('Tree');
$tree = $table->getTree();

$query = $table->createQuery('t, Tree p')
               ->select('t.*')
               ->orderBy('t.lft ASC')
               ->where('p.id = ?', $id)
               ->andWhere('t.root_id = p.root_id')
               ->andWhere('t.level >= p.level')
               ->andWhere('t.lft BETWEEN p.lft and p.rgt');

$tree->setBaseQuery($query);
$hierarchy = $tree->fetchTree();
$tree->resetBaseQuery();
27.thumbnail Doctrine 1.2 und Nested Sets

Autor: Eric Lippmann

Eric kam während seines ersten Lehrjahres zu NETWAYS und hat seine Ausbildung bereits 2011 sehr erfolgreich abgeschlossen. Seit Beginn arbeitet er in der Softwareentwicklung und dort an den unterschiedlichen NETWAYS Open Source Lösungen, insbesondere inGraph und im Icinga Team an Icinga Web. Darüber hinaus zeichnet er sich für viele Kundenentwicklungen in der Finanz- und Automobilbranche verantwortlich.

Jenkins ist ein erweiterbares, webbasiertes System zur kontinuierlichen Integration in agilen Softwareprojekten.“ (Danke für diese praktische Einleitung, Wikipedia!).

Ich habe das schnieke Jenkins-System gerade für ein PHP-basiertes Projekt eingerichtet, und zwar mit Apache Ant als Build-Tool, Git übernimmt das Source-Code-Management. Winstone wird als Servlet-Container schon mitgeliefert, andere Programme wie etwa Tomcat sind möglich, aber nicht nötig.

Eine genaue Anleitungen zum Einrichten samt Template gibt’s hier: Jenkins Job Template for PHP-Projects. Die dort zu findende Vorlage liefert für den ersten Jenkins-PHP-Job die gängigsten Einstellungen der Post-Built-Aktionen, Graphen etc.
Hier sei angemerkt, dass zwar ein Jenkins-Template-Plugin als solches existiert, das es allerdings nur erlaubt, einen Teil der Optionen zu übertragen – praktisch gänzlich unnötig, lassen sich bestehende Job-Ordner doch einfach kopieren, umbenennen oder zu anderen Jenkins-Installationen verschieben (anschließend die Konfiguration von Jenkins neu laden).

Für PHP-Projekte sind folgende Jenkins-Plugins interessant:JenkinsScreen 300x233 Build am Donnerstag: Jenkins Continuous Build Server für PHP Projekte
Checkstyle (verarbeitet PHP_CodeSniffer-Logdateien im Checkstyle-Format)
Clover PHP (verarbeitet PHPUnit Code-Coverage xml-Ausgabe)
DRY (verarbeitet phpcpd-Logdateien im PMD-CPD-Format)
HTML Publisher (z.B. zum veröffentlichen des PHPUnit code coverage report)
JDepend (verarbeitet PHP_Depend-Logdateien im JDepend Format)
Plot (verarbeitet phploc CSV-Ausgabe)
PMD (verarbeitet PHPMD-Logdateien im PMD-Format)
Violations (verarbeitet diverse Logdateien)
xUnit (verarbeitet PHPUnit-Logdateien im JUnit format)

Automation
Für die Steuerung legt man ein Ant-Build-Skript an, sowie die Konfigurationen/Rulesets für die einzelnen Tools (etwa für CodeSniffer – siehe unseren Artikel). So lassen sich Builds individuell schneidern, von Code Coverage, Dupliziertem Quelltext, bis hin zur Verfügbarkeit der Datenbank.
In unserem Fall fungiert Git zudem als Build-Trigger und startet bei neuen Versionen im Repository den Job – inklusive Benachrichtigung der Git-User bei einem Fehlschlag (per E-Mail, Jabber u.A.) oder Git Publisher bei Erfolg. Die Jobs lassen sich alternativ manuell oder per Script starten, zeitlich Planen und Ruheperioden einrichten.


Distributed Builds

Eine Jenkins-Installation kann als Master agieren und Builds auf Nodes (bzw. Slaves) laufen lassen, auf ein und demselben Rechner oder externen Systemen, egal ob nun Windows oder anderen Unixen, etwa Solaris.
Eine Jenkins-Installation auf dem Slave ist nicht nötig – der Master kopiert die nötigen Dateien nach der Einrichtung. Wohl aber sollte der Node über alle für den Build erforderlichen Tools, etwa CVS, Pear, PHP und PHP-Tools (PHPUnit etwa schreit nach PHP ab 5.2.7) sowie die Konfigurationsdateien (sofern diese nicht im Repository liegen) verfügen. Einige Programme wie Maven, Ant, JDKs und Git installiert Jenkins auf Wunsch automatisch, wobei sich verschiedene Arten einstellen lassen.

Jobs legt man auf dem Master an und weist diese entweder dediziert einem dieser „Dumb“-Slaves zu (wer es sucht: nennt sich „Beschränke wo dieses Projekt ausgeführt werden darf“) oder es werden automatisch die vorhandenen Build-Prozessoren bei anstehenden Jobs ausgelastet. D.h. ein Job wird immer komplett ausgelagert, einzelne Test zu verteilen geht leider nicht. Die Ergebnisse bestaunt man auf dem Master.

Bei meinem Versuchsaufbau greift Jenkins unter Debian auf einen CentOS-Slave per ssh zu. Statt per ssh ließe sich ein Node auch „headless“ per Command-Line oder Skript sowie Java Web Start (JNLP) steuern.
Pferdefuß in meinem Fall: die unterschiedlichen PHP-Versionen. Einige PHPUnit-Test, die auf dem Master (mit PHP 5.3) funktionieren, laufen nicht auf dem vorgesehenen Slave. Ergo Tests umschreiben, oder für die Zukunft vorher überlegen, wo diese laufen sollen icon wink Build am Donnerstag: Jenkins Continuous Build Server für PHP Projekte

Page 1 of 3123