+<?php
+/* HTTPConnector.class.php - HTTP Connector Class
+ * Copyright (C) 2011-2013 Philipp Kreil (pk910)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+class HTTPConnector {
+ private $cookies = array();
+ public $debug = false;
+
+ private $default_header = array(
+ "Accept-Encoding" => "deflate",
+ "Accept-Language" => "de-DE",
+ "User-Agent" => "Mozilla/5.0 (Windows NT 6.1; WOW64; rv:18.0) Gecko/20100101 Firefox/18.0",
+ "Connection" => "Keep-Alive",
+ "Cache-Control" => "no-cache",
+ );
+
+ private function fputs($fp, $line) {
+ if($this->debug)
+ echo $line;
+ fputs($fp, $line);
+ }
+
+ private function create_request($host) {
+ if(!preg_match('#^((http|https)://|)(([a-zA-Z0-9][a-zA-Z0-9_-]+[a-zA-Z0-9]\.)+[a-zA-Z]{2,5}|[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3})(:([0-9]{1,5})|)(/.*|)$#', $host, $matches))
+ return null;
+ if(empty($matches[3]))
+ return null;
+ $request = array();
+ $request['host'] = $matches[3];
+ $request['ssl'] = (strtolower($matches[2]) == "https");
+ $request['port'] = ($matches[6] ? $matches[6] : 80);
+ $request['path'] = ($matches[7] ? $matches[7] : "/");
+ $request['header'] = $this->default_header;
+ $request['header_only'] = false;
+ $this->set_header($request, "Host", $request['host']);
+
+ $host = ($request['ssl'] ? "ssl://" : "").$request['host'];
+ $request['fp'] = fsockopen($host, $request['port']);
+ return $request;
+ }
+
+ private function set_header(&$req, $header, $value) {
+ foreach($req['header'] as $name => $val) {
+ if(strtolower($name) == strtolower($header)) {
+ unset($req['header'][$name]);
+ break;
+ }
+ }
+ $req['header'][$header] = $value;
+ }
+
+ private function send_header($req) {
+ foreach($req['header'] as $name => $val) {
+ $this->fputs($req['fp'], $name.": ".$val."\r\n");
+ }
+ $cookiestr = NULL;
+ foreach($this->cookies as $cookiename => $cookievalue) {
+ if($cookiestr)
+ $cookiestr.="; ";
+ $cookiestr .= $cookiename."=".$cookievalue;
+ }
+ if($cookiestr)
+ $this->fputs($req['fp'], "Cookie: ".$cookiestr."\r\n");
+ }
+
+ private function process_request(&$req, $data = null) {
+ $this->fputs($req['fp'], $req['method']." ".$req['path']." HTTP/1.1\r\n");
+ $this->send_header($req);
+ $this->fputs($req['fp'], "\r\n");
+ if($data)
+ $this->fputs($req['fp'], $data);
+
+ $req['reply_header'] = array();
+ $req['reply'] = "";
+ $recv_state = true;
+ $recv_header = true;
+ while(!feof($req['fp'])) {
+ if($recv_header) {
+ $recv = fgets($req['fp']);
+ if($this->debug)
+ echo $recv;
+ $line = str_replace(array("\r", "\n"), array("", ""), $recv);
+ if($recv_state) {
+ $exp = explode(" ", $line, 3);
+ $req['state'] = $exp[1];
+ $req['state_text'] = $exp[2];
+ $recv_state = false;
+ continue;
+ }
+ else if($line == "") {
+ $recv_header = false;
+ if($req['header_only'])
+ break;
+ else
+ continue;
+ }
+ $line = explode(": ", $line, 2);
+ if(strtolower($line[0]) == "set-cookie") {
+ $cookie = explode("=", $line[1], 2);
+ $cookieval = explode(";", $cookie[1]);
+ $this->cookies[$cookie[0]] = $cookieval[0];
+ }
+ $req['reply_header'][$line[0]] = $line[1];
+ } else {
+ $recv = fread($req['fp'], 512);
+ if($this->debug)
+ echo $recv;
+ $req['reply'] .= $recv;
+ }
+ }
+ if(!$req['header_only'])
+ fclose($req['fp']);
+ }
+
+ public function post($host, $post, $full = false) {
+ $req = $this->create_request($host);
+ if(!$req)
+ return null;
+ $req['method'] = "POST";
+
+ $data = "";
+ foreach($post as $key => $val) {
+ if(is_array($val)) {
+ foreach($val as $subval) {
+ if($data != "") { $data.="&"; }
+ $data .= urlencode($key)."=".urlencode($subval);
+ }
+ } else {
+ if($data != "") { $data.="&"; }
+ $data .= urlencode($key)."=".urlencode($val);
+ }
+ }
+
+ $this->set_header($req, "Content-Type", "application/x-www-form-urlencoded");
+ $this->set_header($req, "Content-Length", strlen($data));
+ $this->process_request($req, $data);
+
+ if($full)
+ return $req;
+ return $req['reply'];
+ }
+
+ public function get($host, $full) {
+ $req = $this->create_request($host);
+ if(!$req)
+ return null;
+ $req['method'] = "GET";
+
+ $this->process_request($req);
+
+ if($full)
+ return $req;
+ return $req['reply'];
+ }
+
+ public function connect($host, $target, $full = false) {
+ $req = $this->create_request($host);
+ if(!$req)
+ return null;
+ $req['method'] = "CONNECT";
+ $req['path'] = $target;
+ $req['header_only'] = true;
+
+ $this->process_request($req);
+
+ if($full)
+ return $req;
+ return ($req['state'] == "200" ? $req['fp'] : NULL);
+ }
+
+}
+
+?>
\ No newline at end of file