Speedcoding

vom 16. August 2007

Christian Strang ruft in seinem Webdesignblog zum zweiten mal in Folge zum Hochgeschwindigkeitsprogrammieren auf. Ich werde diesmal auch mitmachen und mein Projekt wird das Backend meiner neuen Homepage sein. Das Design habe ich schon seit längerem so gut wie fertig, nur die Programmierung fehlt bis jetzt noch.

Ich habe in den letzten Wochen mehrere CMS-Systeme getestet und ich bin schlussendlich bei Textpattern gelandet. Ich kämpfte mehrere Tage, die Templates nach meinen wünschen in das CMS-System einzubinden, allerdings stellte sich gegen Ende immer mehr heraus, das das System nicht flexibel Genug für meine Wünsche ist. Darum habe ich gestern etwas Aufwandsabschätzung betrieben und bin zu dem Schluss gekommen, das ich nicht auf ein fertiges CMS bauen werde, sondern auf ein PHP-Framework, und die Seite (incl. Backend) selbst programmiere.

Folgende Features will ich bis zum 31.8.07 umsetzen:

  • Meine Homepage mit den Unterkategorien "Blog", "Projekte" und "Artikel" wird erstellt. Das XHTML ist bereits fertig.
  • Jede Kategorie hat Unterkategorien, in denen die eigentlichen Beiträge stecken.
  • Blog und Artikel erhalten eine Kommentarfunktion.
  • Trackbacks und Pingbacks zu Blog-Einträgen und Artikeln sind möglich.
  • Die komplette Seite enthält eine Suchfunktion.
  • Ein Backend, das folgende Features enthält:
    • Einpflegen und Bearbeiten von Blog-Einträgen, Projekten und Artikeln.
    • Eingetragene Texte können als "sichtbar" oder "versteckt" markiert werden.
    • Beim Erstellen eines Blog-Eintrags kann ein Trackback gesendet werden.
    • Eingetragen und gespeichert werden die Texte in Markdown-Syntax.
    • Es lassen sich Bilder hochladen und einbinden

Für die Realisierung verwende ich folgende Techniken und Hilfen:

  • Picora: Ein leichtgewichtiges PHP-Framework welches momentan in Beta 4 steht und einen sehr guten Eindruck macht. Ich habe zuvor schon einmal mit der Beta 1 gearbeitet und war sehr zufrieden.
  • PHP Markdown: Ein Markdown nach XHTML Parser.
  • Control.TextArea: Eine JavaScript-Klasse, welche es einfach macht, Buttons für Textboxen zu erstellen. Ich möchte keinen WYSIWYM-Editor ala FCKEditor verwenden, da mir dese zu aufgebläht sind.
  • Lighttpd mit mod_rewrite: Leichtgewichtiger Webserver mit URL-Rewriting für pretty URLs :)
  • prototype.js und MooTools: Um kleinere Spielereien und AJAX-Requests zu erzeugen.
  • Als Datenbank kommt entweder SQLite, MySQL oder PostgreSQL zum Einsatz, programmiert wird in PHP 5.2+.
  • Der komplette Sourcecode wird in SVN abgelegt und mit Phing auf meinem Server deployed. Auf UnitTests wird vermutlich (mal wieder) aus Zeitgründen verzichtet.

Kommentar schreiben, delicious bookmark del.icio.us


(cons 'CLISP '(and SDRAW))

vom 10. August 2007

Ich habe vor ein paar Tagen angefangen, Common Lisp zu lernen. Als Einstieg lese ich zur Zeit das Buch "A Gentle Introduction to Symbolic Computation" von David S. Touretzky. Das Buch wird leider nicht mehr gedruckt, aber man kann es als eBook herunterladen.

lambda

Mittlerweile auf Seite 177 angekommen, werden neue (makro)-Funktionen für Listenmanipulation vorgestellt. Um dies noch zu vereinfachen, hat Touretzky ein kleines Lisp-Programm geschrieben, mit dem man die internen Vorgänge beim Evaluieren grafisch als "Zellen-Diagramm" anzeigen lassen kann.

