| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468 |
- <?xml version="1.0" encoding="UTF-8"?>
- <!-- EN-Revision: 24249 -->
- <!-- Reviewed: 22769 -->
- <sect1 id="zend.http.client.advanced">
- <title>Zend_Http_Client - Fortgeschrittende Nutzung</title>
- <sect2 id="zend.http.client.redirections">
- <title>HTTP-Umleitungen</title>
- <para>
- Standardmäßig verarbeitet <classname>Zend_Http_Client</classname>
- <acronym>HTTP</acronym>-Umleitungen automatisch und folgt bis zu 5 Umleitungen. Dies
- kann durch Setzen des Konfigurationsparameters 'maxredirects' gändert werden.
- </para>
- <para>
- Gemäß dem <acronym>HTTP</acronym>/1.1 RFC sollten <acronym>HTTP</acronym> 301 und 302
- Antworten vom Client behandelt werden, indem dieselbe Anfrage erneut an die angebene
- Stelle versendet wird - unter Verwendung derselben Anfragemethode. Allerdings haben
- dies die meisten Clients nicht implementiert und verwenden beim Umleiten eine
- <constant>GET</constant>-Anfrage. Standardmäßig macht
- <classname>Zend_Http_Client</classname> genau dasselbe - beim Umleiten einer 301 oder
- 302 Antwort, werden alle <constant>GET</constant>- und POST-Parameter zurückgesetzt und
- eine <constant>GET</constant>-Anfrage wird an die neue Stelle versandt. Dieses Verhalten
- kann durch Setzen des Konfigurationsparameters 'strictredirects' auf das boolesche
- <constant>TRUE</constant> geändert werden.
- <example id="zend.http.client.redirections.example-1">
- <title>Strikte Umleitung von 301 und 302 Antworten nach RFC 2616 erzwingen</title>
- <programlisting language="php"><![CDATA[
- // Strikte Umleitungen
- $client->setConfig(array('strictredirects' => true);
- // Nicht strikte Umleitungen
- $client->setConfig(array('strictredirects' => false);
- ]]></programlisting>
- </example>
- </para>
- <para>
- Man kann immer die Anzahl der durchgeführten Umleitungen nach dem Senden einer Anfrage
- durch Verwendung der Methode getRedirectionsCount() erhalten.
- </para>
- </sect2>
- <sect2 id="zend.http.client.cookies">
- <title>Hinzufügen von Cookies und Verwendung von persistenten Cookies</title>
- <para>
- <classname>Zend_Http_Client</classname> stellt eine einfache Schnittstelle zum
- Hinzufügen von Cookies zu einer Anfrage bereit, so dass keine direkten Header
- Änderungen notwendig sind. Dies wird durch Verwendung der Methode setCookie() erledigt.
- Diese Methode kann auf mehrere Arten verwendet werden:
- <example id="zend.http.client.cookies.example-1">
- <title>Cookies setzen durch Verwendung von setCookie()</title>
- <programlisting language="php"><![CDATA[
- // Ganz einfach: durch Übergabe von Namen und Wert für das Cookie
- $client->setCookie('flavor', 'chocolate chips');
- // Durch direktes Übergeben eines unverarbeiteten Cookie Strings (Name=Wert)
- // Beachte, dass der Wert bereits URL kodiert sein muss
- $client->setCookie('flavor=chocolate%20chips');
- // Durch Übergabe eines Zend_Http_Cookie-Objekts
- $cookie = Zend_Http_Cookie::fromString('flavor=chocolate%20chips');
- $client->setCookie($cookie);
- ]]></programlisting>
- </example>
- Für weitere Informationen über <classname>Zend_Http_Cookie</classname>-Objekte, siehe
- <link linkend="zend.http.cookies">diesen Abschnitt</link>.
- </para>
- <para>
- <classname>Zend_Http_Client</classname> stellt außerdem die Möglichkeiten für "Cookie
- Stickiness" bereit - das bedeutet, dass der Client intern alle gesendeten und erhaltenen
- Cookies speichert und bei nachfolgenden Anfragen automatisch wieder mit sendet. Dies ist
- z.B. nützlich, wenn man sich bei einer entfernten Site zuerst einloggen muss und ein
- Authentifizierungs- oder Session-Cookie erhält, bevor man weitere Anfragen versenden
- kann.
- <example id="zend.http.client.cookies.example-2">
- <title>Cookie Stickiness aktivieren</title>
- <programlisting language="php"><![CDATA[
- // Um die Cookie Stickiness einzuschalten, setze eine Cookie Jar (Keksdose)
- $client->setCookieJar();
- // Erste Anfrage: einloggen und eine Session starten
- $client->setUri('http://example.com/login.php');
- $client->setParameterPost('user', 'h4x0r');
- $client->setParameterPost('password', '1337');
- $client->request('POST');
- // Die Cookie Jar speichert die Cookies automatisch in der Antwort
- // wie z.B. ein Session-ID Cookie.
- // Nun können wir die nächste Anfrage senden - die gespeicherten Cookies
- // werden automatisch mit gesendet
- $client->setUri('http://example.com/read_member_news.php');
- $client->request('GET');
- ]]></programlisting>
- </example>
- Für weitere Informationen über die Klasse <classname>Zend_Http_CookieJar</classname>,
- siehe <link linkend="zend.http.cookies.cookiejar">diesen Abschnitt</link>.
- </para>
- </sect2>
- <sect2 id="zend.http.client.custom_headers">
- <title>Setzen von individuellen Anfrageheadern</title>
- <para>
- Das Setzen von individuellen Headern kann durch Verwendung der Methode setHeaders()
- erledigt werden. Diese Methode ist sehr facettenreich und kann auf verschiedene Arten
- verwendet werden, wie das folgende Beispiel zeigt:
- <example id="zend.http.client.custom_headers.example-1">
- <title>Setzen eines einzelnen individuellen Anfrageheaders</title>
- <programlisting language="php"><![CDATA[
- // Setzen eines einzelnen Headers, vorherige werden überschrieben
- $client->setHeaders('Host', 'www.example.com');
- // Ein anderer Weg um genau das Gleiche zu erreichen
- $client->setHeaders('Host: www.example.com');
- // Setzen von verschiedenen Werten für denselben Header
- // (besonders für Cookie Header nützlich):
- $client->setHeaders('Cookie', array(
- 'PHPSESSID=1234567890abcdef1234567890abcdef',
- 'language=he'
- ));
- ]]></programlisting>
- </example>
- </para>
- <para>
- setHeader() kann genauso einfach für das Setzen mehrerer Header in einem Aufruf durch
- Übergabe eines Array mit Headern als einzigen Parameter verwendet werden:
- <example id="zend.http.client.custom_headers.example-2">
- <title>Setzen von mehreren individuellen Anfrageheaders</title>
- <programlisting language="php"><![CDATA[
- // Setzen von mehreren Headern, vorherige werden überschrieben
- $client->setHeaders(array(
- 'Host' => 'www.example.com',
- 'Accept-encoding' => 'gzip,deflate',
- 'X-Powered-By' => 'Zend Framework'));
- // Das Array kann auch komplette Array Strings enthalten:
- $client->setHeaders(array(
- 'Host: www.example.com',
- 'Accept-encoding: gzip,deflate',
- 'X-Powered-By: Zend Framework'));
- ]]></programlisting>
- </example>
- </para>
- </sect2>
- <sect2 id="zend.http.client.file_uploads">
- <title>Dateiuploads</title>
- <para>
- Man kann Dateien über <acronym>HTTP</acronym> hochladen, indem man die Methode
- setFileUpload verwendet. Diese Methode nimmt einen Dateinamen als ersten Parameter, einen
- Formularnamen als zweiten Parameter und Daten als einen dritten, optionalen Parameter
- entgegen. Wenn der dritte Parameter <constant>NULL</constant> ist, wird angenommen, dass
- der erste Dateinamen-Parameter auf eine echte Datei auf der Platte verweist, und
- <classname>Zend_Http_Client</classname> wird versuchen die Datei zu lesen und
- hochzuladen. Wenn der Daten-Parameter nicht <constant>NULL</constant> ist, wird der
- erste Dateinamen-Parameter als der Dateiname versendet, aber die Datei muss nicht
- wirklich auf der Platte existieren. Der zweite Formularnamen-Parameter wird immer
- benötigt und ist gleichbedeutend mit dem Attribut "name" eines >input< Tags, wenn
- die Datei durch ein <acronym>HTML</acronym>-Formular hochgeladen worden ist. Ein vierter
- optionaler Parameter gibt den Content-type der Datei an. Wenn er nicht angegeben wird,
- liest <classname>Zend_Http_Client</classname> die Datei von der Platte und verwendet die
- Funktion mime_content_type, um den Content-type der Datei zu erraten, wenn er verfügbar
- ist. Auf jeden Fall ist der Standard-MIME-Typ 'application/octet-stream'.
- <example id="zend.http.client.file_uploads.example-1">
- <title>Verwendung von setFileUpload um Dateien hochzuladen</title>
- <programlisting language="php"><![CDATA[
- // Hochladen beliebiger Daten als Datei
- $text = 'this is some plain text';
- $client->setFileUpload('some_text.txt', 'upload', $text, 'text/plain');
- // Hochladen einer vorhandenen Datei
- $client->setFileUpload('/tmp/Backup.tar.gz', 'bufile');
- // Dateien absenden
- $client->request('POST');
- ]]></programlisting>
- </example>
- Im ersten Beispiel, wird die Variable $text hochgeladen und als $_FILES['upload'] auf
- der Serverseite verfügbar sein. Im zweiten Beispiel wird die vorhandene Datei
- /tmp/Backup.tar.gz auf den Server geladen und als $_FILES['bufile'] verfügbar sein. Der
- Content-type wird automatisch erraten, wenn möglich - und wenn nicht, wird der
- Content-type auf 'application/octet-stream' gesetzt.
- </para>
- <note>
- <title>Dateien hochladen</title>
- <para>
- Beim Hochladen von Dateien wird der Content-type der <acronym>HTTP</acronym>-Anfrage
- automatisch auf 'multipart/form-data' gesetzt. Man sollte beachten, dass man eine
- POST- oder PUT-Anfrage absenden muss, um Dateien hochzuladen. Die meisten Server
- werden den Hauptteil der Anfrage bei anderen Anfragetypen ignorieren.
- </para>
- </note>
- </sect2>
- <sect2 id="zend.http.client.raw_post_data">
- <title>Unverarbeitete POST-Daten versenden</title>
- <para>
- Man kann <classname>Zend_Http_Client</classname> verwenden, um mit der Methode
- setRawData() unverarbeitete POST-Daten zu versenden. Diese Methode nimmt zwei Parameter
- entgegen: der erste ist die im Anfrage Hauptteil zu versendenen Daten. Der zweite
- optionale Parameter ist der Content-type der Daten. Obwohl dieser Parameter optional
- ist, sollte man ihn normalerweise vor dem Absenden der Anfrage setzen - entweder durch
- Verwendung von setRawData() oder durch eine andere Methode: setEncType().
- <example id="zend.http.client.raw_post_data.example-1">
- <title>Unverarbeitete POST-Daten versenden</title>
- <programlisting language="php"><![CDATA[
- $xml = '<book>' .
- ' <title>Islands in the Stream</title>' .
- ' <author>Ernest Hemingway</author>' .
- ' <year>1970</year>' .
- '</book>';
- $client->setRawData($xml, 'text/xml')->request('POST');
- // Ein anderer Weg, um dasselbe zu tun:
- $client->setRawData($xml)->setEncType('text/xml')->request('POST');
- ]]></programlisting>
- </example>
- Die Daten sollten auf der Serverseite über die <acronym>PHP</acronym>-Variable
- $HTTP_RAW_POST_DATA oder über den php://input stream verfügbar sein.
- </para>
- <note>
- <title>Unverarbeitete POST-Daten verwenden</title>
- <para>
- Das Setzen von unverarbeiteten POST-Daten für eine Anfrage überschreibt jeden
- POST-Parameter oder Dateiuploads. Man sollte nicht beides in derselben Anfrage
- verwenden. Es ist zu beachten, dass die meisten Server den Hauptteil der Anfrage
- ignorieren, wenn keine POST-Anfrage gesendet wird.
- </para>
- </note>
- </sect2>
- <sect2 id="zend.http.client.http_authentication">
- <title>HTTP-Authentifizierung</title>
- <para>
- Derzeit unterstützt <classname>Zend_Http_Client</classname> nur die Basis
- <acronym>HTTP</acronym>-Authentifizierung. Diese Funktion kann durch Verwendung der
- Methode <methodname>setAuth()</methodname> oder durch Spezifikation von Benutzername und
- Passwort in der URI genutzt werden. Die Methode <methodname>setAuth()</methodname> nimmt
- 3 Parameter entgegen: den Benutzernamen, das Passwort und einen optionalen
- Authentifizierungstyp-Parameter. Wie gesagt, wird derzeit nur die Basis
- Authentifizierung unterstützt (Unterstützung für eine Digest Authentifizierung ist
- geplant).
- <example id="zend.http.client.http_authentication.example-1">
- <title>Setzen von Benutzer und Passwort für eine HTTP Authentifizierung</title>
- <programlisting language="php"><![CDATA[
- // Verwende die Basis Authentifizierung
- $client->setAuth('shahar', 'myPassword!', Zend_Http_Client::AUTH_BASIC);
- // Da Basis Authentifizierung Standard ist, kann man auch dies verwenden:
- $client->setAuth('shahar', 'myPassword!');
- // Man kann auch den Benutzernamen und das Passwort in der URI spezifizieren
- $client->setUri('http://christer:secret@example.com');
- ]]></programlisting>
- </example>
- </para>
- </sect2>
- <sect2 id="zend.http.client.multiple_requests">
- <title>Versenden mehrerer Anfragen mit demselben Client</title>
- <para>
- <classname>Zend_Http_Client</classname> wurde zusätzlich besonders dafür entwickelt, um
- mehrere, aufeinander folgende Abfragen durch dasselbe Objekt verarbeiten zu können.
- Dies ist nützlich, wenn z.B. ein Skript es erfordert, Daten von verschiedenen Stellen
- abzurufen, oder wenn eine spezielle <acronym>HTTP</acronym>-Ressource das Einloggen und
- Erhalten eines Session Cookies erfordert.
- </para>
- <para>
- Beim Ausführen mehrere Anfrage an denselben Host, wird es besonders empfohlen, den
- Konfigurationsschalter 'keepalive' zu aktivieren. Wenn der Server keep-alive
- Verbindungen unterstützt, wird auf diesem Weg die Verbindung zum Server nur beendet,
- sobald alle Anfragen abgeschlossen sind und das Client-Objekt zerstört wird. Dies
- verhindert den Overhead beim Öffnen und Schließen von
- <acronym>TCP</acronym>-Verbindungen zum Server.
- </para>
- <para>
- Wenn man verschiedene Anfragen mit demselben Client durchführt, aber sicherstellen
- möchte, dass alle anfragespezifischen Parameter entfernt werden, sollte man die
- Methode resetParameters() verwenden. Dies stellt sicher, dass <constant>GET</constant>-
- und POST-Parameter, Anfragehauptteil und anfragespezifischen Header zurückgesetzt und
- nicht bei der nächsten Anfrage wiederverwendet werden.
- </para>
- <note>
- <title>Parameter zurücksetzen</title>
- <para>
- Bitte beachten, dass Header, die nicht anfragespezifisch sind, standardmäßig nicht
- zurückgesetzt werden, wenn die Methode <methodname>resetParameters()</methodname>
- verwendet wird. Nur die 'Content-length' und 'Content-type' Header werden zurück
- gesetzt. Dies erlaubt das Setzen und Vergessen von Headern wie 'Accept-language' und
- 'Accept-encoding'.
- </para>
- <para>
- Um alle Header und Daten aus der URI und der Methode zu löschen kann
- <methodname>resetParameters(true)</methodname> verwendet werden.
- </para>
- </note>
- <para>
- Ein weiteres Feature, welches speziell für aufeinander folgende Anfragen entwickelt
- worden ist, ist das Cookie Jar Objekt (Keksdose). Cookie Jars erlauben das automatische
- Speichern von Cookies, die vom Server bei der ersten Anfrage gesetzt worden sind, und
- das Versenden bei nachfolgenden Anfragen. Dies erlaubt es z.B. eine
- Authentifizierungsanfrage zu durchlaufen, bevor die eigentliche Anfrage zum
- Erhalten der Daten gesendet wird.
- </para>
- <para>
- Wenn die Applikation eine Authentifizierungsanfrage pro Benutzer erfordert und
- nachfolgende Anfragen in mehr als einem Skript in der Applikation durchgeführt werden
- könnten, könnte es eine gute Idee sein, das Cookie Jar Objekt in der Benutzersession zu
- speichern. Auf diese Weise muß der Benutzer nur einmal pro Session authentifiziert
- werden.
- </para>
- <example id="zend.http.client.multiple_requests.example-1">
- <title>Durchführen von aufeinander folgenden Anfrage mit einem Client</title>
- <programlisting language="php"><![CDATA[
- // Zuerst den Client instanzieren
- $client = new Zend_Http_Client('http://www.example.com/fetchdata.php', array(
- 'keepalive' => true
- ));
- // Haben wir die Cookies in unserer Session gespeichert?
- if (isset($_SESSION['cookiejar']) &&
- $_SESSION['cookiejar'] instanceof Zend_Http_CookieJar) {
- $client->setCookieJar($_SESSION['cookiejar']);
- } else {
- // Falls nicht, authentifiziere und speichere die Cookies
- $client->setCookieJar();
- $client->setUri('http://www.example.com/login.php');
- $client->setParameterPost(array(
- 'user' => 'shahar',
- 'pass' => 'somesecret'
- ));
- $client->request(Zend_Http_Client::POST);
- // Nun entferne die Parameter und setze die URI auf das Original
- // (Bitte beachten, dass das Cookie, das vom Server gesetzt worden ist,
- // nun in der Dose ist)
- $client->resetParameters();
- $client->setUri('http://www.example.com/fetchdata.php');
- }
- $response = $client->request(Zend_Http_Client::GET);
- // Speichere die Cookies in der Session für die nächste Seite
- $_SESSION['cookiejar'] = $client->getCookieJar();
- ]]></programlisting>
- </example>
- </sect2>
- <sect2 id="zend.http.client.streaming">
- <title>Daten-Streaming</title>
- <para>
- Standardmäßig akzeptiert <classname>Zend_Http_Client</classname>-Daten als
- <acronym>PHP</acronym>-Strings und gibt diese auch zurück. Trotzdem sind in vielen
- Fällen große Dateien zu Senden oder zu Empfangen. Diese im Speicher zu halten, könnte
- unnötig oder zu teuer sein. Für diese Fälle unterstützt
- <classname>Zend_Http_Client</classname> das Lesen von Daten aus Dateien (und generell
- auch <acronym>PHP</acronym>-Streams) und das Schreiben von Daten in Dateien (Streams).
- </para>
- <para>
- Um Streams für die Übergabe von Daten zu <classname>Zend_Http_Client</classname> zu
- verwenden, muss die Methode <methodname>setRawData()</methodname> verwendet werden,
- wobei das Daten-Argument eine Stream-Ressource ist (z.B. das Ergebnis von
- <methodname>fopen()</methodname>).
- <example id="zend.http.client.streaming.example-1">
- <title>Senden von Dateien zum HTTP-Server durch Streamen</title>
- <programlisting language="php"><![CDATA[
- $fp = fopen("mybigfile.zip", "r");
- $client->setRawData($fp, 'application/zip')->request('PUT');
- ]]></programlisting>
- </example>
- </para>
- <para>
- Aktuell unterstützen nur PUT-Anfragen das Senden von Streams zum
- <acronym>HTTP</acronym>-Server.
- </para>
- <para>
- Um Daten vom Server als Stream zu Empfangen kann <methodname>setStream()</methodname>
- verwendet werden. Das optionale Argument spezifiziert den Dateinamen, unter dem die
- Daten gespeichert werden. Wenn das Argument einfach nur <constant>TRUE</constant> ist
- (Standard), wird eine temporäre Datei verwendet und gelöscht, sobald das Antwort-Objekt
- zerstört wird. Wenn das Argument auf <constant>FALSE</constant> gesetzt wird, ist die
- Streaming-Funktionalität ausgeschaltet.
- </para>
- <para>
- Wenn Streaming verwendet wird, gibt die Methode <methodname>request()</methodname> ein
- Objekt der Klasse <classname>Zend_Http_Client_Response_Stream</classname> zurück,
- welches zwei nützliche Methoden hat: <methodname>getStreamName()</methodname> gibt den
- Namen der Datei zurück, in welcher die Antwort gespeichert wird, und
- <methodname>getStream()</methodname> gibt den Stream zurück, von dem die Antwort gelesen
- werden könnte.
- </para>
- <para>
- Man kann die Antwort entweder in eine vordefinierte Datei schreiben, oder eine temporäre
- Datei hierfür verwenden und sie woanders hinsenden, oder sie durch Verwendung von
- regulären Streaming-Funktionen an eine andere Datei senden.
- <example id="zend.http.client.streaming.example-2">
- <title>Empfangen von Dateien vom HTTP Server durch Streamen</title>
- <programlisting language="php"><![CDATA[
- $client->setStream(); // will use temp file
- $response = $client->request('GET');
- // Datei kopieren
- copy($response->getStreamName(), "my/downloads/file");
- // Stream verwenden
- $fp = fopen("my/downloads/file2", "w");
- stream_copy_to_stream($response->getStream(), $fp);
- // Kann auch in eine bekannte Datei schreiben
- $client->setStream("my/downloads/myfile")->request('GET');
- ]]></programlisting>
- </example>
- </para>
- </sect2>
- </sect1>
|