Własna implementacja biblioteki cURL w PHP

Opis pomysłu
Pomysł powstał podczas realizacji projektu Uwierzytelnienie użytkownika domenowego w PHP (Single Sign On), kiedy to okazało się, że na firmowym serwerze HTTP (opartym na linuksowym Apache) skrypty w PHP nie mogą korzystać z biblioteki cURL, ponieważ ta jest wyłączona (dla bezpieczeństwa lub taka akurat była domyślna konfiguracja podczas instalacji). Ponieważ obecnych ustawień nie bardzo można zmieniać, sytuacja ta spowodowała potrzebę obejścia tego ograniczenia przy pomocy skorzystania z funkcji fsockopen i wtedy podjąłem decyzję o napisaniu własnej (mocno uproszczonej) biblioteki cURL, którą można by używać analogicznie jak cURL w sytuacji niedostępności tejże biblioteki.

Właściwości biblioteki
W bibliotece są zdefiniowane wszystkie stałe (z dokładnością do oryginalnych wartości), które występują w standardowym cURL. Wprawdzie wiele z nich nie jest do użycia, ponieważ nie ma zaimplementowanych stosownych funkcji, ale dzięki temu zapewnia to przenaszalność i uniwersalność tej biblioteki. Być może kiedyś w przyszłości brakująca funkcjonalność zostanie dodana, jeśli będzie taka wyraźna potrzeba.
Biblioteka ma obecnie zdefiniowane następujące funkcje:
  curl_init();
  curl_reset();
  curl_setopt();
  curl_setopt_array();
  curl_exec();
  curl_close();
  curl_copy_handle();
  curl_getinfo();
  curl_escape();
  curl_unescape();
  curl_version();
  curl_errno();
  curl_error();