Das Programm muss nur compiliert werden, danach kann mit einem Aufruf von (sdraw <beliebige Listenformation>) die ASCII-Grafik erzeugt werden. Es gibt auch einen interaktiven Modus mit (sdraw-loop):

 S> (list '(a b) 'c)
[*|*]------------------>[*|*]--->NIL
 |                       |
 v                       v
[*|*]--->[*|*]--->NIL    C
 |        |
 v        v
 A        B

Result:  ((A B) C)

Das Programm ist verdammt praktisch zum Verstehen der Vorgänge; Wieso zum Beispiel (append '(a b) 'c) zu (A B . C) und nicht zu (A B C) wird:

S> (append '(a b) 'c)
[*|*]--->[*|*]--->C
 |        |
 v        v
 A        B

Result:  (A B . C)

Kommentar schreiben, delicious bookmark del.icio.us


STS-118

vom 8. August 2007

sts118

Heute kurz vor Mitternacht (22:36 UTC) wird die Mission STS-118 von der Startrampe 39A am Kennedy Space Center starten. NasaTV liefert schon die ersten Bilder von den Vorbereitungen.

Ziele dieser Mission sind das Anliefern des S5-Trägers für die ISS (liegt zwischen den Solar-Segeln auf der linken Seite) und des Spacehab-Modul mit einer Menge Ausrüstung was für Reperaturarbeiten benötigt wird. Zudem wird eine Lehrerin mitfliegen, um Unterrichtsstunden von der ISS aus zu geben.

Die Wetterverhältnisse stehen laut NasaTV auf 80%.

Kommentar schreiben, delicious bookmark del.icio.us


The Beer Game - Download NOW!

vom 7. August 2007

beergame_startscreen.png

So, wie versprochen hier nun das Neckarbräu-BeerGame zum Download. Falls jemand das Pflichtenheft, die technische Dokumentation o.ä. braucht, um das Spiel weiterzuentwickeln (wir haben noch ein paar tolle Features geplant, die nicht mehr umgesetzt wurden), kann sich jederzeit bei mir melden. Viel Spaß!

Kommentar schreiben, delicious bookmark del.icio.us


The Web is changing, once again.

vom 5. August 2007

Vor ca. zwei Jahren war AJAX der letzte Schrei. Doch nun zeigt sich wieder ein neuer Trend: Weg vom Browser, zurück zum Desktop. Der wirklich lesenswerte Artikel Return of the Desktop von Michael Swaine zieht Bilanz aus den gerade sprießenden Technologien von Adobe, Google, Microsoft und Apple. Es bleibt also weiterhin spannend :-)

Kommentar schreiben, delicious bookmark del.icio.us


Stöckchen: 8 Dinger über mich

vom 31. July 2007

Ein Stöckchen, überreicht von Markus:

Hier die Regeln: Jeder Spieler, jede Spielerin beschreibt acht Dinge von sich. Wer das Stöckchen zugeworfen bekommt, schreibt das alles in seinen Blog rein, mitsamt den Regeln. Nun überlegt man sich, an welche acht Personen resp. Blogs man das Stöckchen weiter reicht. Schlussendlich schreibt man bei den Betreffenden einen entsprechenden Beitrag/Kommentar in den Blog.

Und nun die 8 Dinge über mich:

  1. Ich lese viel und markier mir interessante/lustige/bloggenswerte/komische Stellen mit kleinen, klebenden "Markierungs-Fähnchen".
  2. Ich kann mich nicht zwischen Linux und Mac OSX entscheiden.
  3. Mein Nachbar geht mir manchmal voll auf den Sack.
  4. Nachts, wenn alle anderen schlafen, kann ich am Besten arbeiten.
  5. Die "Programming"-Sektion auf digg.com ödet mich an.
  6. Ich nehme mir immer viel zu viel in den Semesterferien vor.
  7. Ich habe keinen Führerschein.
  8. Ich will irgend wann mal ein Buch schreiben.

