Homepage selbermachen 7.851 Themen, 35.616 Beiträge

Mal eine kleine Abhandlung über die Zukunft von PHP

xafford / 5 Antworten / Flachansicht Nickles

Aus eigenem, vor allem beruflichem, Interesse habe ich mir in den letzten Paar Tagen mal die ausstehenden Änderungen in PHP für die kommende Version 5.3 und das nächste Major Release PHP6 angeschaut. Einiges wird sich tun, einiges wurde leider nicht als Änderung angenommen, vieles ist noch nicht abschließend klar, leider nicht einmal für PHP5.3 (welches eigentlich bald released werden sollte). Hier mal eine kleine und leider unvollständige Abhandlung, worauf man sich freuen darf.

Vorweg erst einmal das Wichtigste und die größte Änderung: PHP bekommt endlich Namespaces und zwar bereits mit PHP5.3. Wer schon einmal ein etwas größeres Projekt erstellt hat, oder mit umfangreicheren Frameworks gearbeitet hat kennt bestimmt das Ärgernis des globalen Namespace von PHP und der damit verbundenen "Verschmutzung" des Namesraumes. Spätestens seit dem (kleinen) Desaster mit der Date-Klasse von Pear und der Einführung einer Date-Klasse in PHP5 war jedem klar, der mit PHP etwas mehr zu tun hatte, dass PHP aus der Größe herausgewachsen ist bei der man sich einen globalen Namensraum leisten kann.

Mit Namespaces wird es komfortabel möglich, Klassen und Funktionsnamen zu definieren, die nicht ewigLangSeinMuessenUmKollisionenZuVermeiden();

Man kann dann eine Funktion connect() im Namespace Net::HTTP und im Namespace Net::FTP definieren und beide benutzen, ohne Probleme und niemand muss sich Net_HTTP_connect() oder Net_FTP_connect() merken.

Im Bereich der Klassen tut sich auch etwas. Hinzukommen wird z.B. das Late-Static-Bindung. Dazu eine kleine Erklärung. Derzeit werden statische Methoden und deren Auflösung zu Kompilierungszeit ausgewertet, nicht zur Laufzeit wasmanchmal zu etwas problematischem Verhalten führen kann bei der Vererbung, denn erweitert eine Klasse B eine Klasse A und beide implementieren eine statische Methode C(), so ruft ein Aufruf von B::C() in Klasse B nicht wie man vermuten könnte die Methode C() wie in Klasse B definiert auf, sondern die statische Methode C() in Klasse A. Durch Verwendung von static::C() in Klasse B lässt sich nun jedoch die statische Methode C() korrekt in Klasse B aufrufen wenn dies gewünscht ist.

Weiterhin wird es die Möglichkeit der statischen Klassen geben, definiert als static class XXX. Hier wird das Static-Keyword umgenutzt. Dies lässt sich gut nutzen, um z.B. eine Art "Werkzeugkasten" zu implementieren, eine Klasse die auch ohne Instanzierung logisch gruppierte Funktionalität bereit stellt.

Im Bereich von statischen Methoden und Klassen wird es auch eine neue magische Funktion geben analog zu __call(), nämlich __callStatic().

Generell im Bereich Klassen ist auch angedacht Type-Hints (Hinweise auf den Typen) für Methoden einzuführen, wie es bei PHP5 bereits für Parameter eingeführt wurde. Wie die Syntax dafür aussehen soll steht aber wohl noch in den Sternen.

Eine weitere wichtige und äußerst hilfreiche Änderung ist die bessere Unterstützung von Unicode. Gerade internationalisierte Webprojekte kennen die Probleme mit verschiedenen Kodierungen und die daraus resultierenden Probleme.

Weiterhin im Bereich von Strings wird auch etwas geändert, was erst zu PHP5 geändert wurde, nämlich der gewünschte Umgang mit String-Offsets. Um einen Offset in einem String zu adressieren (sprich ein einzelnes Char [Zeichen]) gibt es in PHP parallel die Syntax $string{offset} und $string[offset]. Mit Einführung von PHP5 wurde die Syntax über die eckigen Klammern [] als unerwünscht gekennzeichnet, es sollten die geschweiften Klammern genutzt werden {}. Mit Einfürhung von PHP6 (oder schon 5.3?) soll es nun wieder genau umgekehrt werden (was auch eigentlich naheliegender war) und die geschweiften Klammern werden die unerwünschte Version.

