PHP: fsockopen() – Sending POST data with HTTP request

I have come across many occurrences where I have needed to pass data to a websites form via POST, this is simple enough if doing via a browser as all you need to do is duplicate / copy the original form parse it with your default data possibly from a database and a bit of JavaScript code to initiate the form sending process. But what if you want to make it fully automatic via a cronjob? The code I am going to show you simply sends a POST request to the target web server and waits for the response. I have previously used this code to secretly post data to a website process the result and display the output in a different format (so it’s all hidden and the users on the website never know or see the other website). I have written a previous post found here related to the fsockopen function.

The Header String

This is the first bit of data we send to the web server it basically tells the web server the format of our information and any other related data, if we don’t send this the server might refuse the request or return something complexly different. I will go into this section in more detail now.

//This tells the web server what version of HTTP protocal we are using
//It also tells it the file we are sending the request to which in this case is /files/post.php which translates to shanerutter.co.uk/files/post.php
$http  = "POST /files/post.php HTTP/1.1\r\n";

//This is the url or IP of whcih the request is coming from
$http .= "Host: shanerutter.co.uk\r\n";

//The user agent being used to send the request
$http .= "User-Agent: " . $_SERVER['HTTP_USER_AGENT'] . "\r\n";

//The content type, this is important and much look like the following if sending POST data.
//If this is not provided the server may not process the POST data
$http .= "Content-Type: application/x-www-form-urlencoded\r\n";

//Lets the web server know the total length/size of are POST content
//It is not always required but some servers will refuse requests if not provided
$http .= "Content-length: " . strlen($post_data) . "\r\n";

//Tells the server are header request is complete and the rest if content / POST data
$http .= "Connection: close\r\n\r\n";

//Adds are post data
$http .= $post_data . "\r\n\r\n";

The Code

< ?php
//Variable storing the post data we want to send. Starts with the post field name then its content followed by a & if there is another to come after it.
$post_data = 'name=bob&age=12&county=uk';

//Initiates a connection to example.com using port 80 with a timeout of 15 seconds.
$socket = fsockopen("example.com", 80, $errno, $errstr, 15);

//Checks if the connection was fine
if(!$socket){
	//Connection failed so we display the error number and message and stop the script from continuing
	echo ' error: ' . $errno . ' ' . $errstr;
	die;
}else{
	//Builds the header data we will send along with are post data. This header data tells the web server we are connecting to what 
	//we are, what we are requesting and the content type so that it can process are request.
	$http  = "POST /files/post.php HTTP/1.1\r\n";
	$http .= "Host: shanerutter.co.uk\r\n";
	$http .= "User-Agent: " . $_SERVER['HTTP_USER_AGENT'] . "\r\n";
	$http .= "Content-Type: application/x-www-form-urlencoded\r\n";
	$http .= "Content-length: " . strlen($post_data) . "\r\n";
	$http .= "Connection: close\r\n\r\n";
	$http .= $post_data . "\r\n\r\n";
	//Sends are header data to the web server
	fwrite($socket, $http);		
	$contents = "";
	//Waits for the web server to send the full response. On every line returned we append it onto the $contents 
	//variable which will store the whole returned request once completed.
	while (!feof($socket)) {
		$contents .= fgets($socket, 4096);
	}
	//Close are request or the connection will stay open untill are script has completed.
	fclose($socket);
}
?>

Leave a Reply

This site uses Akismet to reduce spam. Learn how your comment data is processed.

4 Comments

  1. Gopalakrishnan

    Dear Mr Shane,

    Iam new to php and programming in general. I have a “PAW” webserver installed on my Android Phone. I would like to connect to other remote webservers thru php script running on the PAW server.I use php version is 5.4.2.

    I get “Warning: fsockopen(): php_network_getaddresses: gethostbyname failed. errno=111” . Iam not able to ping the remote server also thru php and system call .But Using android app(network Utility) I am able to ping google on port 80 from the same phone where the “PAW” is installed. Can you tell me what could be the problem? Very many thanks in Advance.

    • Are you using a host name or ip address? Maybe the host name is not returning an ip address?

  2. Udenewu Kingsley

    Hi thanks for the tutorial it was well explained but the my question is after a data has been posted how can you retrieve the data back.

    Thank you.

    • On line 29

      $contents .= fgets($socket, 4096);

      we read any data back from the socket into a variable called $contents. When you post any response should be in this variable. On line 32 we have

      fclose($socket);

      You want to put your code below this, for example to process the response from the post request.