Und hier die acht glücklichen, die mitmachen dürfen :) Andreas Maier, Clemens Krack, Martin Rößler, Christian 'Neff' Hayungs, Nils Werner, Thomas Monninger, Wolfgang Ellsässer und Steeefan Heinz

Kommentar schreiben, delicious bookmark del.icio.us


!important

vom 26. July 2007

CSS ist schon eine tolle Sache, fast wie eine kleine Programmiersprache. Zwei wichtige Prinzipien möchte ich jetzt einmal kurz vorstellen:

Vererbung In den meisten Programmiersprachen erbt eine spezialisierte Klasse von einer Basisklasse, in dem die erweiterte Klasse die Eigenschaften und Methoden von der Basisklasse übernimmt (meist mit dem Schlüsselwort extends oder <). In CSS gibt es nur Eigenschaften, aber das Vorgehen ist gleich:

h2 {
  border-bottom: 1px solid black;
  display: block;
}

div#headline h2 {
  color: blue;
}

Der normale h2-Tag wird überall als Blockelement angesehen und unterstreicht den Inhalt. h2-Tags, die sich im div mit der ID "headline" befinden, erhalten allerdings noch das Farb-Attribut zusätzlich.

Konstanten oder "final" In Java bspw. gibt es das Schlüsselwort "final", welches dafür sorgt, das der Inhalt der Variable nicht mehr geändert werden kann. In CSS geht dies ähnlich; Will man dafür sorgen, das ein Wert unter keinen Umständen nachträglich geändert werden kann, setzte man ein !important dahinter.

h2 {
  color: blue !important;
}

div#headline h2 {
  color: red;
}

Hier erhält der Inhalt aller h2-Tags eine blaue Farbe, auch wenn in anderen Definitionen etwas anderes definiert ist. Natürlich wirkt dieses Beispiel etwas komisch und man denkt sich sicher "wenn man richtig hinschaut und keinen Fehler macht, braucht man das doch garnicht". Wäre da nicht die Kaskadierungsreihenfolge (bzw. die Prioritäten):

Im Browser werden intern alle Stilangaben (symbolhaft) in einem großen Stylesheet gesammelt und anschließend auf das (X)HTML losgelassen. Die Reihenfolge, in welcher die Angaben in das "große Stylesheet" eingefügt werden, hängt natürlich zum einen von der tatsächlichen Anordnung im Stylesheet ab (der Browser arbeitet sich von oben nach unten durch), aber zum anderen auch von der Prioritätsreihenfolge:

css-kaskade neu

Wenn kein Stylesheet angegeben ist, wird das Browserinterne Stylesheet verwendet (blau unterstrichene Links, große Überschriften, etc.). Wenn eine externe CSS-Datei eingebunden wird, kann diese die Defaulteinstellungen des Browsers überschreiben. Sind zudem im head-Bereich mit dem style-Tag weitere Stilangaben eingebunden, werden diese vorgezogen. Direkt im Tag als Attribut angegebene Stilangaben werden vor allen anderen Angaben vorgezogen - seiden, ja seiden man verwendet das Schlüsselwort !important an einer Stelle der Kette, dann bleibt diese Angabe dauerhaft und wird nicht überschrieben.

Kommentar schreiben, delicious bookmark del.icio.us


Move != Copy

vom 24. July 2007

Ich habe gerade an einem automatisierten Build-Script für eventon.de gearbeitet, da das Deployen einer neuen Version bisher mit etwas Tipparbeit verbunden war. Als Automations-Tool hab ich mich für Phing, einem ANT-Klon, entschieden. Alles funktionierte bestens, doch das Umbenennen eines Verzeichnisses war doch etwas merkwürdig.

Das Umbenennen dauerte Ewigkeiten und die Statusmeldungen verrieten auch den Grund: "[move] Copying 426 file to ..." Dabei wollte ich doch nur den Verzeichnisnamen ändern, und das so schnell wie möglich. Nach einem Blick in den Sourcecode war dann alles klar: "class MoveTask extends CopyTask { ...". Es wurde tatsächlich das komplette Verzeichnis, Datei für Datei, kopiert und das Quellverzeichnis anschließend gelöscht.