Zudem soll die Syntax zum Zugriff auf Offsets auch weitere Funktionalität bekommen (und zum Zugriff auf Arrays auch):

$string[1,3] soll 3 Zeichen, beginnend ab Offset 1 liefern (bei Arrays 3 Einträgeab Offset 1). Dummerweise soll dann jedoch die Syntax $string[1, -2] alle Zeichen ab Offset 1, außer der letzten beiden Zeichen zurück liefern. Mir persönlich wäre es sinnvoller vorggekommen, wenn $string[1,3] den String von Offset 1 bis Offset 3 zurück liefern würde.

Weiterhin wird im Bereich der Stirngs eine zusätzliche HEREDOC-Syntax hinzu kommen. Neben:

>>>END
Dies ist ein $string
END;

wird es auch:

>>>`END`
Dies ist ein $string
END;

geben, wobei bei der neuen Syntax die Variable $string auch ohne Maskierung nicht ausgewertet werden wird.

Weiterhin erhält PHP einen neuen grundlegenden Typen, ein int64, also ein 64Bit langes Integer und dies unabhängig von der Plattform auch auf einem 32Bit-System. Dies ist sehr hilfreich beim Umgang mit großen Integern (kleiner Hinweis: ip2long(), pow(2, 32)).

Weiterhin wird es einen neuen Operator geben, bzw ein vorhandener mit neuer Funktionalität implementiert. Angedacht war zuerst ein neues Sprachkonstrukt namens ifsetor, was nun als ?: implementiert wird (Ternäroperator ohne mittleres Argument. Dies soll folgendes Konstrukt überflüssig machen:

$var = isset ( $_GET['var'] ) ? $_GET['var'] : 42;

Es vereinfacht sich zu:

$var = $_GET['var'] ?: 42;

oder sauber umgesetzt:

$var = filter_input ( FILTER_GET, 'var', FILTER_VALIDATE_INT ) ?: 42;

Zum Umgang mit MySQL wird wieder eine Bibliothek direkt in den PHP-Kern wandern, welche auch aus Sicht der Performance eine Verbesserung darstellen soll und bis zu 20% mehr Leistung bringen soll. Diese neue Bibliothek soll auch in MySQLi und PDO verwendung finden.

Was viele böse Script-Kiddies freuen wird ist, dass in PHP magic_quotes verschinden werden. Vom CLient übermittelte Daten werden also nicht mehr automatisch "entschärft". Man wird dann mal abwarten dürfen, wieviele SQL-Injection-Lücken beim Wechsel bei den Massenhostern aufgerissen werden. Zwar ist das einerseits sinnvoll, denn die Behandlung von Daten liegt beim Programmierer, wo sie sein soll, andererseits wurde magic_quotes so lange mitgeschleppt und es gibt so viele "Trottel" denen das Problem nicht bewusst ist, dass diese Änderung ziemlich heftige Effekte nach sich ziehen dürfte. Ich würde einmal vorsichtig schätzen, dass durch die Umstellung über Nacht ein zeweistelliger Prozentsatz an Seiten die mit Datenbanken arbeiten potenzielle Opfer von Hacks werden dürften.

Ebenso verschwinden wird der safe_mode (der nie das war, was man anhand des Namens vermuten könnte). Weiterhin wird register_globals verschwinden.

Das Wörtchen "var", welches beim Umstieg von PHP4 zu PHP5 als "deprecated" (veraltet) markiert wurde wird wiederbelebt und bekommt bei Klasseneigenschaften die Bedeutung von Public verpasst (öfter mal was Neues).

So, rein aus dem Gedächtnis war es das jetzt mal mit anstehenden Neuerungen (obwohl ich einiges vergessen haben dürfte), dafür haben es andere durchaus sinnvolle Änderungen wahrscheinlich nicht geschafft ernsthaft in Erwägung gezogen zu werden:

Setter/Getter wurden als unnütz angesehen... Schade. Die Argumentation war, dass sie im Vergleich zu Setter-/Getter-Methoden nichts vereinfachen würden. Da haben in meinen Augen die PHP-Entwickler jedoch einen Punkt vergessen, nämlich die automatische Generierung von Klasseninstanzen aus Datenbankinhalten z.B. bei PDO mit setFetchMode(PDO::FETCH_CLASS). Hierbei werden die Eigenschaften des Objektes stumpf mit Strings gesetzt, ohne dass man dies beeinflussen könnte.

Type-Hints für Eigenschaften in Klassen widersprechen nach Ansicht der Entwickler auch dem PHP-Way. Dies mag legitim sein, diese Option zu haben wäre aber in manchen Fällen durchaus wünschenswert. Was jedoch in meinen Augen nicht legitim ist wäre der Umstand, dass der Vorschlag für magische Funktionen bei Casts, ähnlich wie bei __toString() für andere Casts (Umwandlungen) abgeschmettert wurde. Im Gespräch waren Methoden für __toInt(), __toArray, __toFloat etc, also für eingebaute Typen. Ich hätte mir sogar gewünscht, dass es generell die Option gegeben hätte hier freie Methoden zu definieren für jeden beliebigen Cast über __toXXX(), gerade bei einer Sprache ohne feste Typisierung hätte dies im Bereich der OO einen immensen Vorteil gebracht.
Dies führt auch leider zu noch einem Punkt der es leider nicht geschafft hat (aber wohl auch recht aufwändig geworden wäre): Operatoren-Überladung. Ich mag ja C++ nicht so sehr, aber die Möglichkeit für eine Klasse Operatoren zu definieren finde ich schon äußerst praktisch.

Auch der Vorschlag einen Tainted-Mode für möglicherweise korrumpierte Daten (z.B. vom Client übermittelte Daten) einzuführen wurde verworfen, aber wahrscheinlich wäre diese Funktionalität auch nicht wirklich sinnvoll umzusetzen gewesen.

Im Bereich der OO wurden auch Traits erst einmal nicht angenommen, obwohl es da wohl noch möglich wäre, denn ein Patch hierfür existiert wohl bereits. Wem Trait nichts sagt, der kann es sich einfach wie eine Art Interface, allerdings mit der Definition der Methode vorstellen. Prinzipiell ist ein Trait ein sinnvoller Ersatz eine Mehrfachbeziehung (Mehrfachvererbung) bei Objekten festzuschreiben, ohne wie bei Interfaces gleichartige Methoden mehrfach implementieren zu müssen.

Was es zum Glück nicht geschafft hat den Weg in PHP6 zu finden ist die Mehrfachvererbung und Named-Parameters.

Was es leider auch in PHP geschafft hat ist ein "labeled break" bzw goto. *Ärghhh*

So, das reicht erst einmal. Zwar fällt mir noch die ein oder andere kleinere Änderung ein, aber da ich wahrscheinlich eh den Großteil vergessen habe oder noch nicht weiß lasse ich es dabei erst einmal bewenden. Ich hoffe dies ist trotzdem für irgend jemanden von Nutzen.

Pauschalurteile sind immer falsch!!!
bei Antwort benachrichtigen
xafford Zaphod „Danke für die Zusammenfassung, da ich im Moment wenig Zeit habe, hilft die beim...“
Optionen

Hi Z... wie so oft fielen mit im Nachhinein noch paar kleinere, aber nicht ganz unwichtige Änderungen ein:

Ab PHP5.3 wird nur noch FastCGI als Schnittstelle neben den Modulen unterstützt, CGI fällt komplett raus.

Die Funktion dl() funktioniert nur noch auf der Kommandozeile und bei Embedded afair.

In die Standarddistribution wird der Bytecode-Cache APC integriert, jedoch nicht per default aktiviert (bringt je nach Scriptgröße bis zu 300% Beschleunigung).

Die Option register_long_vars und damit die $HTTP_*-Variablen verschwinden komplett, es stehen nur noch die Superglobals $_POST, $_GET, $_REQUEST, $_COOKIES, $_SERVER, $_FILES zur Verfügung.

E_STRICT-Warnungen gehen in E_ALL auf, d.h. wer beim error_reporting E_ALL nutzt sollte sich darauf gefasst machen dann auch Meldungen bei unsauberer Programmierung zu sehen zu bekommen.

Nicht definitiv sicher bin ich, ob es bei der Verwendung uninitialisierter Eigenschaften einer Klasse zu einer Warnung kommen wird.

Es kommt ein neues Error-Level: E_RECOVERABLE_ERROR, dieser wird die Ausführung des Scriptes nicht abbrechen, sofern es einen error_handler gibt.

Konstanten sollen auch mit Arrays inisialisiert werden können (ist aber wohl noch nicht definitiv).

Pauschalurteile sind immer falsch!!!
bei Antwort benachrichtigen