PageRenderTime 55ms CodeModel.GetById 29ms RepoModel.GetById 1ms app.codeStats 0ms

/app/vendors/OpenID/Yadis/PlainHTTPFetcher.php

https://github.com/tanepiper/pastemonkey
PHP | 245 lines | 183 code | 35 blank | 27 comment | 22 complexity | 4a2a022d802839d7af316b035391586f MD5 | raw file
  1. <?php
  2. /**
  3. * This module contains the plain non-curl HTTP fetcher
  4. * implementation.
  5. *
  6. * PHP versions 4 and 5
  7. *
  8. * LICENSE: See the COPYING file included in this distribution.
  9. *
  10. * @package OpenID
  11. * @author JanRain, Inc. <openid@janrain.com>
  12. * @copyright 2005 Janrain, Inc.
  13. * @license http://www.gnu.org/copyleft/lesser.html LGPL
  14. */
  15. /**
  16. * Interface import
  17. */
  18. require_once "Auth/Yadis/HTTPFetcher.php";
  19. /**
  20. * This class implements a plain, hand-built socket-based fetcher
  21. * which will be used in the event that CURL is unavailable.
  22. *
  23. * @package OpenID
  24. */
  25. class Auth_Yadis_PlainHTTPFetcher extends Auth_Yadis_HTTPFetcher {
  26. function get($url, $extra_headers = null)
  27. {
  28. if (!$this->allowedURL($url)) {
  29. trigger_error("Bad URL scheme in url: " . $url,
  30. E_USER_WARNING);
  31. return null;
  32. }
  33. $redir = true;
  34. $stop = time() + $this->timeout;
  35. $off = $this->timeout;
  36. while ($redir && ($off > 0)) {
  37. $parts = parse_url($url);
  38. $specify_port = true;
  39. // Set a default port.
  40. if (!array_key_exists('port', $parts)) {
  41. $specify_port = false;
  42. if ($parts['scheme'] == 'http') {
  43. $parts['port'] = 80;
  44. } elseif ($parts['scheme'] == 'https') {
  45. $parts['port'] = 443;
  46. } else {
  47. trigger_error("fetcher post method doesn't support " .
  48. " scheme '" . $parts['scheme'] .
  49. "', no default port available",
  50. E_USER_WARNING);
  51. return null;
  52. }
  53. }
  54. $host = $parts['host'];
  55. if ($parts['scheme'] == 'https') {
  56. $host = 'ssl://' . $host;
  57. }
  58. $user_agent = "PHP Yadis Library Fetcher";
  59. $headers = array(
  60. "GET ".$parts['path'].
  61. (array_key_exists('query', $parts) ?
  62. "?".$parts['query'] : "").
  63. " HTTP/1.0",
  64. "User-Agent: $user_agent",
  65. "Host: ".$parts['host'].
  66. ($specify_port ? ":".$parts['port'] : ""),
  67. "Port: ".$parts['port']);
  68. $errno = 0;
  69. $errstr = '';
  70. if ($extra_headers) {
  71. foreach ($extra_headers as $h) {
  72. $headers[] = $h;
  73. }
  74. }
  75. @$sock = fsockopen($host, $parts['port'], $errno, $errstr,
  76. $this->timeout);
  77. if ($sock === false) {
  78. return false;
  79. }
  80. stream_set_timeout($sock, $this->timeout);
  81. fputs($sock, implode("\r\n", $headers) . "\r\n\r\n");
  82. $data = "";
  83. while (!feof($sock)) {
  84. $data .= fgets($sock, 1024);
  85. }
  86. fclose($sock);
  87. // Split response into header and body sections
  88. list($headers, $body) = explode("\r\n\r\n", $data, 2);
  89. $headers = explode("\r\n", $headers);
  90. $http_code = explode(" ", $headers[0]);
  91. $code = $http_code[1];
  92. if (in_array($code, array('301', '302'))) {
  93. $url = $this->_findRedirect($headers);
  94. $redir = true;
  95. } else {
  96. $redir = false;
  97. }
  98. $off = $stop - time();
  99. }
  100. $new_headers = array();
  101. foreach ($headers as $header) {
  102. if (preg_match("/:/", $header)) {
  103. list($name, $value) = explode(": ", $header, 2);
  104. $new_headers[$name] = $value;
  105. }
  106. }
  107. return new Auth_Yadis_HTTPResponse($url, $code, $new_headers, $body);
  108. }
  109. function post($url, $body, $extra_headers = null)
  110. {
  111. if (!$this->allowedURL($url)) {
  112. trigger_error("Bad URL scheme in url: " . $url,
  113. E_USER_WARNING);
  114. return null;
  115. }
  116. $parts = parse_url($url);
  117. $headers = array();
  118. $post_path = $parts['path'];
  119. if (isset($parts['query'])) {
  120. $post_path .= '?' . $parts['query'];
  121. }
  122. $headers[] = "POST ".$post_path." HTTP/1.0";
  123. $headers[] = "Host: " . $parts['host'];
  124. $headers[] = "Content-type: application/x-www-form-urlencoded";
  125. $headers[] = "Content-length: " . strval(strlen($body));
  126. if ($extra_headers &&
  127. is_array($extra_headers)) {
  128. $headers = array_merge($headers, $extra_headers);
  129. }
  130. // Join all headers together.
  131. $all_headers = implode("\r\n", $headers);
  132. // Add headers, two newlines, and request body.
  133. $request = $all_headers . "\r\n\r\n" . $body;
  134. // Set a default port.
  135. if (!array_key_exists('port', $parts)) {
  136. if ($parts['scheme'] == 'http') {
  137. $parts['port'] = 80;
  138. } elseif ($parts['scheme'] == 'https') {
  139. $parts['port'] = 443;
  140. } else {
  141. trigger_error("fetcher post method doesn't support scheme '" .
  142. $parts['scheme'] .
  143. "', no default port available",
  144. E_USER_WARNING);
  145. return null;
  146. }
  147. }
  148. if ($parts['scheme'] == 'https') {
  149. $parts['host'] = sprintf("ssl://%s", $parts['host']);
  150. }
  151. // Connect to the remote server.
  152. $errno = 0;
  153. $errstr = '';
  154. $sock = fsockopen($parts['host'], $parts['port'], $errno, $errstr,
  155. $this->timeout);
  156. if ($sock === false) {
  157. trigger_error("Could not connect to " . $parts['host'] .
  158. " port " . $parts['port'],
  159. E_USER_WARNING);
  160. return null;
  161. }
  162. stream_set_timeout($sock, $this->timeout);
  163. // Write the POST request.
  164. fputs($sock, $request);
  165. // Get the response from the server.
  166. $response = "";
  167. while (!feof($sock)) {
  168. if ($data = fgets($sock, 128)) {
  169. $response .= $data;
  170. } else {
  171. break;
  172. }
  173. }
  174. // Split the request into headers and body.
  175. list($headers, $response_body) = explode("\r\n\r\n", $response, 2);
  176. $headers = explode("\r\n", $headers);
  177. // Expect the first line of the headers data to be something
  178. // like HTTP/1.1 200 OK. Split the line on spaces and take
  179. // the second token, which should be the return code.
  180. $http_code = explode(" ", $headers[0]);
  181. $code = $http_code[1];
  182. $new_headers = array();
  183. foreach ($headers as $header) {
  184. if (preg_match("/:/", $header)) {
  185. list($name, $value) = explode(": ", $header, 2);
  186. $new_headers[$name] = $value;
  187. }
  188. }
  189. return new Auth_Yadis_HTTPResponse($url, $code,
  190. $new_headers, $response_body);
  191. }
  192. }
  193. ?>