This article presents a way to communicate between two distinct webserver using php. The goal is to send a http request to another website in order to get some raw information (XML, JSON,…) or to get some html. The protocol of communication is HTTP and I will be using the cUrl library, which is part of any PHP distribution over the version 4.0.2 in order to send the request (you do not need to install cUrl, it is part of the PHP package). This library provides a lot of control on the formation you getting and sending across the two servers.
Here’s a simple algorithm that send a GET HTTP request to a server and display the result:
<php
$ch = curl_init("http://www.ted-gueniche.com/");
curl_setopt($ch, CURLOPT_HEADER, 0);
echo curl_exec($ch);
curl_close($ch);
?>
To complete this example, the following code (placed at www.ted-gueniche.com) intercept and display the http request.
<php echo 'You successfully communicated with this server'; ?>
Some of you might ask why I did not use javascript to do the http request, well most browser forbid javascript to make request to external domains. It means that this website (www.ted-gueniche.com) connot use ajax to request a page from google.com or any other website but ted-gueniche.com.
The previous technique is awesome but it would be even better if it could communicate with a distant server asynchrosly like an AJAX request. Meaning that we do not need to reload the page to make the request. Let’s do a javascript event that will send an ajax request to the previous php code (the one that send HTTP request) .That way we bypassed the cross domain limitation of ajax.
The program is divided in three files:
- index.php is our main page where the AJAX is originated.
- post.php is the script that send the HTTP request using PHP cUrl. This file is located on the same server as index.php
- distant.php is located on another server and only generate some html when viewed.
index.php
<script type="text/javascript">
function sendHttp(url) //send an ajax request to "post.php" with the "url" parameter
{
var localUrl = "post.php";
var request = new XMLHttpRequest();
request.open('POST', localUrl, true); //setting up a HTTP GET request
request.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
request.setRequestHeader("Content-length", url.length);
request.setRequestHeader("Connection", "close");
request.onreadystatechange = notify; //callback function
request.send("url=" + url); //send the request
function notify()
{
if(request.readyState == 4) //the response is complete
{
//displaying the response in the #render element
var render = document.getElementById("render");
render.innerHTML = request.responseText;
}
}
}
</script>
<a id="targetEvent" onclick="sendHttp('http://www.google.ca')" href="#"> Click here to send an http request to my blog and receive its frontpage, without reloading the current page. </a>
post.php
isset($_POST['url']) && strlen($_POST['url']) > 0 && strlen($_POST['url']) < 123)
{
//initiate the request
$ch = curl_init($_POST['url']);
curl_setopt($ch, CURLOPT_HEADER, 0);
echo curl_exec($ch); //send and display the request
curl_close($ch); //cleaning up }
?>
distant.php
<?php echo 'You successfully communicated with this server'; ?>
Once that you put index.php and post.php on a server and distant.php on another one, visit index.php and click on the link.It should display “You successfully communicated with this server” without reloading the page. I’ll finish with a word on security. You do not want people using “post.php” as a proxy or to put down your website. So I’ll propose the following security measures:
- Check if the request’s ip is the same as the server’s ip.
- Generate a token on index.php that would be sent to post.php which would verify is the token is valid.