Unter ANT gibt es das Target rename, welches in Phing nirgends aufzufinden war. Also habe ich das Manko gleich behoben, in dem ich den RenameTask nachimplementiert haben. (Download: RenameTask.php). Der Code ist alles andere als schön, aber er tut seinen Zweck.

Wer ihn nutzen will, kopiert die Datei nach /usr/lib/php/phing/tasks/ext/ (ohne die .txt-Endung) und fügt in seine Build.xml folgende Zeile ein, um den Task zu nutzen:

<taskdef name="rename" classname="phing.tasks.ext.RenameTask" />

Der RenameTask funktioniert analog zum ANT-Task.

Kommentar schreiben, delicious bookmark del.icio.us


UML mit Style

vom 20. July 2007

UML-Diagramme können manchmal wirklich langweilig sein. Vorallem dann, wenn man gezwungen wird, UseCases oder Sequenzdiagramme für triviale Dinge anzufertigen, die man im Kopf sowieso schon zuende gedacht hat und eigentlich nur noch runterprogrammieren will.

Bei komplexeren Programmen kommt man allerdings nicht drum rum. Es stellt sich also die Frage: Wie und mit welchem Tool mache ich jetzt meine Diagramme? In den letzten Wochen sind mir einige interessante Ansätze untergekommen, die ich hier nun zusammentragen möchte.

Saffron AIR UML

saffron

Bisher verwende ich ArgoUML für Klassendiagramme und JUDE für Sequenzdiagramme (diese lassen sich mit ArgoUML nur sehr umständlich erstellen und der Editor ist immer noch sehr buggy) für den Alltagsgebrauch. Ich komme eigentlich recht gut damit zurecht, aber Spaß macht es nicht wirklich.

Saffron geht einen ganz anderen Weg. Es nutzt das neue AIR (von Adobe) um eine schicke, interaktive Oberfläche zu bieten. Das Programm ist leider noch nicht fertig, aber die Screenshots sehen schon sehr vielversprechend aus.

UMLGraph

Ich habe mich schon oft gefragt, welches Tool denn die ganzen Autoren der Fachbücher für die Diagramme verwenden, denn diese sehen meist sehr schick aus. Ich denke die Antwort gefunden zu haben: Mit UMLGraph lassen sich Klassen- und Sequenzdiagramme mit einer Metasprache definieren und mit der Unterstützung von Graphviz in Bilder wandeln. Das Ergebnis sieht sehr professionell aus. Allerdings ist diese Art der Modellierung nicht für den Entwurfsprozess geeignet, eher fürs "Reinzeichnen".

Zum Entwerfen von Systemen habe ich auf YouTube ein interessantes Video entdeckt.

[youtube v3-ozq-ZbHE]

Allerdings ist mir jetzt schon bei mehreren Projekten aufgefallen, das der Rechner in der Entwurfs- und Planungsphase mehr im Wege steht als das es einen Vorteil gebracht hätte. Ein Klassendiagramm ist schneller mit Papier und Stift gezeichnet. Wenn man zusammen an einem Tisch sitzt, kann jeder schnell seine Ideen einbringen und dazumalen, und wenn das Chaos auf dem Papier zu groß wird, zeichnet man es noch einmal neu. Dies hat auch den Vorteil, das man sich viel mehr Gedanken über die Klassen macht. Wenn man eine Klasse in einem UML-Tool erstellt, und an den richtigen Platz gerückt hat, löscht man es in den seltensten Fällen wieder.

