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.
Completed
Pull Request — master (#93)
by Martin
07:30
created

FiftyOneDegreesCom::hydrateBrowser()   A

Complexity

Conditions 3
Paths 4

Size

Total Lines 10
Code Lines 5

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 6
CRAP Score 3

Importance

Changes 2
Bugs 0 Features 0
Metric Value
c 2
b 0
f 0
dl 0
loc 10
ccs 6
cts 6
cp 1
rs 9.4285
cc 3
eloc 5
nc 4
nop 2
crap 3
1
<?php
2
namespace UserAgentParser\Provider\Http;
3
4
use GuzzleHttp\Client;
5
use GuzzleHttp\Psr7\Request;
6
use stdClass;
7
use UserAgentParser\Exception;
8
use UserAgentParser\Model;
9
10
/**
11
 * Abstraction of neutrinoapi.com
12
 *
13
 * @author Martin Keckeis <[email protected]>
14
 * @license MIT
15
 * @see https://51degrees.com
16
 */
17
class FiftyOneDegreesCom extends AbstractHttpProvider
18
{
19
    /**
20
     * Name of the provider
21
     *
22
     * @var string
23
     */
24
    protected $name = 'FiftyOneDegreesCom';
25
26
    /**
27
     * Homepage of the provider
28
     *
29
     * @var string
30
     */
31
    protected $homepage = 'https://51degrees.com';
32
33
    protected $detectionCapabilities = [
34
35
        'browser' => [
36
            'name'    => true,
37
            'version' => true,
38
        ],
39
40
        'renderingEngine' => [
41
            'name'    => true,
42
            'version' => false,
43
        ],
44
45
        'operatingSystem' => [
46
            'name'    => true,
47
            'version' => true,
48
        ],
49
50
        'device' => [
51
            'model'    => true,
52
            'brand'    => true,
53
            'type'     => true,
54
            'isMobile' => true,
55
            'isTouch'  => false,
56
        ],
57
58
        'bot' => [
59
            'isBot' => true,
60
            'name'  => false,
61
            'type'  => false,
62
        ],
63
    ];
64
65
    protected $defaultValues = [
66
        'general' => [
67
            '/^Unknown$/i',
68
        ],
69
    ];
70
71
    private static $uri = 'https://cloud.51degrees.com/api/v1';
72
73
    private $apiKey;
74
75 18
    public function __construct(Client $client, $apiKey)
76
    {
77 18
        parent::__construct($client);
78
79 18
        $this->apiKey = $apiKey;
80 18
    }
81
82
    /**
83
     *
84
     * @param  string                     $userAgent
85
     * @param  array                      $headers
86
     * @return stdClass
87
     * @throws Exception\RequestException
88
     */
89 11
    protected function getResult($userAgent, array $headers)
90
    {
91
        /*
92
         * an empty UserAgent makes no sense
93
         */
94 11
        if ($userAgent == '') {
95 1
            throw new Exception\NoResultFoundException('No result found for user agent: ' . $userAgent);
96
        }
97
98 10
        $headers['User-Agent'] = $userAgent;
99
100 10
        $parameters = '/' . $this->apiKey;
101 10
        $parameters .= '/match?';
102
103 10
        $headerString = [];
104 10
        foreach ($headers as $key => $value) {
105 10
            $headerString[] = $key . '=' . rawurlencode($value);
106
        }
107
108 10
        $parameters .= implode('&', $headerString);
109
110 10
        $uri = self::$uri . $parameters;
111
112 10
        $request = new Request('GET', $uri);
113
114
        try {
115 10
            $response = $this->getResponse($request);
116 2
        } catch (Exception\RequestException $ex) {
117
            /* @var $prevEx \GuzzleHttp\Exception\ClientException */
118 2
            $prevEx = $ex->getPrevious();
119
120 2
            if ($prevEx->hasResponse() === true && $prevEx->getResponse()->getStatusCode() === 403) {
121 1
                throw new Exception\InvalidCredentialsException('Your API key "' . $this->apiKey . '" is not valid for ' . $this->getName(), null, $ex);
122 1
            } elseif ($prevEx->hasResponse() !== true) {
123
                var_dump($prevEx->__toString());
0 ignored issues
show
Security Debugging Code introduced by
var_dump($prevEx->__toString()); looks like debug code. Are you sure you do not want to remove it? This might expose sensitive data.
Loading history...
124
                var_dump($ex->__toString());
125
                exit();
0 ignored issues
show
Coding Style Compatibility introduced by
The method getResult() contains an exit expression.

An exit expression should only be used in rare cases. For example, if you write a short command line script.

In most cases however, using an exit expression makes the code untestable and often causes incompatibilities with other libraries. Thus, unless you are absolutely sure it is required here, we recommend to refactor your code to avoid its usage.

Loading history...
126
            }
127
128 1
            throw $ex;
129
        }
130
131
        /*
132
         * no json returned?
133
         */
134 8
        $contentType = $response->getHeader('Content-Type');
135 8
        if (! isset($contentType[0]) || $contentType[0] != 'application/json; charset=utf-8') {
136 1
            throw new Exception\RequestException('Could not get valid "application/json; charset=utf-8" response from "' . $request->getUri() . '". Response is "' . $response->getBody()->getContents() . '"');
137
        }
138
139 7
        $content = json_decode($response->getBody()->getContents());
140
141
        /*
142
         * No result
143
         */
144 7
        if (isset($content->MatchMethod) && $content->MatchMethod == 'None') {
145 1
            throw new Exception\NoResultFoundException('No result found for user agent: ' . $userAgent);
146
        }
147
148
        /*
149
         * Missing data?
150
         */
151 6
        if (! $content instanceof stdClass || ! isset($content->Values)) {
152 1
            throw new Exception\RequestException('Could not get valid response from "' . $request->getUri() . '". Data is missing "' . $response->getBody()->getContents() . '"');
153
        }
154
155
        /*
156
         * Convert the values, to something useable
157
         */
158 5
        $values              = new \stdClass();
159 5
        $values->MatchMethod = $content->MatchMethod;
160
161 5
        foreach ($content->Values as $key => $value) {
162 5
            if (is_array($value) && count($value) === 1 && isset($value[0])) {
163 5
                $values->{$key} = $value[0];
164
            }
165
        }
166
167 5
        foreach ($values as $key => $value) {
0 ignored issues
show
Bug introduced by
The expression $values of type object<stdClass> is not traversable.
Loading history...
168 5
            if ($value === 'True') {
169 2
                $values->{$key} = true;
170 5
            } elseif ($value === 'False') {
171 5
                $values->{$key} = false;
172
            }
173
        }
174
175 5
        return $values;
176
    }
177
178
    /**
179
     *
180
     * @param Model\Bot $bot
181
     * @param stdClass  $resultRaw
182
     */
183 1
    private function hydrateBot(Model\Bot $bot, stdClass $resultRaw)
0 ignored issues
show
Unused Code introduced by
The parameter $resultRaw is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
184
    {
185 1
        $bot->setIsBot(true);
186 1
    }
187
188
    /**
189
     *
190
     * @param Model\Browser $browser
191
     * @param stdClass      $resultRaw
192
     */
193 4
    private function hydrateBrowser(Model\Browser $browser, stdClass $resultRaw)
194
    {
195 4
        if (isset($resultRaw->BrowserName)) {
196 1
            $browser->setName($this->getRealResult($resultRaw->BrowserName));
197
        }
198
199 4
        if (isset($resultRaw->BrowserVersion)) {
200 1
            $browser->getVersion()->setComplete($this->getRealResult($resultRaw->BrowserVersion));
201
        }
202 4
    }
203
204
    /**
205
     *
206
     * @param Model\RenderingEngine $engine
207
     * @param stdClass              $resultRaw
208
     */
209 4
    private function hydrateRenderingEngine(Model\RenderingEngine $engine, stdClass $resultRaw)
210
    {
211 4
        if (isset($resultRaw->LayoutEngine)) {
212 1
            $engine->setName($this->getRealResult($resultRaw->LayoutEngine));
213
        }
214 4
    }
215
216
    /**
217
     *
218
     * @param Model\OperatingSystem $os
219
     * @param stdClass              $resultRaw
220
     */
221 4
    private function hydrateOperatingSystem(Model\OperatingSystem $os, stdClass $resultRaw)
222
    {
223 4
        if (isset($resultRaw->PlatformName)) {
224 1
            $os->setName($this->getRealResult($resultRaw->PlatformName));
225
        }
226
227 4
        if (isset($resultRaw->PlatformVersion)) {
228 1
            $os->getVersion()->setComplete($this->getRealResult($resultRaw->PlatformVersion));
229
        }
230 4
    }
231
232
    /**
233
     *
234
     * @param Model\Device $device
235
     * @param stdClass     $resultRaw
236
     */
237 4
    private function hydrateDevice(Model\Device $device, stdClass $resultRaw)
238
    {
239 4
        if (isset($resultRaw->HardwareVendor)) {
240 1
            $device->setBrand($this->getRealResult($resultRaw->HardwareVendor));
241
        }
242 4
        if (isset($resultRaw->HardwareFamily)) {
243 1
            $device->setModel($this->getRealResult($resultRaw->HardwareFamily));
244
        }
245 4
        if (isset($resultRaw->DeviceType)) {
246 1
            $device->setType($this->getRealResult($resultRaw->DeviceType));
247
        }
248 4
        if (isset($resultRaw->IsMobile)) {
249 1
            $device->setIsMobile($this->getRealResult($resultRaw->IsMobile));
250
        }
251 4
    }
252
253 11
    public function parse($userAgent, array $headers = [])
254
    {
255 11
        $resultRaw = $this->getResult($userAgent, $headers);
256
257
        /*
258
         * Hydrate the model
259
         */
260 5
        $result = new Model\UserAgent();
261 5
        $result->setProviderResultRaw($resultRaw);
262
263
        /*
264
         * Bot detection
265
         */
266 5
        if (isset($resultRaw->IsCrawler) && $resultRaw->IsCrawler === true) {
267 1
            $this->hydrateBot($result->getBot(), $resultRaw);
268
269 1
            return $result;
270
        }
271
272
        /*
273
         * hydrate the result
274
         */
275 4
        $this->hydrateBrowser($result->getBrowser(), $resultRaw);
276 4
        $this->hydrateRenderingEngine($result->getRenderingEngine(), $resultRaw);
277 4
        $this->hydrateOperatingSystem($result->getOperatingSystem(), $resultRaw);
278 4
        $this->hydrateDevice($result->getDevice(), $resultRaw);
279
280 4
        return $result;
281
    }
282
}
283