Web Services w PHP
Transkrypt
Web Services w PHP
Web Services w PHP Michał 'Seth' Gołębiowski 1. Czym są Web Services ? 2. Packaging 2.1. XML-RPC 2.2. SOAP 2.2.1. Envelope 2.2.2. Header 2.2.3. Body 2.2.4. Fault 2.2.5. Implementacje w PHP 2.3. Który protokół wybrać? 3. Co w następnej części ? Witam w pierwszej części artykułu poświęconemu Web Servicom (Serwisom Sieciowym). Z części tej dowiesz się czym są i z czego składają się Web Services oraz o ich pierwszej "warstwie" - Packaging - i jej implementacjach w PHP. Artykuł ten jest skierowany do osób znających XMLa i podstawy wymiany danych między klientem, a serwerem w protokole HTTP. http://www.php.pl Strona 1 z 9 1. Czym są Web Services ? Web Services jest to ogólna nazwa dla technologii dostępu do zdalnych procedur wykorzystująca do komunikacji standardowe techniki przekazywania danych HTTP - oraz XML jako źródło danych. Powodem, dla których powstało Web Serices było stworzenie sposobu na komunikacje aplikacji między sobą, niezależnie od rodzaju platformy, na której pracują, oraz języka użytego w tworzeniu ich. Istnieją co prawda podobne systemy takie jak CORBA (Common Object Request Broker Architecture) czy DCOM (Distributed Component Object Model) jednak oferują one inny sposób komunikacji i wymiany danych. Nie "przechodzą" przez firewall'e bez uprzedniego ich skonfigurowania oraz nie oferują takiej elastyczności jak Web Services. Jednak tam gdzie liczy się wydajność są lepsze. Web Services to interfejs oferujący innym (klientom) uruchamianie dostępnych metod i zwracanie z powrotem wyników działania przez serwer WS (w dalszej części będę używał tego skrótu w odniesieniu do Web Services). Żądania są, w postaci specjalnie sformatowanego XMLa, wysyłane przez POST protokołem HTTP, a następnie wynik działania zwracany jest do użytkownika, także w postaci XMLa. WS dzielimy na trzy warstwy: 1. Packaging 2. Description 3. Discovery 2. Packaging Jest to warstwa wymiany danych, która odbywa się poprzez TCP/IP na porcie 80 wykorzystując jak wyżej wspomniałem protokół HTTP i XML jako źródło danych. Takie rozwiązanie ma tą zaletę, że przepuszcza je firewall bez potrzeby dodatkowej konfiguracji. Warstwa packaging pozwala na wymianę danych. Jednak, aby obie strony mogły zrozumieć je, muszą korzystać z ustalonych standardów. Istnieje kilka standardów tworzenia - pakowania - danych XMLowych. Najpopularniejszymi standardami są SOAP (Simple Object Access Protocol) oraz XML-RPC (XML-Remote Procedure Call). Jest jeszcze kilka innych standardów min. OPML (Outline Processor Markup Language), które jednak nie cieszą się taką popularnością jak dwa pierwsze. http://www.php.pl Strona 2 z 9 2.1. XML-RPC XML-RPC został zaprojektowany jako łatwy w implementacji i bardzo prosty system pakowania danych dla zdalnych procedur. Struktura XMLa jest na tyle prosta, że z łatwością można zorientować się w jej "przeznaczeniu". Jednak mimo swej prostoty oferuje kompleksowe wsparcie dla przekazywania złożonych struktur danych. Ciekawostką może być fakt, że dokumentacja zajmuje tylko siedem stron w porównaniu z dokumentacją SOAPa zajmującą czterdzieści. Typy danych jakimi dysponuje XML-RPC to: • • • • • • • • 32-bitowy integer - znaczniki: <i4> lub <int> Boolean - znacznik: <boolean> Znaki z tablicy ASCII - znacznik: <string> "Podwójnie precyzyjne" liczby zmienno-przecinkowe znacznik: <double> Data i czas w formacie ISO 8601 (przykład: 19980717T14:08:55) znacznik: <dateTime.iso8601> Base64-encoded binary - znacznik: <base64> Struktury danych - znacznik: <struct> Tablice - znacznik: <array> Poniżej jest przykładowe zapytanie, jakie wysyłane jest do serwera WS w "czystej" postaci. Example 1. Przykład rządania XML-RPC POST /server.php HTTP/1.0 User-Agent: Mozilla/5.0 rv:1.6a) Gecko/20031031 Host: services.php.pl Content-Type: text/xml Content-length: 181 (X11; U; Linux i686; en-US; <?xml version="1.0"?> <methodCall> <methodName>examples.getStateName</methodName> <params> <param> <value> <i4>41</i4> </value> </param> </params> </methodCall> Z tego przykładu można odczytać, że chcemy wywołać metodę getStateName obiektu examples z parametrem typu integer o wartości 41. http://www.php.pl Strona 3 z 9 Example 2. Odpowiedź serwera XML-RPC HTTP/1.1 200 OK Connection: close Content-Length: 158 Content-Type: text/xml Date: Fri, 17 Jul 1998 19:55:08 GMT Server: services.php.pl XML-RPC server <?xml version="1.0"?> <methodResponse> <params> <param> <value> <string>South Dakota</string> </value> </param> </params> </methodResponse> Jak widać odpowiedź jest podobna do żądania. Prostota XML-RPC jest jej główną zaletą, dlatego właśnie jest to dobre rozwiązanie w budowaniu pierwszych prostych WS-ów. Przyjrzyjmy się teraz implementacjom XML-RPC w PHP. IXR - The Incutio XML-RPC Library IXR jest to bardzo ułatwiająca prace implementacja. Została tak zaprojektowana, aby osoby znające powierzchownie WS mogły bez problemu poradzić sobie z napisaniem serwera jak i klienta WS. Posiada udogodnienia takie jak łatwa konwersja typów PHP do postaci XML-RPC czy też możliwość tworzenia własnych rozszerzeń. IXR w pełni obsługuje XML-RPC. Wspiera także wielokrotne wywołania system.multicall oraz inne rozszerzenia. phpXMLRPC phpxmlrpc zostało napisane przez samych twórców XML-RPC - Useful Inc. - co od razu sugeruje pełne wsparcie standardu. Zaletami implementacji są jej duże możliwości. Dostarcza wiele elementów niezbędnych w tworzeniu WS jednak dla mniej wtajemniczonych użytkowników może nastręczać problemów na przykład w podawaniu typów zmiennych czy korzystania z dostępnych obiektów. Inne implementacje phpRPC - dysponująca możliwościami wykraczającymi wysyłanie i odbieranie rządań i odpowiedzi. http://www.php.pl poza zwykłe Strona 4 z 9 XML-RPC Client/Server (K. Devense) - zestaw funkcji umożliwiające w łatwy sposób stworzenie klienta i serwera XML-RPC. eZ xmlrpc - klasa do obsługi XML-RPC dostępna w eZ Publish. 2.2. SOAP SOAP jest to jak piszą twórcy: "lekki protkół, do łatwej wymiany dowolnego typu danych w zdecentralizowanym systemie. Oparty jest on o XMLa i składa się z trzech elementów: opakowania definiującego framework, opisującego wiadomość ( oraz to jak ją przetwarzać ), zestawu zasad kodowania opisujących instancje zdefiniowanych w aplikacji typów danych oraz konwencji dla prezentacji zdalnych wywołań procedur i odpowiedzi" Co do jego "malych rozmiarow" można dyskutować jednak jest to na pewno bogaty protokół dysponujący szeregiem pomocnych elementów niestety kosztem tego co w XML-RPC jest zaletą - przejrzystości i łatwości implementacji. Trzeba także zaznaczyć, ze SOAP wspierany jest min. przez Microsoft na platformie .NET i dlatego właśnie będzie się wciąż rozwijał i tak szybko nie umrze. Przyjrzyjmy się jednak bliżej protokołowi SOAP. Głównym elementem SOAP'a jest "blok wiadomości" - message. Zawiera on następujące elementy: 1. Element opakowania - envelope - identyfikuje on SOAP'a. Zawiera on także następujące przestrzenie nazw: • dla envelope: http://www.w3.org/2001/12/soap-envelope • dla kodowania: http://www.w3.org/2001/12/soap-encoding 2. Opcjonalnie nagłówek - header 3. Element ciała SOAP - body - znajdują się w nim wywołania jak i odpowiedzi serwera. 4. Opcjonalny element błędów - fault - dostarczający informacje o błędach, które powstały podczas przetwarzania wiadomości. Przykład szkieletu SOAP'a znajduje się poniżej. Jak widać przypomina on trochę budowę strony XHTML. http://www.php.pl Strona 5 z 9 Example 3. Szkielet SOAP'a <?xml version="1.0"?> <soap:Envelope xmlns:soap="http://www.w3.org/2001/12/soap-envelope" soap:encodingStyle="http://www.w3.org/2001/12/soap-encoding"> <soap:Header> ... </soap:Header> <soap:Body> ... <soap:Fault> ... </soap:Fault> </soap:Body> </soap:Envelope> Przyjrzyjmy się teraz dokładniej poszczególnym elementom SOAP'a. 2.2.1. Envelope Envelope jest głównym elementem SOAP'a. Definiuje on nam ten protokół. Zawiera on dwie przestrzenie nazw: xmlns:soap="http://www.w3.org/2001/12/soap-envelope" soap:encodingStyle="http://www.w3.org/2001/12/soap-encoding" Jak pierwsza przestrzeń musi zawierać podane wyżej URI, tak (soap:encoding) nie może zawierać innego adresu niż ten z przykładu. druga Example 4. Przykładowa konstrukcja envelope <?xml version="1.0"?> <soap:Envelope xmlns:soap="http://www.w3.org/2001/12/soap-envelope" soap:encodingStyle="http://www.w3.org/2001/12/soap-encoding"> ... </soap:Envelope> http://www.php.pl Strona 6 z 9 2.2.2. Header Header zawiera opis wiadomości SOAP. Jest on opcjonalny, lecz gdy już się pojawi musi on być pierwszym podelementem w elemencie envelope. Example 5. Przykład elementu header <env:Header xmlns:env="http://www.w3.org/2003/05/soap-envelope" > <t:Transaction xmlns:t="http://example.org/2001/06/tx" env:mustUnderstand="true" > 5 </t:Transaction> </env:Header> W przykładzie podany jest atrybut mustUnderstand. Ustawienie go na 1/true oznacza, że parser odpowiedzialny za przetworzenie headera musi rozpoznać ten element, w przeciwnym razie ma zwrócić błąd. 2.2.3. Body Element body jest główną częścią SOAP'a, to tutaj podawane są "rozkazy" serwisowi jak i zwracane jego odpowiedzi. Example 6. Przykład żądania <?xml version="1.0"?> <soap:Envelope xmlns:soap="http://www.w3.org/2001/12/soap-envelope" soap:encodingStyle="http://www.w3.org/2001/12/soap-encoding"> <soap:Body> <m:GetLoginName xmlns:m="http://php.pl/login"> <m:Item>42</m:Item> </m:GetPrice> </soap:Body> </soap:Envelope> W przykładzie widzimy, że wywołujemy metodę GetLoginName z parametrem 12. Odpowiedź serwera SOAP może być następująca: http://www.php.pl Strona 7 z 9 Example 7. Przykład odpowiedzi <?xml version="1.0"?> <soap:Envelope xmlns:soap="http://www.w3.org/2001/12/soap-envelope" soap:encodingStyle="http://www.w3.org/2001/12/soap-encoding"> <soap:Body> <m:GetLoginNameResponse xmlns:m="http://php.pl/login"> <m:LoginName>Seth</m:LoginName> </m:GetPriceResponse> </soap:Body> </soap:Envelope> W odpowiedzi dostaliśmy wartość, która jest nazwą loginu dla podanego ID. 2.2.4. Fault Element fault zawiera informacje o błędach. Jest on zawsze elementem body i może się pojawić tylko raz w "wiadomości". Elementy fault zawiera następujące elementy: • • • • <faultcode> - kod błędu. Dostępne kody błędów to: o VersionMismatch ? błąd określający niepoprawną przestrzeń nazw w elemencie envelope o MustUnderstand - jeżeli ustawiliśmy w headerze wartość mustUnderstand na 1, a serwer nie rozpoznał nagłówków, zwracany jest właśnie ten błąd o Client - wiadomość SOAP wysłana od klienta była niepoprawna o Server - wystąpił błąd na serwerze, dlatego wiadomość nie mogła zostać obsłużona <faultstring> -tekst błędu <faultactor> - informacja o tym kto/co spowodowało błąd <detail> - szczegóły błędu 2.2.5. Implementacje w PHP Przyjrzyjmy się niektórym implementacjom SOAP'a w PHP. PHP-SOAP PHP-SOAP to rozwijająca się implementacja posiadająca jednak już sporo możliwości i łatwe API. Dokumentacja pozostawia wiele do życzenia, ale przykłady zastosowania tej implementacji pozwalają łatwo zrozumieć sposób budowania Web Services w oparciu o tą implementacje. http://www.php.pl Strona 8 z 9 nuSOAP nuSOAP jest to dobrze udokumentowana implementacja, która cały czas się rozwija co dobrze wrózy jej na przyszłość. Istnieje także lista mailowa, na której można zadawać pytania dotyczące nuSOAPa. 2.3. Który protokół wybrać? Na to pytanie nie można odpowiedzieć jednoznacznie. Wszystko zależy od tego czym dysponujemy i do jakich celów chcemy użyć Web Services. XML-RPC to bardzo "łatwy protokół", który można szybko wdrożyć. Jest na tyle prosty, że czytając XMLa można z łatwością zrozumieć, jakie komunikaty wychodzą i wchodzą do/od serwera - przez co można łatwo debugować taki Web Service. Protokół jak wcześniej wspomniałem jest prosty, a więc i nie trzeba skomplikowanych algorytmów (skryptów) do jego obsługi. Mimo, że XML-RPC dysponuje dużymi możliwościami SOAP jest znacznie bardziej rozbudowany i pozwala na jeszcze więcej. Możemy min. tworzyć własne struktury danych. Zaletą jest też to, że w rozwój SOAPa zaangażował się Microsoft co na pewno przyczyni się do rozpropagowania tego protokołu. Dlatego też jeżeli chcemy użyć Web Services do prostych zastosowań takich jak np. udostępnianie artykułów czy innych danych najlepiej użyć XML-RPC, a w poważniejszych zastosowaniach wymagających min. komunikacji z innymi aplikacjami wykorzystującymi SOAPa odpowiedź nasuwa się sama ;) 3. Co w następnej części ? W następnej części przyjrzymy się kolejnym elementom Web Services - warstwie Description i Discovery. Zbierzemy także do kupy dotychczasowe wiadomości i napiszemy wstępny szkic Web Services. http://www.php.pl Strona 9 z 9