55
Leseprobe Diese Leseprobe verrät Ihnen zuerst die Grundlagen und Beson- derheiten von Zend Framework 3. Schauen Sie dann, wie Sie mit Middleware Anwendungen einrichten, bevor Sie mit Controllern und Views richtig tief in MVC einsteigen. Außerdem können Sie einen Blick in das vollständige Inhalts- und Stichwortverzeichnis des Buches werfen. Ralf Eggert Zend Framework 3 – Das umfassende Handbuch 960 Seiten, gebunden, 2. Auflage 2016 44,90 Euro, ISBN 978-3-8362-3965-3 www.rheinwerk-verlag.de/4016 »Einführung in das Zend Framework 3« (Auszug) »Middleware-Anwendungen einrichten« (Auszug) »Controller und View (Auszug) Inhaltsverzeichnis Index Der Autor Leseprobe weiterempfehlen Wissen, wie’s geht.

Zend Framework 3 – Das umfassende Handbuch

Embed Size (px)

Citation preview

Page 1: Zend Framework 3 – Das umfassende Handbuch

LeseprobeDiese Leseprobe verrät Ihnen zuerst die Grundlagen und Beson-derheiten von Zend Framework 3. Schauen Sie dann, wie Sie mit Middleware Anwendungen einrichten, bevor Sie mit Controllern und Views richtig tief in MVC einsteigen. Außerdem können Sie einen Blick in das vollständige Inhalts- und Stichwortverzeichnis des Buches werfen.

Ralf Eggert

Zend Framework 3 – Das umfassende Handbuch960 Seiten, gebunden, 2. Auflage 2016 44,90 Euro, ISBN 978-3-8362-3965-3

www.rheinwerk-verlag.de/4016

»Einführung in das Zend Framework 3« (Auszug) »Middleware-Anwendungen einrichten« (Auszug) »Controller und View (Auszug)

Inhaltsverzeichnis

Index

Der Autor

Leseprobe weiterempfehlen

Wissen, wie’s geht.

Page 2: Zend Framework 3 – Das umfassende Handbuch

31

1Kapitel 1

Einführung in das Zend Framework 3

Bevor ich mit Ihnen in die Zend Framework 3-Projekte einsteige, lernen

Sie in diesem Kapitel grundlegende Konzepte und technische Aspekte

kennen. Zudem lernen Sie die Framework-Varianten und die Anwen-

dungen kennen, mit denen Sie sich in diesem Buch beschäftigen werden.

