GitHub Access Token became invalid

It seems like the GitHub access token used for retrieving details about this repository from GitHub became invalid. This might prevent certain types of inspections from being run (in particular, everything related to pull requests).
Please ask an admin of your repository to re-new the access token on this website.
Passed
Pull Request — master (#139)
by Yong
03:32
created

RoaRequest::resolveSecurityToken()   A

Complexity

Conditions 3
Paths 3

Size

Total Lines 11
Code Lines 5

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 5
CRAP Score 3.0416

Importance

Changes 0
Metric Value
cc 3
eloc 5
nc 3
nop 0
dl 0
loc 11
ccs 5
cts 6
cp 0.8333
crap 3.0416
rs 10
c 0
b 0
f 0
1
<?php
2
3
namespace AlibabaCloud\Client\Request;
4
5
use Exception;
6
use Stringy\Stringy;
7
use Ramsey\Uuid\Uuid;
8
use RuntimeException;
9
use AlibabaCloud\Client\SDK;
10
use AlibabaCloud\Client\Encode;
11
use AlibabaCloud\Client\Accept;
12
use AlibabaCloud\Client\Filter\Filter;
13
use AlibabaCloud\Client\Filter\ApiFilter;
14
use AlibabaCloud\Client\Credentials\StsCredential;
15
use AlibabaCloud\Client\Exception\ClientException;
16
use AlibabaCloud\Client\Exception\ServerException;
17
use AlibabaCloud\Client\Credentials\AccessKeyCredential;
18
use AlibabaCloud\Client\Credentials\BearerTokenCredential;
19
use AlibabaCloud\Client\Request\Traits\DeprecatedRoaTrait;
20
21
/**
22
 * RESTful ROA Request.
23
 *
24
 * @package   AlibabaCloud\Client\Request
25
 * @method setParameter()
26
 */
27
class RoaRequest extends Request
28
{
29
    use DeprecatedRoaTrait;
30
31
    /**
32
     * @var string
33
     */
34
    private static $headerSeparator = "\n";
35
36
    /**
37
     * @var string
38
     */
39
    public $pathPattern = '/';
40
41
    /**
42
     * @var array
43
     */
44
    public $pathParameters = [];
45
46
    /**
47
     * @var string
48
     */
49
    private $dateTimeFormat = "D, d M Y H:i:s \G\M\T";
50
51
    /**
52
     * Resolve request parameter.
53
     *
54
     * @throws ClientException
55
     * @throws Exception
56
     */
57 18
    public function resolveParameter()
58
    {
59 18
        $this->resolveQuery();
60 18
        $this->resolveHeaders();
61 18
        $this->resolveBody();
62 18
        $this->resolveSignature();
63 18
    }
64
65 18
    private function resolveQuery()
66
    {
67 18
        if (!isset($this->options['query']['Version'])) {
68 18
            $this->options['query']['Version'] = $this->version;
69 18
        }
70 18
    }
71
72 18
    private function resolveBody()
73
    {
74
        // If the body has already been specified, it will not be resolved.
75 18
        if (isset($this->options['body'])) {
76 1
            return;
77
        }
78
79 17
        if (!isset($this->options['form_params'])) {
80 14
            return;
81
        }
82
83
        // Merge data, compatible with parameters set from constructor.
84 3
        $params = \AlibabaCloud\Client\arrayMerge(
85
            [
86 3
                $this->data,
87 3
                $this->options['form_params']
88 3
            ]
89 3
        );
90
91 3
        $this->encodeBody($params);
92
93 3
        unset($this->options['form_params']);
94 3
    }
95
96
    /**
97
     * Determine the body format based on the Content-Type and calculate the MD5 value.
98
     *
99
     * @param array $params
100
     */
101 3
    private function encodeBody(array $params)
102
    {
103 3
        $stringy = Stringy::create($this->options['headers']['Content-Type']);
104
105 3
        if ($stringy->contains('application/json', false)) {
106 2
            $this->options['body']                   = json_encode($params);
107 2
            $this->options['headers']['Content-MD5'] = base64_encode(md5($this->options['body'], true));
108
109 2
            return;
110
        }
111
112 1
        $this->options['body']                    = Encode::create($params)->ksort()->toString();
113 1
        $this->options['headers']['Content-MD5']  = base64_encode(md5($this->options['body'], true));
114 1
        $this->options['headers']['Content-Type'] = 'application/x-www-form-urlencoded; charset=UTF-8';
115 1
    }
116
117
    /**
118
     * @throws ClientException
119
     * @throws ServerException
120
     * @throws Exception
121
     */
122 18
    private function resolveHeaders()
123
    {
124 18
        $this->options['headers']['x-acs-version']   = $this->version;
125 18
        $this->options['headers']['x-acs-region-id'] = $this->realRegionId();
126 18
        $this->options['headers']['Date']            = gmdate($this->dateTimeFormat);
127
128 18
        $signature                                           = $this->httpClient()->getSignature();
129 18
        $this->options['headers']['x-acs-signature-method']  = $signature->getMethod();
130 18
        $this->options['headers']['x-acs-signature-nonce']   = Uuid::uuid1()->toString();
131 18
        $this->options['headers']['x-acs-signature-version'] = $signature->getVersion();
132 18
        if ($signature->getType()) {
133 4
            $this->options['headers']['x-acs-signature-type'] = $signature->getType();
134 4
        }
135
136 18
        $this->resolveAccept();
137 18
        $this->resolveContentType();
138 18
        $this->resolveSecurityToken();
139 18
        $this->resolveBearerToken();
140 18
    }
141
142
    /**
143
     * @throws ClientException
144
     * @throws Exception
145
     */
146 18
    private function resolveSignature()
147
    {
148 18
        $this->options['headers']['Authorization'] = $this->signature();
149 18
    }
150
151
    /**
152
     * If accept is not specified, it is determined by format.
153
     */
154 18
    private function resolveAccept()
155
    {
156 18
        if (!isset($this->options['headers']['Accept'])) {
157 17
            $this->options['headers']['Accept'] = Accept::create($this->format)->toString();
158 17
        }
159 18
    }
160
161
    /**
162
     * If the Content-Type is not specified, it is determined according to accept.
163
     */
164 18
    private function resolveContentType()
165
    {
166 18
        if (!isset($this->options['headers']['Content-Type'])) {
167 17
            $this->options['headers']['Content-Type'] = "{$this->options['headers']['Accept']}; chrset=utf-8";
168 17
        }
169 18
    }
170
171
    /**
172
     * @throws ClientException
173
     * @throws ServerException
174
     */
175 19
    private function resolveSecurityToken()
176
    {
177 19
        if (!$this->credential() instanceof StsCredential) {
178 18
            return;
179
        }
180
181 1
        if (!$this->credential()->getSecurityToken()) {
182
            return;
183
        }
184
185 1
        $this->options['headers']['x-acs-security-token'] = $this->credential()->getSecurityToken();
186 1
    }
187
188
    /**
189
     * @throws ClientException
190
     * @throws ServerException
191
     */
192 18
    private function resolveBearerToken()
193
    {
194 18
        if ($this->credential() instanceof BearerTokenCredential) {
195 4
            $this->options['headers']['x-acs-bearer-token'] = $this->credential()->getBearerToken();
196 4
        }
197 18
    }
198
199
    /**
200
     * Sign the request message.
201
     *
202
     * @return string
203
     * @throws ClientException
204
     * @throws ServerException
205
     */
206 18
    private function signature()
207
    {
208
        /**
209
         * @var AccessKeyCredential $credential
210
         */
211 18
        $credential    = $this->credential();
212 18
        $access_key_id = $credential->getAccessKeyId();
213 18
        $signature     = $this->httpClient()
214 18
                              ->getSignature()
215 18
                              ->sign(
216 18
                                  $this->stringToSign(),
217 18
                                  $credential->getAccessKeySecret()
218 18
                              );
219
220 18
        return "acs $access_key_id:$signature";
221
    }
222
223
    /**
224
     * @return string
225
     */
226 18
    public function stringToSign()
227
    {
228 18
        return $this->headerStringToSign() . $this->resourceStringToSign();
229
    }
230
231
    /**
232
     * @return string
233
     */
234 18
    private function headerStringToSign()
235
    {
236 18
        $string = $this->method . self::$headerSeparator;
237 18
        if (isset($this->options['headers']['Accept'])) {
238 18
            $string .= $this->options['headers']['Accept'];
239 18
        }
240 18
        $string .= self::$headerSeparator;
241
242 18
        if (isset($this->options['headers']['Content-MD5'])) {
243 3
            $string .= $this->options['headers']['Content-MD5'];
244 3
        }
245 18
        $string .= self::$headerSeparator;
246
247 18
        if (isset($this->options['headers']['Content-Type'])) {
248 18
            $string .= $this->options['headers']['Content-Type'];
249 18
        }
250 18
        $string .= self::$headerSeparator;
251
252 18
        if (isset($this->options['headers']['Date'])) {
253 18
            $string .= $this->options['headers']['Date'];
254 18
        }
255 18
        $string .= self::$headerSeparator;
256
257 18
        $string .= $this->acsHeaderString();
258
259 18
        return $string;
260
    }
261
262
    /**
263
     * Construct standard Header for Alibaba Cloud.
264
     *
265
     * @return string
266
     */
267 18
    private function acsHeaderString()
268
    {
269 18
        $array = [];
270 18
        foreach ($this->options['headers'] as $headerKey => $headerValue) {
271 18
            $key = strtolower($headerKey);
272 18
            if (strncmp($key, 'x-acs-', 6) === 0) {
273 18
                $array[$key] = $headerValue;
274 18
            }
275 18
        }
276 18
        ksort($array);
277 18
        $string = '';
278 18
        foreach ($array as $sortMapKey => $sortMapValue) {
279 18
            $string .= $sortMapKey . ':' . $sortMapValue . self::$headerSeparator;
280 18
        }
281
282 18
        return $string;
283
    }
284
285
    /**
286
     * @return string
287
     */
288 18
    private function resourceStringToSign()
289
    {
290 18
        $this->uri = $this->uri->withPath($this->resolvePath())
291 18
                               ->withQuery(
292 18
                                   Encode::create(isset($this->options['query'])
293 18
                                                      ? $this->options['query']
294 18
                                                      : [])
295 18
                                         ->ksort()
296 18
                                         ->toString()
297 18
                               );
298
299 18
        return $this->uri->getPath() . '?' . $this->uri->getQuery();
300
    }
301
302
    /**
303
     * Assign path parameters to the url.
304
     *
305
     * @return string
306
     */
307 20
    private function resolvePath()
308
    {
309 20
        $path = $this->pathPattern;
310 20
        foreach ($this->pathParameters as $pathKey => $value) {
311 12
            $target = "[$pathKey]";
312 12
            $path   = str_replace($target, $value, $path);
313 20
        }
314
315 20
        return $path;
316
    }
317
318
    /**
319
     * Set path parameter by name.
320
     *
321
     * @param string $name
322
     * @param string $value
323
     *
324
     * @return RoaRequest
325
     * @throws ClientException
326
     */
327 11
    public function pathParameter($name, $value)
328
    {
329 11
        Filter::name($name);
330
331 9
        if ($value === '') {
332 1
            throw new ClientException(
333 1
                'Value cannot be empty',
334
                SDK::INVALID_ARGUMENT
335 1
            );
336
        }
337
338 8
        $this->pathParameters[$name] = $value;
339
340 8
        return $this;
341
    }
342
343
    /**
344
     * Set path pattern.
345
     *
346
     * @param string $pattern
347
     *
348
     * @return self
349
     * @throws ClientException
350
     */
351 10
    public function pathPattern($pattern)
352
    {
353 10
        ApiFilter::pattern($pattern);
354
355 8
        $this->pathPattern = $pattern;
356
357 8
        return $this;
358
    }
359
360
    /**
361
     * Magic method for set or get request parameters.
362
     *
363
     * @param string $name
364
     * @param mixed  $arguments
365
     *
366
     * @return $this
367
     */
368 12
    public function __call($name, $arguments)
369
    {
370 12
        if (strncmp($name, 'get', 3) === 0) {
371 1
            $parameterName = $this->propertyNameByMethodName($name);
372
373 1
            return $this->__get($parameterName);
374
        }
375
376 12
        if (strncmp($name, 'with', 4) === 0) {
377 10
            $parameterName = $this->propertyNameByMethodName($name, 4);
378 10
            $this->__set($parameterName, $arguments[0]);
379 10
            $this->pathParameters[$parameterName] = $arguments[0];
380
381 10
            return $this;
382
        }
383
384 2
        if (strncmp($name, 'set', 3) === 0) {
385 1
            $parameterName = $this->propertyNameByMethodName($name);
386 1
            $withMethod    = "with$parameterName";
387
388 1
            throw new RuntimeException("Please use $withMethod instead of $name");
389
        }
390
391 1
        throw new RuntimeException('Call to undefined method ' . __CLASS__ . '::' . $name . '()');
392
    }
393
}
394