ContentClient::setLimits()   A
last analyzed

Complexity

Conditions 3
Paths 3

Size

Total Lines 21

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 12

Importance

Changes 0
Metric Value
dl 0
loc 21
ccs 0
cts 7
cp 0
rs 9.584
c 0
b 0
f 0
cc 3
nc 3
nop 1
crap 12
1
<?php
2
/**
3
 * Yandex PHP Library
4
 *
5
 * @copyright NIX Solutions Ltd.
6
 * @link      https://github.com/nixsolutions/yandex-php-library
7
 */
8
9
/**
10
 * @namespace
11
 */
12
namespace Yandex\Market\Content;
13
14
use GuzzleHttp\Client;
15
use GuzzleHttp\ClientInterface;
16
use Yandex\Common\AbstractServiceClient;
17
use GuzzleHttp\Psr7\Response;
18
use GuzzleHttp\Exception\ClientException;
19
use Yandex\Common\Exception\ForbiddenException;
20
use Yandex\Common\Exception\UnauthorizedException;
21
use Yandex\Market\Content\Exception\ContentRequestException;
22
23
/**
24
 * Class ContentClient
25
 *
26
 * @category Yandex
27
 * @package  MarketContent
28
 *
29
 * @author  Oleg Scherbakov <[email protected]>
30
 * @created 27.12.15 19:50
31
 */