Das Zend Framework (http://framework.zend.com/) wird seit über 10 Jahren von Zend

Technologies und einer großen internationalen Community entwickelt. Zend Frame-

work 1 (kurz ZF1) erschien im Jahr 2007, und die Nachfolgeversion, Zend Framework 2

(kurz ZF2), erblickte im Jahr 2012 das Licht der Welt. Zend Framework 3 (kurz ZF3)

wurde 2016 veröffentlicht und ist der logische nächste Schritt in der Evolution.

1.1 Was ist das Zend Framework 3?

Das Zend Framework 3 ist gleichermaßen ein PHP-Framework sowie eine Sammlung

von Komponenten für den Aufbau von Anwendungen auf Basis von PHP.

Sie können mit dem ZF3 sowohl klassische Webanwendungen als auch API-Server

aufbauen. Zusätzlich bietet das Zend Framework 3 auch alle Komponenten für das

Schreiben leichtgewichtiger Konsolenanwendungen. Durch das offene Konzept eig-

net sich das Zend Framework 3 sowohl für kleine und mittelgroße Anwendungen als

auch für den Betrieb komplexer Enterprise-Anwendungen.

1.2 An wen richtet sich dieses Buch?

Dieses Buch richtet sich gleichermaßen an Einsteiger in das Zend Framework 3 und

an Umsteiger vom ZF2 sowie vom ZF1. Sie müssen kein Profi in den beiden Vorgän-

gerversionen sein, um sich zurechtzufinden. Ein gewisses Maß an Vorwissen im Zend

Framework schadet aber sicher nicht,

Um mit dem Zend Framework 3 effektiv arbeiten zu können, sollten Sie solide Erfah-

rungen in der objektorientierten Programmierung (OOP) mit PHP haben. Begriffe wie

Interfaces, abstrakte Klassen, Sichtbarkeit oder Vererbung sollten für Sie keine Fremd-

wörter sein. Um Ihr Wissen etwas aufzufrischen, schauen Sie bitte in Anhang A,

»Objektorientierte Programmierung in PHP«.

3965-3.book Seite 31 Donnerstag, 6. Oktober 2016 1:19 13

Page 3: Zend Framework 3 – Das umfassende Handbuch

1 Einführung in das Zend Framework 3

32

Außerdem sind grundlegende Kenntnisse von Entwurfsmustern (engl.: Design Pat-

terns) in PHP hilfreich. Entwurfsmuster wie Factory, Table Data Gateway oder das

Repository Pattern sollten Sie zumindest einmal gehört haben. Auch sind Erfahrun-

gen mit Architekturmustern wie dem bekannten Model-View-Controller von Vorteil.

Sollten Ihnen diese Begriffe neu sein, schauen Sie in Anhang B, »Architekturmuster

und Entwurfsmuster«.

Lassen Sie sich aber nicht entmutigen, wenn Ihnen einige Begriffe oder Sachverhalte

nicht auf Anhieb bekannt sind. Manche Bezeichnungen und Ausdrücke sind dem

einen Entwickler total geläufig, während ein anderer davon noch nie gehört hat. Die-

ses Buch kann nicht jeden Aspekt der modernen Webentwicklung in aller Breite

erläutern. Lassen Sie sich dadurch nicht entmutigen, und machen Sie es sich zur täg-

lichen Angewohnheit, unbekannte Begriffe im Internet zu recherchieren. Sie glauben

gar nicht, wie oft ich bei meiner täglichen Arbeit nach unbekannten Abkürzungen,

Fachbegriffen oder Softwareparadigmen im Netz suche, um sie besser zu verstehen.

1.3 Warum das Zend Framework 3 einsetzen?

Das Angebot an PHP-Frameworks ist heutzutage riesengroß. Der Markt scheint seit

Jahren gesättigt zu sein, sodass es Neulinge recht schwer haben. Doch warum sollten

Sie sich für das Zend Framework 3 entscheiden, wenn Sie mit Ihrem alten Framework

seit Jahren erfolgreich Projekte umsetzen? Für einen Wechsel zum ZF3 sprechen ver-

schiedene Gründe (siehe Abbildung 1.1).

Abbildung 1.1 Gründe für den Einsatz vom Zend Framework 3

Gründe fürZend Framework 3

ZF1 EOL

EinfacheMigrationvom ZF2

Unterstützungfür PHP 7

Kontinuität

VerbesserteDokumentation

Flexibilität

VerbessertePerformance

EntkoppelteKomponenten

3965-3.book Seite 32 Donnerstag, 6. Oktober 2016 1:19 13

1.3 Warum das Zend Framework 3 einsetzen?

33

1Schauen Sie sich zudem als Einstimmung auch die kurze Fallstudie zu einem Projekt

an, das bereits vom Zend Framework 2 auf das Zend Framework 3 gewechselt ist

(siehe Infokasten).

Fallstudie über Migration vom ZF2 zum ZF3

Die Firma BORDONARO IT GmbH & Co. KG hat es bereits geschafft und ein umfang-

reiches Projekt, das auf dem ZF2 basierte, zum Zend Framework 3 migriert. Das Pro-

jekt myMedax, eine komplexe Software zur digitalen Anamnese in Arztpraxen und

Krankenhäusern, wurde im Kundenauftrag erstellt (http://www.mymedax.de/). Es

basierte auf dem ZF2 und litt unter einer verbesserungswürdigen Performance.

Dino Bordonaro fasst seine Erkenntnisse nach der Migration zum Zend Framework 3

wie folgt zusammen:

� Die Performance der Anwendung hat sich verdoppelt bis verdreifacht. Die Lade-

zeiten konnten von 700 bis 1.400 Millisekunden auf 200 bis 500 Millisekunden

reduziert werden.

� Die Migration der fast 50 Module zur 3er-Version von Zend\Mvc konnte ein Zwei-

mannteam in 6 Manntagen abschließen.

� Allein fast 500 Factorys mussten dabei refaktoriert werden, um die Performance-

vorteile der 3er-Version vom Zend\ServiceManager ausreizen zu können.

� Kleinere Probleme gab es beim Einsatz der View-Helper, da im ZF3 die Schreib-

weise in Groß- und Kleinschreibung genau beachtet werden muss.

Alles in allem hat sich die Migration mehr als ausgezahlt. Dabei wurde bisher noch

nicht auf das schnelle Zend\Expressive gewechselt.

1.3.1 Warum vom ZF1 oder ZF2 migrieren?

Wenn Sie bereits mit einer älteren Version vom Zend Framework arbeiten, fragen Sie

sich vielleicht, was für einen Wechsel auf die neueste Generation des Zend Frame-

works sprechen könnte. Es folgen ein paar Denkanstöße.

� Ende September 2016 hat das ZF1 das EOL (End of Life) erreicht. Es wird somit nicht

mehr weiterentwickelt und auch nicht mehr mit Sicherheitspatches versehen. Das

Ende des offiziellen Supports für das ZF1 und die veraltete Technik machen einen

Wechsel auf die modernere Generation des Zend Frameworks notwendig. Wer

vom ZF1 migrieren möchte, muss sich jedoch auf viel Handarbeit einstellen.

� Das ZF3 stellt im Vergleich zum ZF2 ein evolutionäres Update dar. Umsteiger vom

ZF2 finden sich schnell zurecht, und die Migration vom ZF2 ist deutlich einfacher als

auf die Vorgängerversion. Einem schnellen Wechsel steht somit nichts entgegen.

� Das ZF3 ist schneller, leichter zu warten und konsistenter als das ZF2. Zudem wur-

den die Komponenten weiter entkoppelt, d. h., die Abhängigkeiten zu anderen

3965-3.book Seite 33 Donnerstag, 6. Oktober 2016 1:19 13

Page 4: Zend Framework 3 – Das umfassende Handbuch

1 Einführung in das Zend Framework 3

34

Komponenten wurden stark reduziert. Damit wird es noch leichter, bei Bedarf nur

ausgewählte Komponenten in einem Projekt einzusetzen. Auch dies spricht für

einen zeitnahen Wechsel vom ZF2 zum ZF3.

� Mit dem neuen Middleware-Konzept gibt es im ZF3 eine schlankere Alternative

zum klassischen MVC-Konzept. Dennoch wurde der bewährte MVC-Ansatz weiter

optimiert, sodass Sie für Ihr Projekt die Wahl zwischen zwei ebenbürtigen Alterna-

tiven haben.

� Das Zend Framework 3 ist PHP 7 ready. Damit setzt es die neueste PHP-Version

zwar nicht voraus, läuft damit aber reibungslos. Alle Inkompatibilitäten älterer

PHP-Versionen wurden entfernt. Auch wenn das ZF3 nicht die neuen Features von

PHP 7 ausnutzt, können Sie dennoch sorglos Ihre neuen Projekte gleich mit PHP 7

aufsetzen.

Akzeptanz von PHP 7

Ein großes Problem von PHP 5 war die jahrelang sehr schleppende Akzeptanz. Neue

Minor-Releases wurden nur zögerlich von der Community auf Produktionsservern

eingesetzt. Doch erste Meldungen im Sommer 2016 zeigen, dass die Akzeptanz von

PHP 7 vor allem aufgrund der verbesserten Performance deutlich schneller voran-

schreitet.

Der aktive Support für PHP 7.0 endet am 3. Dezember 2017, und danach wird das

Minor-Release noch ein weiteres Jahr mit Sicherheitspatches versorgt. Für Ende 2016

ist zudem schon PHP 7.1 angekündigt. Es spricht also nichts dagegen, frühzeitig auf

PHP 7 zu wechseln.

1.3.2 Warum vom anderen Framework wechseln?

Seit dem Jahr 2015 haben mit CakePHP, TYPO3 Flow, Symfony und dem Zend Frame-

work die meisten relevanten PHP-Frameworks die 3er-Version und damit ein neues

Major-Release veröffentlicht.

Software-Releases

Bei der Einteilung von Software-Releases sind drei Stufen zu unterscheiden.

Dafür gibt es verschiedene Notationen:

� Major.Minor.Patch

� Hauptversion.Nebenversion.Revision

� Breaking.Feature.Fix

Ein Software-Release mit der Nummer 2.3.4 bezeichnet somit den vierten Patch des

dritten Minor-Releases vom zweiten Major-Release oder die vierte Revision der drit-

ten Nebenversion von der zweiten Hauptversion.

3965-3.book Seite 34 Donnerstag, 6. Oktober 2016 1:19 13

1.3 Warum das Zend Framework 3 einsetzen?

35

1Wer mit seinem aktuellen PHP-Framework unzufrieden ist und mit dem Gedanken

spielt, auf ein anderes zu wechseln, findet hier ein paar Gründe für einen Wechsel

zum Zend Framework 3.

� Die meisten PHP-Frameworks sind seit ihrer ersten Generation als Full-Stack-

Framework konzipiert. Dies sind meist geschlossene Systeme, die dem Entwickler

viele Entscheidungen abnehmen und für alle Aspekte einer Webanwendung eine

passende Komponente bereitstellen. Erst in den letzten Jahren haben sich die

meisten Frameworks nach außen geöffnet und bieten ihre entkoppelten Kompo-

nenten auch separat an. Dies ist auch durch den Siegeszug der Paketverwaltung

Composer (siehe Abschnitt 1.6.7) bedingt.

� Das Zend Framework war schon immer ein Komponentenframework, anders, als

der Name vermuten lässt. Somit lässt es sich auch mit PEAR vergleichen oder in

grauer Vorzeit mit phpLib. Sie haben beim Zend Framework 3 in vielen Aspekten

immer eine Wahlfreiheit. Sie werden nicht gezwungen, eine bestimmte Template-

Engine oder ein ORM (Object Relational Mapper) zu verwenden, weil das Frame-

work Ihnen dies mehr oder minder vorschreibt. Wenn Sie diese Flexibilität brau-

chen, sind Sie beim Zend Framework 3 genau richtig.

� Das Zend Framework 3 zeichnet sich durch seine Flexibilität aus. Sie können im

ZF3 die MVC-Implementation verwenden, müssen es aber nicht. Sie können alter-

nativ das Middleware-Konzept einsetzen, sind aber auch dazu nicht gezwungen.

Sie können auch Ihre eigene MVC-Implementation oder die eines anderen Frame-

works verwenden und müssen dennoch nicht auf den Einsatz von Zend-Frame-

work-Komponenten verzichten.

� Ein weiterer Vorteil ist die Kontinuität, die das Zend Framework 3 Ihnen bietet. Sie

müssen sich nicht gefühlt jedes Jahr mit einem neuen Major-Release auseinander-

setzen, das wieder einmal das gerade Gelernte komplett über den Haufen wirft.

� Es gibt immer wieder neue PHP-Frameworks, die extrem angesagt sind, und so

mancher Entwickler fühlt sich verleitet, diese für ein neues Projekt einmal auszu-

probieren. Dennoch ist das Zend Framework im professionellen Enterprise-

Bereich seit Jahren etabliert und wird von international tätigen Unternehmen

erfolgreich eingesetzt.

1.3.3 Welche Konzepte werden im ZF3 implementiert?

Das Zend Framework 3 implementiert mehrere technische Konzepte, die dem Ent-

wickler die Arbeit deutlich erleichtern. Diese Konzepte basieren zum Teil auf weit

verbreitete Entwurfsmustern, zum Teil aber auch auf bewährten Modellen der Soft-

wareentwicklung. Einen Überblick über einige grundlegende Konzepte im ZF3 finden

Sie in Abbildung 1.2.

3965-3.book Seite 35 Donnerstag, 6. Oktober 2016 1:19 13

Page 5: Zend Framework 3 – Das umfassende Handbuch

1 Einführung in das Zend Framework 3

36

Abbildung 1.2 Konzepte im Zend Framework 3

� Bei der Dependency Injection geht es darum, Abhängigkeiten von Klassen unter-

einander lose zu koppeln und zu injizieren, statt innerhalb einer Klasse die andere

zu instanziieren. Benötigt die Klasse CustomerTable eine Instanz von DbAdapter,

sollte die Klasse DbAdapter z. B. nicht innerhalb der Klasse CustomerTable instanzi-

iert werden (z. B. im Konstruktor). Stattdessen wird der DbAdapter außerhalb der

Klasse erzeugt und dann über den Konstruktor oder eine Setter-Methode injiziert.

Die Aufgabe der Injizierung von Abhängigkeiten bei der Instanziierung von Objek-

ten übernimmt der Service-Locator, der im Zend Framework in der Komponente

Zend\ServiceManager implementiert wird. In diesem Zusammenhang kommt auch

das Factory-Entwurfsmuster zum Einsatz.

� Mit der ereignisgesteuerten Entwicklung (engl.: event-driven architecture) ist es

möglich, die Funktionalitäten von Klassen lose zu koppeln. Dabei wird die Funkti-

onalität der anderen Klasse nicht direkt in einer Klasse aufgerufen. Stattdessen

wird ein Ereignis über den sogenannten Event-Manager verarbeitet. In diesem

Event-Manager sind verschiedene Event-Listener registriert, die auf die Ereignisse

lauschen und ihre Arbeit erst dann aufnehmen, sollte »ihr« Ereignis angestoßen

werden. Somit können in einem OrderService beim Speichern einer Bestellung

mithilfe eines Event-Managers der Versand von Bestellbestätigungen per E-Mail

oder die Prüfung und Aktualisierung der Warenwirtschaft angestoßen werden. Im

Zend Framework 3 übernimmt der Zend\EventManager diese Aufgaben, wobei die

Event-Listener auch das Observer-Entwurfsmuster implementieren.

Zend Framework 3Konzepte

DependencyInjection

Ereignis-gesteuerte

Entwicklung

Middleware

ModelView

Controller

Modularität

3965-3.book Seite 36 Donnerstag, 6. Oktober 2016 1:19 13

1.3 Warum das Zend Framework 3 einsetzen?

37

1� Um Funktionalitäten einer Anwendung zu kapseln und auch wiederverwendbar

zu machen, sollte eine Applikation modular aufgebaut sein. Diese Modularität

wird durch den Modul-Manager bereitgestellt. Dieser übernimmt das Laden und

Konfigurieren der Module. Die Module können dabei eine Bibliothek mit Klassen

und Interfaces bereitstellen, vollständige Funktionalitäten inklusive Controller

und View kapseln oder auch wiederkehrende Aufgaben wie das Logging oder den

Versand von E-Mails für eine Anwendung übernehmen. Der Zend\ModuleManagerist im Zend Framework 3 für das Laden und Ausführen aller Module zuständig.

� Die Trennung einer Anwendung in Model, View und Controller ist in der Webent-

wicklung weit verbreitet und basiert auf dem Model-View-Controller-Entwurfs-

muster (kurz MVC). Im Model wird die Geschäftslogik der Anwendung und

meistens auch die Persistierung der Daten implementiert. Der View ist für die Dar-

stellung zuständig und sollte nur Ausgabelogik enthalten, kann aber auch lesend

auf das Model zugreifen. Im Controller wiederum erfolgt das Zusammenspiel aller

Komponenten, wobei der Controller Daten an das Model übergibt bzw. vom

Model bekommt und diese an den View weiterleitet. Im Controller sollte aus-

schließlich Controller-Logik enthalten sein. Im Zend Framework 3 wird das MVC-

Entwurfsmuster in der Komponente Zend\Mvc implementiert.

� Beim Middleware-Konzept wird ein anderer Ansatz als beim klassischen MVC ver-

folgt. Die Anfrage (engl.: Request) an einen Server wird normalerweise durch das

Senden einer Antwort (engl.: Response) abgeschlossen. Die Idee hinter diesem Kon-

zept ist, dass sich die Middleware zwischen den Request und die Response einklinkt.

Dabei können beliebige Middleware-Container auch hintereinander ausgeführt

werden. Mit der Komponente Zend\Expressive hat das Zend Framework 3 somit eine

leichtgewichtige Alternative zur MVC-Implementation geschaffen. Zend\Expressivewird in diesem Zusammenhang auch als Zend Framework light bezeichnet.

Neben diesen grundlegenden Konzepten und Entwurfsmustern werden im Zend Fra-

mework 3 weitere Konzepte und Entwurfsmuster implementiert, auf die ich an geeig-

neter Stelle eingehe.

1.3.4 Wofür das Zend Framework einsetzen?

Das Zend Framework 3 ist sehr flexibel, und es gibt verschiedene Einsatzzwecke, bei

denen das ZF3 das Mittel Ihrer Wahl sein sollte.

� Sie können mit dem Zend Framework 3 klassische Webanwendungen implemen-

tieren. Dabei haben Sie die Wahl zwischen dem MVC-Ansatz mit Zend\Mvc und

einer PSR-7-kompatiblen Middleware-Anwendung auf Basis von Zend\Expressive.

� Das Zend Framework 3 unterstützt Sie auch bei der Einrichtung von RESTful Web-

services. Dabei haben Sie neben der MVC-Variante und der Middleware-Alterna-

tive auch die Wahl, das spezialisierte Apigility einzusetzen.

3965-3.book Seite 37 Donnerstag, 6. Oktober 2016 1:19 13

Page 6: Zend Framework 3 – Das umfassende Handbuch

1 Einführung in das Zend Framework 3

38

� Auch Konsolenanwendungen lassen sich mit dem Zend Framework 3 implemen-

tieren. Erneut können Sie zwischen MVC und Middleware wählen, haben aber mit

ZF\Console eine weitere Auswahlmöglichkeit.

Wie Sie sehen können, ist das Zend Framework 3 für sehr unterschiedliche Ein-

satzzwecke und Projekte geeignet. Details zu den verschiedenen Installationsvarian-

ten finden Sie auch in Abschnitt 1.7.

1.4 Aufbau des Buches

Das Buch ist in insgesamt sechs Teile und 24 Kapitel aufgeteilt. Sie können das Buch

sowohl von Anfang bis Ende lesen als auch sich gezielt die Teile und Kapitel heraus-

suchen, die Sie gerade am meisten interessieren. Dennoch sind Teil V und der An-

hang eher zum Nachschlagen als zum kompletten Durchlesen gedacht.

1.4.1 Teil I

Teil I, »Grundlagen«, enthält ein Kapitel.

� In Kapitel 1, »Einführung in das Zend Framework 3«, lernen Sie die Vorteile und

Gründe für den Einsatz des Zend Framework 3 kennen. Außerdem erfahren Sie

alles zu den technischen Voraussetzungen und den Installationsvarianten. Zudem

werden Ihnen alle Beispiel- und Übungsanwendungen vorgestellt.

1.4.2 Teil II

Teil II, »Middleware-Anwendungen«, enthält acht Kapitel.

� In Kapitel 2, »Middleware-Anwendungen einrichten«, steigen Sie in das Konzept

der Middleware-Anwendungen ein und installieren die Beispielanwendung.

Außerdem lernen Sie den Aufbau einer Zend\Expressive-Anwendung sowie der

Module kennen.

� In Kapitel 3, »Routing, Actions und Templates«, legen Sie ein neues Modul an

und richten das Routing für die Middleware-Anwendung mit Zend\Router ein.

Zudem werden die benötigten Aktionen für Zend\Expressive und Templates für

Zend\View erstellt, und die Middleware-Konfiguration wird umgesetzt.

� In Kapitel 4, »Datenbanken und Repositorys«, dreht sich alles um die Anbindung

der Middleware-Anwendung an eine Datenbank mit Zend\Db. Sie richten den

Datenbankadapter und Storage-Klassen ein. Sie implementieren die notwendigen

Repositorys und binden diese in die Aktionen ein.

� In Kapitel 5, »Formulare und Benutzereingaben«, wird die Middleware-Anwen-

dung um die Verarbeitung von Benutzereingaben erweitert. Sie erfahren, wie Sie

3965-3.book Seite 38 Donnerstag, 6. Oktober 2016 1:19 13

1.4 Aufbau des Buches

39

1Input-Filter mit Zend\InputFilter erstellen können und wie Sie sich von Zend\Formbeim Aufbau und der Ausgabe von Formularen unterstützen lassen können.

� In Kapitel 6, »Internationalisierung«, kümmern Sie sich um die Internationalisie-

rung einer Middleware-Anwendung mit Zend\I18n. Sie erfahren darin unter ande-

rem, wie Sie einen Sprachschlüssel in die Routen integrieren und den Locale für

die Anwendung setzen können. Außerdem erfahren Sie alles Wissenswerte zum

Übersetzen der Texte Ihrer Anwendung.

� In Kapitel 7, »Authentifizierung und Autorisierung«, erfahren Sie Details zur

Zugriffskontrolle Ihrer Benutzer. Dabei werden die Benutzerrechte mit Zend\Per-missions\Rbac und die Sessions mit Zend\Session konfiguriert. Zudem erfolgt die

Authentifizierung mit Zend\Authentication, und Sie erweitern die Middleware-

Pipeline um die Autorisierung Ihrer Benutzer.

� In Kapitel 8, »Zend\Expressive-Anwendung optimieren«, erhalten Sie hilfreiche

Tipps, wie Sie eine schnell gewachsene Middleware-Anwendung verbessern kön-

nen. Unter anderem wird ein mehrstufiges Layout eingerichtet, ein View-Helper

für die Formularausgabe integriert und Traits zur Codereduktion eingesetzt.

� In Kapitel 9, »Unit-Tests für Middleware-Anwendungen«, können Sie sich ganz

der Qualitätssicherung der Middleware-Anwendung widmen. Sie erfahren, wie Sie

erstellte Middleware-Aktionen und die Middleware für die Pipeline testen können.

Doch auch das Testen der Formulare und Modelklassen kommt dabei nicht zu kurz.

1.4.3 Teil III

Teil III, »MVC-Anwendungen«, enthält sieben Kapitel.

� In Kapitel 10, »MVC-Anwendung einrichten«, richten Sie eine MVC-Anwendung

mit Zend\Mvc ein. Dabei wird die Beispielanwendung installiert und der Aufbau der

Anwendung sowie der Module erläutert. Auch die eingesetzten Fremdmodule

werden vorgestellt.

� In Kapitel 11, »Controller und View«, wird die MVC-Anwendung um weitere Mo-

dule erweitert. Darin werden mit Zend\Mvc das Routing konfiguriert und Action-

Controller angelegt sowie Templates mit Zend\View erstellt. Außerdem werden eine

Paginierung mit Zend\Paginator und ein Menü mit Zend\Navigation integriert.

� In Kapitel 12, »Model-Layer implementieren«, werden die bisher statischen Daten

in der MVC-Anwendung durch einen mehrschichtigen Model-Layer ausgetauscht.

Es werden neue Entitäten erstellt und für deren Datenaustausch neue Hydratoren

mit Zend\Hydrator implementiert. Danach werden Storages mit Zend\Db\Table-Gateway aufgesetzt und in die Repositorys integriert.

� In Kapitel 13, »Formularverarbeitung im MVC«, wird die Möglichkeit geschaffen,

die vorhandenen Daten in der MVC-Anwendung auch ändern zu können. Auf Basis

von Zend\InputFilter wird die Eingabevalidierung und -filterung umgesetzt. Zudem

3965-3.book Seite 39 Donnerstag, 6. Oktober 2016 1:19 13

Page 7: Zend Framework 3 – Das umfassende Handbuch

1 Einführung in das Zend Framework 3

40

werden mit Zend\Form neue Formulare implementiert, ausgegeben und validiert.

Zudem werden der CKEditor für die HTML-Eingabe sowie Dateiuploads integriert.

� In Kapitel 14, »Internationalisierung im MVC«, wird die Internationalisierung der

MVC-Anwendung umgesetzt. Dabei werden im Wesentlichen das Routing überar-

beitet sowie die Textfragmente der Anwendung mit dem Translator von Zend\I18nübersetzt. Außerdem wird ein Sprachwechsler eingerichtet.

� In Kapitel 15, »Authentifizierung und Autorisierung im MVC«, wird die MVC-

Anwendung gegen unberechtigten Zugriff abgesichert. Die Benutzerrechte wer-

den mit Zend\Permissions\Acl konfiguriert, und die Authentifizierung wird mit

Zend\Authentication umgesetzt. Für die Authentifizierung und Autorisierung

kommt dabei der Zend\EventManager zum Einsatz. Zudem wird das Menü mit Zend\Navigation je nach Benutzerrolle reduziert und ein User-Widget zum einfachen

An- und Abmelden integriert.

� In Kapitel 16, »Tests für MVC-Anwendungen«, erfahren Sie, wie Sie Ihre MVC-

Anwendung mit Unit-Tests und Integrationstests absichern können. Dabei kommt

die Komponente Zend\Test in Kombination mit PHPUnit und DbUnit zum Einsatz.

1.4.4 Teil IV

Teil IV, »Weitere Themen«, enthält drei Kapitel.

� In Kapitel 17, »Migration vom ZF2 und ZF1«, erfahren Sie alles Wissenswerte zur

Migration Ihrer Anwendungen zum Zend Framework 3. Dabei wird sowohl die

Migration vom ZF2 zum ZF3 und vom ZF1 zum ZF3 beleuchtet als auch die Migration

einer MVC-Anwendung in einer Middleware-Anwendung mit Zend\Expressive.

� In Kapitel 18, »Webservices und Apigility«, lernen Sie drei Wege kennen, wie Sie

einen RESTful Webservice mit dem Zend Framework 3 implementieren können.

Das Kapitel zeigt den Aufbau eines Webservice in einer Zend\Mvc- sowie in einer

Zend\Expressive-Anwendung. Außerdem wird das Projekt Apigility vorgestellt.

� In Kapitel 19, »Konsolenanwendungen«, können Sie nachlesen, wie Sie auf Basis

der Komponente Zend\Console und des Tools ZF\Console eigene Konsolenanwen-

dungen mit dem Zend Framework 3 umsetzen können. Außerdem erfahren Sie,

wie Sie die Komponente Zend\Code für die Codegenerierung einsetzen können.

1.4.5 Teil V

Teil V, »Komponenten«, enthält ein Kapitel.

� In Kapitel 20, »Zend-Framework-Komponenten«, werden die Zend-Framework-

Komponenten kurz vorgestellt, die in diesem Buch eingesetzt werden. Die Einfüh-

rungen zeigen nur die Grundlagen, tiefere Details vor allem zur Integration in

Middleware- und MVC-Anwendungen bieten die anderen Teile des Buches.

3965-3.book Seite 40 Donnerstag, 6. Oktober 2016 1:19 13

1.5 Listings und Programmierstil

41

11.4.6 Anhang

Der Anhang enthält vier Kapitel.

� In Anhang A, »Objektorientierte Programmierung in PHP«, finden Sie Erläute-

rungen für einige grundlegende Begriffe und Konzepte aus der objektorientierten

Programmierung mit PHP.

� In Anhang B, »Architekturmuster und Entwurfsmuster«, werden verschiedene

Architektur- und Entwurfsmuster vorgestellt, die in diesem Buch oder innerhalb

vom Zend Framework 3 verwendet werden.

� In Anhang C, »Unit-Testing mit PHPUnit«, lernen Sie die wichtigsten Grundlagen

beim Einsatz von PHPUnit kennen. Neben der Konfiguration erfahren Sie auch

Wissenswertes zum Erstellen und Ausführen von Unit-Tests mit PHPUnit.

� In Anhang D, »Zend Framework 3 und Doctrine«, erfahren Sie, wie Sie Doctrine 2

in Ihre ZF3-Anwendungen integrieren können.

1.5 Listings und Programmierstil

Alle Listings werden im gesamten Buch hervorgehoben. Bitte beachten Sie, dass die

meisten DocBlocks für Klassen oder Methoden aus Platzgründen nicht im Buch abge-

druckt werden. Sie finden diese DocBlocks aber im Code der Beispiel- und Übungsan-

wendungen (siehe Abschnitt 1.8).

Da es sich beim überwiegenden Teil der Listings um reine PHP-Listings handelt, wird

das öffnende <?php-Tag nicht extra angeführt (siehe Listing 1.1). Das abschließende

?>-Tag ist sowieso in der Regel nicht nötig.

foreach ($values as $key => $value) {echo $key . ' => ' . $value;

}

Listing 1.1 Beispiel für ein reines PHP-Listing

Bei Listings, die sowohl PHP als auch HTML enthalten, werden die öffnenden und

schließenden PHP-Tags in der Regel angegeben. Beachten Sie hierbei wie in Listing 1.2

auch die alternative Schreibweise der Kontrollstrukturen.

<?php foreach ($values as $key => $value) : ?><?php echo $key; ?> => <?php echo $value; ?>

<?php endforeach; ?>

Listing 1.2 Beispiel für gemischtes PHP- und HTML-Listing

3965-3.book Seite 41 Donnerstag, 6. Oktober 2016 1:19 13

Page 8: Zend Framework 3 – Das umfassende Handbuch

1 Einführung in das Zend Framework 3

42

Zeilenlänge in Listings und im Beispielcode

Die Zeilenlänge der Listings im Buch ist auf maximal 75 Zeichen begrenzt und auch

die Listings in den Beispiel- und Übungsanwendungen haben ebenfalls eine Zeilen-

länge von höchstens 75 Zeichen, um ein einheitliches Bild zwischen Listings im Buch

und dem Code in den Repositorys zu gewährleisten. Details zu den Anwendungen

finden Sie in Abschnitt 1.8.

Kommandos, die Sie auf der Konsole (Linux), am Dienstprogramm Terminal (macOS)

oder an der Eingabeaufforderung (Windows) ausführen müssen, beginnen immer

mit einem vorangestellten $ und sind in der Regel nicht mit einer Listingunterschrift

versehen.

$ php --version

1.6 Technische Voraussetzungen

Die technischen Voraussetzungen für den Einsatz des Zend Frameworks sind über-

schaubar. Abbildung 1.3 bietet dazu einen Überblick.

Abbildung 1.3 Technische Voraussetzungen für das Zend Framework 3

In der Regel benötigen Sie neben PHP noch einen Webserver. Sie können dabei auf

den internen PHP CLI Server (Command Line Interface, auf Deutsch: Kommandozeile)

oder einen »richtigen« Webserver wie Apache 2 oder nginx zurückgreifen. Bei Bedarf

benötigen Sie zusätzlich eine relationale Datenbank wie MySQL oder eine dokumen-

tenorientierte Datenbank wie MongoDB. Außerdem sollten Sie mit Composer und Git

ein wenig vertraut sein.

3965-3.book Seite 42 Donnerstag, 6. Oktober 2016 1:19 13

Page 9: Zend Framework 3 – Das umfassende Handbuch

71

2

Kapitel 2

Middleware-Anwendungen einrichten

Middleware ist die Zend-Framework-Antwort auf viele neue leicht-

gewichtigere PHP-Frameworks, die den etablierten MVC-Frameworks

immer mehr Paroli bieten. Basierend auf der stetig voranschreitenden

Standardisierung in der PHP-Welt, bietet der Middleware-Ansatz vom

Zend Framework 3 eine weitere Alternative für die Umsetzung Ihrer

Anwendungen.

Neben den klassischen Model-View-Controller-Frameworks sind in den letzten Jah-

ren immer mehr neue und leichtgewichtigere PHP-Frameworks aus dem Boden

gesprossen. Ein Ansatz, der sich immer mehr durchsetzt und auch vom Zend Frame-

work 3 implementiert wird, ist die sogenannte Middleware.

Allgemein gesprochen ist eine Middleware eine Softwarekomponente, die zwei andere

Softwarekomponenten miteinander verbindet. Bezogen auf Webanwendungen im

Allgemeinen und auf das Zend Framework 3 im Speziellen, kann sich eine Middleware

zwischen den Request und die Response einer Anfrage an einen Webserver hängen.

Zudem kann Middleware auch in einer Pipeline aneinandergekoppelt und nacheinan-

der ausgeführt werden. Basis für die Middleware-Implementation im Zend Frame-

work 3 ist der PSR-7 der PHP FIG (siehe den folgenden Kasten).

2.1 Einstieg

2.1.1 Problemstellung

In diesem Kapitel zeige ich Ihnen die Lösung folgender Problemstellung:

� Auf einer neuen Website Vote My Pizza! sollen Besucher zwei zufällig ausgewählte

gegenübergestellte Bilder bewerten und kommentieren können.

� Wegen der einfachen Struktur dieses Projekts soll dies mit dem neuen Middle-

ware-Konzept umgesetzt werden. Dafür soll als Basis eine Middleware Skeleton

Application installiert werden.

� Sie erfahren alles zum Aufbau einer Zend Framework 3-Middleware-Anwendung.

3965-3.book Seite 71 Donnerstag, 6. Oktober 2016 1:19 13

Page 10: Zend Framework 3 – Das umfassende Handbuch

2 Middleware-Anwendungen einrichten

72

2.1.2 PSR-7 und Middleware

Die PHP FIG stellt eine Reihe von PSRs (PHP Standard Recommendations) bereit, um

die Entwicklung von PHP-Anwendungen zu standardisieren. Der Name bedeutet so-

mit, dass diese Standards nur als unverbindliche Empfehlungen zu verstehen sind.

Was ist die PHP FIG, und was bedeutet PSR?

Die PHP Framework Interop Group (PHP FIG, http://www.php-fig.org/) hat sich zum

Ziel gesetzt, für die PHP-Welt Empfehlungen für gemeinsame Standards zu schaffen.

Mitglieder der PHP FIG sind unter anderem Vertreter verschiedener PHP-Frameworks

wie Aura, CakePHP, Flow, Laravel, Symfony und Zend Framework, von Tools wie Com-

poser, Doctrine oder Phing sowie von Open-Source-Projekten wie Joomla, Neos, Sugar-

CRM oder Drupal.

Die Standardempfehlungen der PHP FIG werden PSR (PHP Standard Recommenda-

tions) genannt und idealerweise von möglichst vielen Mitgliedern und Nichtmitglie-

dern unterstützt. Die Implementierung der Standards funktioniert auf freiwilliger

Basis, sodass niemand – nicht mal die Mitglieder der PHP FIG – verpflichtet ist, alle

PSRs in allen Details umzusetzen.

Bekannt und bereits weitverbreitet sind die Autoloading-Standards PSR-0 und PSR-4

und die Empfehlungen für Code Styles PSR-1 und PSR-2. Weitere Empfehlungen für

Standards sind in Vorbereitung.

Eine relativ junge Standardempfehlung ist der PSR-7 (http://www.php-fig.org/psr/

psr-7/), die im Mai 2015 akzeptiert worden ist. In diesem Dokument wird eine Reihe

von Interfaces zur Darstellung von HTTP-Nachrichten, URIs, Server-Requests und

Dateiuploads definiert. Vereinfacht gesagt, vereinheitlicht der PSR-7 den Zugriff auf

HTTP-Nachrichten auf PHP-Ebene.

HTTP-Nachrichten (Requests und Responses) bilden das Gerüst der Webentwicklung

(siehe Abbildung 2.1). HTTP-Clients wie Webbrowser oder Tools wie cURL und Wget,

aber auch die von JavaScript unterstützten XMLHttpRequests generieren HTTP-Re-

quests und versenden diese an den Webserver. Der Webserver wiederum sendet an

den Client als Antwort eine HTTP-Response zurück.

Abbildung 2.1 HTTP-Request und HTTP-Response

HTTPResponse

HTTPRequest

WebserverClient

3965-3.book Seite 72 Donnerstag, 6. Oktober 2016 1:19 13

2.1 Einstieg

73

2

HTTP-Requests und -Responses sind seit Langem standardisiert. In der Vergangen-

heit hat jedoch nahezu jedes PHP-Framework oder CMS eine eigene PHP-Implemen-

tation zur Darstellung von HTTP-Nachrichten verwendet. Dies hat die übergreifende

Kommunikation zwischen PHP-Frameworks stark erschwert. Durch den PSR-7 wird

dieser Austausch in Zukunft für alle Projekte vereinfacht, die diese Empfehlung

unterstützen.

Der PSR-7 stellt die Basis dar, um Webprojekte als Middleware-Anwendungen umzu-

setzen. Dabei verbindet die Middleware quasi die Verarbeitung zwischen Request und

Response (siehe Abbildung 2.2). Sie kann dabei auf die Daten des Requests zugreifen

und zudem alle Daten der Response verändern.

Abbildung 2.2 Middleware im Kontext einer Webanwendung

Bei der Implementierung des Middleware-Konzepts kann zwischen drei Varianten

unterschieden werden.

� Bei der Lambda-Variante wird an die Middleware nur das Request-Objekt über-

geben und die Middleware gibt ein Response-Objekt zurück.

interface LambdaMiddlewareInterface{

/*** @param RequestInterface $request* @return ResponseInterface*/public function __invoke($request);

}

Listing 2.1 Middleware in der Lambda-Variante

� Die Injected Response-Variante unterscheidet sich darin, dass sowohl Request- als

auch Response-Objekt injiziert werden und das Response-Objekt in veränderter

Form zurückgegeben wird.

interface InjectedResponseMiddlewareInterface{

/*** @param RequestInterface $request* @param ResponseInterface $response

HTTPRequest

MiddlewareHTTP

Response

3965-3.book Seite 73 Donnerstag, 6. Oktober 2016 1:19 13

Page 11: Zend Framework 3 – Das umfassende Handbuch

2 Middleware-Anwendungen einrichten

74

* @return ResponseInterface*/public function __invoke($request, $response);

}

Listing 2.2 Middleware in der Injected-Response-Variante

� Die dritte Variante trägt den Namen Injected Next Middleware und erweitert die

vorherige Variante derart, dass auch die nächste auszuführende Variante injiziert

werden kann.

interface InjectedNextMiddlewareInterface{

/*** @param RequestInterface $request* @param ResponseInterface $response* @param callable $next* @return ResponseInterface*/public function __invoke($request, $response, $next = null);

}

Listing 2.3 Middleware in der Injected-Next-Middleware-Variante

Alle Varianten haben ihre jeweiligen Vor- und Nachteile, und somit ist je nach Anfor-

derung eine andere Variante zu bevorzugen. Im Zend Framework 3 wird die dritte

Variante implementiert, da diese am flexibelsten von allen drei Varianten ist und das

Aneinanderkoppeln von mehreren Middleware-Komponenten ermöglicht.

Was ist eine Middleware-Pipeline?

Eine Middleware zwischen Request und Response ist zwar gut, eine Middleware-Pipe-

line ist aber besser.

Sie können in einer Middleware-Pipeline eine ganze Reihe von Middleware-Kom-

ponenten hintereinander ausführen lassen. Dies entspricht dem Konzept der dritten

Variante Injected Next Middleware. Abbildung 2.3 zeigt dies anhand eines Beispiels

mit einer Middleware-Pipeline, welche drei Middlewares nacheinander ausführt:

� Die Routing Middleware führt das Routing der Anwendung aus.

� Die Authorization Middleware führt die Autorisierung der Benutzer durch und kann

bei fehlenden Zugriffsrechten den Prozess auch abbrechen, um eine Fehlerseite

auszugeben.

� Die Dispatching Middleware verarbeitet die Anfrage auf Basis des Routings und

der Daten aus dem Request.

3965-3.book Seite 74 Donnerstag, 6. Oktober 2016 1:19 13

2.2 Installation der Beispielanwendung

75

2

Abbildung 2.3 Middleware-Pipeline mit Routing, Autorisierung, Dispatching

In einer Middleware-Pipeline können Sie zudem Middlewares gruppieren und die Rei-

henfolge bei der Ausführung direkt durch Prioritäten definieren.

2.1.3 Komponenten

Zum besseren Verständnis dieses Kapitels sollten Sie mit folgenden Zend-Framework-

Komponenten vertraut sein:

� Zend\Config (siehe Abschnitt 20.4)

� Zend\Diactoros (siehe Abschnitt 20.7)

� Zend\Expressive (siehe Abschnitt 20.9)

� Zend\ServiceManager (siehe Abschnitt 20.21)

� Zend\Stratigility (siehe Abschnitt 20.23)

2.2 Installation der Beispielanwendung

Der normale Weg für die Einrichtung einer neuen Middleware-Anwendung wäre die

Ausführung des Installers für Zend\Expressive. Es ist jedoch nicht mit vertretbarem

Aufwand möglich, in den folgenden Beispielen auf alle Varianten einzugehen. Zudem

werden einige Dateien aus der generierten Skeleton Application für die Beispielan-

wendung nicht benötigt. Deshalb zeige ich Ihnen direkt die Installation der Beispielan-

wendung Vote My Pizza!.

Beachten Sie, dass Sie mindestens PHP 5.6 installiert haben sollten. Ältere Versionen

von Zend\Expressive laufen auch noch mit PHP 5.5 (siehe auch Abschnitt 1.6.1), Sie

sollten aber die neueste Version von Zend\Expressive bevorzugen. Außerdem kann

es passieren, dass bei der Installation Fehler wie der folgende angezeigt werden:

The requested PHP extension dom is missing from your system.

In diesem Fall fehlt eine PHP-Erweiterung, die von einer der Komponenten vorausge-

setzt wird. Konkret fehlt hier die DOM-Erweiterung. Schauen Sie für die Installation

von PHP-Erweiterungen bitte auch in Abschnitt 1.6.1.

HTTPRequest

RoutingMiddleware

AuthorizationMiddleware

DispatchingMiddleware

HTTPResponse

3965-3.book Seite 75 Donnerstag, 6. Oktober 2016 1:19 13

Page 12: Zend Framework 3 – Das umfassende Handbuch

2 Middleware-Anwendungen einrichten

76

2.2.1 Installation unter Ubuntu Linux

Unter Ubuntu Linux ist die Installation schnell erledigt.

1. Wechseln Sie zuerst in ein Verzeichnis, in das Sie das Projekt installieren möchten:

$ cd /home/devhost

2. Klonen Sie das Projekt mit Git. Geben Sie dabei das Unterverzeichnis zf3buch.vote-

my-pizza an, da dieses Verzeichnis im weiteren Verlauf des Buches ebenfalls ver-

wendet wird.

$ git clone https://github.com/zf3buch/vote-my-pizzazf3buch.vote-my-pizza

3. Wechseln Sie nun in das neue Unterverzeichnis zf3buch.vote-my-pizza, und instal-

lieren Sie alle Abhängigkeiten mit dem Composer (siehe auch Abschnitt 1.6.7).

$ cd zf3buch.vote-my-pizza$ composer install

4. Setzen Sie ausreichende Schreibrechte auf folgende Verzeichnisse.

$ sudo chmod 777 –R data/

2.2.2 Installation unter OS X und macOS Sierra

Die Installation unter OS X und macOS Sierra entspricht im Wesentlichen derjenigen

unter Linux und ist ebenfalls schnell erledigt. Wechseln Sie mit

$ cd ~/Sites

in das Verzeichnis für das Projekt. Der Befehl zur Änderung der Zugriffsrechte lautet

auf dem Mac:

$ chmod -R 777 data/

2.2.3 Installation unter Windows

Unter Windows sieht die Vorgehensweise ähnlich aus.

1. Zuerst wechseln Sie in ein übergeordnetes Verzeichnis für das Projekt:

$ cd C:\devhost

2. Nun folgen Sie den Schritten 2. bis 3. der obigen Installationsanleitung für Ubuntu

Linux. Das abschließende Setzen der Schreibrechte ist unter Windows in der Regel

nicht erforderlich.

3965-3.book Seite 76 Donnerstag, 6. Oktober 2016 1:19 13

2.2 Installation der Beispielanwendung

77

2

$ git clone https://github.com/zf3buch/vote-my-pizzazf3buch.vote-my-pizza

$ cd zf3buch.vote-my-pizza$ composer install

GitHub-API-Limitierung

Es kann sein, dass Sie bei der Installation des Projekts auf eine Fehlermeldung stoßen,

die in etwa wie folgt lautet:

Could not fetch [LINK1], please create a GitHub OAuth token to go over theAPI rate limit. Head to [LINK2] to retrieve a token. It will be stored in[File1] for future use by Composer.

Zudem werden Sie aufgefordert, einen Token einzugeben. Wenn Sie (¢) drücken,

geht es zwar weiter, aber beim nächsten zu installierenden Paket erscheint die Mel-

dung erneut.

Kopieren Sie bitte den [LINK2], und öffnen Sie die Seite in Ihrem Browser. Sie werden

aufgefordert, sich bei GitHub einzuloggen. Nach dem Einloggen können Sie den ge-

wünschten Token erstellen und kopieren. Leider benötigen Sie für diesen Vorgang

einen GitHub-Account.

Fügen Sie den Token in den Prompt in der Konsole ein, und schließen Sie die Eingabe

ab. Danach sollte die Meldung nicht erneut erscheinen.

2.2.4 Virtual Host einrichten

Im nächsten Schritt müssen Sie das Projekt über einen Webserver für den Virtual Host

http://zf3buch.vote-my-pizza erreichbar machen. Dabei haben Sie vielfältige Möglich-

keiten:

� PHP CLI Server (siehe Abschnitt 1.6.2)

� Apache 2 (siehe Abschnitt 1.6.3)

� nginx (siehe Abschnitt 1.6.4)

� Vagrant mit einer virtuellen Maschine wie VirtualBox oder VMware

� Entwicklungsumgebung wie XAMPP oder Zend Server

Welche Variante Sie wählen, hängt ganz von Ihren persönlichen Bedürfnissen und

Anforderungen ab. An dieser Stelle können nicht alle Varianten detailliert vorgestellt

werden. In den genannten Abschnitten finden Sie weitere Details zu den jeweiligen

Webservern. Sie sollten aber die Einrichtung eines Virtual Host und nicht den PHP

CLI Server bevorzugen.

3965-3.book Seite 77 Donnerstag, 6. Oktober 2016 1:19 13

Page 13: Zend Framework 3 – Das umfassende Handbuch

2 Middleware-Anwendungen einrichten

78

Tipp für Einrichtung mit Apache 2 und nginx

Wenn Sie den Apache 2 verwenden, achten Sie beim Einrichten des Virtual Host da-

rauf, dass die Umgebungsvariable APPLICATION_ENV gesetzt wird (siehe Abschnitt

1.6.3). Wie Sie diese Umgebungsvariable für nginx senden können, erfahren Sie in

Abschnitt 1.6.4.

Nach der Einrichtung sollte nach dem Aufruf von http://zf3buch.vote-my-pizza eine

Website wie in Abbildung 2.4 angezeigt werden.

Abbildung 2.4 Beispielanwendung »Vote My Pizza!«

2.3 Aufbau einer Zend\Expressive-Anwendung

Nach der erfolgreichen Installation werde ich Ihnen nun den Aufbau der Zend\Expres-

sive-Anwendung genauer erläutern. Am einfachsten ist dies für Sie, wenn Sie dafür in

Ihrer IDE (siehe auch Abschnitt 1.6.8) ein neues Projekt einrichten, das auf das Projekt-

verzeichnis verweist (unter Linux /home/devhost/zf3buch.vote-my-pizza, unter OS X

und macOS Sierra /Users/[Accountname]/zf3buch.vote-my-pizza oder unter Windows

C:/devhost/zf3buch.vote-my-pizza).

In Tabelle 2.1 sind die wichtigen Verzeichnisse und Dateien aufgelistet. Weitere De-

tails zu den einzelnen Bereichen finden Sie in den jeweils genannten Abschnitten.

Datei/Verzeichnis Erläuterung

/config/ Das Konfigurationsverzeichnis enthält die Anwendungskonfi-

guration (Details siehe Abschnitt 2.3.3).

Tabelle 2.1 Dateien und Verzeichnisse auf oberster Projektebene

3965-3.book Seite 78 Donnerstag, 6. Oktober 2016 1:19 13

2.3 Aufbau einer Zend\Expressive-Anwendung

79

2

2.3.1 »composer.json«-Datei

Die composer.json-Datei in Ihrem Projektverzeichnis definiert, welche Pakete und

Abhängigkeiten Sie für Ihr Projekt einsetzen. In Listing 2.4 finden Sie die gekürzte

composer.json-Datei aus der Beispielanwendung.

{"name": "zf3buch/vote-my-pizza","description": "Vote My Pizza Example Application for the ZF3","license": "The MIT License (MIT)","authors": [

{"name": "Ralf Eggert","email": "[email protected]",

/data/ Das Datenverzeichnis enthält vergängliche Daten wie Cache-

Dateien, Session-Daten, Logs usw. (Details siehe Abschnitt 2.3.4).

/modules/ Im Modulverzeichnis sind die Zend\Expressive-Module für diese

Anwendung abgelegt. Die Module können wiederum eigene Kon-

figurationen, Klassen, Templates oder Tests enthalten (Details

siehe Abschnitt 2.3.6).

/public/ Das öffentliche Verzeichnis enthält den Front-Controller

index.php sowie die Assets wie Grafiken, CSS- und JavaScript-

Dateien (Details siehe Abschnitt 2.3.5).

/vendor/ Das Vendorverzeichnis enthält Fremdmodule, Komponenten,

Librarys usw. Alle Abhängigkeiten, die Sie über den Composer

installieren, landen in diesem Verzeichnis. Wird bei neuem Com-

poser-Update aktualisiert (Details siehe Abschnitt 2.3.2).

/.gitignore Benennt alle Dateien und Verzeichnisse, die nicht in ein

Git-Repository eingecheckt werden sollen.

/composer.json Benennt alle Abhängigkeiten, die vom Composer installiert und

aktualisiert werden. Dies können die PHP-Version, die Zend-

Framework-Version oder Fremdmodule sein, die Sie verwenden

möchten (Details siehe Abschnitt 2.3.1).

/composer.lock Enthält die Informationen über alle Abhängigkeiten, die vom

Composer installiert wurden.

Datei/Verzeichnis Erläuterung

Tabelle 2.1 Dateien und Verzeichnisse auf oberster Projektebene (Forts.)

3965-3.book Seite 79 Donnerstag, 6. Oktober 2016 1:19 13

Page 14: Zend Framework 3 – Das umfassende Handbuch

2 Middleware-Anwendungen einrichten

80

"homepage": "http://www.travello.de","role": "Developer"

}],"require": {

"php": "^5.5 || ^7.0","roave/security-advisories": "dev-master","zendframework/zend-expressive": "^1.0","zendframework/zend-expressive-helpers": "^2.0","zendframework/zend-stdlib": "^2.7 || ^3.0","zendframework/zend-expressive-zendrouter": "^1.0","zendframework/zend-servicemanager": "^2.7.3 || ^3.0","ocramius/proxy-manager": "^1.0 || ^2.0","zendframework/zend-expressive-zendviewrenderer": "^1.0","zendframework/zend-component-installer": "^0.3.0","mtymek/expressive-config-manager": "^0.4.0","zendframework/zend-config": "^2.6"

},"require-dev": {

"phpunit/phpunit": "^5.0","squizlabs/php_codesniffer": "^2.3","filp/whoops": "^1.1"

},"autoload": {

"psr-4": {"Application\\": "modules/Application/src/"

}},"autoload-dev": {/* ... */},"scripts": {/* ... */}

}

Listing 2.4 »composer.json« aus Beispielanwendung »Vote My Pizza!«

An dieser Stelle würde es den Rahmen dieses Abschnitts sprengen, wenn ich Ihnen

jede Einzelheit der composer.json-Konfiguration erläutere. Die Konfigurationsmög-

lichkeiten des Composers sind sehr vielfältig, sodass Sie für einen tieferen Einblick in

alle Details die Dokumentation unter https://getcomposer.org/doc/04-schema.md

aufrufen sollten. Deshalb folgt nur eine Erläuterung der wichtigsten Punkte:

� Unter dem Parameter require werden alle Abhängigkeiten für das Projekt definiert.

Dies kann die PHP-Version sein, aber auch der Name eines Pakets mit vorangestell-

tem Vendor. Wenn Sie keine weiteren Composer-Repositorys verwenden, müssen

diese Pakete auf der Website https://packagist.org/ zu finden sein, damit sie vom

3965-3.book Seite 80 Donnerstag, 6. Oktober 2016 1:19 13

2.3 Aufbau einer Zend\Expressive-Anwendung

81

2

Composer installiert werden können. Neben dem Namen des Pakets geben Sie

zusätzlich noch die gewünschte Versionsnummer an.

� Unter der Angabe require-dev werden Abhängigkeiten definiert, die nur auf der

Entwicklungsebene benötigt und nicht auf dem Produktivsystem installiert wer-

den sollen.

� Mit dem Parameter autoload können Sie weitere Verzeichnisse für das Composer-

Autoloading definieren. Dies ist z. B. nützlich für Verzeichnisse außerhalb von /ven-

dor/. In der Beispielanwendung wird das Source-Verzeichnis für den Namensraum

Application festgelegt.

Composer-Konfiguration

Weitere Details zu den Konfigurationsmöglichkeiten und wie Sie dem Composer mit-

teilen, Pakete direkt aus einem Git-Repository zu installieren, finden Sie in der Doku-

mentation unter https://getcomposer.org/doc/.

2.3.2 Vendorverzeichnis

Das Vendorverzeichnis /vendor/ enthält alle externen Komponenten und Librarys, die

über den Composer installiert und aktuell gehalten werden. Achten Sie unbedingt da-

rauf, dass Sie in diesem Verzeichnis niemals Änderungen per Hand vornehmen, da

diese bei einem erneuten Update durch den Composer überschrieben werden können.

Möchten Sie die definierten Abhängigkeiten ändern, passen Sie die composer.json-

Datei (siehe Abschnitt 2.3.1) an und führen danach ein Composer-Update durch.

Die Pakete werden in einer zweistufigen Verzeichnisstruktur installiert, wobei der

Name vom Vendor übergeordnet wird und darunter die Verzeichnisse mit den Paket-

namen abgelegt werden. Unter dem Vendornamen zendframework werden somit alle

Zend-Framework-Komponenten installiert. Dadurch wird bei einer hohen Zahl an

Paketen eine gewisse Struktur durch die Vendornamen vorgegeben.

Einige Besonderheiten im Vendorverzeichnis sollten Sie beachten:

� Die Datei /vendor/autoload.php wird vom Composer bei jeder Aktualisierung neu

erstellt. Sie wird von dem Front-Controller /public/index.php eingelesen und stellt

für Ihre Anwendung das Autoloading für alle im Vendorverzeichnis installierten

Pakete bereit. Diese Datei sollten Sie niemals manuell verändern, da sie bei jedem

Composer-Update überschrieben wird.

� Im Verzeichnis /vendor/composer/ werden durch ein Composer-Update weitere

Dateien aktualisiert, die von der /vendor/autoload.php-Datei verwendet werden.

Diese Dateien werden ebenfalls für das Autoloading der installierten Pakete benö-

tigt und sollten nicht von Ihnen geändert werden.

3965-3.book Seite 81 Donnerstag, 6. Oktober 2016 1:19 13

Page 15: Zend Framework 3 – Das umfassende Handbuch

2 Middleware-Anwendungen einrichten

82

� Die Datei /vendor/.gitignore stellt sicher, dass die installierten Pakete nicht in das

Git-Repository für Ihr Projekt eingecheckt werden. Dies würde zum einen Ihr Re-

pository nur unnötig aufblähen, und zum anderen sind diese Pakete ja bereits in

der Regel in einem anderen Repository versioniert.

Beim Verteilen Ihrer Anwendung auf den Produktivserver dürfen Sie das Vendorver-

zeichnis aber nicht ausschließen, da Ihre Anwendung nach dem Deployment ansons-

ten nicht lauffähig wäre.

2.3.3 Konfigurationsverzeichnis für Anwendung

Im Konfigurationsverzeichnis /config/ liegt die Konfiguration für die Anwendung.

Dieses Verzeichnis sollten Sie nicht mit dem Konfigurationsverzeichnis für Module

verwechseln (siehe Abschnitt 2.4.1).

Aufteilung der Konfiguration auf mehrere Dateien

Die Konfiguration der Anwendung ist bewusst auf mehrere Dateien aufgeteilt, damit

die Konfigurationen für unterschiedliche Aspekte wie Abhängigkeiten und Middle-

ware-Pipeline sauber voneinander getrennt sind. Sie können die gesamte Konfigura-

tion in einer einzelnen Datei zusammenfassen, müssen dann aber mit einer etwas

unübersichtlicheren Datei rechnen.

Der Einstieg in das Bereitstellen der Konfiguration erfolgt über die Datei contai-

ner.php, die vom Front-Controller geladen wird. Diese wird in Listing 2.5 dargestellt

und zeigt, wie die Konfigurationsdatei config.php geladen und der Zend\ServiceMana-

ger damit konfiguriert wird. Zudem wird die gesamte geladene Konfiguration eben-

falls im Service-Manager mit dem Bezeichner config abgelegt.

use Zend\ServiceManager\ServiceManager;

$config = require PROJECT_ROOT . '/config/config.php';

$container = new ServiceManager($config['dependencies']);$container->setService('config', $config);

return $container;

Listing 2.5 Datei »/config/container.php« konfiguriert Service-Manager

Das eigentliche Laden der Konfigurationsdateien übernimmt die Datei config.php,

die in Listing 2.6 zu sehen ist. Darin wird der ConfigManager von Zend\Expressive ein-

gesetzt, der das Laden der Konfiguration aus den Modulen stark vereinfacht.

3965-3.book Seite 82 Donnerstag, 6. Oktober 2016 1:19 13

2.3 Aufbau einer Zend\Expressive-Anwendung

83

2

use Zend\Expressive\ConfigManager\ConfigManager;use Zend\Expressive\ConfigManager\PhpFileProvider;

$cachedConfigFile = PROJECT_ROOT . '/data/cache/app_config.php';

$pattern = PROJECT_ROOT . '/config/autoload/{{,*.}global,{,*.}'. APPLICATION_ENV . ',{,*.}local}.php';

$configManager = new ConfigManager([

Application\ConfigProvider::class,new PhpFileProvider($pattern),

],$cachedConfigFile

);

return new ArrayObject($configManager->getMergedConfig(), ArrayObject::ARRAY_AS_PROPS

);

Listing 2.6 Datei »/config/config.php« lädt alle Konfigurationsdateien

Was ist der ConfigManager?

Der Konfigurationsmanager ist eine leichtgewichtige Erweiterung für Zend\Expres-sive, mit der das Einlesen und Zusammenführen von Konfigurationsdaten aus unter-

schiedlichen Quellen sehr erleichtert wird. Mit den sogenannten Config-Providern

können Konfigurationsdateien, aber auch Klassen geladen werden, die Konfigurati-

onsdaten bereitstellen. Zudem ermöglicht die Komponente das Caching der gelese-

nen Konfiguration.

Der ConfigManager ist in der Beispielanwendung bereits integriert und aktiviert. Die

offizielle Zend\Expressive Skeleton Application (siehe Abschnitt 1.7.4) wird den Kon-

figurationsmanager erst ab dem Release 1.1 integrieren. Sollten Sie für Ihre eigene

Zend\Expressive-Anwendung den ConfigManager einsetzen wollen, können Sie ihn

direkt mit dem Composer installieren:

$ composer require mytek/expressive-config-manager

Der ConfigManager unterstützt das Caching der gesamten Konfiguration, sodass der

Name der einzusetzenden Cache-Datei konfiguriert werden muss. Zum Einsatz kom-

men zwei Provider-Klassen, welche die Konfiguration bereitstellen:

� Die Klasse Application\ConfigProvider liegt im Application-Modul und muss eine

__invoke()-Methode implementieren, welche die Konfiguration des Moduls zu-

3965-3.book Seite 83 Donnerstag, 6. Oktober 2016 1:19 13

Page 16: Zend Framework 3 – Das umfassende Handbuch

2 Middleware-Anwendungen einrichten

84

rückgibt. Ob die Konfiguration direkt in der Klasse notiert oder aus einer Konfigu-

rationsdatei gelesen wird, bleibt Ihnen überlassen (siehe auch Abschnitt 2.4.2).

� Die Klasse Zend\Expressive\ConfigManager\PhpFileProvider ermöglicht die Angabe

eines Suchmusters für Konfigurationsdateien. Das angegebene Suchmuster liest

alle Dateien, die einer der folgenden Regeln entsprechen:

– Sie lauten global.php oder enden auf .global.php.

– Sie verwenden den Wert der Konstanten APPLICATION_ENV mit nachfolgendem

.php (diese Konstante wird im Front-Controller gesetzt, siehe Abschnitt 2.3.5).

Dies könnte z. B. development.php oder production.php sein. Alternativ können

sie entsprechend auf .development.php oder .production.php enden.

– Sie lauten local.php oder enden auf .local.php.

– Dabei werden zuerst die Dateien geladen, die auf global.php enden, und zuletzt

die Dateien, die auf local.php enden.

� Die Inhalte aus den beiden Providern werden in einem großen Array zusammen-

geführt.

Egal, ob die Konfigurationsdaten aus der Caching-Datei gelesen wurden oder neu ge-

laden werden mussten, am Ende werden sie gleichermaßen zurückgegeben.

Warum eine dreistufige Struktur für Konfigurationsdateien?

Diese dreistufige Struktur der Konfigurationsdateien hat ein paar wichtige Vorteile

(siehe Abbildung 2.5).

Abbildung 2.5 Dreistufige Struktur der Konfigurationsdateien

� Konfigurationsdaten, die auf allen Ebenen gebraucht werden, können Sie in den

(*.)global.php-Dateien ablegen.

� Konfigurationsdaten, die nur in einer bestimmten Umgebung gebraucht werden,

wie auf dem Entwicklungsserver oder dem Produktivserver, können Sie in den

entsprechenden Dateien ablegen, die auf (*.)development.php bzw. (*.)produc-

tion.php enden.

(*.)local.php

(*.)development.php

(*.)global.php

3965-3.book Seite 84 Donnerstag, 6. Oktober 2016 1:19 13

2.3 Aufbau einer Zend\Expressive-Anwendung

85

2

� Konfigurationsdateien, die auf (*.)local.php enden, sollten nie in die Versionsver-

waltung eingecheckt werden. Sie sind für Änderungen gedacht, die ein Entwick-

ler nur für seine spezielle Umgebung benötigt. Dies könnte z. B. der Fall sein,

wenn ein Entwickler eine eigene Datenbank verwendet und nicht auf die Daten

der Entwicklungsdatenbank zugreifen kann.

In dem Verzeichnis /config/autoload/ finden Sie mehrere Dateien, die unterschiedli-

che Aspekte der Middleware-Anwendung konfigurieren.

� Die Datei dependencies.global.php enthält die Konfiguration für die Services der

Anwendung (siehe Listing 2.7). An dieser Stelle werden einige Helper- und Middle-

ware-Klassen, der Template-Renderer, der Router sowie das Anwendungsobjekt

konfiguriert. Hierbei wird überwiegend Gebrauch von der Class Name Resolution

gemacht (siehe Kasten »Class Name Resolution« in Abschnitt 20.21.1).

return ['dependencies' => [

'invokables' => [Zend\Expressive\Router\RouterInterface::class =>

Zend\Expressive\Router\ZendRouter::class,

Zend\Expressive\Helper\ServerUrlHelper::class =>Zend\Expressive\Helper\ServerUrlHelper::class,

],

'factories' => [Zend\Expressive\Application::class =>

Zend\Expressive\Container\ApplicationFactory::class,

'Zend\Expressive\FinalHandler' =>Zend\Expressive\Container\TemplatedErrorHandlerFactory

::class,

Zend\Expressive\Template\TemplateRendererInterface::class =>Zend\Expressive\ZendView\ZendViewRendererFactory::class,

Zend\View\HelperPluginManager::class =>Zend\Expressive\ZendView\HelperPluginManagerFactory

::class,

Zend\Expressive\Helper\UrlHelper::class =>Zend\Expressive\Helper\UrlHelperFactory::class,

3965-3.book Seite 85 Donnerstag, 6. Oktober 2016 1:19 13

Page 17: Zend Framework 3 – Das umfassende Handbuch

2 Middleware-Anwendungen einrichten

86

Zend\Expressive\Helper\ServerUrlMiddleware::class =>Zend\Expressive\Helper\ServerUrlMiddlewareFactory::class,

Zend\Expressive\Helper\UrlHelperMiddleware::class =>Zend\Expressive\Helper\UrlHelperMiddlewareFactory::class,

],]

];

Listing 2.7 Konfiguration der Services

Diese Datei ist der richtige Ort für die weitere Konfiguration Ihrer Services, die Sie

anwendungsweit einsetzen möchten. Wenn Sie in Ihrer Anwendung nicht den

Zend\ServiceManager als Dependency-Injection-Container, sondern eine der Alter-

nativen ausgewählt haben, wird die Datei eventuell etwas anders aussehen.

� Die Datei local.php.dist ist für die persönliche Konfiguration des Entwicklers ge-

dacht. Wenn Sie diese Datei einsetzen möchten, müssen Sie zuerst das Suffix .dist

entfernen. Beachten Sie, dass die Datei ohne Suffix nicht in die Versionsverwal-

tung eingecheckt werden sollte.

� Die Datei middleware-pipeline.global.php ist für die Konfiguration der Middleware-

Pipeline gedacht. Damit können Sie festlegen, welche Middleware zusätzlich vor

dem Routing, zwischen Routing und Dispatching und nach dem Dispatching auto-

matisch ausgeführt werden soll (siehe Listing 2.8). Wenn Sie z. B. eine Middleware

für die Authentifizierung Ihrer Anwendung verwenden möchten, können Sie

diese hier einklinken. Die vorhandenen Middlewares sorgen für die korrekte Kon-

figuration einiger Helper-Klassen sowie das Routing und Dispatching. Durch die

Festlegung der Prioritäten können Sie auf die Reihenfolge der Verarbeitung selbst

Einfluss nehmen.

return ['middleware_pipeline' => [

'always' => ['middleware' => [

Zend\Expressive\Helper\ServerUrlMiddleware::class,],'priority' => 10000,

],

'routing' => ['middleware' => [

Zend\Expressive\Container\ApplicationFactory::ROUTING_MIDDLEWARE,

Zend\Expressive\Helper\UrlHelperMiddleware::class,

3965-3.book Seite 86 Donnerstag, 6. Oktober 2016 1:19 13

2.3 Aufbau einer Zend\Expressive-Anwendung

87

2

Zend\Expressive\Container\ApplicationFactory::DISPATCH_MIDDLEWARE,

],'priority' => 1,

],

'error' => ['middleware' => [

// Add error middleware here.],'error' => true,'priority' => -10000,

],],

];

Listing 2.8 Konfiguration für die Middleware-Pipeline

� Die Datei zend-expressive.global.php enthält zusätzliche Optionen für die Konfigu-

ration der Zend\Expressive-Anwendung. Neben einem debug-Parameter ist dies vor

allem die Angabe config_cache_enabled, mit der das Caching der Konfiguration

aktiviert werden kann.

Der Aufbau und die Struktur der Konfigurationsdateien im Verzeichnis /config/auto-

load/ sind im Wesentlichen nur ein Vorschlag. Sie können auch einen anderen Auf-

bau wählen und die Konfiguration anders strukturieren. Sie sollten nur aufpassen,

dass es nicht auf die eine oder andere Weise unübersichtlich wird.

2.3.4 Datenverzeichnis

Im Datenverzeichnis /data/ einer Zend\Expressive-Anwendung können Sie alle ver-

gänglichen Daten ablegen. Nach dem Löschen dieser Daten sollte die Anwendung

weiterhin funktionieren. Folgende Daten würden sich für das Datenverzeichnis an-

bieten:

� Cache-Dateien

� Log-Dateien

� Session-Dateien

� temporäre Dateien

Legen Sie für jede Art von Dateien ein eigenes Verzeichnis an. So können Sie z. B.

/data/cache/ für Ihre Cache-Dateien oder /data/session/ für die Session-Daten ver-

wenden. Stellen Sie sicher, dass die Verzeichnisse zwar in Ihre Versionsverwaltung

aufgenommen werden. Die Dateien selbst sollten aber ignoriert werden. Wenn Sie

3965-3.book Seite 87 Donnerstag, 6. Oktober 2016 1:19 13

Page 18: Zend Framework 3 – Das umfassende Handbuch

2 Middleware-Anwendungen einrichten

88

Git einsetzen, legen Sie dafür eine Datei /data/.gitignore mit folgendem Inhalt an

(siehe Listing 2.9).

*!.gitignore

Listing 2.9 ».gitignore«-Datei für Unterverzeichnis im Datenverzeichnis

Wenn Sie nur mit einstufigen Unterverzeichnissen arbeiten, können Sie alle Dateien

aus diesen Unterverzeichnissen löschen, und Ihre Anwendung sollte weiterhin funk-

tionieren.

Mehrstufige Datenverzeichnisse

Manchmal kann es jedoch sinnvoll sein, dass Sie eines der Verzeichnisse weiter

unterteilen möchten. Vielleicht möchten Sie den Cache gliedern und mit den Ver-

zeichnissen /data/cache/dir1/ und /data/cache/dir2/ arbeiten. In diesem Fall dürfen

Sie die .gitignore-Datei aus Listing 2.9 nicht im Verzeichnis /data/cache/ ablegen.

Stattdessen legen Sie die Datei in den beiden Unterverzeichnissen ab.

Alternativ könnten Sie auch eine komplexere .gitignore-Datei im obersten Verzeich-

nis /data ablegen, welche die gesamte Struktur definiert. Diese könnte so aussehen

wie das Beispiel in Listing 2.10.

*!cache!cache/dir1!cache/dir2!session!.gitignore

Listing 2.10 ».gitignore«-Datei für Datenverzeichnis

Sie müssen jedoch genau darauf achten, dass Sie diese Datei aktuell halten, wenn

sich etwas an der Verzeichnisstruktur ändert. Andernfalls kann es passieren, dass Sie

aus Versehen vergängliche Dateien in Git einchecken.

2.3.5 Öffentliches Verzeichnis

Im öffentlichen Verzeichnis /public/ liegen alle über den Webserver für den Besucher

aufrufbaren Dateien. Wichtigste Dateien sind der Front-Controller index.php und die

Apache 2-Konfiguration .htaccess (wenn Sie Apache 2 als Webserver einsetzen). Dazu

kommen dann CSS- und JavaScript-Dateien, Grafiken, Fonts usw.

Die Apache 2-Konfiguration steuert die Zugriffe aus dem Front-Controller. Betrach-

ten Sie somit zuerst die Konfiguration in der .htaccess-Datei in Listing 2.11.

3965-3.book Seite 88 Donnerstag, 6. Oktober 2016 1:19 13

2.3 Aufbau einer Zend\Expressive-Anwendung

89

2

# Remove slash from endRewriteEngine onRewriteRule ^(.+)/$ http://%{HTTP_HOST}/$1 [R=301,L]

# Redirect requests to index.php if not a file or dirRewriteEngine OnRewriteCond %{REQUEST_FILENAME} -s [OR]RewriteCond %{REQUEST_FILENAME} -l [OR]RewriteCond %{REQUEST_FILENAME} -dRewriteRule ^.*$ - [NC,L]

# Ignore static content and don't redirect it to the app.RewriteCond %{REQUEST_URI} ^(css|js|img|assets)/ [OR]RewriteCond %{REQUEST_FILENAME} \.(js|map|css|ico|gif|jpg|png|eot|svg|ttf)$RewriteRule ^.*$ - [NC,L]

RewriteRule ^.*$ index.php [NC,L]

Listing 2.11 Apache 2-Konfiguration für Middleware-Anwendung

In dieser Datei sind im Wesentlichen Umschreibregeln für die Zugriffe auf den Apa-

che 2-Webserver definiert.

� Zuerst werden alle Zugriffe, die einen Slash am Ende haben, auf dieselbe Adresse

ohne den Slash umgeleitet. Dadurch wird vermieden, dass dieselbe Seite von

Suchmaschinen wie Google als unterschiedliche Adressen aufgefasst wird.

� In der zweiten Regel werden Dateien, Verzeichnisse und symbolische Links, die

tatsächlich existieren, direkt ausgeliefert.

� In der dritten Regel wird sichergestellt, dass statische Inhalte wie Grafiken, CSS-

Dateien usw. ebenfalls direkt ausgeliefert werden.

� Alle anderen Anfragen werden durch den Front-Controller in der Datei index.php

ausgeführt.

Der schon mehrfach erwähnte Front-Controller ist in Listing 2.12 zu sehen. Er wird als

Front-Controller bezeichnet, da alle Anfragen (die nicht bereits durch die .htaccess-

Datei abgefangen wurden) durch diese index.php-Datei verarbeitet werden. Sie ist

damit der Einstieg in die Middleware-Anwendung.

use Interop\Container\ContainerInterface;

define('PROJECT_ROOT', realpath(__DIR__ . '/..'));

define('APPLICATION_ENV', (getenv('APPLICATION_ENV')

3965-3.book Seite 89 Donnerstag, 6. Oktober 2016 1:19 13

Page 19: Zend Framework 3 – Das umfassende Handbuch

2 Middleware-Anwendungen einrichten

90

? getenv('APPLICATION_ENV'): 'production')

);

if (php_sapi_name() === 'cli-server'&& is_file(__DIR__ . parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH))

) {return false;

}

require_once PROJECT_ROOT . '/vendor/autoload.php';

chdir(dirname(__DIR__));

$container = require PROJECT_ROOT . '/config/container.php';

$app = $container->get(Zend\Expressive\Application::class)->run();

Listing 2.12 Front-Controller »index.php« für Middleware-Anwendung

� Zu Beginn werden zwei Konstanten definiert.

– PROJECT_ROOT verweist auf das oberste Verzeichnis der Anwendung und erleich-

tert das Festlegen von Verzeichnispfaden.

– APPLICATION_ENV definiert die aktive Umgebung. Dabei wird geprüft, ob eine

Umgebungsvariable vorhanden ist, und im positiven Fall wird diese übernom-

men. Diese Konstante dient zur Unterscheidung zwischen Entwicklungsserver

und Produktivserver sowie weiterer Umgebungen wie z. B. einen Testserver.

Statt einer Apache 2-Umgebungsvariablen können Sie die Unterscheidung alter-

nativ auch anhand der IP-Adresse oder des Servernamens vornehmen.

� Der nächste Block ist dafür zuständig, dass die Anwendung auch läuft, wenn Sie

den PHP CLI Server verwenden (siehe Abschnitt 1.6.2).

� Als Nächstes wird die Autoloading-Datei aus dem Vendorverzeichnis geladen, die

der Composer bei der Installation erstellt und beim Update aktualisiert. Somit müs-

sen Sie sich nicht selbst um das Autoloading für alle Abhängigkeiten im Vendorver-

zeichnis kümmern. Diese Aufgabe übernimmt der Composer für Sie. Zum korrekten

Arbeiten mit Verzeichnissen wird zudem per chdir() das aktuelle Arbeitsverzeich-

nis korrekt gesetzt.

� Nach diesen Vorbereitungen beginnt die eigentliche Ausführung der Middleware-

Anwendung. Dafür wird der Rückgabewert der Datei /config/container.php an die

Variable $container übergeben (siehe Abschnitt 2.3.3). Der Rückgabewert ent-

spricht einer Instanz des gewählten Dependency-Injection-Containers, in der Bei-

spielanwendung ist dies eine Zend\ServiceManager-Instanz.

3965-3.book Seite 90 Donnerstag, 6. Oktober 2016 1:19 13

2.4 Aufbau eines Zend\Expressive-Moduls

91

2

� Im letzten Schritt wird über den Container die Instanz der Zend\Expressive-

Anwendung angefordert und ausgeführt. Damit beginnt die eigentliche Verarbei-

tung der Anfrage durch die Middleware-Anwendung.

Zu guter Letzt sind im Verzeichnis /public/assets/ alle Grafiken, CSS- und JavaScript-

Dateien usw. abgelegt, die für die Anwendung benötigt werden.

2.3.6 Modulverzeichnis

Alle Zend\Expressive-Module liegen im Modulverzeichnis /modules/. Dabei werden

alle Dateien eines Moduls in einem eigenen Verzeichnis gruppiert. In der installier-

ten Beispielanwendung ist mit dem Application-Modul bisher ein einziges Modul

vorhanden. Der genaue Aufbau eines Moduls wird im folgenden Abschnitt 2.4 aus-

führlich erläutert.

Sie können in diesem Verzeichnis neue Module anlegen, die jedoch dem folgenden

Aufbau entsprechen sollten.

2.4 Aufbau eines Zend\Expressive-Moduls

Der Aufbau der Module für die installierte Zend\Expressive-Anwendung ist standar-

disiert worden. Tabelle 2.1 listet die Verzeichnisse und wichtigsten Dateien auf, die in

einem der Module enthalten sein können. Weitere Details zu den einzelnen Berei-

chen finden Sie in den jeweils genannten Abschnitten.

Datei/Verzeichnis Erläuterung

/config/ Das Konfigurationsverzeichnis enthält die Konfiguration für das

Modul (Details siehe Abschnitt 2.4.1).

/src/ Das Source-Verzeichnis enthält die weiteren Klassen für die

Anwendung (Details siehe Abschnitt 2.4.3). In diesem Verzeich-

nis ist auch die Konfigurationsklasse für das Modul zu finden

(siehe Abschnitt 2.4.2).

/templates/ Das Template-Verzeichnis enthält die Templates für die

Anwendung (Details siehe Abschnitt 2.4.4).

/test/ Das Testverzeichnis enthält alle Testklassen der Anwendung.

Details zum Testen einer Zend\Expressive-Anwendung finden

Sie in Kapitel 9, »Unit-Tests für Middleware-Anwendungen«.

Tabelle 2.2 Dateien und Verzeichnisse auf Modulebene

3965-3.book Seite 91 Donnerstag, 6. Oktober 2016 1:19 13

Page 20: Zend Framework 3 – Das umfassende Handbuch

381

11

Kapitel 11

Controller und View

Nachdem das Zend Framework 3-MVC-Projekt eingerichtet ist, geht

es nun ans Eingemachte. Es wird ein neues Modul erstellt. Zudem

möchten die benötigten Controller und deren Views erstellt und das

Routing der Anwendung muss konfiguriert werden.

Die Basis einer MVC-Anwendung mit dem Zend Framework 3 sind die Module, die

durch den Modul-Manager geladen und konfiguriert werden.

11.1 Einleitung

Bei neuen Projekten sollten Sie sich immer möglichst frühzeitig fundierte Gedanken

zur Struktur Ihrer Anwendung machen. Welche Module brauchen Sie, und wie teilen

Sie diese auf? Welche Funktionen möchten Sie Ihren Nutzern bereitstellen, und wie bil-

den Sie diese auf die passenden Controller und Aktionen ab? Und was ist mit der Aus-

gabe im View?

11.1.1 Problemstellung

Die Beispielanwendung Zend Framework Center soll Unternehmen die Möglichkeit

bieten, Jobs und Projekte auszuschreiben, für die Personal gesucht wird. Jede Aus-

schreibung erfolgt in Form einer Annonce. Interessenten können für eine Annonce

eine Anfrage an das ausschreibende Unternehmen stellen.

Aus dieser Kurzbeschreibung ergibt sich folgende Problemstellung für dieses Kapitel:

� Die wichtigste Anforderung an die Website für das Zend Framework Center ist die

Darstellung der Annoncen für Jobs und Projekte. Diese sollen getrennt voneinan-

der in einer Liste und einzeln dargestellt werden können.

� Auf der Startseite sollen ein zufällig ausgewählter Job und ein zufälliges Projekt

angezeigt werden.

� Zusätzlich muss ein Administrationsbereich eingerichtet werden, in dem die

Annoncen gelistet, bearbeitet, gelöscht, gesperrt, freigegeben sowie neue angelegt

werden können.

� Um diese Anforderungen umzusetzen, müssen die benötigten Module, Controller

und Views angelegt werden. Zudem muss das Routing konfiguriert werden.

3965-3.book Seite 381 Donnerstag, 6. Oktober 2016 1:19 13

Page 21: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

382

� Für die Darstellung der Annoncen soll vorerst auf fixe Beispieldaten zurückgegrif-

fen werden.

In Abbildung 11.1 ist eine mögliche Darstellung für die Startseite der Beispielanwen-

dung zu sehen.

Abbildung 11.1 Startseite der Beispielanwendung »Zend Framework Center«

11.1.2 Komponenten

Zum besseren Verständnis dieses Kapitels sollten Sie mit folgenden Zend-Frame-

work-Komponenten vertraut sein:

� Zend\Config (siehe Abschnitt 20.4)

� Zend\ModuleManager (siehe Abschnitt 20.15)

� Zend\Mvc (siehe Abschnitt 20.16)

� Zend\Navigation (siehe Abschnitt 20.17)

� Zend\Paginator (siehe Abschnitt 20.18)

� Zend\View (siehe Abschnitt 20.26)

11.2 Module erstellen und konfigurieren

Im ersten Schritt zeige ich Ihnen, was bei der Strukturierung der Anwendung in

Module zu beachten ist. Hier sollten Sie lieber etwas länger nachdenken, statt durch

3965-3.book Seite 382 Donnerstag, 6. Oktober 2016 1:19 13

11.2 Module erstellen und konfigurieren

383

11

einen Schnellschuss zukünftige Entwicklungen zu erschweren. Danach zeige ich

Ihnen, wie Sie die Module anlegen und konfigurieren.

11.2.1 Benötigte Funktionen ermitteln

Bei genauerer Betrachtung der Problemstellung in Abschnitt 11.1 ergeben sich für den

ersten Schritt bei der Umsetzung der Beispielanwendung Zend Framework Center fol-

gende Funktionen:

� Liste mit Annoncen anzeigen

� Detailseite einer Annonce anzeigen

� neue Annonce anlegen

� bestehende Annonce ändern

� bestehende Annonce löschen

� bestehende Annonce freigeben/sperren

� Annoncen administrieren

Nachdem die grundlegenden Funktionen notiert sind, geht es darum, diese sinnvoll

auf Module und Controller aufzuteilen. Das Stellen von Anfragen für eine Annonce

wird an dieser Stelle erst einmal außen vor gelassen.

11.2.2 Funktionen auf Module aufteilen, Schritt 1

Eine erste denkbare Unterteilung ist in Abbildung 11.2 zu sehen. Bei dieser Struktur

wird ein Modul Advert mit den beiden Controllern DisplayController und AdminCon-troller erstellt. Auf die beiden Controller werden die Funktionen zur Anzeige der

Annoncen sowie zur Bearbeitung und Administrierung aufgeteilt. Diese Struktur

geht auch davon aus, dass der Model-Layer (der in Kapitel 12, »Model-Layer imple-

mentieren«, behandelt wird) im selben Modul abgelegt wird. Diese Struktur hat den

Vorteil, dass alle Funktionen und die Datenhaltung für die Annoncen an einem Ort

liegen und Sie nicht lange suchen müssen, wenn Sie etwas ändern wollen.

Abbildung 11.2 Modulare Aufteilung der Funktionen, Schritt 1

DisplayController

AdminController

ZendFramework

Center Model-LayerAnnoncen

ModulAdvert

3965-3.book Seite 383 Donnerstag, 6. Oktober 2016 1:19 13

Page 22: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

384

Doch die Struktur hat auch einige Nachteile, welche durch folgende Fragestellungen

offenbart werden:

1. Wenn später Benutzer und Rollen eingeführt werden und ein Administrator bei

der Verwaltung der Annoncen diese anschauen möchte, muss dann der Display-

Controller ausgeführt werden?

2. Wenn ein Unternehmen eine neue Annonce aufruft, muss der Benutzer dann auf

den AdminController zugreifen, um sie bearbeiten zu können?

3. Wenn der Administrationsbereich von der reinen Darstellung in eine andere

Anwendung ausgelagert werden muss, muss das Advert-Modul in beiden Anwen-

dungen vorgehalten werden, obwohl Teile davon nicht überall gebraucht werden?

4. Soll später ein REST Webservice eingerichtet werden, muss dann ein zusätzlicher

RestController in das Modul Advert integriert werden, weil der Model-Layer dort

integriert ist?

Zugegeben, diese Fragestellungen greifen vielleicht zu weit in eine mögliche, unbe-

kannte Zukunft vor. Es gibt bekanntlich das berühmte Zitat von Donald Knuth,

einem US-amerikanischem Informatiker:

Premature optimization is the root of all evil.

Frei ins Deutsche übersetzt bedeutet dies:

Vorzeitige Optimierung ist die Wurzel allen Übels.

Diese Aussage bedeutet im Wesentlichen, dass Entwickler sich in vielen Fällen früh-

zeitig zu viele Gedanken machen über die Dinge, die da eines Tages einmal auf sie

zukommen mögen. Eine Aufteilung der Funktionalitäten auf weitere Module birgt

die Gefahr einer vorzeitigen Optimierung, die vielleicht niemals benötigt wird.

Dennoch sollten Sie in dieser frühen Projektphase einmal genauer überlegen, ob

diese vorzeitige Optimierung wirklich so böse ist oder ob sie nicht doch Sinn machen

könnte, sollten niemals wieder neue Anforderungen für dieses Projekt bei Ihnen auf

den Tisch kommen.

Eine feinere Aufteilung schadet nicht wirklich. Im Wesentlichen wird die vorhandene

Funktionalität lediglich anders strukturiert. Der zusätzliche Aufwand hält sich in

Grenzen, wird Ihnen in Zukunft aber viele Stunden Refaktorierung und Kopfschmer-

zen ersparen.

11.2.3 Funktionen auf Module aufteilen, Schritt 2

Somit können Sie die Struktur dadurch optimieren, dass Sie statt einem überladenen

Modul drei Module mit klarer Abgrenzung zueinander erstellen. In Abbildung 11.3

übernimmt das Modul AdvertFrontend die Funktionen, die für die öffentlich zugäng-

liche Website benötigt werden. Dies sind neben der Anzeige der Annoncen auch das

3965-3.book Seite 384 Donnerstag, 6. Oktober 2016 1:19 13

11.2 Module erstellen und konfigurieren

385

11

Anlegen und Ändern für Unternehmen. Alle administrativen Funktionen werden im

Modul AdvertBackend zusammengefasst. Beide Module greifen für den Zugriff auf

die Daten auf das Modul AdvertModel zu. Dies erleichtert den Zugriff auf die Daten

ungemein.

Abbildung 11.3 Modulare Aufteilung der Funktionen, Schritt 2

Was sind schlanke Controller und fette Models?

Wenn Sie genau aufgepasst haben, werden Sie sicher feststellen, dass es nun zwei

Funktionen zum Anlegen von Annoncen geben wird. Einmal für die Unternehmen im

ModifyController vom AdvertFrontend-Modul und einmal für die Administratoren

im ModifyController vom AdvertBackend-Modul. Das riecht doch förmlich nach

dupliziertem Code, oder nicht?

Es ist natürlich legitim, den Großteil der Geschäftslogik für die Verarbeitung beim

Anlegen einer neuen Annonce direkt im Controller zu platzieren. Doch das sollten Sie

vermeiden, da Ihre Controller ansonsten viel duplizierten Code enthalten. Der Groß-

teil der Geschäftslogik sollte im Model und damit im AdvertModel-Modul gekapselt

werden. Der Controller sollte schön schlank bleiben, während das Model schön fett

werden kann. Das erleichtert Ihnen auf lange Sicht die Arbeit in Ihrem Projekt.

Mit der Struktur aus Abbildung 11.3 im Hinterkopf zeige ich Ihnen nun, wie Sie die

benötigten Module anlegen und konfigurieren.

DisplayController

ModifyController

ModifyController

DisplayController

ZendFramework

Center

Model-LayerAnnoncen

ModulAdvertFrontend

ModulAdvertBackend

ModulAdvertModel

3965-3.book Seite 385 Donnerstag, 6. Oktober 2016 1:19 13

Page 23: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

386

11.2.4 Module anlegen und konfigurieren

Um die folgenden Listings besser nachvollziehen zu können, wechseln Sie für die

Zend Framework Center-Beispielanwendung auf den Branch chapter_11_01. Danach

sollten Sie ein Composer-Update ausführen, um das Projekt und Autoloading zu

aktualisieren.

$ cd /home/devhost/zf3buch.zendframework-center$ git checkout chapter_11_01 -f$ composer update

Am besten öffnen Sie als Nächstes Ihre IDE mit dem Projekt und darin das /module/-

Verzeichnis. Dort sollten Sie die drei neuen Module Advert, AdvertBackend und

AdvertModel wiederfinden. Die Verzeichnisstruktur ist in Abbildung 11.4 dargestellt.

Abbildung 11.4 Verzeichnisstruktur der drei neuen Module

Alle drei Module folgen einem ähnlichen Aufbau (siehe auch Abschnitt 10.5). Ledig-

lich das AdvertModel-Modul benötigt kein /view/-Unterverzeichnis, weil in dem

Modul nur Businesslogik und keinerlei Ausgabe enthalten sein soll. Die Konfigurati-

onsdateien der Module geben nur ein leeres Array zurück. Dieses wird im weiteren

Verlauf nach und nach mit Konfiguration befüllt.

Exemplarisch für alle drei Module zeigt das Listing 11.1 die Module-Klasse aus dem

AdvertFrontend-Modul. Es werden in dieser Modul-Klasse nur zwei der Feature-Inter-

faces vom Zend\ModuleManager implementiert (siehe auch Tabelle 20.8 in Abschnitt

20.15). Mit der Ausführung der init()-Methode, die nach jedem Laden eines Moduls

direkt aufgerufen wird, wird die neue Konstante ADVERT_FRONTEND_MODULE_ROOT defi-

niert. Diese verweist auf das Wurzelverzeichnis des Moduls. Die getConfig()-

Methode wiederum lädt die Konfigurationsdatei, wobei darin gleich die neue Kon-

stante zum Einsatz kommt. Dies ist deshalb möglich, weil diese Methode erst nach

der Initialisierungsmethode aufgerufen wird.

namespace AdvertFrontend;

use Zend\Config\Factory;

3965-3.book Seite 386 Donnerstag, 6. Oktober 2016 1:19 13

11.2 Module erstellen und konfigurieren

387

11

use Zend\ModuleManager\Feature\ConfigProviderInterface;use Zend\ModuleManager\Feature\InitProviderInterface;use Zend\ModuleManager\ModuleManagerInterface;

class Module implements ConfigProviderInterface, InitProviderInterface{

public function init(ModuleManagerInterface $manager){

define('ADVERT_FRONTEND_MODULE_ROOT', __DIR__ . '/..');}

public function getConfig(){

return Factory::fromFile(ADVERT_FRONTEND_MODULE_ROOT . '/config/module.config.php'

);}

}

Listing 11.1 »Module«-Klasse aus dem »AdvertFrontend«-Modul

Die anderen Verzeichnisse der Module sind noch leer. Die .gitkeep-Dateien stellen

sicher, dass das Verzeichnis in Git eingecheckt werden kann. Dies ist für leere Ver-

zeichnisse ansonsten nicht möglich.

Um diese neuen Module zu aktiveren, müssen sie dem Modul-Manager noch in der

Anwendungskonfiguration bekannt gemacht werden. Für den Entwicklungsserver

ist dafür die Anwendungskonfigurationsdatei /config/application.config.php zustän-

dig. Listing 11.2 zeigt, wie die drei neuen Module aktiviert werden.

return ['modules' => [

'Zend\Session','Zend\Router','Zend\Validator','AdvertFrontend','AdvertBackend','AdvertModel','Application',

],/* ... */

];

Listing 11.2 Module in Anwendungskonfiguration aktivieren

3965-3.book Seite 387 Donnerstag, 6. Oktober 2016 1:19 13

Page 24: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

388

Im letzten Schritt müssen Sie noch das Autoloading für den Composer konfigurieren.

Dafür werden im Abschnitt autoload die Source-Verzeichnisse der drei neuen Module

entsprechend definiert. Dies ist in Listing 11.3 zu sehen.

{"autoload": {"psr-4": {"Application\\": "module/Application/src/","AdvertFrontend\\": "module/AdvertFrontend/src/","AdvertBackend\\": "module/AdvertBackend/src/","AdvertModel\\": "module/AdvertModel/src/","Scripts\\": "script/"

}},

}

Listing 11.3 Autoloading der neuen Module in der »composer.json«

Danach muss ein Composer-Update erfolgen, um das Autoloading bereitzustellen.

$ composer update

Nach der Aktivierung aller Module und der Konfiguration des Autoloadings rufen Sie

in Ihrem Browser die Adresse http://zf3buch.zendframework-center/ erneut auf.

Danach prüfen Sie die Anzeige der geladenen Module in der Toolbar unten links auf

dem Bildschirm. Dort sollten jetzt auch die drei neuen Module aufgeführt sein (siehe

Abbildung 11.5).

Abbildung 11.5 Toolbar mit neuen Modulen

Damit sind die Einrichtung und die Konfiguration der neuen Module für die Bei-

spielanwendung abgeschlossen.

3965-3.book Seite 388 Donnerstag, 6. Oktober 2016 1:19 13

11.3 Routing konfigurieren

389

11

11.3 Routing konfigurieren

Im nächsten Schritt muss das Routing für die Module und Controller konfiguriert

werden. Beim Routing geht es, wie bereits weiter oben erwähnt, darum, auf Basis der

URL eines Requests zu ermitteln, welche Controller und welche Aktion darin ausge-

führt werden soll.

11.3.1 Routen für die Module erstellen

Um die Routen-Konfiguration direkt nachvollziehen zu können, wechseln Sie am

besten auf den Branch chapter_11_02 der Beispielanwendung. Danach führen Sie ein

Composer-Update aus, damit das Projekt aktualisiert wird.

$ cd /home/devhost/zf3buch.zendframework-center$ git checkout chapter_11_02 -f$ composer update

Wenn Sie sich noch einmal Abbildung 11.3 auf Seite 265 genauer anschauen, werden

für das AdvertFrontend-Modul zwei Controller benötigt. Jeder dieser Controller wie-

derum soll einige Aktionen enthalten, die bisher noch nicht genauer spezifiziert

waren. Diese Aufgabe übernimmt nun das Routing, denn hierbei werden alle erlaub-

ten Controller und Aktionen festgelegt. Da das Routing auf den ersten Blick recht

komplex wirken kann, zeige ich es Ihnen in zwei Teilen.

Listing 11.4 zeigt das Routing aus der /config/module.config.php-Datei des Advert-

Frontend-Moduls. In dem Listing wurde der Konfigurationsteil für die untergeordne-

ten child_routes ausgeblendet (siehe auch Listing 11.5). Die Konfiguration der Routen

beginnt auf der dritten Ebene mit den beiden Routen-Bezeichnern advert-job für die

Darstellung der Jobs und advert-project für die Projekte. Da diese Routen auf der

obersten Ebene definiert sind, werden sie auch als übergeordnete oder Parent-Rou-

ten bezeichnet.

use AdvertFrontend\Controller\DisplayController;use Zend\Router\Http\Literal;

return ['router' => [

'routes' => ['advert-job' => [

'type' => Literal::class,'options' => [

'route' => '/job','defaults' => [

'controller' => DisplayController::class,

3965-3.book Seite 389 Donnerstag, 6. Oktober 2016 1:19 13

Page 25: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

390

'action' => 'index','type' => 'job',

],],'may_terminate' => true,'child_routes' => [

/* ... */],

],'advert-project' => [

'type' => Literal::class,'options' => [

'route' => '/project','defaults' => [

'controller' => DisplayController::class,'action' => 'index','type' => 'project',

],],'may_terminate' => true,'child_routes' => [

/* ... */],

],],

],];

Listing 11.4 Routen-Konfiguration für »AdvertFrontend«-Modul (Teil 1)

Die Routen advert-job und advert-project setzen sich aus den folgenden Bestandtei-

len zusammen:

� Als Typ wird Zend\Router\Http\Literal verwendet. Durch diesen Routen-Typ wird

festgelegt, dass die URL exakt mit einer in den Optionen definierten Zeichenkette

übereinstimmen muss.

� In den Optionen werden verschiedene Parameter festgelegt.

– Der Wert der Route (route) legt die Zeichenkette fest, mit der die URL genau

übereinstimmen muss, damit dieser Teil der Route als gültig erkannt werden

kann. Dies sind /job bzw. /project.

– Bei den Vorgabewerten (defaults) werden die Namen des auszuführenden Con-

trollers und der Aktion festgelegt. Beim Controllernamen wird der Name der

Controllerklasse angegeben. Beide verwenden übrigens denselben Controller.

3965-3.book Seite 390 Donnerstag, 6. Oktober 2016 1:19 13

11.3 Routing konfigurieren

391

11

Zudem wird ein Vorgabewert type definiert, der sich bei den beiden Routen

unterscheidet und im Controller verwendet wird.

� Mit dem Parameter may_terminate wird festgelegt, dass das Routing abgebrochen

werden darf, sollte eine URL nur aus dem Teil dieser übergeordneten Route beste-

hen. Ist der Wert auf true festgelegt, werden eventuell vorhandene untergeord-

nete Routen nicht mehr geprüft, und die Route ist trotzdem gültig. Beispiel:

– Ist may_terminate auf true festgelegt, wird die Request-URL http://zf3buch.zend-

framework-center/job als gültige Route akzeptiert.

– Ist may_terminate auf false festgelegt, wird die Request-URL http://zf3buch.zend-

framework-center/job nicht als gültige Route akzeptiert.

� Mit dem Parameter child_routes werden die untergeordneten Routen definiert,

die auch als Child-Routes bezeichnet werden. Diese folgen demselben Aufbau wie

die übergeordnete Route. Daraus resultiert auch, dass Routen theoretisch beliebig

tief verschachtelt sein dürfen.

Die definierten Child-Routes der advert-job-Parent-Route sind in Listing 11.5 zu

sehen. Für die advert-project-Parent-Route sind die Child-Routes identisch. Sie

sehen, dass unter der Parent-Route advert-job drei Child-Routes mit den Namen

modify, detail und page definiert worden sind. Sie folgen, wie bereits erwähnt, dem-

selben Aufbau wie die Parent-Routen und erben dabei auch die unter Optionen defi-

nierten Vorgabewerte.

use AdvertFrontend\Controller\ModifyController;use Zend\Router\Http\Segment;

return [/* ... */

'child_routes' => ['modify' => [

'type' => Segment::class,'options' => [

'route' => '/:action[/:id]','defaults' => [

'controller' => ModifyController::class,],'constraints' => [

'action' => '(add|edit|delete)','id' => '[1-9][0-9]*',

],],

],

3965-3.book Seite 391 Donnerstag, 6. Oktober 2016 1:19 13

Page 26: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

392

'detail' => ['type' => Segment::class,'options' => [

'route' => '/detail[/:id]','defaults' => [

'action' => 'detail',],'constraints' => [

'id' => '[1-9][0-9]*',],

],],'page' => [

'type' => Segment::class,'options' => [

'route' => '/:page','constraints' => [

'page' => '[1-9][0-9]*',],

],],

],

/* ... */];

Listing 11.5 Routen-Konfiguration für »AdvertFrontend«-Modul (Teil 2)

Die erste Child-Route modify setzt sich aus den folgenden Bestandteilen zusammen.

� Als Routen-Typ wird Zend\Router\Http\Segment verwendet. Anders als eine Literal-

Route verwenden diese keine feste Zeichenkette, sondern Segmente, die sich durch

einen vorangestellten Doppelpunkt auszeichnen und durch einen Schrägstrich

voneinander getrennt werden.

� In den Optionen werden mehrere Parameter festgelegt.

– Die Route ist mit /:action[/:id] definiert. Diese Notation besagt, dass das erste

Segment den Bezeichner action und das zweite den Bezeichner id bekommt.

Das zweite Segment wird durch die ummantelnden eckigen Klammern als opti-

onales Segment deklariert.

– Bei den Vorgabewerten (defaults) wird der Name des auszuführenden Control-

lers neu festgelegt. Der Name der Aktion sowie der Typ werden aus den Vorga-

bewerten der übergeordneten Route übernommen.

3965-3.book Seite 392 Donnerstag, 6. Oktober 2016 1:19 13

11.3 Routing konfigurieren

393

11

– Die Bedingungen (constraints) legen fest, welche Werte die beiden Segmente

annehmen dürfen. Der Wert für das Segment action darf somit nur add, edit

oder delete sein. Der Wert für das optionale Segment id darf nur aus beliebig

vielen Ziffern bestehen, wobei die erste Ziffer keine 0 sein darf.

� Die Parameter may_terminate und child_routes sind für diese Route nicht gesetzt.

Sie könnten die Unterteilung an dieser Stelle jedoch fortführen und zusätzliche

Ebenen hinzufügen.

Die zweite Child-Route detail ist ähnlich aufgebaut. Hierbei ist der Wert für die

Aktion jedoch nicht variabel. Zudem wird der Vorgabewert für den Controller nicht

überschrieben, sondern von der Parent-Route übernommen. Stattdessen wird der

Wert für die Aktion fest mit detail vorgegeben.

Die dritte Child-Route page verwendet nur ein Segment page, das die Seitenzahl für

die Paginierung enthalten soll. Auch diese Route überschreibt die Vorgabewerte der

Parent-Route nicht.

Tabelle 11.1 demonstriert, welche URL auf welche der Routen passt. Außerdem wer-

den die Werte für die einzelnen Routen-Parameter angegeben. Parent- und Child-

Routen werden durch einen Schrägstrich miteinander verknüpft. Dabei dürfen Sie

den Namen der passenden Route nicht mit der URL verwechseln, auch wenn beide

einen Schrägstrich enthalten. Zudem wurde das führende http://zf3buch.zendframe-

work-center aufgrund der besseren Übersichtlichkeit nicht mit aufgeführt.

URL Passende Route Controller Action Type Id Page

/job advert-job Display index job - 1

/job/3 advert-job/page Display index job - 3

/job/detail/123 advert-job/detail Display detail job 123 -

/job/add advert-job/modify Modify add job - -

/job/edit/123 advert-job/modify Modify edit job 123 -

/job/delete/123 advert-job/modify Modify delete job 123 -

/job/123/display keine - - - - -

/job/update/123 keine - - - - -

/job/list keine - - - - -

Tabelle 11.1 Gültige und ungültige URLs mit passenden Routen

3965-3.book Seite 393 Donnerstag, 6. Oktober 2016 1:19 13

Page 27: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

394

Die Routen-Konfiguration für das AdvertBackend-Modul sieht prinzipiell sehr ähnlich

aus. Details schauen Sie sich direkt an, indem Sie die Datei /config/module.config.php

aus dem AdvertBackend-Modul öffnen. Der wichtigste Unterschied ist die andere Be-

zeichnung der Parent-Route. Diese lautet nämlich advert-backend und spiegelt damit

auch die Zugehörigkeit zu dem Modul wider. Anhand der Ausführungen dieses Ab-

schnitts sollten Sie keine größeren Schwierigkeiten haben, die Routen-Konfiguration

des Moduls nachvollziehen zu können.

Das AdvertModel-Modul hat keinerlei Routen-Konfiguration, da es ausschließlich

Geschäftslogik für das Model enthalten wird.

11.3.2 Routen-Konfiguration testen

Sie können die Konfiguration des Routings testen. Dafür müssen Sie die einzelnen

URLs aus Tabelle 11.1 im Browser eingeben und das Ergebnis in der Toolbar am Seiten-

ende überprüfen (siehe Abbildung 11.6).

Abbildung 11.6 Routen-Konfiguration mit Toolbar prüfen

Wenn Sie diese URLs aufrufen, wird Ihnen zwar eine Fehlerseite angezeigt, die besagt,

dass die angeforderte Seite nicht gefunden werden kann. In der Toolbar am Ende der

Seite bekommen Sie auch angezeigt, dass die Anfrage zu einem 404-Fehler führte.

Doch direkt daneben können Sie das Ergebnis des Routings einsehen. Dies folgt

einem festen Muster:

DisplayController::index on advert-jobDisplayController::index on advert-job/pageModifyController::add on advert-job/modify

Dabei wird angegeben, welche Controller und welche Aktion darin ausgeführt wer-

den sollten. Zudem wird angegeben, welche Route zu einem Treffer führte. Die Rou-

ten setzen sich dabei aus der Parent-Route sowie der optionalen Child-Route

zusammen, die durch einen Schrägstrich voneinander getrennt sind.

Wenn Sie alle Routen ausprobieren und dabei auch die Werte für die Segmente vari-

ieren, sollten Sie die Korrektheit des Routings schnell überprüfen können.

3965-3.book Seite 394 Donnerstag, 6. Oktober 2016 1:19 13

11.4 Action-Controller anlegen

395

11

11.4 Action-Controller anlegen

Jetzt sind die Action-Controller an der Reihe. Das Routing gibt vor, dass Sie vier ver-

schiedene Controller mit unterschiedlicher Anzahl an Aktionen benötigen. Um

gleich mit einigen Daten arbeiten zu können, zeige ich Ihnen ein Repository, welches

diese Daten liefern kann.

Damit Sie die neuen Controller genauer anschauen können, wechseln Sie für die Bei-

spielanwendung auf den Branch chapter_11_03. Danach führen Sie ein Composer-

Update aus, um das Projekt zu aktualisieren.

$ cd /home/devhost/zf3buch.zendframework-center$ git checkout chapter_11_03 -f$ composer update

Um die Komplexität in diesem Kapitel nicht zu groß werden zu lassen, wird nur mit

einem sehr einfachen Model-Layer gestartet. Abbildung 11.7 zeigt, dass der Controller

auf ein Repository zugreift, welches die Daten aus einigen PHP-Array-Dateien be-

zieht. Dieser Model-Layer wird im nächsten Kapitel dann durch eine Anbindung an

eine Datenbank ausgetauscht.

Abbildung 11.7 Einfacher Model-Layer mit statischen Array-Dateien

11.4.1 Repository für Annoncen

Das AdvertRepository soll im ersten Schritt nur lesende Methoden bereitstellen, wie

das Interface in Listing 11.6 zeigt. Das Interface liegt im AdvertModel-Modul und defi-

niert eine Methode zum Lesen aller Annoncen für einen Typ und eine Seite sowie

zum Lesen einer einzelnen Annonce anhand einer ID. Außerdem wird die zufällige

Auswahl einer Anzeige anhand des Typs (Job oder Projekt) definiert.

namespace AdvertModel\Repository;

interface AdvertRepositoryInterface{

public function getAdvertsByPage(

Controller Repository

Application-Layer Model-Layer Infrastructure-Layer

PHP ArrayDateien

3965-3.book Seite 395 Donnerstag, 6. Oktober 2016 1:19 13

Page 28: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

396

$type = null, $approved = true, $page = 1, $count = 5);public function getSingleAdvertById($id);public function getRandomAdvert($type = 'job');

}

Listing 11.6 Interface für »AdvertRepository«

Die konkrete Implementierung dieses Interface ist in Listing 11.7 zu sehen. Die Klasse

AdvertRepository implementiert das vorherige Interface. Da dieses Repository noch

nicht mit einer Datenbank zusammenarbeitet, verwendet es für die Daten zwei

Arrays für die Daten der Annoncen und der Unternehmen. Diese Arrays können über

den Konstruktor injiziert werden.

namespace AdvertModel\Repository;

class AdvertRepository implements AdvertRepositoryInterface{

private $advertData = [];private $companyData = [];

public function __construct(array $advertData, array $companyData){

$this->advertData = $advertData;$this->companyData = $companyData;

}

public function getAdvertsByPage($type = null, $approved = true, $page = 1, $count = 5

) {if (!is_null($type)) {

$jobAdverts = $this->getAdvertsByType($type, $approved);} else {

$jobAdverts = $this->advertData;}

$offset = ($page - 1) * $count;

$advertList = array_slice($jobAdverts, $offset, $count, true);

foreach ($advertList as $key => $advert) {$company = $this->companyData[$advert['company']];

$advertList[$key]['company'] = $company;

3965-3.book Seite 396 Donnerstag, 6. Oktober 2016 1:19 13

11.4 Action-Controller anlegen

397

11

}

return $advertList;}

public function getSingleAdvertById($id){

if (!isset($this->advertData[$id])) {return false;

}

$advert = $this->advertData[$id];$company = $this->companyData[$advert['company']];

$advert['company'] = $company;

return $advert;}

public function getRandomAdvert($type = 'job'){

$jobAdverts = $this->getAdvertsByType($type, true);

if (empty($jobAdverts)) {return false;

}

$advertKeys = array_keys($jobAdverts);

$randomKey = array_rand($advertKeys);

return $this->getSingleAdvertById($advertKeys[$randomKey]);}

private function getAdvertsByType($type, $approved = true){

$jobAdverts = [];

foreach ($this->advertData as $advert) {if ($approved && $advert['status'] != 'approved') {

continue;}

3965-3.book Seite 397 Donnerstag, 6. Oktober 2016 1:19 13

Page 29: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

398

if ($advert['type'] != $type) {continue;

}

$jobAdverts[$advert['id']] = $advert;}

return $jobAdverts;}

}

Listing 11.7 Repository für Annoncen

� Die Methode getAdvertsByPage() erwartet als Parameter den Typ, ein Flag, das

angibt, ob nur genehmigte Annoncen gelesen werden sollen, die Nummer der

aktuellen Seite sowie die Anzahl der Annoncen pro Seite. Abhängig davon, ob der

Typ übergeben wurde, wird die Teilmenge ermittelt, oder die gesamten Daten wer-

den genommen. Bei der Ermittlung der Teilmenge wird die private Methode

getAdvertsByType() verwendet. Danach wird der aktuell zu betrachtende Aus-

schnitt der Annoncendaten ermittelt. Als Nächstes wird dieser Ausschnitt mit den

Unternehmensdaten für diese Annonce angereichert. Die ermittelten Annoncen

werden am Ende der Methode zurückgegeben.

� Die zweite Methode getSingleAdvertById() erwartet als Parameter die ID der zu

lesenden Annonce. Wird diese gefunden, werden die Annoncendaten ebenfalls

mit den Unternehmensdaten angereichert und im Anschluss zurückgegeben.

Diese statische Implementation kann später durch ein Repository ausgetauscht

werden, das die Daten aus einer Datenbank extrahiert.

� Die dritte Methode getRandomAdvert() lässt sich zuerst mithilfe der privaten

Methode getAdvertsByType() die Teilmenge für den übermittelten Typ liefern.

Danach wird ein zufälliger Schlüssel aus der Menge der IDs gewählt, und die Daten

werden mithilfe der getSingleAdvertById()-Methode zurückgegeben.

� Die private Methode getAdvertsByType() durchläuft alle vorhandenen Annoncen

und wählt die aus, die mit dem übermittelten Typ übereinstimmen. Bei Bedarf

wird die Liste zudem nur auf die Annoncen beschränkt, die genehmigt sind.

Der Vollständigkeit halber ist die AdvertRepositoryFactory in Listing 11.8 zu sehen,

welche die Daten für Annoncen und Unternehmen aus zwei Dateien einliest und an

den Konstruktor übergibt.

namespace AdvertModel\Repository;

use Interop\Container\ContainerInterface;use Zend\ServiceManager\Factory\FactoryInterface;

3965-3.book Seite 398 Donnerstag, 6. Oktober 2016 1:19 13

11.4 Action-Controller anlegen

399

11

class AdvertRepositoryFactory implements FactoryInterface{

public function __invoke(ContainerInterface $container,$requestedName,array $options = null

) {$advertData = include PROJECT_ROOT . '/data/advert-data.php';$companyData = include PROJECT_ROOT . '/data/company-data.php';

return new AdvertRepository($advertData, $companyData);}

}

Listing 11.8 Factory für »AdvertRepository«

Die beiden Dateien enthalten einige Testdaten im Array-Format. Sie finden sie direkt

im Verzeichnis /data/.

Zum Schluss muss das neue Repository noch in der Konfigurationsdatei /config/

module.config.php im AdvertModel konfiguriert werden. Listing 11.9 zeigt den Aus-

schnitt mit der Konfiguration für den Service-Manager. Dabei kommen der Klassen-

name als Bezeichner und die Factory für die Generierung zum Einsatz.

return ['service_manager' => [

'factories' => [AdvertModel\Repository\AdvertRepositoryInterface::class =>

AdvertModel\Repository\AdvertRepositoryFactory::class],

],];

Listing 11.9 Konfiguration für »AdvertRepository«

Somit wurde jetzt die Möglichkeit geschaffen, in den Controllern mit den statischen

Daten zu arbeiten. Doch keine Sorge, ich zeige Ihnen in Kapitel 12, »Model-Layer

implementieren«, selbstverständlich noch, wie Sie »echte« Daten aus einer Daten-

bank auslesen können.

11.4.2 Controller für die Ausgabe von Annoncen

Bevor ich Ihnen den DisplayController aus dem AdvertFrontend-Modul zeige, werfen

Sie bitte einen Blick auf die Konfiguration der Controller in diesem Modul. Sie liegt

3965-3.book Seite 399 Donnerstag, 6. Oktober 2016 1:19 13

Page 30: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

400

wie die Routen-Konfiguration in der Konfigurationsdatei /config/module.config.php

des Moduls und ist in Listing 11.10 zu sehen. Die beiden Controller, die im Routing

(siehe Abschnitt 11.3.1) als Vorgabewerte für den controller-Parameter festgelegt

wurden, müssen in der Controller-Konfiguration mit denselben Bezeichnern defi-

niert werden.

use AdvertFrontend\Controller\DisplayController;use AdvertFrontend\Controller\DisplayControllerFactory;use AdvertFrontend\Controller\ModifyController;use AdvertFrontend\Controller\ModifyControllerFactory;

return [/* ... */

'controllers' => ['factories' => [

DisplayController::class => DisplayControllerFactory::class,ModifyController::class => ModifyControllerFactory::class,

],],

];

Listing 11.10 Konfiguration der Controller im »AdvertFrontend«-Modul

Alle Controller werden im ControllerManager vorgehalten, einem spezialisierten Ser-

vice-Manager, der nur für die Controller verwendet wird. Da der ControllerManager

auf Zend\ServiceManager aufbaut, können Sie bei der Konfiguration ebenfalls Services

konfigurieren.

Streitfrage Dependency Injection bei Controllern

Bei der richtigen Implementierung der Dependency Injection für Controller gibt es

zwei unterschiedliche Auffassungen.

� Bei der einen Variante werden alle zwingend benötigten Abhängigkeiten per

Konstruktor injiziert. Dies hat den Vorteil, dass die Klasse gar nicht instanziiert

werden kann, wenn die Abhängigkeit nicht injiziert wird. Dagegen spricht, dass

Sie dann dauerhaft darauf achten müssen, ob der von der Zend\Mvc-Komponente

bereitgestellte abstrakte Controller nicht irgendwann einen eigenen Konstruktor

implementiert, den Sie dann überschreiben würden.

� Bei der anderen Variante werden alle benötigten Abhängigkeiten per Setter-Me-

thoden injiziert. Dies hat den Vorteil, dass Sie nicht darauf achten müssen, ob in

Zukunft einmal ein Konstruktor eingeführt wird. Es hat aber eben auch den

Nachteil, dass der Controller instanziiert werden kann, ohne dass alle benötigten

Abhängigkeiten injiziert wurden.

3965-3.book Seite 400 Donnerstag, 6. Oktober 2016 1:19 13

11.4 Action-Controller anlegen

401

11

Welche der beiden Varianten Sie bevorzugen, müssen Sie selbst entscheiden. Beide

haben Ihre Vor- und Nachteile. Sie sollten jedoch immer darauf achten, dass Sie in

Ihren Projekten konsequent nur eine Variante verwenden.

Zunächst sollten Sie Ihre Aufmerksamkeit auf den DisplayController in Listing 11.11

lenken. Der Controller ist für die Ausgabe einer Liste mit Annoncen sowie einer ein-

zelnen Annonce zuständig. Zum Laden der Annoncen benötigt er das AdvertReposi-

tory, das über eine Setter-Methode injiziert werden kann.

namespace AdvertFrontend\Controller;

use AdvertModel\Repository\AdvertRepositoryInterface;use Zend\Mvc\Controller\AbstractActionController;use Zend\View\Model\ViewModel;

class DisplayController extends AbstractActionController{

private $advertRepository;

public function setAdvertRepository($advertRepository){

$this->advertRepository = $advertRepository;}

public function indexAction(){

$page = $this->params()->fromRoute('page', 1);$type = $this->params()->fromRoute('type', 'job');

$advertList = $this->advertRepository->getAdvertsByPage($type, true, $page

);

if (!$advertList) {return $this->redirect()->toRoute($type);

}

// Dump, da es kein Template gibt und es sonst eine Exception gibtvar_dump($advertList);exit;

}

public function detailAction()

3965-3.book Seite 401 Donnerstag, 6. Oktober 2016 1:19 13

Page 31: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

402

{$id = $this->params()->fromRoute('id');$type = $this->params()->fromRoute('type', 'job');

if (!$id) {return $this->redirect()->toRoute($type);

}

$advert = $this->advertRepository->getSingleAdvertById($id);

if (!$advert || $advert['type'] != $type) {return $this->redirect()->toRoute($type);

}

// Dump, da es kein Template gibt und es sonst eine Exception gibtvar_dump($advert);exit;

}}

Listing 11.11 Controller zur Anzeige von Annoncen

Die indexAction()-Methode soll eine Liste von Annoncen lesen. Im Folgenden wird

der Ablauf innerhalb dieser Methode erläutert.

� Zuerst wird ermittelt, welche Seite gerade aufgerufen wird. Der page-Parameter

aus dem Routing kann über das Params-Plug-in mit dessen fromRoute()-Methode

abgerufen werden. Sollte der Parameter nicht gesetzt sein, wird der Vorgabewert 1

verwendet.

� Zudem wird der type-Parameter aus dem Routing abgerufen, wobei hier der Vor-

gabewert auf job gesetzt wird. Dieser wird automatisch durch das Routing jeweils

in den beiden Parent-Routen vorbelegt.

� Mit den Parametern $type und $page wird über das AdvertRepository die Liste der

Annoncen für die aktuelle Seite angefordert Durch das Setzen des zweiten Para-

meters auf den Wert true werden nur genehmigte Annoncen gelesen.

� Sollte diese Liste leer sein, weil z. B. eine zu hohe Seitennummer aufgerufen wurde,

erfolgt eine Umleitung. Das Redirect-Plug-in ermöglicht, mit der toRoute()-Methode

eine Umleitung für eine Route zu erstellen. Hier kommt wieder der Typ zum Einsatz,

um auf die erste Seite der Liste umzuleiten. Dies funktioniert deshalb direkt, weil der

Name der Parent-Route exakt mit dem Namen des Typs übereinstimmt.

� Wenn der Ablauf erfolgreich war, wird die Liste einfach ausgegeben, und der Pro-

zess wird durch exit abgebrochen. Dieser Abbruch ist deshalb sinnvoll, damit Sie

überhaupt testen können, dass die richtigen Daten gelesen worden sind. Ohne die-

3965-3.book Seite 402 Donnerstag, 6. Oktober 2016 1:19 13

11.4 Action-Controller anlegen

403

11

sen Abbruch versucht das Zend Framework 3, ein Template zu finden, um dieses

verarbeiten zu können. Da bisher aber noch kein Template für diese Aktion vor-

handen ist, ist der Abbruch per exit eine Möglichkeit, die Ausgabe der gelesenen

Daten zu überprüfen. Das Template wird in Abschnitt 11.5 erstellt.

Die detailAction()-Methode hat die Aufgabe, eine einzelne Annonce zu lesen. Der

Ablauf unterscheidet sich dabei von der vorherigen Aktion.

� Zuerst muss der Routen-Parameter für die ID aus dem Routing gelesen werden.

Hier kommt erneut das Params-Plug-in zum Einsatz, wobei dieses Mal kein Vorga-

bewert gesetzt wird.

� Auch der type-Parameter wird wieder ermittelt.

� Sollte der Parameter $id keine ID enthalten, wird umgehend über den Namen des

Typs auf die Liste aller Annoncen umgeleitet.

� Der $id-Parameter wird an die getSingleAdvertById()-Methode des Repositorys

übergeben, um die Annonce zu laden.

� Sollte keine Annonce mit der ID gefunden werden oder sollte die gefundene

Annonce nicht mit dem vorgegebenen Typ übereinstimmen, wird ebenfalls auf

die Liste mit den Annoncen umgeleitet.

� War das Lesen der Daten erfolgreich, wird die Annonce direkt ausgegeben, und der

Ablauf wird aus denselben Gründen abgebrochen wie bei der indexAction()-

Methode.

Dieser Controller muss noch einmal leicht überarbeitet werden, wenn die Templates

erstellt wurden. Für die geplante Umsetzung des Repositorys, das die Daten aus einer

Datenbank liest, muss aufgrund des Einsatzes des AdvertRepositoryInterface am

Controller nichts mehr verändert werden.

Abschließend ist in Listing 11.12 die DisplayControllerFactory dargestellt. Sie imple-

mentiert das FactoryInterface aus der Komponente Zend\ServiceManager und hat die

Aufgabe, eine Instanz des Controllers DisplayController zu instanziieren.

namespace AdvertFrontend\Controller;

use AdvertModel\Repository\AdvertRepositoryInterface;use Interop\Container\ContainerInterface;use Zend\ServiceManager\Factory\FactoryInterface;

class DisplayControllerFactory implements FactoryInterface{

public function __invoke(ContainerInterface $container,$requestedName,array $options = null

3965-3.book Seite 403 Donnerstag, 6. Oktober 2016 1:19 13

Page 32: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

404

) {$advertRepository = $container->get(

AdvertRepositoryInterface::class);

$controller = new DisplayController();$controller->setAdvertRepository($advertRepository);

return $controller;}

}

Listing 11.12 Factory für »DisplayController«

Die Methode __invoke() bekommt die Instanz des DI-Containers übergeben, was in

unserem Fall dem Zend\ServiceManager entspricht. Damit können Sie die Instanz des

AdvertRepository abfragen. Danach kann der DisplayController instanziiert und das

Repository über die Setter-Methode injiziert werden. Damit ist die Aufgabe der Fac-

tory abgeschlossen.

Warum Repository nicht über Konstruktor injizieren?

Der DisplayController hat eine feste Abhängigkeit zur AdvertRepository. Somit

muss das Repository in den Controller injiziert werden. Dies wurde hier über die

setAdvertRepository()-Methode gelöst, die in der Factory direkt nach der Instanzi-

ierung aufgerufen wird. Doch warum wurde das Repository nicht gleich bei der In-

stanziierung an den Konstruktor übergeben?

Wenn Sie eine Klasse aus einer fremden Quelle erweitern und dabei den Konstruktor

verwenden wollen, müssen Sie schauen, ob die erweiterte Klasse einen eigenen Kon-

struktor hat. Falls ja, müssen Sie sicherstellen, dass Sie in Ihrer erweiternden Klasse

den Parent-Konstruktor aufrufen. Sollte sich dieser in der erweiterten Klasse ändern,

müssen Sie auch Ihren Konstruktor anpassen. Um dies zu verhindern, können Sie

statt der Injektion per Konstruktor auch auf eine Injektion per Setter-Methode

zurückgreifen. Dann sind Sie vor unerwarteten Erweiterungen in der Regel sicher.

Beim AbstractActionController ist es übrigens so, dass dieser über gar keinen Kon-

struktor verfügt. Sollten Sie per Konstruktor Abhängigkeiten injizieren und bekommt

diese Klasse irgendwann doch noch einen eigenen Konstruktor, würden Sie mögliche

Fehler eventuell nur sehr schwer finden.

Sie können den Controller nun ausprobieren, indem Sie in Ihrem Browser die

Adresse http://zf3buch.zendframework-center/job aufrufen. Wundern Sie sich aber

nicht über die Ausgabe (siehe Abbildung 11.8). Wie erwähnt, wird die Verarbeitung in

den Aktionsmethoden abgebrochen, weil sie ohne vorhandenes Template ansonsten

in einen Fehler laufen würde.

3965-3.book Seite 404 Donnerstag, 6. Oktober 2016 1:19 13

11.4 Action-Controller anlegen

405

11

Abbildung 11.8 Ausgabe der Rohdaten der Annoncenliste

Ausgabe der Rohdaten

Die Ausgabe in Abbildung 11.8 erfolgt übrigens mit aktiviertem Xdebug und ist des-

halb formatiert. Bei Ihnen könnte es im Detail etwas anders aussehen.

11.4.3 Weitere Controller

Neben dem bereits ausführlich betrachteten DisplayController aus dem AdvertFront-

end-Modul sind auch die anderen drei Controller bereits in chapter_11_03 vorbereitet.

� Im AdvertFrontend\Controller\ModifyController wurden die drei Aktionsmetho-

den addAction(), editAction() und deleteAction() eingerichtet. Logik ist in den

Methoden aber noch nicht vorhanden.

3965-3.book Seite 405 Donnerstag, 6. Oktober 2016 1:19 13

Page 33: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

406

� Gleiches trifft auf den AdvertBackend\Controller\ModifyController zu. Darin wur-

den nur die Aktionsmethoden addAction(), editAction(), deleteAction(), approve-Action() und blockAction() für die spätere Implementierung der Controller-Logik

vorbereitet.

� Der AdvertBackend\Controller\DisplayController ist ähnlich aufgebaut wie der

AdvertFrontend\Controller\DisplayController. Auch darin werden die Daten gele-

sen und dann direkt ausgegeben.

� Der Application\Controller\IndexController für die Startseite gibt jeweils eine

zufällige Annonce für einen Job und für ein Projekt aus.

Alle Controller werden in diesem und den nächsten Kapiteln noch vervollständigt.

Controller-Factory für faule Entwickler

In der Komponente Zend\Mvc gibt es eine spezielle Factory für Controller. Die Zend\Mvc\Controller\LazyControllerAbstractFactory erlaubt Ihnen, das Schreiben vieler

Factorys zu vereinfachen. Diese Factory analysiert den Konstruktor einer Factory und

versucht, die notwendigen Abhängigkeiten nach den folgenden Regeln zu finden.

� Ein Parameter $config, der Arrays erwartet, bekommt die Konfiguration überge-

ben, die im Service-Manager über den Schlüssel config erreichbar ist.

� Alle anderen Array-Parameter bekommen ein leeres Array und skalare Parameter

den Wert NULL übergeben.

� Für Parameter mit einem Type-Hint für eine Klasse oder ein Interface versucht

der Service-Manager, einen passenden Service zu finden. Im Erfolgsfall wird er

injiziert, ansonsten wird ein Fehler geworfen.

� Zudem gibt es Unterstützung für spezialisierte Service-Manager wie den Vali-

datorManager und den HydratorManager (siehe Abschnitt 20.21.3). Diese sollten

Sie jedoch niemals direkt in einen Controller injizieren. Falls Sie dies doch

machen möchten, finden Sie Details in der Dokumentation:

https://docs.zendframework.com/zend-mvc/cookbook/automating-controller-

factories/

Beachten Sie, dass Sie den LazyControllerAbstractFactory nur in Ausnahmefällen

oder übergangsweise einsetzen, da diese Factory aufgrund des Einsatzes von Reflec-

tion immer langsamer ist als eine konkrete Factory.

11.5 Templates erstellen

Im nächsten Schritt dieses Kapitels sind nun die Templates an der Reihe. Diese müs-

sen erstellt und konfiguriert werden, damit sie automatisch geladen werden kön-

nen. Zudem müssen die Aktionsmethoden in den Controllern zum Teil noch

angepasst werden.

3965-3.book Seite 406 Donnerstag, 6. Oktober 2016 1:19 13

11.5 Templates erstellen

407

11

Damit Sie die Templates und die weiteren Änderungen besser nachvollziehen kön-

nen, wechseln Sie auf den Branch chapter_11_04 und führen danach ein Composer-

Update aus, um das Projekt zu aktualisieren.

$ cd /home/devhost/zf3buch.zendframework-center$ git checkout chapter_11_04 -f$ composer update

11.5.1 Controller überarbeiten

Die Überarbeitung der Controller ist schnell gemacht, da diese in Abschnitt 11.4

bereits vorbereitet wurden. Bisher wurden die gelesenen Daten direkt ausgegeben,

und danach wurde die Verarbeitung abgebrochen. Jetzt müssen die Daten jedoch an

eine ViewModel-Instanz übergeben werden.

Exemplarisch können Sie sich in Listing 11.13 den überarbeiteten DisplayController

aus dem AdvertFrontend-Modul anschauen. Darin sind nur die Überarbeitungen zu

sehen. Dabei wird eine ViewModel-Instanz erstellt, und die gelesenen Daten sowie der

Typ werden als Variable an das ViewModel übergeben. Am Ende wird das View-Model

zurückgegeben und kann somit im weiteren MVC-Ablauf verarbeitet werden.

namespace AdvertFrontend\Controller;

use AdvertModel\Repository\AdvertRepositoryInterface;use Zend\Mvc\Controller\AbstractActionController;use Zend\View\Model\ViewModel;

class DisplayController extends AbstractActionController{

/* ... */

public function indexAction(){

/* ... */

$viewModel = new ViewModel();$viewModel->setVariable('advertList', $advertList);$viewModel->setVariable('type', $type);

return $viewModel;}

public function detailAction(){

3965-3.book Seite 407 Donnerstag, 6. Oktober 2016 1:19 13

Page 34: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

408

/* ... */

$viewModel = new ViewModel();$viewModel->setVariable('advert', $advert);$viewModel->setVariable('type', $type);

return $viewModel;}

}

Listing 11.13 »DisplayController« übergibt Daten an »ViewModel«

Auch im ModifyController des AdvertFrontend-Moduls und in den beiden Control-

lern im AdvertBackend-Modul wird eine ViewModel-Instanz erstellt, und am Ende der

Aktionsmethode wird dieses Objekt zurückgegeben.

Ist es sinnvoll, das Template im »ViewModel« zu konfigurieren?

Kurze Antwort: Ja.

Ausführlicher betrachtet, passiert Folgendes. Bei jeder ViewModel-Instanz können Sie

durch den Aufruf der setTemplate()-Methode das Template festlegen, das bei der

Ausgabe verarbeitet werden soll. Wenn Sie in Ihrem Controller kein Template im

ViewModel setzen wie in Listing 11.17, sorgt Zend\Mvc dafür, dass der Template-Name

anhand der aktuellen Parameter für Modul, Controller und Aktion automatisch

ermittelt wird. Sie müssen das Template also nicht selbst setzen.

Wenn Sie es doch tun, dann haben Sie den Vorteil, dass der Template-Name nicht

ermittelt werden muss. Das Setzen des Template-Namens ist somit eine kleine Per-

formanceoptimierung. Doch versprechen Sie sich davon nicht zu viel. Auf die Perfor-

mance wirkt sich das nur sehr marginal aus. Aber eben doch ein wenig.

11.5.2 Templates einrichten

Als Nächstes sind die Templates an der Reihe. Dabei beginne ich mit dem Template

für die Ausgabe der Annoncenliste. Für die Darstellung der indexAction() aus dem

DisplayController des AdvertFrontend-Moduls ist das Template /view/advert-front-

end/display/index.phtml in diesem Modul zuständig. Dieses Template wird dadurch

ermittelt, weil der Name des Moduls auf das /advert-frontend/-Verzeichnis, der Name

des Controllers auf das /display/-Verzeichnis und der Name der Aktion auf die

index.phtml-Datei abgebildet wird.

In Abbildung 11.9 wird die Ausgabe des Templates für die Seite mit den Job-Annoncen

angezeigt, die über die URL http://zf3buch.zendframework-center/job aufgerufen

werden kann.

3965-3.book Seite 408 Donnerstag, 6. Oktober 2016 1:19 13

11.5 Templates erstellen

409

11

Abbildung 11.9 Anzeige der Liste mit den Job-Annoncen

Der Inhalt des /view/advert-frontend/display/index.phtml-Templates ist in Listing

11.14 abgebildet. Es wurde gekürzt, um das Wesentliche herauszustellen. Zu Beginn

werden einige Werte abhängig vom Typ festgelegt, und die URL zur Homepage wird

mithilfe des Url-View-Helpers generiert.

<?phpif ($this->type == 'job') {

$color = 'primary';$advertType = 'Job';$headTitleText = 'Aktuelle Zend Framework Jobs';$h1Text = 'Aktuelle Zend Framework Jobs';

} else {$color = 'success';$advertType = 'Projekt';$headTitleText = 'Aktuelle Zend Framework Projekte';$h1Text = 'Aktuelle Zend Framework Projekte';

}

3965-3.book Seite 409 Donnerstag, 6. Oktober 2016 1:19 13

Page 35: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

410

$listLink = $this->url('home', [], true);

$this->headTitle($headTitleText);?><div class="page-header"><h1><?= $h1Text ?></h1>

</div><!-- ... --><?php foreach ($this->advertList as $advert) : ?><?php$advertText = strip_tags($advert['text']);$advertText = implode(

' ', array_slice(explode(' ', $advertText), 0, 50));$advertLink = $this->url(

'advert-' . $this->type . '/detail', ['id' => $advert['id']], true);

?><div class="panel panel-<?= $color ?>"><div class="panel-heading clearfix"><div class="left-text"><strong><a href="<?= $advertLink ?>"><?= $advert['title']; ?>

</a></strong>

</div><div class="right-text"><?= $advert['company']['name'] ?>

</div></div><div class="panel-body"><div class="col-sm-9"><p><?= $advertText; ?> ...</p><!-- ... -->

</div><div class="col-sm-3 company"><img class="img-responsive"

src="<?= $advert['company']['logo'] ?>"></div>

</div><div class="panel-footer clearfix"><!-- ... -->

</div>

3965-3.book Seite 410 Donnerstag, 6. Oktober 2016 1:19 13

11.5 Templates erstellen

411

11

</div><?php endforeach; ?><!-- ... -->

Listing 11.14 Template für Liste der Annoncen

Der Kern des Templates ist die foreach()-Schleife, die alle vom Controller an den

View übergebenen Annoncen durchläuft. Zu Beginn eines Durchlaufs wird der Text

der Annonce auf maximal 50 Wörter gekürzt, und es wird die URL für die Seite zur

Anzeige einer Annonce generiert.

Die Ausgabe erfolgt in einem Bootstrap Panel. Darin werden unter anderem der Titel

der Annonce, der Name des Unternehmens, das Logo und der gekürzte Text der

Anzeige ausgegeben. Zudem wird die Detailseite mithilfe der vorgenerierten URL als

Link ausgegeben. Der Großteil des Listings besteht aus HTML-Markup, das für die

Ausgabe mit Bootstrap benötigt wird.

Abbildung 11.10 zeigt die Detailseite für eine Anzeige, die über die URL http://zf3-

buch.zendframework-center/job/detail/1 aufgerufen werden kann.

Abbildung 11.10 Anzeige der Detailseite einer Annonce

3965-3.book Seite 411 Donnerstag, 6. Oktober 2016 1:19 13

Page 36: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

412

Das Template /view/advert-frontend/display/detail.phtml ist dem vorherigen Tem-

plate recht ähnlich aufgebaut. Es fehlt die foreach()-Schleife, aber die Ausgabe erfolgt

ebenfalls über ein Bootstrap Panel. Auch hier erfolgt teilweise eine Unterscheidung

anhand des Typs. Zudem sind Links zurück zur Liste der Annoncen enthalten. Da die

Darstellung des Listings im Buch nur wenig neue Erkenntnisse bringen würde, habe

ich an dieser Stelle darauf verzichtet. Öffnen Sie die Datei einfach in Ihrer IDE, und

schauen Sie den Code dort im Detail an.

Die überarbeitete Startseite wurde bereits in diesem Kapitel in Abbildung 11.1 gezeigt.

Das entsprechende Template ist in der Datei /view/application/index/index.phtml zu

finden und gibt die beiden zufällig ausgewählten Annoncen sowie Links zu den An-

noncen und den Listen der Jobs und Prospekte aus.

Abschließend möchte ich Ihre Aufmerksamkeit auf die Ausgabe der Annoncen im

Administrationsbereich lenken. Das Template ist in der Datei /view/advert-backend/

display/index.phtml im AdvertBackend-Modul zu finden und wird in Listing 11.15 dar-

gestellt. Darin erfolgt die Ausgabe in einer Tabelle. Jede Zeile der Tabelle ist mit Links

zu den einzelnen weiteren Seiten bestückt (wobei die Links für Löschen, Freigeben

und Sperren gekürzt wurden).

<?php$addLink = $this->url(

'advert-backend/modify', ['action' => 'add']);

$this->headTitle('Annoncen administrieren');?><table class="table table-condensed table-bordered table-striped"><thead><tr><th>Typ</th><th>Status</th><th>Titel</th><th class="hidden-xs">Firma</th><th class="hidden-xs">Ort</th><th class="hidden-xs">Datum</th><th class="text-center"><a href="<?= $addLink ?>"><i class="fa fa-plus-square-o"></i></a>

</th></tr></thead><tbody><?php foreach ($this->advertList as $advert) : ?><?php$advertType = ($advert['type'] == 'job') ? 'Job' : 'Projekt';

3965-3.book Seite 412 Donnerstag, 6. Oktober 2016 1:19 13

11.5 Templates erstellen

413

11

$showLink = $this->url('advert-backend/show', ['id' => $advert['id']]

);$editLink = $this->url('advert-backend/modify',['action' => 'edit', 'id' => $advert['id']]

);/* ... */

?><tr><td><?= $advertType ?>

</td><td><?= $advert['status'] ?>

</td><td><a href="<?= $showLink ?>"><?= $advert['title'] ?>

</a></td><td class="hidden-xs"><?= $advert['company']['name'] ?>

</td><td class="hidden-xs"><?= $advert['location'] ?>

</td><td class="hidden-xs"><?= $advert['updated'] ?>

</td><td class="text-center"><a href="<?= $showLink ?>" class="hidden-xs hidden-sm"><i class="fa fa-file-text-o"></i>

</a><a href="<?= $editLink ?>"><i class="fa fa-pencil"></i>

</a><!-- ... -->

</td></tr>

<?php endforeach; ?></tbody>

</table>

Listing 11.15 Template für Administrationsbereich der Annoncen

3965-3.book Seite 413 Donnerstag, 6. Oktober 2016 1:19 13

Page 37: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

414

Die Annoncen werden auf dieser Seite also deutlich kompakter dargestellt als im

öffentlichen Bereich, wie es Abbildung 11.9 weiter vorne zeigt. Der Ablauf innerhalb

des Templates ist jedoch sehr ähnlich. Abbildung 11.11 zeigt die Ausgabe der Tabelle.

Abbildung 11.11 Liste der Annoncen im Administrationsbereich

Übrigens passt sich die Ausgabe der Breite Ihres Browsers an. Dies wurde durch den

Einsatz der CSS-Klassen hidden-xs und hidden-sm erreicht. Diese werde von Bootstrap

bereitgestellt und bewirken das Ausblenden abhängig von den sogenannten Break-

points. Aus Gründen der besseren Übersichtlichkeit wurden diese CSS-Klassen in

dem Listing nicht dargestellt. Sie finden Sie aber im Code des Beispielprojekts.

Im Modul AdvertBackend sind weitere Templates enthalten, die jedoch größtenteils

noch leer sind. Wenn Sie eine der Funktionen wie Bearbeiten aufrufen, können Sie

sich die leere Ausgabe selbst einmal anschauen.

11.5.3 Templates konfigurieren

Damit die Templates im Zend\Mvc-Ablauf geladen werden können, müssen diese kon-

figuriert werden. Die Konfiguration ist exemplarisch für das AdvertFrontend-Modul

in Listing 11.16 zu sehen. Darin ist ein Ausschnitt aus der /config/module.config.php

des Moduls zu sehen.

3965-3.book Seite 414 Donnerstag, 6. Oktober 2016 1:19 13

11.5 Templates erstellen

415

11

return [/* ... */

'view_manager' => ['template_map' =>

include ADVERT_FRONTEND_MODULE_ROOT . '/template_map.php','template_path_stack' => [

ADVERT_FRONTEND_MODULE_ROOT . '/view'],

],];

Listing 11.16 Konfiguration der Templates für das »AdvertFrontend«-Modul

Über die Konfiguration für den View-Manager werden die Templates für das Modul

konfiguriert.

� Mit dem Parameter template_map können Sie eine Template-Map für die Templa-

tes in diesem Modul festlegen. Eine Template-Map ist eine Datei, die für jeden

Template-Namen festlegt, wo genau die entsprechende Datei zu finden ist (siehe

Infokasten weiter unten). Die Template-Map für das AdvertFrontend-Modul liegt

direkt im Hauptverzeichnis des Moduls.

� Zusätzlich können Sie über den Parameter template_path_stack ein Verzeichnis

für das Path-Stack festlegen, in dem die Templates für dieses Modul zu finden sind.

Dabei handelt es sich um das /view/-Verzeichnis des AdvertFrontend-Moduls.

Beide Varianten können in Kombination verwendet werden. Dabei wird zuerst in der

Template-Map geschaut und, wenn dort das gesuchte Template nicht gefunden wird,

werden die Verzeichnisse des Path-Stacks durchlaufen, um das Template zu finden.

Das Finden über eine Template-Map ist dabei immer performanter als die Suche über

den Path-Stack.

Wie ist eine Template-Map aufgebaut, und wie wird sie erstellt?

Der Aufbau einer Template-Map ist recht simpel (siehe Listing 11.17). Der Template-

Name setzt sich immer aus dem Namen des Moduls, des Controllers und der Aktion

zusammen. Der Name wiederum verweist direkt auf die Datei.

return array('advert-frontend/display/detail' =>

__DIR__ . '/view/advert-frontend/display/detail.phtml','advert-frontend/display/index' =>

__DIR__ . '/view/advert-frontend/display/index.phtml',);

Listing 11.17 Template-Map des »AdvertFrontend«-Moduls

3965-3.book Seite 415 Donnerstag, 6. Oktober 2016 1:19 13

Page 38: Zend Framework 3 – Das umfassende Handbuch

11 Controller und View

416

Sie sollten für jedes Modul, das Templates enthält, eine eigene Template-Map erstel-

len. Sie können diese Template-Maps manuell erstellen. Besser ist jedoch der Einsatz

des sogenannten Template-Map-Generators. Um diesen nutzen zu können, wech-

seln Sie zuerst in das entsprechende Projektverzeichnis und danach in das Konfigura-

tionsverzeichnis des Moduls, für das eine Template-Map erstellt werden soll.

Mit Ubuntu Linux könnte dieser Aufruf wie folgt aussehen:

$ cd /home/devhost/zf3buch.zendframework-center/$ cd module/AdvertFrontend/config/$ ../../../vendor/bin/templatemap_generator.php ../view/ >template_map.config.php

Auf dem Mac müssten Sie lediglich in ein anderes Verzeichnis wechseln:

$ cd /Users/[Accountname]/Sites/zf3buch.zendframework-center/$ cd module/AdvertFrontend/config/$ ../../../vendor/bin/templatemap_generator.php ../view/ >template_map.config.php

Unter Windows sieht der Aufruf etwas anders aus. Sie müssen hier die template-

map_generator.php.bat-Datei verwenden.

$ cd C:\devhost\zf3buch.zendframework-center$ cd module\AdvertFrontend\config$ ..\..\..\vendor\bin\templatemap_generator.php.bat ..\view\ >template_map.config.php

Sie sollten die Template-Maps vor allem auf dem Produktivserver immer aktuell hal-

ten. Auf dem Entwicklungsserver kommt immer der Path-Stack als Fallback zum Ein-

satz. Am besten integrieren Sie den Aufruf des Template-Map-Generators in Ihren

Build-Prozess.

Für das AdvertBackend-Modul sieht die Konfiguration genauso aus. Im Application-

Modul ist die Konfiguration für Template-Map und Path-Stack bereits vorhanden.

Das Modul AdvertModel braucht dies nicht.

11.5.4 Ausgabe kontrollieren

Die Ausgabe der Templates ist bereits in einigen der bisherigen Abbildungen zu

sehen:

� Abbildung 11.1 am Anfang des Kapitels zeigt die überarbeitete Startseite, die über

die URL http://zf3buch.zendframework-center/ aufgerufen werden kann.

� In Abbildung 11.9 ist die Ausgabe der Liste mit den Job-Annoncen zu sehen, die

über http://zf3buch.zendframework-center/job angezeigt werden kann.

3965-3.book Seite 416 Donnerstag, 6. Oktober 2016 1:19 13

11.5 Templates erstellen

417

11

� Die Detailseite einer Job-Annonce zeigt Abbildung 11.10 nach Aufruf der URL http://

zf3buch.zendframework-center/job/detail/1.

� Die Administrationsseite ist in Abbildung 11.11 zu sehen und kann durch die URL

http://zf3buch.zendframework-center/advert-backend angezeigt werden.

Der Vollständigkeit halber zeigt Abbildung 11.12 die Liste der Projekte, die farblich

etwas anders dargestellt ist. Sie können die Projektliste durch Aufruf der URL http://

zf3buch.zendframework-center/project anschauen.

Abbildung 11.12 Darstellung der Projektliste in der Beispielanwendung

Achtung: Keine echten Daten!

Bei den Beispieldaten für die Annoncen und die dort verwendeten Unternehmen

handelt es sich ausschließlich um Fantasienamen. Diese Firmen existieren nicht, und

jegliche Ähnlichkeiten mit real existierenden Unternehmen und deren Mitarbeitern

sind rein zufällig.

Unter der Adresse http://www.zendframework.center/ können Sie das Projekt in

etwas erweiterter Form und mit echten Daten einmal im Livebetrieb in Augenschein

nehmen.

3965-3.book Seite 417 Donnerstag, 6. Oktober 2016 1:19 13

Page 39: Zend Framework 3 – Das umfassende Handbuch

Auf einen Blick

Auf einen Blick

TEIL I Grundlagen

1 Einführung in das Zend Framework 3 ............................................................ 31

TEIL II Middleware-Anwendungen

2 Middleware-Anwendungen einrichten .......................................................... 71

3 Routing, Actions und Templates ...................................................................... 101

4 Datenbanken und Repositorys .......................................................................... 139

5 Formulare und Benutzereingaben ................................................................... 165

6 Internationalisierung ........................................................................................... 191

7 Authentifizierung und Autorisierung ............................................................. 227

8 Zend\Expressive-Anwendung optimieren .................................................... 267

9 Unit-Tests für Middleware-Anwendungen ................................................... 293

TEIL III MVC-Anwendungen

10 MVC-Anwendung einrichten ............................................................................. 353

11 Controller und View .............................................................................................. 381

12 Model-Layer implementieren ............................................................................ 431

13 Formularverarbeitung im MVC ......................................................................... 475

14 Internationalisierung im MVC ........................................................................... 545

15 Authentifizierung und Autorisierung im MVC ............................................ 575

16 Tests für MVC-Anwendungen ........................................................................... 641

TEIL IV Weitere Themen

17 Migration vom ZF2 und ZF1 ............................................................................... 705

18 Webservices und Apigility .................................................................................. 763

19 Konsolenanwendungen ...................................................................................... 793

TEIL V Komponenten

20 Zend-Framework-Komponenten ...................................................................... 817

3965-3.book Seite 3 Donnerstag, 6. Oktober 2016 1:19 13

Page 40: Zend Framework 3 – Das umfassende Handbuch

Inhalt

5

Inhalt

Geleitwort .............................................................................................................................................. 25

Vorwort .................................................................................................................................................. 27

TEIL I Grundlagen

1 Einführung in das Zend Framework 3 31

1.1 Was ist das Zend Framework 3? ................................................................................... 31

1.2 An wen richtet sich dieses Buch? ................................................................................. 31

1.3 Warum das Zend Framework 3 einsetzen? ............................................................. 32

1.3.1 Warum vom ZF1 oder ZF2 migrieren? .......................................................... 33

1.3.2 Warum vom anderen Framework wechseln? ............................................ 34

1.3.3 Welche Konzepte werden im ZF3 implementiert? ................................... 35

1.3.4 Wofür das Zend Framework einsetzen? ....................................................... 37

1.4 Aufbau des Buches ............................................................................................................. 38

1.4.1 Teil I ........................................................................................................................... 38

1.4.2 Teil II ......................................................................................................................... 38

1.4.3 Teil III ........................................................................................................................ 39

1.4.4 Teil IV ........................................................................................................................ 40

1.4.5 Teil V ......................................................................................................................... 40

1.4.6 Anhang .................................................................................................................... 41

1.5 Listings und Programmierstil ......................................................................................... 41

1.6 Technische Voraussetzungen ........................................................................................ 42

1.6.1 PHP ............................................................................................................................ 43

1.6.2 PHP CLI-Webserver .............................................................................................. 45

1.6.3 Apache 2-Webserver ........................................................................................... 45

1.6.4 Nginx-Webserver ................................................................................................. 49

1.6.5 Datenbank .............................................................................................................. 50

1.6.6 Git .............................................................................................................................. 51

1.6.7 Composer ................................................................................................................ 52

1.6.8 Wahl der IDE .......................................................................................................... 54

1.7 Installationsvarianten ....................................................................................................... 54

1.7.1 Zend Framework 3 als ZIP-Paket herunterladen und entpacken ......... 55

1.7.2 Zend Framework 3 per Composer installieren ........................................... 55

3965-3.book Seite 5 Donnerstag, 6. Oktober 2016 1:19 13

Page 41: Zend Framework 3 – Das umfassende Handbuch

Inhalt

6

1.7.3 Zend\Mvc Skeleton Application ...................................................................... 56

1.7.4 Zend\Expressive Skeleton Application ......................................................... 58

1.7.5 Apigility Skeleton Application .......................................................................... 60

1.8 Beispiel- und Übungsanwendungen .......................................................................... 62

1.8.1 Beispielanwendung »Vote My Pizza!« .......................................................... 62

1.8.2 Übungsanwendung »Pin Your Pizza!« .......................................................... 63

1.8.3 Beispielanwendung »Zend Framework Center« ....................................... 63

1.8.4 Übungsanwendung »Simple CMS« ............................................................... 64

1.8.5 Beispielanwendung »ZF3buch Examples« .................................................. 65

1.8.6 Migrationsanwendung »ZF1legacy« ............................................................. 66

1.8.7 Konsolenanwendung »Entity-Builder« ......................................................... 66

1.9 Zusammenfassung ............................................................................................................. 67

TEIL II Middleware-Anwendungen

2 Middleware-Anwendungen einrichten 71

2.1 Einstieg .................................................................................................................................... 71

2.1.1 Problemstellung ................................................................................................... 71

2.1.2 PSR-7 und Middleware ....................................................................................... 72

2.1.3 Komponenten ....................................................................................................... 75

2.2 Installation der Beispielanwendung .......................................................................... 75

2.2.1 Installation unter Ubuntu Linux ..................................................................... 76

2.2.2 Installation unter OS X und macOS Sierra ................................................... 76

2.2.3 Installation unter Windows ............................................................................. 76

2.2.4 Virtual Host einrichten ....................................................................................... 77

2.3 Aufbau einer Zend\Expressive-Anwendung .......................................................... 78

2.3.1 »composer.json«-Datei ...................................................................................... 79

2.3.2 Vendorverzeichnis ............................................................................................... 81

2.3.3 Konfigurationsverzeichnis für Anwendung ................................................ 82

2.3.4 Datenverzeichnis .................................................................................................. 87

2.3.5 Öffentliches Verzeichnis .................................................................................... 88

2.3.6 Modulverzeichnis ................................................................................................. 91

2.4 Aufbau eines Zend\Expressive-Moduls .................................................................... 91

2.4.1 Konfigurationsverzeichnis für Modul ........................................................... 92

2.4.2 Konfigurationsklasse für Modul ..................................................................... 93

2.4.3 Source-Verzeichnis .............................................................................................. 94

3965-3.book Seite 6 Donnerstag, 6. Oktober 2016 1:19 13

Inhalt

7

2.4.4 Template-Verzeichnis ......................................................................................... 96

2.4.5 Testverzeichnis ..................................................................................................... 98

2.5 Zusammenfassung ............................................................................................................. 98

2.6 Übung und Lösung .............................................................................................................. 98

2.6.1 Aufgaben ................................................................................................................ 98

2.6.2 Lösungen ................................................................................................................. 99

3 Routing, Actions und Templates 101

3.1 Einstieg .................................................................................................................................... 101

3.1.1 Problemstellung ................................................................................................... 101

3.1.2 Komponenten ....................................................................................................... 102

3.2 Neues Modul anlegen und konfigurieren ................................................................ 102

3.3 Middleware-Routing einrichten ................................................................................... 104

3.3.1 Routing-Parameter verstehen ......................................................................... 105

3.3.2 Routen für Pizza-Modul konfigurieren ......................................................... 105

3.4 Middleware-Actions implementieren ....................................................................... 108

3.4.1 Repositorys einrichten ........................................................................................ 109

3.4.2 Aktion für Introseite ............................................................................................ 113

3.4.3 Aktion für Pizzaseite ........................................................................................... 115

3.4.4 Aktion für Abstimmseite ................................................................................... 116

3.4.5 Aktion für Abstimmungsverarbeitung ......................................................... 117

3.5 Middleware-Templates erstellen ................................................................................. 120

3.5.1 Template-Konfiguration .................................................................................... 120

3.5.2 Template für Introseite ...................................................................................... 121

3.5.3 Template für Abstimmseite ............................................................................. 123

3.6 Middleware konfigurieren .............................................................................................. 126

3.6.1 Factory für die Repositorys ............................................................................... 126

3.6.2 Middleware-Factory für die Anzeige von Seiten ....................................... 128

3.6.3 Middleware-Factory für Verarbeitungen ..................................................... 129

3.6.4 Konfiguration für Middleware und Repositorys ........................................ 129

3.7 Zusammenfassung ............................................................................................................. 130

3.8 Übung und Lösung .............................................................................................................. 131

3.8.1 Aufgaben ................................................................................................................ 131

3.8.2 Lösung ...................................................................................................................... 134

3965-3.book Seite 7 Donnerstag, 6. Oktober 2016 1:19 13

Page 42: Zend Framework 3 – Das umfassende Handbuch

Inhalt

8

4 Datenbanken und Repositorys 139

4.1 Einleitung ................................................................................................................................ 139

4.1.1 Problemstellung ................................................................................................... 139

4.1.2 Komponenten ....................................................................................................... 140

4.1.3 Datenbank einrichten ......................................................................................... 140

4.2 Datenbankadapter konfigurieren ............................................................................... 141

4.3 Model-Layer definieren .................................................................................................... 143

4.4 Storage einrichten .............................................................................................................. 145

4.4.1 Interface für »PizzaStorage« ............................................................................ 145

4.4.2 Implementierung der »PizzaDbStorage« ..................................................... 146

4.4.3 Storage für Restaurant-Datenbanktabelle .................................................. 150

4.5 Repositorys implementieren ......................................................................................... 151

4.5.1 Repository für Pizzadaten ................................................................................. 152

4.5.2 Repository für Restaurants ............................................................................... 154

4.6 Integration in Middleware-Anwendung .................................................................. 155

4.6.1 Factorys für Storages .......................................................................................... 156

4.6.2 Factory für Repository ........................................................................................ 157

4.6.3 Konfiguration ........................................................................................................ 158

4.7 Zusammenfassung ............................................................................................................. 158

4.8 Übung und Lösung .............................................................................................................. 159

4.8.1 Aufgaben ................................................................................................................ 160

4.8.2 Lösung ...................................................................................................................... 161

5 Formulare und Benutzereingaben 165

5.1 Einleitung ................................................................................................................................ 165

5.1.1 Problemstellung ................................................................................................... 165

5.1.2 Komponenten ....................................................................................................... 166

5.2 Input-Filter erstellen .......................................................................................................... 166

5.2.1 Input-Filter-Klasse ............................................................................................... 167

5.2.2 Input-Filter-Factory ............................................................................................. 171

5.2.3 Input-Filter-Konfiguration ................................................................................ 172

5.3 Formulare erstellen ............................................................................................................ 172

5.3.1 Formular-Klasse .................................................................................................... 172

3965-3.book Seite 8 Donnerstag, 6. Oktober 2016 1:19 13

Inhalt

9

5.3.2 Formular-Factory .................................................................................................. 174

5.3.3 Formular-Konfiguration .................................................................................... 175

5.4 Aktionen anpassen ............................................................................................................. 176

5.4.1 Middleware für Pizzaseite überarbeiten ...................................................... 176

5.4.2 Middleware für Restaurantpreisverarbeitung überarbeiten ................ 178

5.5 Formulare ausgeben .......................................................................................................... 181

5.5.1 »Form«-View-Helper konfigurieren ............................................................... 182

5.5.2 Template für Ausgabe anpassen .................................................................... 182

5.6 Zusammenfassung ............................................................................................................. 185

5.7 Übung und Lösung .............................................................................................................. 185

5.7.1 Aufgaben ................................................................................................................ 185

5.7.2 Lösung ...................................................................................................................... 188

6 Internationalisierung 191

6.1 Einleitung ................................................................................................................................ 191

6.1.1 Problemstellung ................................................................................................... 192

6.1.2 Komponenten ....................................................................................................... 192

6.1.3 Neues »I18n Expressive«-Modul anlegen .................................................... 193

6.2 Routing überarbeiten ........................................................................................................ 194

6.2.1 Grundlegende Überlegungen .......................................................................... 194

6.2.2 Routen anpassen .................................................................................................. 195

6.2.3 Sprache bei Redirects setzen ............................................................................ 196

6.2.4 »Url«-View-Helper überschreiben .................................................................. 197

6.2.5 Route für Homepage anpassen ....................................................................... 200

6.3 Locale per Middleware setzen ....................................................................................... 202

6.3.1 »LocalizationMiddleware« erstellen .............................................................. 202

6.3.2 Middleware konfigurieren ................................................................................ 204

6.4 Texte übersetzen ................................................................................................................. 205

6.4.1 »Translator« konfigurieren ............................................................................... 206

6.4.2 »Translate«-View-Helper bereitstellen ......................................................... 208

6.4.3 »Translator« in View-Helper und Validatoren injizieren ........................ 208

6.4.4 Sprachdateien erstellen ..................................................................................... 212

6.4.5 Sprachfragmente durch Textidentifier ersetzen ....................................... 214

6.4.6 Sprachauswahl einfügen ................................................................................... 217

6.5 Datum, Uhrzeit und Währungen ausgeben ............................................................ 218

3965-3.book Seite 9 Donnerstag, 6. Oktober 2016 1:19 13

Page 43: Zend Framework 3 – Das umfassende Handbuch

Inhalt

10

6.6 Datenbankinhalte internationalisieren .................................................................... 220

6.7 Zusammenfassung ............................................................................................................. 220

6.8 Übung und Lösung .............................................................................................................. 221

6.8.1 Aufgaben ................................................................................................................ 221

6.8.2 Lösung ...................................................................................................................... 223

7 Authentifizierung und Autorisierung 227

7.1 Einleitung ................................................................................................................................ 227

7.1.1 Problemstellung ................................................................................................... 227

7.1.2 Komponenten ....................................................................................................... 228

7.1.3 Vorbereitungen ..................................................................................................... 228

7.2 Benutzerrechte konfigurieren ....................................................................................... 231

7.2.1 Benötigte Benutzerrechte ermitteln ............................................................. 231

7.2.2 Rollen implementieren ...................................................................................... 233

7.2.3 RBAC implementieren ........................................................................................ 235

7.3 Sessions konfigurieren ..................................................................................................... 236

7.4 Benutzer authentifizieren ............................................................................................... 238

7.4.1 Authentifizierungsservice konfigurieren ..................................................... 239

7.4.2 Authentifizierung in Middleware durchführen ......................................... 241

7.4.3 Factory für Middleware konfigurieren .......................................................... 244

7.5 Autorisierung angemeldeter Benutzer ..................................................................... 245

7.5.1 Middleware für Autorisierung einrichten .................................................... 246

7.5.2 Fehlerseite für nicht autorisierte Benutzer ................................................. 249

7.6 Authentifizierten Benutzer handhaben ................................................................... 251

7.6.1 Benutzerrechte im Template überprüfen .................................................... 251

7.6.2 View-Helper für Benutzerrechtsprüfung einsetzen ................................. 254

7.6.3 Authentifizierten Benutzer ausgeben .......................................................... 255

7.6.4 Benutzer ausloggen ............................................................................................ 257

7.7 Zusammenfassung ............................................................................................................. 259

7.8 Übung und Lösung .............................................................................................................. 260

7.8.1 Aufgaben ................................................................................................................ 261

7.8.2 Lösung ...................................................................................................................... 263

3965-3.book Seite 10 Donnerstag, 6. Oktober 2016 1:19 13

Inhalt

11

8 Zend\Expressive-Anwendung optimieren 267

8.1 Einleitung ................................................................................................................................ 268

8.1.1 Problemstellung ................................................................................................... 268

8.1.2 Komponenten ....................................................................................................... 268

8.2 Startseite entfernen ........................................................................................................... 268

8.2.1 Aufräumarbeiten ................................................................................................. 269

8.2.2 Middleware zum Umleiten erstellen ............................................................ 270

8.3 Mehrstufiges Layout einrichten ................................................................................... 272

8.3.1 Layout-Template aufteilen ............................................................................... 273

8.3.2 »LayoutModel« erstellen ................................................................................... 275

8.3.3 »ViewRendererFactory« überschreiben ....................................................... 277

8.4 View-Helper für Formularausgabe erstellen .......................................................... 279

8.4.1 Vorüberlegungen ................................................................................................. 279

8.4.2 Bootstrap-Modul einrichten ............................................................................. 280

8.4.3 Formular-View-Helper erstellen ..................................................................... 280

8.4.4 Formular-View-Helper einsetzen ................................................................... 283

8.5 Traits einsetzen zur Codereduktion ............................................................................ 284

8.5.1 Redundanten Code erkennen .......................................................................... 285

8.5.2 Redundanten Code durch Traits ersetzen ................................................... 287

8.6 Zusammenfassung ............................................................................................................. 289

8.7 Übung und Lösung .............................................................................................................. 289

8.7.1 Aufgaben ................................................................................................................ 289

8.7.2 Lösung ...................................................................................................................... 290

9 Unit-Tests für Middleware-Anwendungen 293

9.1 Einleitung ................................................................................................................................ 294

9.1.1 Problemstellung ................................................................................................... 294

9.1.2 Komponenten ....................................................................................................... 294

9.2 Middleware-Aktionen testen ........................................................................................ 294

9.2.1 Abstrakte Testklasse ........................................................................................... 295

9.2.2 Test für Pizza-Introseite ..................................................................................... 299

9.2.3 Test für Speicherung von Restaurantpreisen ............................................. 302

9.2.4 Test für Umleitung auf Introseite .................................................................. 307

9.2.5 Tests der Factorys für Aktions-Middleware-Klassen ................................ 309

9.2.6 Weitere Middleware-Aktionen testen .......................................................... 311

3965-3.book Seite 11 Donnerstag, 6. Oktober 2016 1:19 13

Page 44: Zend Framework 3 – Das umfassende Handbuch

Inhalt

12

9.3 Middleware aus der Pipeline testen ........................................................................... 311

9.3.1 Test für »CheckRootUriMiddleware« ............................................................ 312

9.3.2 Test für »InjectTranslatorMiddleware« ........................................................ 314

9.3.3 Test für »AuthorizationMiddleware« ............................................................ 317

9.3.4 Weitere Pipeline-Middlewares und deren Factorys testen .................... 323

9.4 Formulare und Modelklassen testen .......................................................................... 324

9.4.1 Formulare testen .................................................................................................. 325

9.4.2 Input-Filter testen ................................................................................................ 327

9.4.3 Repositorys testen ............................................................................................... 330

9.4.4 Storages testen ..................................................................................................... 335

9.5 Weitere Klassen testen ..................................................................................................... 342

9.6 Zusammenfassung ............................................................................................................. 343

9.7 Übung und Lösung .............................................................................................................. 344

9.7.1 Aufgaben ................................................................................................................ 345

9.7.2 Lösung ...................................................................................................................... 346

TEIL III MVC-Anwendungen

10 MVC-Anwendung einrichten 353

10.1 Einleitung ................................................................................................................................ 354

10.1.1 Problemstellung ................................................................................................... 354

10.1.2 Komponenten ....................................................................................................... 354

10.2 Installation der Beispielanwendung .......................................................................... 354

10.2.1 Installation unter Ubuntu Linux ..................................................................... 355

10.2.2 Installation unter OS X und macOS Sierra ................................................... 355

10.2.3 Installation unter Windows ............................................................................. 356

10.2.4 Virtual Host einrichten ....................................................................................... 356

10.3 Aufbau einer Zend Framework 3-MVC-Anwendung .......................................... 357

10.3.1 »composer.json«-Datei ...................................................................................... 358

10.3.2 Vendorverzeichnis ............................................................................................... 360

10.3.3 Konfigurationsverzeichnis ................................................................................ 361

10.3.4 Datenverzeichnis .................................................................................................. 364

10.3.5 Öffentliches Verzeichnis .................................................................................... 365

10.3.6 Modulverzeichnis ................................................................................................. 369

10.4 Aufbau eines Zend Framework 3-Moduls ................................................................ 369

10.4.1 Modulklasse ........................................................................................................... 370

3965-3.book Seite 12 Donnerstag, 6. Oktober 2016 1:19 13

Inhalt

13

10.4.2 Konfigurationsverzeichnis ................................................................................ 372

10.4.3 Source-Verzeichnis .............................................................................................. 373

10.4.4 View-Verzeichnis .................................................................................................. 374

10.5 Fremdmodule ........................................................................................................................ 375

10.5.1 ZendDeveloperTools ........................................................................................... 375

10.5.2 SanSessionToolbar ............................................................................................... 376

10.5.3 BjyProfiler ............................................................................................................... 376

10.5.4 AssetManager ....................................................................................................... 377

10.6 Übung ....................................................................................................................................... 378

11 Controller und View 381

11.1 Einleitung ................................................................................................................................ 381

11.1.1 Problemstellung ................................................................................................... 381

11.1.2 Komponenten ....................................................................................................... 382

11.2 Module erstellen und konfigurieren .......................................................................... 382

11.2.1 Benötigte Funktionen ermitteln ..................................................................... 383

11.2.2 Funktionen auf Module aufteilen, Schritt 1 ................................................ 383

11.2.3 Funktionen auf Module aufteilen, Schritt 2 ................................................ 384

11.2.4 Module anlegen und konfigurieren ............................................................... 386

11.3 Routing konfigurieren ...................................................................................................... 389

11.3.1 Routen für die Module erstellen ..................................................................... 389

11.3.2 Routen-Konfiguration testen ........................................................................... 394

11.4 Action-Controller anlegen ............................................................................................... 395

11.4.1 Repository für Annoncen ................................................................................... 395

11.4.2 Controller für die Ausgabe von Annoncen .................................................. 399

11.4.3 Weitere Controller ............................................................................................... 405

11.5 Templates erstellen ............................................................................................................ 406

11.5.1 Controller überarbeiten ..................................................................................... 407

11.5.2 Templates einrichten .......................................................................................... 408

11.5.3 Templates konfigurieren ................................................................................... 414

11.5.4 Ausgabe kontrollieren ........................................................................................ 416

11.6 Paginierung hinzufügen .................................................................................................. 418

11.6.1 Repository anpassen ........................................................................................... 418

11.6.2 Template für Seitennavigation erstellen ..................................................... 420

11.6.3 Seitennavigation in Templates integrieren ................................................ 422

3965-3.book Seite 13 Donnerstag, 6. Oktober 2016 1:19 13

Page 45: Zend Framework 3 – Das umfassende Handbuch

Inhalt

14

11.7 Navigation hinzufügen ..................................................................................................... 423

11.7.1 Ausgabe der Navigation im Seitenkopf ........................................................ 424

11.7.2 Navigationselemente in Modulen konfigurieren ..................................... 424

11.8 Zusammenfassung ............................................................................................................. 427

11.9 Übung ....................................................................................................................................... 428

12 Model-Layer implementieren 431

12.1 Einleitung ................................................................................................................................ 431

12.1.1 Problemstellung ................................................................................................... 431

12.1.2 Komponenten ....................................................................................................... 432

12.1.3 Vorbereitungen ..................................................................................................... 433

12.2 Model-Layer definieren .................................................................................................... 433

12.3 Entitäten implementieren .............................................................................................. 434

12.3.1 Entitäten, Beziehungen und Module ............................................................ 435

12.3.2 Entität für Unternehmen .................................................................................. 436

12.3.3 Entität für Annoncen .......................................................................................... 440

12.4 Hydratoren implementieren .......................................................................................... 444

12.4.1 Hydrator erstellen ................................................................................................ 444

12.4.2 Vorhandene Hydrator-Strategies verwenden ............................................ 447

12.4.3 Neue Hydrator-Strategy implementieren ................................................... 449

12.5 Storage mit Table-Gateway umsetzen ...................................................................... 453

12.5.1 Datenbank einrichten ......................................................................................... 453

12.5.2 Datenbankadapter konfigurieren .................................................................. 454

12.5.3 Storage-Interface definieren ............................................................................ 455

12.5.4 Storage für Annoncen implementieren ....................................................... 456

12.5.5 Factory für »AdvertDbStorage« erstellen .................................................... 462

12.5.6 Storage testweise einsetzen ............................................................................ 464

12.5.7 Storage für Unternehmen ................................................................................. 466

12.6 Repository und Templates überarbeiten .................................................................. 467

12.6.1 Storage im Repository verwenden ................................................................. 467

12.6.2 Factory für Repository anpassen ..................................................................... 469

12.6.3 Templates anpassen ........................................................................................... 470

12.7 Zusammenfassung ............................................................................................................. 471

12.8 Übung ....................................................................................................................................... 472

3965-3.book Seite 14 Donnerstag, 6. Oktober 2016 1:19 13

Inhalt

15

13 Formularverarbeitung im MVC 475

13.1 Einleitung ................................................................................................................................ 475

13.1.1 Problemstellung ................................................................................................... 475

13.1.2 Komponenten ....................................................................................................... 477

13.2 Vorbereitungen .................................................................................................................... 477

13.2.1 Entitäten erweitern ............................................................................................. 477

13.2.2 Storages erweitern .............................................................................................. 478

13.2.3 Repositorys erweitern ......................................................................................... 480

13.2.4 Weitere Veränderungen .................................................................................... 482

13.3 Input-Filter erstellen .......................................................................................................... 482

13.3.1 Input-Filter für Annoncen ................................................................................. 483

13.3.2 Input-Filter konfigurieren ................................................................................. 487

13.3.3 Input-Filter für Unternehmen ......................................................................... 489

13.4 Formulare implementieren ............................................................................................ 489

13.4.1 Formular für Annoncen ...................................................................................... 489

13.4.2 Formular konfigurieren ...................................................................................... 496

13.4.3 Formular für Unternehmen .............................................................................. 500

13.5 Formulare ausgeben .......................................................................................................... 502

13.5.1 Formular an den View übergeben .................................................................. 502

13.5.2 Formular im View ausgeben ............................................................................ 506

13.5.3 Genehmigen, Sperren und Löschen im View vorbereiten ...................... 511

13.5.4 Formular für Unternehmen ausgeben ......................................................... 513

13.6 Formulare verarbeiten ...................................................................................................... 513

13.6.1 Flash-Messenger einrichten ............................................................................. 513

13.6.2 Neue Annoncen speichern ................................................................................ 514

13.6.3 Bestehende Annoncen speichern ................................................................... 517

13.6.4 Bestehende Annoncen löschen, genehmigen und sperren ................... 519

13.6.5 Formularverarbeitung für Unternehmen .................................................... 521

13.7 HTML-Eingaben ermöglichen ........................................................................................ 522

13.7.1 CKEditor einsetzen .............................................................................................. 522

13.7.2 HTML Purifier einsetzen ..................................................................................... 526

13.8 Dateiuploads implementieren ...................................................................................... 529

13.8.1 Input-Filter anpassen .......................................................................................... 530

13.8.2 Neuen Filter für Logos erstellen ...................................................................... 532

13.8.3 Formular anpassen .............................................................................................. 533

13.8.4 Controller überarbeiten ..................................................................................... 537

3965-3.book Seite 15 Donnerstag, 6. Oktober 2016 1:19 13

Page 46: Zend Framework 3 – Das umfassende Handbuch

Inhalt

16

13.9 Ausgabe vereinfachen ...................................................................................................... 539

13.9.1 Ausgabe der Formulare vereinfachen ........................................................... 540

13.9.2 Ausgabe der Seitenüberschrift vereinfachen ............................................. 541

13.10 Zusammenfassung ............................................................................................................. 542

13.11 Übung ....................................................................................................................................... 542

14 Internationalisierung im MVC 545

14.1 Einleitung ................................................................................................................................ 545

14.1.1 Problemstellung ................................................................................................... 545

14.1.2 Komponenten ....................................................................................................... 546

14.2 Routing überarbeiten und Locale setzen .................................................................. 547

14.2.1 Routing anpassen ................................................................................................ 547

14.2.2 Locale per Event-Listener setzen ..................................................................... 550

14.3 Texte übersetzen ................................................................................................................. 555

14.3.1 Translator konfigurieren .................................................................................... 556

14.3.2 Übersetzungsdateien erstellen ....................................................................... 557

14.3.3 Texte in Templates übersetzen ....................................................................... 559

14.3.4 Texte in Input-Filtern übersetzen ................................................................... 562

14.3.5 Texte in Formularen übersetzen ..................................................................... 564

14.3.6 Texte in Controllern übersetzen ..................................................................... 567

14.3.7 Texte in der Navigation übersetzen .............................................................. 568

14.4 Datum und Uhrzeiten ausgeben .................................................................................. 569

14.5 Sprachwechsler einfügen ................................................................................................ 570

14.6 Zusammenfassung ............................................................................................................. 572

14.7 Übung ....................................................................................................................................... 573

15 Authentifizierung und Autorisierung im MVC 575

15.1 Einleitung ................................................................................................................................ 575

15.1.1 Problemstellung ................................................................................................... 575

15.1.2 Komponenten ....................................................................................................... 576

15.1.3 Vorbereitungen ..................................................................................................... 577

15.1.4 Abstrakte Formulare mit abstrakter Factory .............................................. 579

15.1.5 Abstrakte Factory für View-Helper ................................................................. 584

3965-3.book Seite 16 Donnerstag, 6. Oktober 2016 1:19 13

Inhalt

17

15.2 Benutzerrechte definieren .............................................................................................. 586

15.2.1 Vorüberlegungen ................................................................................................. 587

15.2.2 Benutzerrollen definieren ................................................................................. 587

15.2.3 Ressourcen und Privilegien definieren ......................................................... 589

15.2.4 ACL konfigurieren ................................................................................................ 591

15.2.5 Konfiguration für Benutzerrechte erstellen ................................................ 594

15.3 Sessions konfigurieren ..................................................................................................... 597

15.4 Benutzer authentifizieren ............................................................................................... 600

15.4.1 Vorüberlegungen ................................................................................................. 600

15.4.2 Authentifizierungsservice mit Adapter konfigurieren ............................ 602

15.4.3 Event-Listener für Authentifizierung implementieren ........................... 605

15.4.4 Event-Listener konfigurieren ............................................................................ 612

15.4.5 Event-Listener registrieren ................................................................................ 613

15.4.6 Anpassungen in Controller und Views ......................................................... 616

15.5 Benutzer autorisieren ....................................................................................................... 618

15.5.1 Event-Listener für Autorisierung erstellen .................................................. 620

15.5.2 Event-Listener konfigurieren und registrieren ........................................... 623

15.5.3 Event-Listener registrieren ................................................................................ 624

15.6 Menü durch Benutzerrechte einschränken ............................................................. 626

15.6.1 Event-Listener für Autorisierung erweitern ................................................ 626

15.6.2 Konfiguration für Navigation erweitern ...................................................... 629

15.6.3 Menüausgabe prüfen ......................................................................................... 630

15.7 User-Widget einbauen ...................................................................................................... 632

15.7.1 View-Helper erstellen ......................................................................................... 632

15.7.2 View-Helper-Template ....................................................................................... 633

15.7.3 View-Helper konfigurieren ............................................................................... 634

15.7.4 User-Widget ins Layout einbauen .................................................................. 636

15.8 Zusammenfassung ............................................................................................................. 638

15.9 Übung ....................................................................................................................................... 638

16 Tests für MVC-Anwendungen 641

16.1 Einleitung ................................................................................................................................ 641

16.1.1 Problemstellung ................................................................................................... 642

16.1.2 Komponenten ....................................................................................................... 642

16.1.3 Vorbereitungen ..................................................................................................... 643

3965-3.book Seite 17 Donnerstag, 6. Oktober 2016 1:19 13

Page 47: Zend Framework 3 – Das umfassende Handbuch

Inhalt

18

16.2 Modulklassen testen ......................................................................................................... 644

16.3 Event-Listener testen ........................................................................................................ 647

16.3.1 »I18nListener« testen ......................................................................................... 648

16.3.2 »AuthorizationListener« testen ...................................................................... 657

16.3.3 Weitere Event-Listener testen ......................................................................... 666

16.4 Integrationstests für Controller schreiben .............................................................. 667

16.4.1 DbUnit und Zend\Test kombinieren ............................................................. 669

16.4.2 Datenbank mit Testdaten einrichten ............................................................ 674

16.4.3 Controller für Startseite testen ....................................................................... 675

16.4.4 Controller für Anzeige von Annoncen testen ............................................. 682

16.4.5 Controller für Pflege von Annoncen testen ................................................. 689

16.5 Weitere Klassen testen ..................................................................................................... 699

16.6 Zusammenfassung ............................................................................................................. 700

16.7 Übung ....................................................................................................................................... 701

TEIL IV Weitere Themen

17 Migration vom ZF2 und ZF1 705

17.1 Migration – eine Einführung .......................................................................................... 705

17.2 Migration vom ZF2 zum ZF3 .......................................................................................... 708

17.2.1 Checkliste für Migration vom ZF2 zum ZF3 ................................................ 709

17.2.2 Bereits migrierte ZF3-Komponenten ............................................................. 709

17.2.3 MVC-Komponente ............................................................................................... 710

17.2.4 Service-Manager .................................................................................................. 713

17.2.5 Event-Manager ..................................................................................................... 719

17.2.6 Weitere Komponenten ....................................................................................... 720

17.2.7 Zend-Framework-Meta-Package .................................................................... 721

17.2.8 Zend-Framework-Anwendung migrieren .................................................... 723

17.3 Migration vom ZF1 zum ZF3 .......................................................................................... 726

17.3.1 Checkliste für Migration vom ZF1 zum ZF3 ................................................ 728

17.3.2 Wesentliche Änderungen zwischen ZF1 und ZF3 ..................................... 729

17.3.3 Vorbereitungen in der ZF1-Anwendung treffen ....................................... 730

17.3.4 Neue Struktur für den parallelen Betrieb von ZF1 und ZF3 ................... 732

17.3.5 Parallele Front-Controller betreiben .............................................................. 735

3965-3.book Seite 18 Donnerstag, 6. Oktober 2016 1:19 13

Inhalt

19

17.3.6 Anwendungskonfiguration migrieren .......................................................... 736

17.3.7 MVC migrieren ...................................................................................................... 737

17.3.8 Model-Layer migrieren ....................................................................................... 742

17.3.9 Weitere Komponenten migrieren .................................................................. 744

17.3.10 Alte ZF1-Anwendung entfernen ..................................................................... 745

17.4 Migration von MVC zur Middleware .......................................................................... 746

17.4.1 Checkliste für Migration von MVC zur Middleware ................................. 748

17.4.2 Config-Provider für Module einrichten ........................................................ 748

17.4.3 Anwendungskonfiguration migrieren .......................................................... 750

17.4.4 Composer-Konfiguration anpassen ............................................................... 751

17.4.5 Von Controllern zu Aktions-Middleware migrieren ................................. 752

17.4.6 Routing migrieren ................................................................................................ 756

17.4.7 Templates verschieben und anpassen .......................................................... 759

17.4.8 Front-Controller anpassen ................................................................................ 760

17.4.9 Event-Listener zu Pipeline-Middleware migrieren ................................... 760

17.5 Zusammenfassung ............................................................................................................. 761

18 Webservices und Apigility 763

18.1 Einführung: RESTful Webservice .................................................................................. 763

18.2 RESTful Webservice mit Zend\Mvc implementieren .......................................... 765

18.2.1 JSON als Rückgabe erlauben ............................................................................ 765

18.2.2 Neues Modul anlegen und Routing konfigurieren ................................... 766

18.2.3 RESTful Controller einrichten ........................................................................... 769

18.2.4 RESTful Webservice testen ............................................................................... 776

18.3 RESTful Webservice mit Zend\Expressive umsetzen .......................................... 778

18.3.1 Modul anlegen und konfigurieren ................................................................. 778

18.3.2 Routen und Middleware konfigurieren ........................................................ 779

18.3.3 Aktions-Middleware für »GET« und »POST« ............................................... 781

18.3.4 Zusammenfassung .............................................................................................. 785

18.4 RESTful Webservice mit Apigility implementieren .............................................. 785

18.4.1 Datenbankgestützte REST API erstellen ....................................................... 786

18.4.2 REST API mit Postman testen ........................................................................... 788

18.4.3 Weitere Möglichkeiten mit Apigility ............................................................. 791

18.5 Zusammenfassung ............................................................................................................. 791

3965-3.book Seite 19 Donnerstag, 6. Oktober 2016 1:19 13

Page 48: Zend Framework 3 – Das umfassende Handbuch

Inhalt

20

19 Konsolenanwendungen 793

19.1 Komponenten ....................................................................................................................... 794

19.2 Vorbereitungen .................................................................................................................... 794

19.3 Einführung in ZF\Console ................................................................................................ 795

19.4 Abstrakte Command-Klasse ........................................................................................... 796

19.5 Befehl zum Prüfen des Datenbankadapters ........................................................... 798

19.6 Befehl zum Anzeigen der Datenbanktabellen ....................................................... 800

19.7 Generator für Entitätsklassen ....................................................................................... 802

19.8 Befehl zum Anlegen einer Entität ............................................................................... 807

19.9 Zusammenfassung ............................................................................................................. 813

TEIL V Komponenten

20 Zend-Framework-Komponenten 817

20.1 Zend\Authentication ........................................................................................................ 818

20.1.1 Authentifizierungsadapter ............................................................................... 818

20.1.2 Authentifizierungsservice ................................................................................. 819

20.1.3 Identität speichern .............................................................................................. 821

20.2 Zend\Cache ............................................................................................................................ 822

20.2.1 Cache-Storage konfigurieren ........................................................................... 823

20.2.2 Cache-Pattern einsetzen ................................................................................... 824

20.3 Zend\Code .............................................................................................................................. 825

20.4 Zend\Config .......................................................................................................................... 827

20.4.1 Lesen von Konfigurationsdateien ................................................................... 828

20.4.2 Schreiben von Konfigurationsdateien .......................................................... 829

20.5 Zend\Console ........................................................................................................................ 830

20.5.1 Konsolen-Route konfigurieren ........................................................................ 830

20.5.2 Konsolen-Controller mit Prompts verwenden ........................................... 831

20.6 Zend\Db .................................................................................................................................. 832

20.6.1 Zend\Db\Adapter ................................................................................................ 832

20.6.2 Zend\Db\ResultSet .............................................................................................. 833

20.6.3 Zend\Db\Sql .......................................................................................................... 834

20.6.4 Zend\Db\TableGateway .................................................................................... 838

3965-3.book Seite 20 Donnerstag, 6. Oktober 2016 1:19 13

Inhalt

21

20.7 Zend\Diactoros .................................................................................................................... 841

20.8 Zend\EventManager ......................................................................................................... 842

20.8.1 Event-Manager in Klasse einsetzen ............................................................... 843

20.8.2 Event-Listener erstellen ..................................................................................... 844

20.8.3 Event-Listener und Klasse kombinieren ....................................................... 846

20.9 Zend\Expressive .................................................................................................................. 846

20.9.1 Unterstützte Komponenten ............................................................................. 847

20.9.2 Installer für Zend\Expressive ........................................................................... 848

20.10 Zend\Filter ............................................................................................................................. 848

20.10.1 Filter direkt einsetzen ......................................................................................... 849

20.10.2 Statischen Filter einsetzen ................................................................................ 850

20.10.3 Filterketten einsetzen ......................................................................................... 850

20.10.4 Filter für Komprimierung und Verschlüsselung einsetzen .................... 851

20.11 Zend\Form ............................................................................................................................. 851

20.11.1 Formular programmatisch generieren ......................................................... 852

20.11.2 Fieldsets erstellen ................................................................................................ 853

20.11.3 Formular per Factory erstellen ........................................................................ 853

20.11.4 Formulare ausgeben ........................................................................................... 855

20.12 Zend\Hydrator ..................................................................................................................... 857

20.12.1 Hydratoren einsetzen ......................................................................................... 857

20.12.2 Hydrator-Strategies einsetzen ........................................................................ 860

20.13 Zend\I18n ............................................................................................................................... 861

20.13.1 Translator einsetzen ........................................................................................... 861

20.13.2 Ausgaben per View-Helper ............................................................................... 864

20.14 Zend\InputFilter .................................................................................................................. 864

20.14.1 Input-Filter definieren ........................................................................................ 865

20.14.2 Mit Input-Filter Eingaben validieren ............................................................. 866

20.14.3 Input-Filter hierarchisch aufbauen ................................................................ 867

20.15 Zend\ModuleManager ..................................................................................................... 868

20.15.1 Vorgaben für Module ......................................................................................... 869

20.15.2 Feature-Interfaces für Modulklassen ............................................................ 869

20.15.3 Konfiguration für Modul-Manager ................................................................ 871

20.16 Zend\Mvc ............................................................................................................................... 873

20.16.1 Teilkomponenten ................................................................................................. 874

20.16.2 Eventbasierter MVC-Prozess ............................................................................ 875

20.17 Zend\Navigation ................................................................................................................. 876

20.17.1 Konfiguration für Zend\Navigation .............................................................. 877

20.17.2 Ausgabe einer Navigation ................................................................................. 878

3965-3.book Seite 21 Donnerstag, 6. Oktober 2016 1:19 13

Page 49: Zend Framework 3 – Das umfassende Handbuch

Inhalt

22

20.18 Zend\Paginator .................................................................................................................... 878

20.18.1 Adapter für Zend\Paginator ............................................................................. 878

20.18.2 Vorgehensweise beim Einsatz ......................................................................... 879

20.18.3 Anbindung an eine Datenbank ....................................................................... 879

20.19 Zend\Permissions\Acl ...................................................................................................... 881

20.19.1 Aufbau eines ACL-Objekts ................................................................................. 881

20.19.2 Rechte mit einem ACL-Objekt abfragen ....................................................... 882

20.20 Zend\Permissions\Rbac ................................................................................................... 883

20.20.1 Aufbau eines RBAC-Objekts ............................................................................. 884

20.20.2 Rechte in einem RBAC-Objekt abfragen ....................................................... 885

20.21 Zend\ServiceManager ...................................................................................................... 886

20.21.1 Konfiguration ........................................................................................................ 886

20.21.2 Factorys für Services ............................................................................................ 888

20.21.3 Spezialisierte Service-Manager ....................................................................... 890

20.22 Zend\Session ........................................................................................................................ 891

20.22.1 Session-Container nutzen ................................................................................. 891

20.22.2 Session-Konfiguration ........................................................................................ 892

20.23 Zend\Stratigility .................................................................................................................. 893

20.23.1 Middleware-Pipeline ........................................................................................... 893

20.24 Zend\Test ............................................................................................................................... 895

20.25 Zend\Validator ..................................................................................................................... 896

20.25.1 Validatoren direkt einsetzen ............................................................................ 897

20.25.2 Statischen Validator einsetzen ........................................................................ 897

20.25.3 Validatorketten einsetzen ................................................................................. 898

20.25.4 Fehlermeldungen anpassen ............................................................................. 898

20.26 Zend\View .............................................................................................................................. 899

20.26.1 Templates erstellen ............................................................................................. 899

20.26.2 Template verarbeiten und ausgeben ............................................................ 900

20.26.3 Alternativ JSON ausgeben ................................................................................. 902

20.26.4 View-Helper einsetzen ....................................................................................... 902

20.27 Composer-Plug-in Zend\ComponentInstaller ....................................................... 903

20.27.1 Installation in Zend\Expressive-Anwendung ............................................. 903

20.27.2 Installation in Zend\Mvc-Anwendung ......................................................... 904

20.28 Weitere Komponenten ..................................................................................................... 904

3965-3.book Seite 22 Donnerstag, 6. Oktober 2016 1:19 13

Inhalt

23

Anhang 907

A Objektorientierte Programmierung in PHP ............................................................. 909

A.1 Grundbegriffe ........................................................................................................ 909

A.2 Vererbung ............................................................................................................... 911

A.3 Interfaces ................................................................................................................ 912

A.4 Traits ......................................................................................................................... 912

A.5 Weitere Begriffe ................................................................................................... 914

B Architekturmuster und Entwurfsmuster .................................................................. 915

B.1 Architekturmuster ............................................................................................... 915

B.2 Entwurfsmuster ................................................................................................... 920

C Unit-Testing mit PHPUnit ................................................................................................ 929

C.1 PHPUnit installieren ............................................................................................ 929

C.2 Tests einrichten für PHPUnit ............................................................................ 930

C.3 Einfache Tests schreiben mit PHPUnit ......................................................... 931

C.4 Data-Provider mit PHPUnit verwenden ....................................................... 934

C.5 Exceptions mit PHPUnit testen ....................................................................... 936

C.6 Mock-Objekte mit Prophecy und PHPUnit einsetzen .............................. 937

C.7 Tests ausführen für PHPUnit ........................................................................... 941

C.8 Weitere Möglichkeiten mit PHPUnit ............................................................. 942

D Zend Framework 3 und Doctrine ................................................................................. 943

D.1 Einführung zu Doctrine ...................................................................................... 943

D.2 Doctrine 2 oder Zend\Db ................................................................................... 944

D.3 Doctrine-Module für das Zend Framework ................................................. 945

D.4 Weitere Hinweise zur Integration .................................................................. 948

Index ........................................................................................................................................................ 951

3965-3.book Seite 23 Donnerstag, 6. Oktober 2016 1:19 13

Page 50: Zend Framework 3 – Das umfassende Handbuch

Index

951

Index

A

ACL ................................................................... 233, 586

Action-Controller ................................................. 395

Anemic Domain Model ..................................... 437

AngularJS ................................................................. 763

Apache 2 .......................... 45, 78, 88, 356, 367, 735

apachectl ..................................................................... 48

Apigility .................................................. 60, 763, 785

datenbankgestützte REST API .................... 786

Features ............................................................... 791

HAL JSON ............................................................ 786

Postman .............................................................. 788

Skeleton Application ......................................... 60

Architekturmuster .............................................. 915

Domain-Driven Design ................................. 917

Model-View-Controller ................................. 919

Schichtenmodell .............................................. 915

AssetManager ........................................................ 377

AuthenticationListener ........................... 605, 667

Authentifizierung ...................................... 227, 575

Authentifizierungsservice ............................ 821

Benutzer ausgeben ......................................... 255

Benutzer ausloggen ........................................ 257

Bestandteile ....................................................... 601

Controller ........................................................... 610

mit Zend\Expressive ....................................... 227

mit Zend\Mvc ................................................... 575

Autoloading ........................................................... 103

Autorisierung ..................................... 227, 245, 575

AuthorizationListener ......................... 620, 657

AuthorizationMiddleware ................. 246, 317

Bestandteile ....................................................... 619

Middleware-Pipeline ...................................... 249

Zend\Permissions\Acl ................................... 586

Zend\Permissions\Rbac ................................ 233

B

Beispielanwendungen .......................................... 62

Entity-Builder ....................................................... 66

Vote My Pizza ...................................................... 62

Zend Framework Center .................................. 63

ZF1legacy ................................................................ 66

ZF3buch Examples ............................................. 65

Benutzereingaben ..................................... 165, 475

Benutzerrechte ..................................................... 231

im Template abfragen .................................. 251

BjyProfiler ............................................................... 376

Bootstrap ........................................................ 279, 494

BootstrapFlashMessenger-View-Helper .... 514

BootstrapForm-View-Helper .......................... 540

C

CamelCaseToDash-Filter .................................. 622

CheckRootUriMiddleware ................................ 312

CKEditor .................................................................. 522

Class Name Resolution ...................................... 888

Class-Map ................................................................ 427

Composer ................................................ 55, 141, 903

Autoloading ...................................................... 103

Befehle .................................................................... 52

Migration ........................................................... 751

Überblick ............................................................... 52

ConfigManager ........................................................ 83

ConfigProvider .................. 93, 102, 193, 208, 280

Migration ........................................................... 748

Controller ....................................................... 381, 399

Dateiuploads .................................................... 537

Factory ................................................................ 403

Integrationstests ................. 667, 675, 682, 689

Übersetzungen ................................................. 567

Unit-Tests ........................................................... 668

ControllerManager ............................................. 890

Controller-Plug-in

Flash-Messenger .............................................. 513

Identity ................................................................ 617

Params ....................................................... 402, 740

Redirect ...................................................... 402, 740

Url ................................................................. 504, 549

ControllerPluginManager ................................ 890

CouchDb .................................................................. 832

Cross-Site-Request-Forgery ............................. 494

Cross-Site-Scripting ............................................ 526

CSRF ........................................................................... 494

D

DateFormat-View-Helper ................................. 570

Dateiuploads ......................................................... 529

Datenbanken .................................................. 50, 139

Datenbankadapter ................................ 141, 454

3965-3.book Seite 951 Donnerstag, 6. Oktober 2016 1:19 13

Page 51: Zend Framework 3 – Das umfassende Handbuch

Index

952

Datenbanken (Forts.)

einrichten ................................................. 140, 453

Primärschlüssel ................................................ 479

Datenverzeichnis .......................................... 87, 364

DateTime ....................................................... 219, 447

testen .................................................................... 697

DbUnit ................................................... 324, 669, 942

Data-Sets ............................................................ 671

mit Zend\Test .................................................... 669

Testdatenbank .................................................. 674

Dependency Injection .............. 36, 400, 404, 921

Doctrine ................................................................... 943

Domain-Driven Design ..................................... 917

E

Eclipse .......................................................................... 54

Entitäten ............................................... 145, 434, 477

Anemic Domain Model ................................. 437

Hydratoren ........................................................ 444

Entity-Builder ................................................. 66, 794

Entwurfsmuster .................................................... 920

Adapter ................................................................ 920

Anemic Domain Model ................................. 437

Dependency Injection .................................... 921

Factory .......................................................... 36, 923

Repository .......................................................... 924

Table Data Gateway ............................ 838, 927

Ereignisgesteuerte Entwicklung ............. 36, 842

Event-Listener ....................................................... 844

Authentifizierung ............................................ 605

Autorisierung .................................................... 620

im Event-Manager registrieren ................. 613

in Klasse einsetzen .......................................... 846

Konfiguration ................................................... 612

Locale setzen ..................................................... 550

Migration ........................................................... 760

Unit-Test ............................................................. 647

Event-Manager ..................................... 36, 552, 843

F

Factory ...................... 126, 156, 171, 174, 244, 923

abstrakte Factory ............................................ 584

komplexe Factory ............................................ 498

Performance ...................................................... 584

Fehlerseite ............................................................... 249

Fieldsets ................................................................... 853

FilterManager ........................................................ 890

Flash-Messenger ......................................... 513, 713

FormElementErrors-View-Helper ................. 507

FormElementManager ............................. 499, 891

FormElement-View-Helper ............................. 507

FormLabel-View-Helper .................................... 506

Formulare ............................................ 165, 172, 489

Ausgabe .............................................................. 502

HTML-Eingaben ............................................... 522

verarbeiten ........................................................ 513

Formularverarbeitung ....................................... 475

Form-View-Helper ............................ 506, 508, 855

Fremdmodule ....................................................... 375

Front-Controller ............................................ 89, 365

Full-Stack-Framework ........................................... 35

G

Git .................................................................................. 51

GitHub-API-Limitierung ...................................... 77

GitLab ....................................................................... 369

H

H1-View-Helper .................................................... 541

HAL JSON ................................................................. 786

Homebrew ................................................................. 43

HTML Purifier ....................................................... 526

Hydrator .................................................................. 444

Strategy ............................................ 447, 449, 456

HydratorManager ....................................... 497, 891

I

I18nListener .................................................. 552, 648

IDE ................................................................................. 54

identity-Controller-Plug-in ............................. 617

InjectTranslatorMiddleware ........................... 314

Input-Filter .................................................... 166, 482

InputFilterManager ................................... 497, 891

Installation ............................................... 54, 75, 354

Virtual Host .......................................................... 77

Integrationstests .................................................. 667

Abgrenzung ....................................................... 699

mit Unit-Tests ................................................... 668

Interfaces ................................................................ 912

Internationalisierung ............................... 191, 545

Datenbankinhalte .......................................... 220

PHP-Extension ext/intl ................................. 192

Routing ............................................................... 547

Sprachauswahl ................................................ 217

Sprachdateien .................................................. 212

Sprachwechsler ................................................ 570

IntlDateFormatter ............................................... 570

3965-3.book Seite 952 Donnerstag, 6. Oktober 2016 1:19 13

Index

953

J

jQuery ....................................................................... 763

K

Komponenten ............................................. 817, 904

Komprimierung ................................................... 851

Konfigurationsdateien ......................................... 84

Konfigurationsverzeichnis ....................... 82, 361

Konsolenanwendungen ............................. 66, 793

L

launchctl ..................................................................... 48

Layout ....................................................................... 636

LayoutListener .................................................. 666

LayoutModel ..................................................... 275

Mehrstufiges Layout ...................................... 272

Listings ........................................................................ 41

Locale ........................................... 191, 194, 202, 547

per Event-Listener setzen ............................. 550

LocalizationMiddleware .................................... 202

LogFilterManager ................................................. 891

LogFormatterManager ....................................... 891

LogProcessorManager ....................................... 891

LogWriterManager .............................................. 891

M

MariaDB ............................................................ 50, 832

Middleware ......................................................... 37, 69

Aktionen .............................................................. 108

Implementierung ............................................... 73

Konfiguration ................................................... 126

Pipeline ................................................................... 74

Unit-Tests ........................................................... 293

Middleware-Pipeline ......................... 86, 249, 893

Unit-Tests ........................................................... 311

Migration ................................................................. 705

Abhängigkeiten ................................................ 712

andere Frameworks ........................................... 34

Änderungen vom ZF1 ..................................... 729

Anwendungskonfiguration ............... 736, 750

Checkliste ......................................... 709, 728, 748

Composer ............................................................ 751

Einführung ......................................................... 705

Event-Listener ................................................... 760

Factorys kompatibel machen .................... 717

Fallstudie ............................................................... 33

Migration (Forts.)

Front-Controller .............................................. 760

Gründe .................................................................... 33

Middleware-Pipeline ...................................... 760

Model-Layer ...................................................... 742

MVC ...................................................................... 737

MVC-Komponente .......................................... 710

parallele Front-Controller ........................... 735

paralleler Betrieb ZF1 und ZF3 .................... 732

Refactoring ........................................................ 706

Rewrite ................................................................ 706

Routing ............................................................... 756

Templates ........................................................... 759

vom ZF1 zum ZF3 ............................................. 726

vom ZF2 zum ZF3 ............................................ 708

von Controllern zu Aktions-Middleware 752

von MVC zur Middleware ............................ 746

von Zend_Form ................................................ 745

Vorbereitungen ZF1-Anwendungen ......... 730

Zend\Code .......................................................... 720

Zend\EventManager ...................................... 719

Zend\Hydrator ................................................. 720

Zend\ServiceManager ................................... 713

Zend-Framework-Meta-Package .............. 721

ZF2-Anwendung .............................................. 723

ZF3-Komponenten .......................................... 726

zu Middleware wechseln .............................. 747

Migrationsanwendung ........................................ 66

Mock-Objekt ....................................... 295, 297, 937

Model-Layer .................................................. 143, 431

Aufbau ................................................................. 433

Migration ........................................................... 742

Model-View-Controller ..................... 37, 351, 919

Module ............................................................ 382, 869

anlegen ................................................................ 102

Modulklasse ...................................................... 370

Modulstruktur .................................................. 382

Modulverzeichnis ............................................... 91

testen ................................................................... 644

Modul-Manager ............................................ 37, 870

MongoDB ......................................................... 51, 832

MvcEvent ................................................................ 552

N

Navigation ..................................................... 423, 632

Navigation-View-Helper ................ 424, 627, 878

NetBeans .................................................................... 54

nginx-Webserver .......................... 49, 78, 356, 736

NoSQL-Datenbanken .................................. 51, 832

3965-3.book Seite 953 Donnerstag, 6. Oktober 2016 1:19 13

Page 52: Zend Framework 3 – Das umfassende Handbuch

Index

954

O

Object-Relational Mapper ...................... 431, 874

Objektorientierte Programmierung ............ 909

Öffentliches Verzeichnis ............................ 88, 365

OOP ............................................................................ 909

OS X und macOS Sierra .................................. 43, 46

P

Packagist ................................................. 80, 359, 369

PaginationControl View-Helper .................... 421

Paginierung ............................................................ 418

Params-Plug-in ..................................................... 402

PHP

ext/intl ................................................................. 192

objektorientierte Programmierung ......... 909

PHP 5 ....................................................................... 34

PHP 5.6 .................................................................... 43

PHP 7 ....................................................................... 34

PHP CLI Webserver ............................................ 45

PHP Short Tags .................................................... 97

PHP-Version ......................................................... 44

PHP FIG ....................................................................... 72

PhpMyAdmin ........................................................ 140

PhpStorm ................................................................... 54

PHPUnit ................................................ 295, 641, 895

Data-Provider ......................................... 681, 934

DateTime testen ............................................... 697

Exceptions testen ............................................ 936

installieren ......................................................... 929

Integrationstests ............................................. 667

Konfiguration ......................................... 643, 930

Mock-Objekte .................................................... 937

Prophecy ............................................................. 937

Testfälle ............................................................... 931

Testgruppen ....................................................... 647

Tests ausführen ................................................ 941

Übersicht ............................................................. 929

Zusicherungsmethoden ................................ 934

Pin Your Pizza! .................... 63, 98, 131, 159, 185,

221, 260, 289, 344

Postman ......................................................... 776, 788

Programmierstil ...................................................... 41

Prophecy ..................................... 295, 641, 655, 937

PSR-7 ............................................................................ 72

R

RedirectIntroAction-Middleware .................. 270

Redirect-Plug-in .................................................... 402

Redis .......................................................................... 832

Refactoring ............................................................. 706

Repository .............. 109, 139, 151, 395, 467, 924

Datenbankanbindung .................................. 467

Paginator ........................................................... 459

Paginierung ....................................................... 418

Unit-Tests ........................................................... 330

Response-Objekte ................................................ 119

RESTful Controller ............................................... 769

RESTful Webservice ..................................... 37, 763

Aktions-Middleware ...................................... 781

Apigility .............................................................. 785

Einführung ......................................................... 763

HTTP-Methode ................................................. 764

Modul ................................................................... 766

Postman ............................................................. 776

RESTful Controller .......................................... 769

Routing ...................................................... 767, 779

testen ................................................................... 776

ViewJsonStrategy ............................................ 766

Zend\Expressive .............................................. 778

Zend\Mvc ........................................................... 765

Rewrite ..................................................................... 706

RoutePluginManager ......................................... 891

Routing ........................................ 101, 104, 389, 547

Locale ................................................................... 547

Migration ........................................................... 756

Routen überprüfen ......................................... 394

Routen und Rechte ......................................... 247

Routenkonfiguration .................................... 392

S

SanSessionToolbar .............................................. 376

Schichtenmodell .................................................. 915

Schlanke Controller und fette Models ........ 385

Selenium ................................................................. 344

SerializerAdapterManager ............................... 891

Service-Locator .............................................. 36, 886

Sessions .......................................................... 236, 891

ShowUserWidget-View-Helper ...................... 632

Simple CMS ..... 64, 378, 428, 472, 573, 638, 701

Skeleton Application ........................ 55, 56, 58, 60

Source-Verzeichnis ................................................ 94

Sprachdateien ....................................................... 212

Sprachwechsler ..................................................... 570

Storage ......................................... 145, 434, 453, 466

Interface .............................................................. 455

Unit-Tests ........................................................... 335

3965-3.book Seite 954 Donnerstag, 6. Oktober 2016 1:19 13

Index

955

T

Table Data Gateway ............................................. 927

Table-Gateway .................................... 453, 462, 838

Factory ................................................................. 463

Technische Voraussetzungen ............................ 42

Template ..................................... 101, 120, 406, 899

Benutzerrechte ................................................. 251

Entitäten ausgeben ........................................ 470

Konfiguration ................................................... 414

mehrstufiges Layout ...................................... 272

Template-Map ............................................. 415, 900

Template-Map-Generator ................................. 900

Template-Verzeichnis ........................................... 96

Textdomain ............................................................ 862

Textidentifier ......................................................... 214

Traits ...................................................... 284, 669, 912

Translate-View-Helper .................... 559, 571, 864

Translator ................................... 205, 206, 208, 861

einsprachige Website ..................................... 555

Formate ............................................................... 558

Formulare ........................................................... 564

konfigurieren .................................................... 556

Navigation ......................................................... 568

Platzhalter .......................................................... 562

Sprachdateien ................................................... 212

Textdomain ....................................................... 862

Texte aus einer Datenbank ......................... 863

Texte im Controller ......................................... 567

Texte übersetzen .............................................. 555

Textfragmente .................................................. 559

Textidentifier .................................................... 214

Übersetzungsdateien ..................................... 557

View-Helper ....................................................... 864

TranslatorPluginManager ................................ 891

TravelloFilter .......................................................... 526

TravelloViewHelper .................................. 514, 539

U

Übungsanwendungen .......................................... 62

Pin Your Pizza! .................................................... 63

Simple CMS ........................................................... 64

Unit-Tests ............................................. 293, 641, 929

Abgrenzung ....................................................... 699

Data-Provider ......................................... 681, 934

Data-Sets ............................................................ 671

Event-Listener ................................................... 647

Middleware-Aktion ......................................... 299

Module ................................................................. 644

Url-Controller-Plug-in ........................................ 549

Url-View-Helper ................................ 409, 549, 571

User-Widget ........................................................... 632

V

Validator � Zend\Validator

ValidatorManager ............................................... 891

Vendorverzeichnis ....................................... 81, 360

Verschlüsselung ................................................... 851

Versionierung .......................................................... 34

Versionierung � Git

Verzeichnisse

Datenverzeichnis ..................................... 87, 364

Konfigurationsverzeichnis .......... 82, 361, 372

Modulverzeichnis ..................................... 91, 369

Öffentliches Verzeichnis ........................ 88, 365

Source-Verzeichnis .................................. 94, 373

Template-Verzeichnis ............................ 96, 374

Vendorverzeichnis ................................... 81, 360

View ........................................................................... 381

View-Helper .................................................. 197, 902

Allowed ............................................................... 252

BootstrapFlashMessenger ........................... 514

BootstrapForm ................................................. 540

CurrencyFormat .............................................. 219

DateFormat .............................................. 219, 570

Form ............................... 182, 280, 506, 508, 855

FormElement .................................................... 507

FormElementErrors ........................................ 507

FormLabel .......................................................... 506

Formularausgabe ........................................... 279

H1 ........................................................................... 541

Navigation ...................................... 424, 627, 878

PaginationControl ......................................... 421

ShowUserWidget ............................................. 632

Translate ................................ 206, 208, 559, 864

Unit-Tests ........................................................... 342

Url ....................................................... 122, 197, 409

ViewHelperManager .......................................... 891

ViewJsonStrategy ................................................. 766

ViewModel .................................................... 407, 502

Template konfigurieren ............................... 408

ViewRendererFactory ........................................ 277

Vote My Pizza! ....................... 62, 71, 78, 165, 191,

227, 267, 293

W

Webservices ........................................................... 763

Wiederverwendbare Module .......................... 369

3965-3.book Seite 955 Donnerstag, 6. Oktober 2016 1:19 13

Page 53: Zend Framework 3 – Das umfassende Handbuch

Index

956

Z

Zend Framework 1 .................................................. 33

Migration ........................................................... 705

Zend Framework 2 .................................................. 33

Migration ........................................................... 705

Zend Framework 3

Einsatzzwecke ...................................................... 37

Geschichte ............................................................. 31

Gründe für Einsatz ............................................. 32

Komponenten ................................................... 817

Konzepte ................................................................ 35

PHP-Version ......................................................... 44

technische Voraussetzungen ......................... 42

Vorteile ................................................................... 35

Zielgruppe ............................................................. 31

Zend Framework Center ......... 63, 354, 381, 431,

475, 545, 575

Zend Studio ............................................................... 54

Zend\Acl

mit Navigation kombinieren ...................... 626

Zend\Authentication ...................... 239, 600, 818

Adapter ............................................. 239, 602, 818

Identität .............................................................. 821

Service ........................................................ 602, 819

Storage ................................................................ 821

Zend\Cache ............................................................. 822

Cache-Pattern ................................................... 824

Cache-Storage ................................................... 823

Zend\Code\Generator .............................. 802, 826

Dateien generieren ......................................... 806

Entitäten generieren ...................................... 802

Zend\ComponentInstaller .. 141, 166, 193, 903

Zend\Expressive ............................................... 903

Zend\Mvc ............................................................ 904

Zend\Config

Dateiformate .................................................... 827

Lesen ..................................................................... 828

Schreiben ............................................................ 829

Zend\Console ........................................................ 796

Controller ........................................................... 831

Prompts ............................................................... 831

Routing ................................................................ 830

Zend\Db ......................................................... 141, 453

Datenbankadapter ......................................... 454

Datenbanksysteme ......................................... 832

Vergleich zu Doctrine .................................... 944

Zend\Db\Adapter ................................................. 832

Zend\Db\ResultSet .............................................. 833

Zend\Db\Sql ........................................................... 834

Zend\Db\Sql\Ddl .................................................. 837

Zend\Db\TableGateway .................................... 838

Zend\Diactoros ..................................................... 841

Zend\EventManager ................................. 550, 842

Authentifizierung ........................................... 605

Event-Listener ................................................... 844

in Klassen einsetzen ....................................... 843

Zend\Expressive .................................... 58, 75, 846

Actions ................................................................ 101

Aktionen ................................. 108, 113, 115, 176

Anwendung optimieren ............................... 267

Aufbau .................................................................... 78

Authentifizierung ........................................... 241

Autorisierung ................................................... 245

composer.json ..................................................... 79

ConfigManager ................................................... 83

Datenverzeichnis ............................................... 87

Fehlerseite .......................................................... 249

Front-Controller ................................................. 89

Installation ........................................................... 75

Installer ............................................................... 848

Internationalisierung .................................... 193

Konfigurationsverzeichnis ............................. 82

Lokalisierung .................................................... 202

mehrstufiges Layout ...................................... 272

Migration ........................................................... 746

Modul ................................................... 91, 102, 193

Modulverzeichnis ............................................... 91

öffentliches Verzeichnis .................................. 88

Response-Objekte ............................................ 119

RESTful Webservice ........................................ 778

Routing ............................................ 101, 104, 194

Skeleton Application ........................................ 58

Templates ........................................... 96, 101, 120

Traits .................................................................... 284

Unit-Tests ........................................................... 293

unterstützte Komponenten ........................ 847

Vendorverzeichnis ............................................. 81

Zend\ComponentInstaller ........................... 903

Zend\Filter .............................................................. 848

Dateiupload ...................................................... 532

Filterketten ........................................................ 850

HTML Purifier ................................................... 527

Komprimierung ............................................... 851

statischer Filter ................................................ 850

Zend\Form .................................................... 172, 489

Ausgabe ..................................................... 181, 855

CKEditor .............................................................. 522

Dateiuploads ........................................... 529, 533

erstellen ............................................................... 852

Factory ....................................................... 174, 853

Fieldsets .............................................................. 853

3965-3.book Seite 956 Donnerstag, 6. Oktober 2016 1:19 13

Index

957

Zend\Form (Forts.)

Konfiguration ......................................... 175, 496

prepare() .............................................................. 505

Template ............................................................. 182

Übersetzungen ................................................. 564

Unit-Tests ........................................................... 325

View-Helper ....................................................... 182

Zend\Hydrator ............................................ 444, 857

Standardhydratoren ...................................... 859

Strategies ............................................................ 860

Zend\I18n .......................... 193, 205, 219, 547, 861

Datum .................................................................. 569

Translator ................................................. 205, 861

Uhrzeiten ............................................................ 569

Zend\InputFilter ...................... 166, 170, 482, 864

Dateiuploads ..................................................... 530

eigene Fehlermeldungen .............................. 486

Factory ................................................................. 171

Hierarchie ........................................................... 867

Konfiguration ................................ 172, 487, 865

Übersetzungen ................................................. 562

Unit-Tests ........................................................... 327

Validierung ........................................................ 866

Zend\ModuleManager ....................................... 868

Feature-Interfaces ........................................... 869

Konfiguration ................................................... 871

Module ................................................................. 869

Zend\Mvc ............................................... 56, 357, 873

Action-Controller ............................................ 395

Aufbau ................................................................. 357

Authentifizierung .................................. 575, 600

Autorisierung .................................................... 575

composer.json ................................................... 358

Dateiuploads ..................................................... 537

Datenverzeichnis ............................................. 364

Events ................................................ 552, 607, 875

Formulare ........................................................... 489

Formularverarbeitung .................................. 475

Fremdmodule .................................................... 375

Front-Controller ............................................... 365

Input-Filter ......................................................... 482

Installation ........................................................ 354

Integrationskomponenten .......................... 713

Internationalisierung .................................... 545

Konfigurationsverzeichnis .......................... 361

Konsolenintegration ...................................... 793

Migration vom ZF1 .......................................... 737

Modul ......................................................... 369, 382

öffentliches Verzeichnis ................................ 365

RESTful Webservice ......................................... 765

Routing ................................................................ 389

Zend\Mvc (Forts.)

Sessions ............................................................... 597

Skeleton Application ........................................ 56

Teilkomponenten ............................................ 874

Templates ........................................................... 406

Unit-Tests ........................................................... 641

Vendorverzeichnis .......................................... 360

Zend\ComponentInstaller ........................... 904

Zend\Mvc\I18n .................................................... 547

Zend\Navigation ......................................... 424, 876

Ausgabe .............................................................. 878

Konfiguration .......................................... 424, 877

mit ACL kombinieren .................................... 626

Übersetzungen ................................................. 568

Zend\Paginator ................................. 418, 459, 878

Adapter ............................................................... 878

Datenbank ......................................................... 879

Einsatz ................................................................. 879

Seitennavigation ............................................. 420

Zend\Permissions\Acl ........... 233, 586, 618, 881

ACL-Aufbau ....................................................... 881

Benutzerrechte ................................................. 594

Benutzerrollen .................................................. 587

konfigurieren .................................................... 591

Privilegien .......................................................... 589

Rechte prüfen ................................................... 882

Ressourcen ......................................................... 589

Vergleich zu RBAC .......................................... 883

Zend\Permissions\Rbac ....... 233, 245, 252, 883

Aufbau ................................................................. 884

Bestandteile ....................................................... 884

Rechte prüfen ................................................... 885

Vergleich zu ACL .............................................. 886

Zend\ServiceManager .............................. 454, 886

Class Name Resolution ................................. 888

Factorys .............................................................. 888

Konfiguration ................................................... 886

Services benennen .......................................... 887

spezialisierte Service-Manager .................. 890

Zend\Session ...................................... 236, 597, 891

Container ........................................................... 891

Konfiguration ................................................... 892

Konfigurationsservice ................................... 600

Schreibrechte .................................................... 228

Zend\Stratigility ................................................... 893

Middleware-Pipeline ...................................... 893

Zend\Test ............................................. 667, 679, 895

mit DbUnit ......................................................... 669

Zend\Validator ..................................................... 896

Fehlermeldungen anpassen ............... 486, 898

statischer Validator ....................................... 897

3965-3.book Seite 957 Donnerstag, 6. Oktober 2016 1:19 13

Page 54: Zend Framework 3 – Das umfassende Handbuch

Index

958

Zend\Validator (Forts.)

Validatorketten ................................................ 898

Validierungsmeldungen ............................... 564

Zend\View ............................................................... 899

JSON ausgeben ................................................. 902

Template-Map ........................................ 415, 900

Template-Map-Generator ........................... 416

Templates ........................................................... 899

Templates verarbeiten .................................. 900

View-Helper ....................................................... 902

ZendDeveloperTools ....................... 375, 394, 615

Doctrine-Integration ..................................... 948

ZF\Console .............................................................. 793

abstrakte Command-Klasse ....................... 796

Befehl ................................................ 798, 800, 807

Befehl ausführen .......................... 800, 802, 811

Einführung ......................................................... 795

ZF1legacy ................................................. 66, 727, 747

ZF3buch Examples ................................................. 65

ZFrapid ..................................................................... 814

3965-3.book Seite 958 Donnerstag, 6. Oktober 2016 1:19 13

Page 55: Zend Framework 3 – Das umfassende Handbuch

Wir hoffen sehr, dass Ihnen diese Leseprobe gefallen hat. Sie dürfen sie ger-ne empfehlen und weitergeben, allerdings nur vollständig mit allen Seiten. Bitte beachten Sie, dass der Funktionsumfang dieser Leseprobe sowie ihre Darstellung von der E-Book-Fassung des vorgestellten Buches abweichen können. Diese Leseprobe ist in all ihren Teilen urheberrechtlich geschützt. Alle Nutzungs- und Verwertungsrechte liegen beim Autor und beim Verlag.

Teilen Sie Ihre Leseerfahrung mit uns!

Ralf Eggert ist diplomierter Wirtschaftsinformatiker und arbeitet bereits seit über zehn Jahren mit dem Zend Framework. Er ist als Trainer, Berater und Ent-wickler tätig und aktiver Teil der internationalen Zend-Framework-Community.

Ralf Eggert

Zend Framework 3 – Das umfassende Handbuch960 Seiten, gebunden, 2. Auflage 2016 44,90 Euro, ISBN 978-3-8362-3965-3

www.rheinwerk-verlag.de/4016

Wissen, wie’s geht.