[WIP] Refactored response and request handling and cleaned up the API

Facebook SDK 4.1 has been transformed! :)

I feel bad submitting such a huge PR, but I couldn't figure out a way to update the API and refactor the request/response stuff incrementally. Sorry! :/

If you want to Skype, let me know and we'll go over this together. Can't wait to hear your feedback!

I haven't rebased this yet, so it won't be able to be merged until I resolve the conflicts. 


# Some quick bullet points

- Killed `FacebookSession`.
- Made `Facebook` a getter/setter/factory for ease of use.
- Added some new base features:

```php
Facebook::setDefaultAccessToken('access-token');

Facebook::setDefaultGraphApiVersion('v1.0')
$graphVersion = Facebook::getDefaultGraphApiVersion()

$appAccessToken = Facebook::getAppAccessToken();
```


# Request Refactor

As discussed in #141. Here's what made it into the PR:

```php
use Facebook\Facebook;

$request = Facebook::newRequest();
// OR
$request = Facebook::newRequest('access-token');

// Returns a `GraphObject` by default
$graphObject = $request->get('/me?fields=name,email');

// Other possible method setters:
$request
	->withAccessToken('access-token')
	->withFields(['foo' => 'bar'])
	->withETag('some-eTag')
	->get('/foo');

// Other methods
$graphObject = $request->post('/me/feed', ['message' => 'Foo!']);
// OR
$graphObject = $request->withFields(['message' => 'Foo!'])->post('/me/feed');
// If delete was success will return a `GraphObject` with a "was_successful" key set to true
$graphObject = $request->delete('/some-id');

// If you need the `Response` entity to see raw response for more details or debugging or whatevers
$response = $request->getLastResponse();
$eTag = $response->getETag();
```


## Batch Requests

Almost the same as we discussed in #141:

```php
$batchRequest = Facebook::newBatchRequest();

$batchRequest
	->newRequest()
	->get('/me?fields=name');
$batchRequest
	->newRequest('access-token', 'request-name')
	->get('/me/feed');
$batchRequest
	->newRequest()
	->post('/me/feed', ['message' => 'Foo!']);

try {
    // Returns a `BatchResponse` entity
    $responses = $batchRequest->send();
} catch($e FacebookSDKException) {
    // You tried to send more than 50 requests or some other validation error
}

foreach ($responses as $res) {
    if (!$res->isError()) {
        // $res is a `Response` entity
    } else {
        $e = $res->getThrownException();
        echo $e->getMessage();
    }
}


// Other possible method setters:
$batchRequest
	->newRequest()
	->withAccessToken('access-token')
    ->withRequestName('some-name')
    ->withETag('some-eTag')
    ->withFields(['foo' => 'bar'])
	->get('/me');
```


## Beta Mode

You can enable beta mode with `BaseRequest::enableBetaMode();`. Addresses #108.


# Response Refactor

@gfosco - Sorry I chopped off the `Facebook` prefix. This wan't intentional. I did a last-minute refactor before committing and didn't have time to add it back. We can add it back later if you like. :)


## Batch Responses

As shown in the example above you can `foreach` over the `BatchResponse` entity because it makes use of  `IteratorAggregate`. Each iteration returns a `Response` entity from the batch of responses.


## Exception renamed

Renamed `FacebookRequestException` to `FacebookResponseException` since it's the response that's throwing the exception, not the request. And it now takes a `Request` entity on instantiation.


## `GraphNodes/*` Refactor

A whole lot of nice improvements on the this front!


### Based on `Collection`

The `GraphObject` is now based on a very primitive collection object. We can make it way cooler later but some of the new features include:


#### `ArrayAccess`

```php
$graphObject = $request->get('/me');
echo $graphObject['name'];
```


#### `IteratorAggregate`

```php
$graphObject = $request->get('/me');
foreach ($graphObject as $key => $value) {
	//
}
```


#### `Countable`

```php
$graphObject = $request->get('/me/feed');
$feedCount = count($graphObject);
```


### Smarter `Graph*` Casting

Now when data is decoded, it is traversed recursively and cast to either a `GraphObject`, `GraphList` or `DateTime`. It's smart enough to recast certain sub `GraphObject`'s when a developer casts the parent `GraphObject` to a specific Graph object.

Sub types will automatically cast certain properties to their corresponding `Graph*` object. For example, when a `GraphUser` is cast, the key `hometown` will automatically be cast as a `GraphPage`.


### Pagination on the object level

Before this PR, you could only paginate across the root-level of a response. In this PR, you can't paginate at all! Lol. :)

Graph can return pagination meta data on any list of objects - even embedded ones. The new smarter type casting will detect this and cast those special objects into a `GraphList` object. `GraphList` has `next()` and `prev()` which will be functional soon... :)


### Magic getters and casters

In order to streamline the API, `GraphObject`'s can get any attribute magically like so:

```php
// Fetches the key name "id"
$id = $graphObject->getId();
// Fetches the key name "is_valid"
$foo = $graphObject->getIsValid();
// Fetches the key name "some_attribute"
$bar = $graphObject->getSomeAttribute();
```

It makes use of the `__call()` magic method so we don't have to update the SDK with every attribute available to every possible Graph node.

You can also recast a `GraphObject` magically:

```php
$graphUser = $graphObject->castAsGraphUser();
```


# More Isolated Tests

The tests are testing with a lot more isolation, but we can still do better. We were hitting Graph like 25+ times. I got that down to 18. Which isn't ideal, but it's better! :)


# TODO

- Add `GraphFile` support for file uploading.
- Pimp out `Collection` to make response data from Graph even more convient to mess with.
- Finish pagination on the `GraphList` object.


# <<EOF;

Again - sorry for the huge PR. Please don't kill me! :) Looking forward to the feedback!