32
class ContentClient extends AbstractServiceClient
33
{
34
    /**
35
     * Requested version of API
36
     *
37
     * @var string
38
     */
39
    private $version = 'v1';
40
41
    /**
42
     * API domain
43
     *
44
     * @var string
45
     */
46
    protected $serviceDomain = 'api.content.market.yandex.ru';
47
48
    /**
49
     * Store limits information during each API request
50
     *
51
     * @var array
52
     */
53
    private $limits = array();
54
55
    /**
56
     * Get url to service resource with parameters
57
     *
58
     * @param  string $resource
59
     * @see    http://api.yandex.ru/market/partner/doc/dg/concepts/method-call.xml
60
     * @return string
61
     */
62 29
    public function getServiceUrl($resource = '')
63
    {
64 29
        return $this->serviceScheme . '://' . $this->serviceDomain . '/'
65 29
        . $this->version . '/' . $resource;
66
    }
67
68
    /**
69
     * @param string $token access token
70
     */
71 29
    public function __construct($token = '')
72
    {
73 29
        $this->setAccessToken($token);
74 29
    }
75
76
    /**
77
     * @return ClientInterface
78
     */
79 View Code Duplication
    protected function getClient()
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
80
    {
81
        if (is_null($this->client)) {
82
            $defaultOptions = [
83
                'base_uri' => $this->getServiceUrl(),
84
                'headers' => [
85
                    'Host' => $this->getServiceDomain(),
86
                    'Accept' => '*/*',
87
                    'Authorization' => $this->getAccessToken(),
88
                ]
89
            ];
90
            if ($this->getProxy()) {
91
                $defaultOptions['proxy'] = $this->getProxy();
92
            }
93
            if ($this->getDebug()) {
94
                $defaultOptions['debug'] = $this->getDebug();
95
            }
96
            $this->client = new Client($defaultOptions);
0 ignored issues
show
Documentation Bug introduced by
It seems like new \GuzzleHttp\Client($defaultOptions) of type object<GuzzleHttp\Client> is incompatible with the declared type null of property $client.

Our type inference engine has found an assignment to a property that is incompatible with the declared type of that property.

Either this assignment is in error or the assigned type should be added to the documentation/type hint for that property..

Loading history...
97
        }
98
99
        return $this->client;
100
    }
101
102
    /**
103
     * Sends a request
104
     *
105
     * @param string              $method  HTTP method
106
     * @param string $uri     URI object or string.
107
     * @param array               $options Request options to apply.
108
     *
109
     * @return Response
110
     *
111
     * @throws ForbiddenException
112
     * @throws UnauthorizedException
113
     * @throws ContentRequestException
114
     */
115 View Code Duplication
    protected function sendRequest($method, $uri, array $options = [])
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
116
    {
117
        try {
118
            $response = $this->getClient()->request($method, $uri, $options);
119
        } catch (ClientException $ex) {
120
            $result = $ex->getResponse();
121
            $code = $result->getStatusCode();
122
            $message = $result->getReasonPhrase();
123
124
            $body = $result->getBody();
125
            if ($body) {
126
                $jsonBody = json_decode($body);
127
                if ($jsonBody && isset($jsonBody->error) && isset($jsonBody->error->message)) {
128
                    $message = $jsonBody->error->message;
129
                }
130
            }
131
132
            if ($code === 403) {
133
                throw new ForbiddenException($message);
134
            }
135
136
            if ($code === 401) {
137
                throw new UnauthorizedException($message);
138
            }
139
140
            throw new ContentRequestException(
141
                'Service responded with error code: "' . $code . '" and message: "' . $message . '"',
142
                $code
143
            );
144
        }
145
        // @note: Finally? php >= 5.5
146
        $this->setLimits($response->getHeaders());
147
148
        return $response;
149
    }
150
151
    private function setLimits($headers)
152
    {
153
        // const as header name?
154
        $limitHeaders = [
155
            'X-RateLimit-Daily-Limit',
156
            'X-RateLimit-Daily-Remaining',
157
            'X-RateLimit-Global-Limit',
158
            'X-RateLimit-Global-Remaining',
159
            'X-RateLimit-Method-Limit',
160
            'X-RateLimit-Method-Remaining',
161
            'X-RateLimit-Until'
162
        ];
163
164
        $this->limits = array();
165
166
        foreach ($headers as $key => $value) {
167
            if (in_array($key, $limitHeaders, true)) {
168
                $this->limits[$key] = (int) $value[0];
169
            }
170
        }
171
    }
172
173
    /**
174
     * Get information about API limits
175
     *
176
     * @return array|false
177
     */
178
    public function getLimits()
179
    {
180
        return $this->limits;
181
    }
182
183
    /**
184
     * Get information about specified API limit
185
     *
186
     * @return array|false
187
     */
188
    public function getLimit($name)
189
    {
190
        if (isset($this->limits[$name])) {
191
            return $this->limits[$name];
192
        }
193
194
        return false;
195
    }
196
197
    /**
198
     * Returns API service response.
199
     *
200
     * @param  string $resource
201
     * @return array
202
     * @throws ContentRequestException
203
     * @throws ForbiddenException
204
     * @throws UnauthorizedException
205
     */
206 29
    protected function getServiceResponse($resource)
207
    {
208 29
        $response = $this->sendRequest('GET', $this->getServiceUrl($resource));
209 29
        $decodedResponseBody = $this->getDecodedBody($response->getBody());
210
211 29
        return $decodedResponseBody;
212
    }
213
214
    /**
215
     * Returns URL-encoded query string
216
     *
217
     * @note: similar to http_build_query(),
218
     * but transform key=>value where key == value to "?key" param.
219
     *
220
     * @param array|object $queryData
221
     * @param string       $prefix
222
     * @param string       $argSeparator
223
     * @param int          $encType
224
     *
225
     * @return string $queryString
226
     */
227 25
    protected function buildQueryString($queryData, $prefix = '', $argSeparator = '&', $encType = PHP_QUERY_RFC3986)
228
    {
229 25
        foreach ($queryData as $k => &$v) {
230 22
            if (!is_scalar($v)) {
231 22
                $v = implode(',', $v);
232
            }
233
        }
234
235 25
        $queryString = http_build_query($queryData, $prefix, $argSeparator, $encType);
236
237 25
        foreach ($queryData as $k => $v) {
238 22
            if ($k==$v) {
239 22
                $queryString = str_replace("$k=$v", $v, $queryString);
240
            }
241
        }
242
243 25
        return $queryString;
244
    }
245
}
246