Hello, please sign in or register
You are here: Home

A Proxy for Windows Live REST'ful interface in PHP


This article is an introduction to writing a proxy on your website to by-pass XSS browser restrictions.
Here i'm taking advantage of the REST'ful interface of Windows Live. This does make coding pretty cool as you can tap into their JSON strutured ODATA. GET POST PUT and DELETE contents right from the browser with  little javascript. Check it out at http://rex.dev.live.com)

Example

Its all about using your own tools for the job ...
$.getJSON('./proxy.php?path=Contacts/AllContacts', function(json){console.log(json)});
I'm using JQuery to access proxy.php which relays requests to http://apis.live.net/. My proxy.php script is also deciphering the path (Windows Live RESTful service to reduce the ammount of browser->proxy server requests.

Code

My proxy script is included below. I've written it in a way which passes on errors and does not require any additional libraries ... not even the ominpresent cURL library. It supports all kind of request verbs (i.e. GET,POST,PUT,DELETE). Which may be overwritten via querystring e.g. &method=verb - to be compatible with browsers with limited XHR features. 

<?php
/**
* PHP Proxy, resolves XSS security controls.
* Communicate with remote resources.
* @param path (required)
* @param method (optional)
* E.g. "proxy.php?method=GET&path=Contacts/AllContacts"
*
* @author Andrew Dodson
*/
if( isset( $_GET['path'] ) ){

$path = $_GET['path'];
$opts = array(
'http'=> array(
// 'proxy' => 'tcp://127.0.0.1:8888',
'ignore_errors' => true,
'method'=> 'GET',
'header'=>"Content-Type: application/json\r\nAuthorization: WRAP access_token=" . $_COOKIE['accessToken'] . "\r\nAccept: application/json\r\n"
)
);
$a = ( preg_match("#^https?:\/\/#",$path)
? array($path)
: array('http://apis.live.net/v4.0/') + explode('/', '/'.trim($path, '/') ) );

foreach( $a as $path ){
// If this is the last request
if($path===end($a)){
$opts['http']['content'] = file_get_contents("php://input"); // payload
$opts['http']['method'] = (!empty($_GET['method'])?$_GET['method']:$_SERVER['REQUEST_METHOD']); // e.g. GET,POST,PUT
}
// do we need to define the path?
if(!empty($resp)){
$json = (array)json_decode($resp);
$path = $json[$path.'Link'];
if(!preg_match('#^https?:\/\/#', $path))
$path = $json['BaseUri'] . $path;
}
// Make the request
if (!$fp = fopen($path, 'r',false, stream_context_create($opts))) {
break;
}
$resp = stream_get_contents($fp);
}
$meta = stream_get_meta_data($fp);
foreach( $meta['wrapper_data'] as $o) header($o);
print $resp;
}
?>

CSRF - Cross site request forgery

Proxies, by definition, can make a multitude of HTTP requests. This makes them good entry points for malicious scripts running on other websites. Especially if you can defined the verb like the example above can.

The best ways to prevent unscrupulous websites from attacking your users account is to...

  • Require authentication in GET and POST parameters, not only cookies;
  • Check the HTTP Referer header;

Ommitted from the script above - because when accessing the proxy directly, as one would do in development, there are no request headers.

if( parse_url($_SERVER['HTTP_REFERER'], PHP_URL_HOST ) !== $_SERVER['HTTP_HOST'] ) ){
      // CSFR in progress, get me out of here!
}

Comments

Title*
Comment

Prove you are not a robot

To prove you are not a robot, please type in the six character code you see in the picture below
Security confirmation codeI can't see this!
Contact
Name*
Email never shown*
Home Page

Author

Andrew Dodson
Since:Feb 2007

Comment | flag

Categories

Bookmark and Share