Skip to content

Code climate config #55

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 5 commits into from
Nov 11, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
17 changes: 17 additions & 0 deletions .codeclimate.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
engines:
duplication:
enabled: true
config:
languages:
- "php"
phpcodesniffer:
enabled: true
config:
file_extensions: "php"
ratings:
paths:
- "**.php"
exclude_paths:
- "examples/**/*"
- "test/**/*"
- "vendor/**/*"
129 changes: 80 additions & 49 deletions lib/Client.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,6 @@
/**
* HTTP Client library
*
* PHP version 5.4
*
* @author Matt Bernier <[email protected]>
* @author Elmer Thomas <[email protected]>
* @copyright 2016 SendGrid
Expand All @@ -16,8 +14,16 @@
namespace SendGrid;

/**
* Quickly and easily access any REST or REST-like API.
*/
* Quickly and easily access any REST or REST-like API.
*
* @method Response get($body = null, $query = null, $headers = null)
* @method Response post($body = null, $query = null, $headers = null)
* @method Response patch($body = null, $query = null, $headers = null)
* @method Response put($body = null, $query = null, $headers = null)
* @method Response delete($body = null, $query = null, $headers = null)
*
* @method Client version($value)
*/
class Client
{
/** @var string */
Expand All @@ -30,32 +36,33 @@ class Client
protected $path;
/** @var array */
protected $curlOptions;
/** @var array */
private $methods;
/** @var bool */
private $retryOnLimit;
protected $retryOnLimit;

/**
* These are the supported HTTP verbs
*
* @var array
*/
private $methods = ['get', 'post', 'patch', 'put', 'delete'];

/**
* Initialize the client
*
* @param string $host the base url (e.g. https://api.sendgrid.com)
* @param array $headers global request headers
* @param string $version api version (configurable)
* @param array $path holds the segments of the url path
* @param array $curlOptions extra options to set during curl initialization
* @param bool $retryOnLimit set default retry on limit flag
* @param string $host the base url (e.g. https://api.sendgrid.com)
* @param array $headers global request headers
* @param string $version api version (configurable)
* @param array $path holds the segments of the url path
*/
public function __construct($host, $headers = null, $version = null, $path = null, $curlOptions = null, $retryOnLimit = false)
public function __construct($host, $headers = [], $version = '/v3', $path = [])
{
$this->host = $host;
$this->headers = $headers ?: [];
$this->headers = $headers;
$this->version = $version;
$this->path = $path ?: [];
$this->curlOptions = $curlOptions ?: [];
// These are the supported HTTP verbs
$this->methods = ['delete', 'get', 'patch', 'post', 'put'];
$this->path = $path;

$this->retryOnLimit = $retryOnLimit;
$this->curlOptions = [];
$this->retryOnLimit = false;
}

/**
Expand Down Expand Up @@ -91,28 +98,39 @@ public function getPath()
}

/**
* @return array
* Set extra options to set during curl initialization
*
* @param array $options
*
* @return Client
*/
public function getCurlOptions()
public function setCurlOptions(array $options)
{
return $this->curlOptions;
$this->curlOptions = $options;

return $this;
}

/**
* Make a new Client object
*
* @param string $name name of the url segment
*
* @return Client object
*/
private function buildClient($name = null)
* Set default retry on limit flag
*
* @param bool $retry
*
* @return Client
*/
public function setRetryOnLimit($retry)
{
if (isset($name)) {
$this->path[] = $name;
}
$client = new Client($this->host, $this->headers, $this->version, $this->path, $this->curlOptions);
$this->path = [];
return $client;
$this->retryOnLimit = $retry;

return $this;
}

/**
* @return array
*/
public function getCurlOptions()
{
return $this->curlOptions;
}

/**
Expand All @@ -135,10 +153,10 @@ private function buildUrl($queryParams = null)
* Make the API call and return the response. This is separated into
* it's own function, so we can mock it easily for testing.
*
* @param string $method the HTTP verb
* @param string $url the final url to call
* @param array $body request body
* @param array $headers any additional request headers
* @param string $method the HTTP verb
* @param string $url the final url to call
* @param array $body request body
* @param array $headers any additional request headers
* @param bool $retryOnLimit should retry if rate limit is reach?
*
* @return Response object
Expand All @@ -147,13 +165,18 @@ public function makeRequest($method, $url, $body = null, $headers = null, $retry
{
$curl = curl_init($url);

curl_setopt_array($curl, [
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HEADER => 1,
CURLOPT_CUSTOMREQUEST => strtoupper($method),
CURLOPT_SSL_VERIFYPEER => false,
CURLOPT_FAILONERROR => false,
] + $this->curlOptions);
$options = array_merge(
[
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HEADER => 1,
CURLOPT_CUSTOMREQUEST => strtoupper($method),
CURLOPT_SSL_VERIFYPEER => false,
CURLOPT_FAILONERROR => false,
],
$this->curlOptions
);

curl_setopt_array($curl, $options);

if (isset($headers)) {
$this->headers = array_merge($this->headers, $headers);
Expand All @@ -179,7 +202,7 @@ public function makeRequest($method, $url, $body = null, $headers = null, $retry

$response = new Response($statusCode, $responseBody, $responseHeaders);

if ($statusCode == 429 && $retryOnLimit) {
if ($statusCode === 429 && $retryOnLimit) {
$headers = $response->headers(true);
$sleepDurations = $headers['X-Ratelimit-Reset'] - time();
sleep($sleepDurations > 0 ? $sleepDurations : 0);
Expand All @@ -201,7 +224,15 @@ public function makeRequest($method, $url, $body = null, $headers = null, $retry
*/
public function _($name = null)
{
return $this->buildClient($name);
if (isset($name)) {
$this->path[] = $name;
}
$client = new static($this->host, $this->headers, $this->version, $this->path);
$client->setCurlOptions($this->curlOptions);
$client->setRetryOnLimit($this->retryOnLimit);
$this->path = [];

return $client;
}

/**
Expand Down
4 changes: 1 addition & 3 deletions lib/Response.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,6 @@
/**
* HTTP Client library
*
* PHP version 5.4
*
* @author Matt Bernier <[email protected]>
* @author Elmer Thomas <[email protected]>
* @copyright 2016 SendGrid
Expand Down Expand Up @@ -89,7 +87,7 @@ public function headers($assoc = false)
private function prettifyHeaders($headers)
{
if (!is_array($headers)) {
throw new \InvalidArgumentException('$headers should be array');
throw new \InvalidArgumentException('Headers should be an array');
}

return array_reduce(
Expand Down
25 changes: 14 additions & 11 deletions test/unit/ClientTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ protected function setUp()
'Content-Type: application/json',
'Authorization: Bearer SG.XXXX'
];
$this->client = new MockClient($this->host, $this->headers, '/v3', null, null);
$this->client = new MockClient($this->host, $this->headers);
}

public function testConstructor()
Expand All @@ -30,12 +30,14 @@ public function testConstructor()
$this->assertAttributeEquals('/v3', 'version', $this->client);
$this->assertAttributeEquals([], 'path', $this->client);
$this->assertAttributeEquals([], 'curlOptions', $this->client);
$this->assertAttributeEquals(['delete', 'get', 'patch', 'post', 'put'], 'methods', $this->client);
$this->assertAttributeEquals(false, 'retryOnLimit', $this->client);
$this->assertAttributeEquals(['get', 'post', 'patch', 'put', 'delete'], 'methods', $this->client);
}

public function test_()
{
$client = new MockClient($this->host, $this->headers, '/v3', null, ['foo' => 'bar']);
$client = new MockClient($this->host, $this->headers, '/v3');
$client->setCurlOptions(['foo' => 'bar']);
$client = $client->_('test');

$this->assertAttributeEquals(['test'], 'path', $client);
Expand Down Expand Up @@ -79,34 +81,35 @@ public function testGetHeaders()
$client = new Client('https://localhost:4010', ['Content-Type: application/json', 'Authorization: Bearer SG.XXXX']);
$this->assertSame(['Content-Type: application/json', 'Authorization: Bearer SG.XXXX'], $client->getHeaders());

$client2 = new Client('https://localhost:4010', null);
$client2 = new Client('https://localhost:4010');
$this->assertSame([], $client2->getHeaders());
}

public function testGetVersion()
{
$client = new Client('https://localhost:4010', null, '/v3');
$client = new Client('https://localhost:4010', [], '/v3');
$this->assertSame('/v3', $client->getVersion());

$client = new Client('https://localhost:4010', null, null);
$this->assertSame(null, $client->getVersion());
$client = new Client('https://localhost:4010');
$this->assertSame('/v3', $client->getVersion());
}

public function testGetPath()
{
$client = new Client('https://localhost:4010', null, null, ['/foo/bar']);
$client = new Client('https://localhost:4010', [], null, ['/foo/bar']);
$this->assertSame(['/foo/bar'], $client->getPath());

$client = new Client('https://localhost:4010', null, null, null);
$client = new Client('https://localhost:4010');
$this->assertSame([], $client->getPath());
}

public function testGetCurlOptions()
{
$client = new Client('https://localhost:4010', null, null, null, [CURLOPT_PROXY => '127.0.0.1:8080']);
$client = new Client('https://localhost:4010');
$client->setCurlOptions([CURLOPT_PROXY => '127.0.0.1:8080']);
$this->assertSame([CURLOPT_PROXY => '127.0.0.1:8080'], $client->getCurlOptions());

$client = new Client('https://localhost:4010', null, null, null, null);
$client = new Client('https://localhost:4010');
$this->assertSame([], $client->getCurlOptions());
}
}
10 changes: 10 additions & 0 deletions test/unit/ResponseTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -48,4 +48,14 @@ public function testAssociativeHeaders()

$this->assertEquals(['Content-Type' => 'text/html', 'Status' => 'HTTP/1.1 200 OK'], $response->headers(true));
}

/**
* @expectedException \InvalidArgumentException
* @expectedExceptionMessage Headers should be an array
*/
public function testHeadersWithInvalidValue()
{
$response = new Response(null, null, false);
$response->headers(true);
}
}