Noch was zu den UseCases: Ja ich mag sie nicht. Sie verbraten wertvolle Zeit und niemand weiß sie zu würdigen. Der Kunde erschrickt beim Anblick und die Programmierer lesen nicht gerne. Sie bevorzugen eher einfache (nicht unbedingt UML-Konforme) Skizzen, die direkt verstanden werden können und natürlich das bindende Kapitel "Funktionale Anforderungen" aus dem Projektauftrag. Auch der Artikel auf mittechnical.com konnte mich (noch) nicht überzeugen. Vielleicht schaffst Du es ja mit einem Kommentar :-)

Kommentar schreiben, delicious bookmark del.icio.us


Namespaces in PHP

vom 14. July 2007

In den "Enterprise"-Programmiersprachen sind Namensräume bereits seit längerem verfügbar. In Java werden diese mit dem Befehl "package" definiert und mit "import" verwendet, in Ruby spricht man hier von "Modulen". In PHP gibt es dieses Konstrukt leider immer noch nicht, was in größeren Projekten zu langen Klassennamen und Prefixen führt, um keine Namenskonflikte entstehen zu lassen.

Vor ca. einem Jahr waren Namensräume auf der internals-Mailingliste ein heißes Thema, wurde aber wieder fallen gelassen, da niemand eine anständige Implementierung hinbekommen hat. am 4.7.07 hat Dmitry Stogov das Thema wieder aufgegriffen und einen Patch incl. Tests für eine funktionierende Implementierung zum Testen veröffentlicht. In der Diskussion ging es bist jetzt hauptsächlich um das Thema: Soll es in einer Datei nur einen oder mehrere Namensräume geben? Ich persönlich wäre ja für ersteres.

Ich konnte es nicht lassen und hab versucht, den Patch einmal in einen frischen Snapshot einzuspielen. Beim Patchen wurde mir allerdings mitgeteilt, das die Änderungen bereits im Code sind. Also nur noch schnell compilieren und das Testen kann beginnen:

a_c.php

namespace A::C;
class a {
    function __construct() {
        echo "Namespace: " . __NAMESPACE__ . "n";
    }
}

function a() {
    echo "Namespace: " . __NAMESPACE__ . "n";
}

Die Datei repräsentiert den Namensraum "A::C", in dem die Klasse a und die Funktion a() definiert ist.

a_b.php

namespace A::B;
require 'a_c.php';
import A::C as Alias;
function a() {
    echo "Namespace: " . __NAMESPACE__ . "n";
}

new Alias::a;
Alias::a();
A::C::a();
a();

In der zweiten Datei wird der Namensraum "A::B" definiert und die Datei "a_c.php" eingebunden. Der Namensraum "A::C" wird importiert und unter dem Alias-Namen "Alias" geführt. Auf diesen kann dann äquivalent zu "A::C" zugegriffen werden. Im Namensraum "A::B" wird noch einmal die Funktion a() definiert, um den Effekt zu demonstrieren.

Die neue Instanz aus "Alias::a" stammt aus dem "A::C" Namensraum, welches die Ausgabe "Namespace: A::C" bestätigt. Der Aufruf "Alias::a()" wird intern (wie die Zeile darüber) auf "A::B::a()" gemapped und vom entsprechenden Namensraum ausgeführt. Genauso die nächste Zeile. Der Aufruf "a()" gibt nun "Namespace: A::B" aus, da sie im Namensraum "A::B" definiert ist.

Die gleichen Namensräume können auch in mehreren Dateien verwendet werden. Also wenn ich in beiden Dateien den Namensraum "A::B" verwendet hätte, gäbe es bei dem Aufruf "a()" einen Namenskonflikt.

Fatal error: Cannot redeclare a::b::a()

Alles in Allem funktioniert die Sache schon recht gut. Die Fehlerausgabe ist noch etwas dürftig und missverständlich, aber das wird sich vermutlich schnell richten. Ich freue mich auf jeden Fall schon auf ein offizielles (pre) Release und hoffe, das die Namespaces drinbleiben. Und noch eine erfreuliche Nachricht: Ab dem 1.1.2008 ist PHP4 offiziell tot. Mal sehen ob das die großen Hoster bis dahin gebacken kriegen.

Kommentar schreiben, delicious bookmark del.icio.us