Biblioteka poprawnie obsługuje pobieranie stron HTTP oraz HTTPS (połączenia szyfrowane wymagają, by w PHP była dostępna biblioteka php_openssl, zauważyłem że w PHP 4.x są z tym problemy, być może to kwestia konfiguracji), przesyłanie i odbieranie ciasteczek (w tym pełna obsługa obu formatów plików do przechowywania ciasteczek) oraz przesyłanie danych metodą POST (wysyłanie plików metodą PUT będzie wkrótce dodane), poprawnie zachowuje się także w przypadku pobierania samego nagłówka strony (metodą HEAD). Obsługuje także wielokrotne przekierowania (redirect), uwzględniana jest maksymalna liczba takich przekierowań zdefiniowana przez użytkownika, poprawnie działają też ustawione limity czasowe (timeout). Dodatkowo biblioteka obsługuje kompresję zawartości strony (gzip, compress) a także składanie strony podzielonej na kawałki (chunked transfer encoding), który jest wykorzystywany przez niektóre serwery HTTP.
Biblioteka aktualnie wspiera następujące parametry funkcji curl_setopt():
  CURLOPT_URL - ustawia adres URL strony do pobierania;
  CURLOPT_USERAGENT - ustawia wartość User-Agent wywołania (domyślnie brak jest tego nagłówka);
  CURLOPT_REFERER - ustawia wartość Referer wywołania (domyślnie brak jest tego nagłówka);
  CURLOPT_ENCODING - ustawia wartość Accept-Encoding wywołania (domyślnie brak jest tego nagłówka);
  CURLOPT_HEADER - dołącza zawartość odczytanego nagłówka przy zwracaniu wyniku zapytania;
  CURLOPT_NOBODY - pobiera sam nagłówek (bez zawartości strony) poprzez użycie wywołania HEAD, lub jeśli to niemożliwe, nie zwraca treści (body) odebranej z serwera odpowiedzi;
  CURLOPT_HTTPHEADER - przekazuje tablicę zawierającą zestaw dodatkowych nagłówków do wysłania;
  CURLOPT_COOKIE - przekazuje ciasteczka, które zostaną przekazane w nagłówku Cookie w postaci kolejnych par "nazwa=wartość" oddzielonych "; ";
  CURLOPT_COOKIEFILE - wskazuje nazwę pliku, zawierającego zapisane ciasteczka (w specjalnym formacie Netscape lub w formacie występującym w nagłówku odpowiedzi HTTP), które mają być wysłane podczas wywołania do serwera;
  CURLOPT_COOKIEJAR - wskazuje nazwę pliku, w którym zostaną zapisane odebrane z serwera ciasteczka;
  CURLOPT_RETURNTRANSFER - informuje, by zamiast wyświetlać wynik wywołania (odpowiedź serwera) na ekranie, zwrócić go w postaci tekstu jako wynik funkcji curl_exec();
  CURLOPT_MUTE - ma analogiczne znaczenie jak opcja CURLOPT_RETURNTRANSFER, dodana dla zapewnienia zgodności ze starszymi wersjami biblioteki cURL;
  CURLOPT_FAILONERROR - w przypadku wystąpienia błędu HTTP od 400 wzwyż przerywa działanie funkcji curl_exec() zwracając błąd (false), domyślnym działaniem biblioteki cURL jest zwrócenie (lub wyświetlenie) odebranej odpowiedzi bez względu na zwrócony przez serwer kod statusu żądania HTTP;
  CURLOPT_POST - wskazuje by użyć w wywołaniu żądania metodę POST, ustawia typ przesyłanych danych (Content-Type) na application/x-www-form-urlencoded, używany najczęściej przy przesyłaniu formularzy;
  CURLOPT_POSTFIELDS - zawiera zakodowane dane (funkcją urlencode) wysyłane metodą POST w postaci ciągu zawierającym kolejne pary "nazwa=wartość" oddzielone znakiem "&", jeśli dane są zapisane w tablicy (w formacie klucz => wartość), to nagłówek Content-Type zostanie ustawiony na multipart/form-data, który jest używany najczęściej przy przesyłaniu plików;
  CURLOPT_HTTPGET - ustawia metodę pobrania strony na GET - ta metoda jest domyślna, ale mogą ją zmienić inne parametry;
  CURLOPT_PUT - wskazuje by użyć w wywołaniu metodę PUT, używaną przy przesyłaniu plików - wymaga ustawienia dodatkowych danych w parametrach CURLOPT_INFILE oraz CURLOPT_INFILESIZE;
  CURLOPT_CUSTOMREQUEST - ustala metodę, jaka zostanie użyta w wywołaniu żądania - poza standardowymi "GET" i "HEAD" można użyć innych metod akceptowanych przez docelowy serwer (np. "DELETE" czy "CONNECT");
  CURLOPT_CONNECTTIMEOUT - liczba sekund czasu oczekiwania na nawiązanie połączenia - wartość 0 (zero) oznacza oczekiwanie bez końca;
  CURLOPT_CONNECTTIMEOUT_MS - liczba milisekund czasu oczekiwania na nawiązanie połączenia;
  CURLOPT_TIMEOUT - liczba sekund czasu oczekiwania na realizację wywołanego żądania;
  CURLOPT_TIMEOUT_MS - liczba milisekund czasu oczekiwania na realizację wywołanego żądania;
  CURLOPT_BUFFERSIZE - ustawia wielkość bufora używanego podczas odczytu wyniku wywołanego żądania;
  CURLOPT_HTTP_VERSION - ustawia wersję używanego protokołu HTTP (1.0 lub 1.1);
  CURLOPT_FOLLOWLOCATION - włącza podążanie za kolejnymi przekierowaniami wskazywanymi przez nagłówek Location, uwzględniając maksymalne ograniczenie ustawione przy CURLOPT_MAXREDIRS;
  CURLOPT_MAXREDIRS - maksymalna liczba możliwych do wykonania przekierowań Location, wartość 0 (domyślna) wyłącza ograniczenie liczby przekierowań;
  CURLOPT_AUTOREFERER - automatyczne ustawianie właściwej wartości nagłówka Referer przy podążaniu za przekierowaniem wskazanym w Location;
  CURLOPT_PORT - alternatywny numer portu użytego do połączenia z serwerem;
  CURLOPT_CRLF - włącza konwertowanie znaków uniksowej nowej linii LF na windowsową parę znaków CRLF;
  CURLOPT_FRESH_CONNECT - wymuszenie użycia nowego połączenia do strony zamiast skorzystania z danych zawartych w cache przeglądarki;
  CURLOPT_FORBID_REUSE - wymusza natychmiastowe zamknięcie połączenia po odebraniu wyników żądania z serwera;
  CURLOPT_HTTPPROXYTUNNEL - wskazuje by korzystać w danym wywołaniu z tunelu proxy;
  CURLOPT_PROXY - definiuje parametry tunelu proxy;
  CURLOPT_INFILE - wskazuje nazwę pliku, który ma zostać przesłany metodą PUT;
  CURLOPT_INFILESIZE - ustala rozmiar wysyłanego pliku (w bajtach);
  CURLOPT_HTTP200ALIASES - tablica wartości kodów statusu żądania HTTP, które mają również zostać uznane za powodzenie i nie zgłaszać błędów wykonania;

Największym ograniczeniem mojej biblioteki jest brak obsługi innych protokołów poza http/https oraz brak wspierania połączeń wielokrotnych (równoległych) uzyskiwanych w cURL za pomocą funkcji curl_multi_init() oraz curl_multi_exec(). Nie są to na szczęście jakieś poważne ograniczenia, a podstawowa funkcjonalność biblioteki cURL jest zachowana z zapewnieniem maksymalnej zgodności.
Implementacje biblioteki cURL, które można znaleźć w internecie, mają mocno ograniczoną liczbę obsługiwanych parametrów (curl_setopt) oraz brakuje im niektórych przydatnych funkcjonalności (np. obsługi plików zawierających ciasteczka czy odbierania skompresowanej zawartości strony), dlatego uważam, że moja wersja tej biblioteki jest jedną z najbardziej kompletnych i zaawansowanych.
Napisana przeze mnie biblioteka cURL wymaga środowiska PHP w wersji 4.3 lub nowszej - została specjalnie tak napisana, by móc działać nawet na tak starych wersjach PHP - by nie ograniczać użytkownika, który chciałby z niej skorzystać.

Wkrótce udostępnię wszystkim napisaną przez siebie bibliotekę cURL, obecnie trwają jej wewnętrzne testy.

Powrót do strony z wykazem projektów

Valid HTML 4.01 TransitionalValid CSS