| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464 |
- <?xml version="1.0" encoding="UTF-8"?>
- <!-- EN-Revision: 24249 -->
- <!-- Reviewed: no -->
- <sect1 id="zend.view.scripts">
- <title>View Scripte</title>
- <para>
- Sobald dein Controller die Variablen übergeben und die <methodname>render()</methodname>
- Methode aufgerufen hat, inkludiert <classname>Zend_View</classname> das angeforderte View
- Skript und führt es "innerhalb" des Gültigkeitsbereichs der <classname>Zend_View</classname>
- Instanz aus. Deshalb weisen Referenzen auf $this in deinem View Skript auf die
- <classname>Zend_View</classname> Instanz selber.
- </para>
- <para>
- Auf Variablen, die vom Controller an den View übergeben worden sind, kann als Eigenschaften
- der Instanz zurückgegriffen werden. Wenn der Controller zum Beispiel eine Variable
- 'irgendwas' übergeben hat, würdest du in deinem View Skript über $this->irgendwas darauf
- zugreifen können. (Dies erlaubt es dir, den Überblick darüber zu behalten, welche Variablen
- an das Skript übergeben worden sind und welche Variablen intern zum Skript selber gehören.)
- </para>
- <para>
- Zur Erinnerung hier noch einmal das Beispiel View Skript aus der
- <classname>Zend_View</classname> Einführung.
- </para>
- <programlisting language="php"><![CDATA[
- <?php if ($this->books): ?>
- <!-- Eine Tabelle mit einigen Büchern. -->
- <table>
- <tr>
- <th>Autor</th>
- <th>Titel</th>
- </tr>
- <?php foreach ($this->books as $key => $val): ?>
- <tr>
- <td><?php echo $this->escape($val['author']) ?></td>
- <td><?php echo $this->escape($val['title']) ?></td>
- </tr>
- <?php endforeach; ?>
- </table>
- <?php else: ?>
- <p>Es gibt keine Bücher zum Anzeigen.</p>
- <?php endif; ?>
- ]]></programlisting>
- <sect2 id="zend.view.scripts.escaping">
- <title>Ausgaben maskieren</title>
- <para>
- Eine der wichtigsten Aufgaben, die in einem View Skript zu erledigen sind, ist es
- sicherzustellen, dass die Ausgaben auch richtig maskiert sind; neben anderen Dingen
- hilft dies auch Cross-Site Scripting Attacken zu vermeiden. Sofern du keine Funktion,
- Methode oder einen Helfer verwendest, der die Maskierungen selber durchführt, solltest
- Du Variablen immer maskieren, wenn du sie ausgeben möchtest.
- </para>
- <para>
- <classname>Zend_View</classname> stellt eine Methode escape() bereit, die das Maskieren
- für dich übernimmt.
- </para>
- <programlisting language="php"><![CDATA[
- // schlechte View Skript Praxis:
- echo $this->variable;
- // gute View Skript Praxis:
- echo $this->escape($this->variable);
- ]]></programlisting>
- <para>
- Standardmäßig verwendet escape() die <acronym>PHP</acronym> htmlspecialchars() Funktion
- für die Maskierung. Allerdings könntest du abhängig von deiner Umgebung den Wunsch
- haben, die Maskierung anders durchzuführen. Verwende die setEscape() Methode auf der
- Controller Ebene, um <classname>Zend_View</classname> mitzuteilen, welche
- Maskierungsmöglichkeit als Callback verwendet werden soll.
- </para>
- <programlisting language="php"><![CDATA[
- // erstelle eine Zend_View Instanz
- $view = new Zend_View();
- // teile ihr mit, dass htmlentities für die Maskierung
- // verwendet werden soll
- $view->setEscape('htmlentities');
- // oder teile ihr mit, eine statische Klassenmethode für
- // die Maskierung zu verwenden
- $view->setEscape(array('SomeClass', 'methodName'));
- // sogar Instanzmethoden sind möglich
- $obj = new SomeClass();
- $view->setEscape(array($obj, 'methodName'));
- // und dann erstelle die Ausgabe
- echo $view->render(...);
- ]]></programlisting>
- <para>
- Diese Callback Funktion oder Methode sollte den zu maskierenden Wert als ersten
- Parameter übernehmen und alle anderen Parameter sollten optional sein.
- </para>
- </sect2>
- <sect2 id="zend.view.scripts.templates">
- <title>Verwendung alternativer Templatesysteme</title>
- <para>
- Obwohl <acronym>PHP</acronym> selber eine mächtiges Templatesystem ist, haben viele
- Entwickler das Gefühl, dass es zu mächtig oder komplex für die Template Designer ist und
- möchten ein alternatives Templatesystem verwenden. <classname>Zend_View</classname>
- stellt zwei Mechanismen bereit, um dies zu realisieren, die erste durch Viewskripte und
- die zweite durch Implementierung von <classname>Zend_View_Interface</classname>.
- </para>
- <sect3 id="zend.view.scripts.templates.scripts">
- <title>Template Systeme die View Scripte verwenden</title>
- <para>
- Ein Viewskript kann verwendet werden, um ein separats Templateobjekt zu instanzieren
- und anzupassen, z.B. für eine PHPLIB-style Template. Das
- Viewskript für solch eine Aufgabe könnte so aussehen:
- </para>
- <programlisting language="php"><![CDATA[
- include_once 'template.inc';
- $tpl = new Template();
- if ($this->books) {
- $tpl->setFile(array(
- "booklist" => "booklist.tpl",
- "eachbook" => "eachbook.tpl",
- ));
- foreach ($this->books as $key => $val) {
- $tpl->set_var('author', $this->escape($val['author']);
- $tpl->set_var('title', $this->escape($val['title']);
- $tpl->parse("books", "eachbook", true);
- }
- $tpl->pparse("output", "booklist");
- } else {
- $tpl->setFile("nobooks", "nobooks.tpl")
- $tpl->pparse("output", "nobooks");
- }
- ]]></programlisting>
- <para>
- Dies wären die zugehörigen Template Dateien:
- </para>
- <programlisting language="html"><![CDATA[
- <!-- booklist.tpl -->
- <table>
- <tr>
- <th>Autor</th>
- <th>Titel</th>
- </tr>
- {books}
- </table>
- <!-- eachbook.tpl -->
- <tr>
- <td>{author}</td>
- <td>{title}</td>
- </tr>
- <!-- nobooks.tpl -->
- <p>Es gibt keine Bücher zum Anzeigen.</p>
- ]]></programlisting>
- </sect3>
- <sect3 id="zend.view.scripts.templates.interface">
- <title>Ein Templatesystem mit Hilfe von Zend_View_Interface verwenden</title>
- <para>
- Manche finden es einfacher, ein <classname>Zend_View</classname> kompatibles
- Templatesystem zu verwenden. <classname>Zend_View_Interface</classname> definiert
- die minimale Schnittstelle, die zur Kompatibilität benötigt wird.
- </para>
- <programlisting language="php"><![CDATA[
- /**
- * Gebe das aktuelle Template Engine Objekt zurück
- */
- public function getEngine();
- /**
- * Setze den Pfad zu den Viewskripten / Templates
- */
- public function setScriptPath($path);
- /**
- * Setze den Pfad zu allen View Ressourcen
- */
- public function setBasePath($path, $prefix = 'Zend_View');
- /**
- * Füge einen zusätzlichen Basispfad den View ressourcen hinzu
- */
- public function addBasePath($path, $prefix = 'Zend_View');
- /**
- * Empfange die aktuellen Skript Pfade
- */
- public function getScriptPaths();
- /**
- * Überladungsmethoden zum Zuordnen von Templatevariablen
- * als Objekteigenschaften
- */
- public function __set($key, $value);
- public function __isset($key);
- public function __unset($key);
- /**
- * Manuelle Zuweisung von Templatevariablen oder die Möglichkeit,
- * mehrere Variablen in einem Durchgang zuzuordnen.
- */
- public function assign($spec, $value = null);
- /**
- * Alle zugewiesenen Templatevariablen zurücksetzen
- */
- public function clearVars();
- /**
- * Rendern des Templates mit dem Namen $name
- */
- public function render($name);
- ]]></programlisting>
- <para>
- Durch Verwendung dieses Interfaces ist es relativ einfach, das Templatesystem eines
- Dritten in eine <classname>Zend_View</classname> kompatible Klasse zu umhüllen. Als
- Beispiel folgt ein möglicher Wrapper für Smarty:
- </para>
- <programlisting language="php"><![CDATA[
- class Zend_View_Smarty implements Zend_View_Interface
- {
- /**
- * Smarty object
- * @var Smarty
- */
- protected $_smarty;
- /**
- * Constructor
- *
- * @param string $tmplPath
- * @param array $extraParams
- * @return void
- */
- public function __construct($tmplPath = null, $extraParams = array())
- {
- $this->_smarty = new Smarty;
- if (null !== $tmplPath) {
- $this->setScriptPath($tmplPath);
- }
- foreach ($extraParams as $key => $value) {
- $this->_smarty->$key = $value;
- }
- }
- /**
- * Gebe das aktuelle Template Engine Objekt zurück
- *
- * @return Smarty
- */
- public function getEngine()
- {
- return $this->_smarty;
- }
- /**
- * Setze den Pfad zu den Templates
- *
- * @param string $path Das Verzeichnis, das als Pfad gesetzt werden soll.
- * @return void
- */
- public function setScriptPath($path)
- {
- if (is_readable($path)) {
- $this->_smarty->template_dir = $path;
- return;
- }
- throw new Exception('Invalid path provided');
- }
- /**
- * Empfange das aktuelle template Verzeichnis
- *
- * @return string
- */
- public function getScriptPaths()
- {
- return array($this->_smarty->template_dir);
- }
- /**
- * Alias für setScriptPath
- *
- * @param string $path
- * @param string $prefix nicht verwendet
- * @return void
- */
- public function setBasePath($path, $prefix = 'Zend_View')
- {
- return $this->setScriptPath($path);
- }
- /**
- * Alias für setScriptPath
- *
- * @param string $path
- * @param string $prefix nicht verwendet
- * @return void
- */
- public function addBasePath($path, $prefix = 'Zend_View')
- {
- return $this->setScriptPath($path);
- }
- /**
- * Weise dem Template eine Variable zu
- *
- * @param string $key der Variablenname.
- * @param mixed $val der Variablenwert.
- * @return void
- */
- public function __set($key, $val)
- {
- $this->_smarty->assign($key, $val);
- }
- /**
- * Erlaubt das Testen von empty() und isset()
- *
- * @param string $key
- * @return boolean
- */
- public function __isset($key)
- {
- return (null !== $this->_smarty->get_template_vars($key));
- }
- /**
- * Erlaubt das Zurücksetzen von Objekteigenschaften
- *
- * @param string $key
- * @return void
- */
- public function __unset($key)
- {
- $this->_smarty->clear_assign($key);
- }
- /**
- * Weise dem Template Variablen zu
- *
- * Erlaubt das Zuweisen eines bestimmten Wertes zu einem bestimmten
- * Schlüssel, ODER die Übergabe eines Array mit Schlüssel => Wert
- * Paaren zum Setzen in einem Rutsch.
- *
- * @see __set()
- * @param string|array $spec Die zu verwendene Zuweisungsstrategie
- * (Schlüssel oder Array mit Schlüssel => Wert paaren)
- * @param mixed $value (Optional) Wenn ein Variablenname verwendet wurde,
- * verwende diesen als Wert
- * @return void
- */
- public function assign($spec, $value = null)
- {
- if (is_array($spec)) {
- $this->_smarty->assign($spec);
- return;
- }
- $this->_smarty->assign($spec, $value);
- }
- /**
- * Setze alle zugewiesenen Variablen zurück.
- *
- * Setzt alle Variablen zurück, die Zend_View entweder durch
- * {@link assign()} oder Überladen von Eigenschaften
- * ({@link __get()}/{@link __set()}) zugewiesen worden sind.
- *
- * @return void
- */
- public function clearVars()
- {
- $this->_smarty->clear_all_assign();
- }
- /**
- * Verarbeitet ein Template und gibt die Ausgabe zurück
- *
- * @param string $name Das zu verarbeitende Template
- * @return string Die Ausgabe.
- */
- public function render($name)
- {
- return $this->_smarty->fetch($name);
- }
- }
- ]]></programlisting>
- <para>
- In diesem Beispiel kannst du die <classname>Zend_View_Smarty</classname> anstelle
- von <classname>Zend_View</classname> instanzieren und es dann ungefähr wie
- <classname>Zend_View</classname> verwenden:
- </para>
- <programlisting language="php"><![CDATA[
- // Beispiel 1. In initView() des Initialisers.
- $view = new Zend_View_Smarty('/Pfad/der/Templates');
- $viewRenderer =
- Zend_Controller_Action_HelperBroker::getStaticHelper('ViewRenderer');
- $viewRenderer->setView($view)
- ->setViewBasePathSpec($view->_smarty->template_dir)
- ->setViewScriptPathSpec(':controller/:action.:suffix')
- ->setViewScriptPathNoControllerSpec(':action.:suffix')
- ->setViewSuffix('tpl');
- // Beispiel 2. Die Verwendung im Action Controller bleibt die gleiche...
- class FooController extends Zend_Controller_Action
- {
- public function barAction()
- {
- $this->view->book = 'Zend PHP 5 Zertifizierungs Study Guide';
- $this->view->author = 'Davey Shafik und Ben Ramsey'
- }
- }
- // Beispiel 3. Initialisierung der View im Action Controller
- class FooController extends Zend_Controller_Action
- {
- public function init()
- {
- $this->view = new Zend_View_Smarty('/path/to/templates');
- $viewRenderer = $this->_helper->getHelper('viewRenderer');
- $viewRenderer->setView($this->view)
- ->setViewBasePathSpec($view->_smarty->template_dir)
- ->setViewScriptPathSpec(':controller/:action.:suffix')
- ->setViewScriptPathNoControllerSpec(':action.:suffix')
- ->setViewSuffix('tpl');
- }
- }
- ]]></programlisting>
- </sect3>
- </sect2>
- </sect1>
|