Verbose   A
last analyzed

Complexity

Total Complexity 29

Size/Duplication

Total Lines 173
Duplicated Lines 12.72 %

Coupling/Cohesion

Components 0
Dependencies 6

Test Coverage

Coverage 100%

Importance

Changes 0
Metric Value
wmc 29
lcom 0
cbo 6
dl 22
loc 173
ccs 77
cts 77
cp 1
rs 10
c 0
b 0
f 0

3 Methods

Rating   Name   Duplication   Size   Complexity  
B getBody() 0 17 5
C __construct() 14 38 13
C __invoke() 8 83 11

How to fix   Duplicated Code   

Duplicated Code

Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.

Common duplication problems, and corresponding solutions are:

1
<?php
2
/**
3
 * Akamai {OPEN} EdgeGrid Auth Client
4
 *
5
 * @author Davey Shafik <[email protected]>
6
 * @copyright Copyright 2016 Akamai Technologies, Inc. All rights reserved.
7
 * @license Apache 2.0
8
 * @link https://github.com/akamai-open/AkamaiOPEN-edgegrid-php-client
9
 * @link https://developer.akamai.com
10
 * @link https://developer.akamai.com/introduction/Client_Auth.html
11
 */
12
namespace Akamai\Open\EdgeGrid\Handler;
13
14
use Akamai\Open\EdgeGrid\Exception\HandlerException\IOException;
15
16
/**
17
 * Verbose Response Guzzle Middleware Handler
18
 *
19
 * @package Akamai\Open\EdgeGrid\Client
20
 */
21
class Verbose
22
{
23
    protected $outputStream;
24
25
    protected $errorStream;
26
27
    /**
28
     * Verbose constructor.
29
     *
30
     * This method accepts stream resources or a valid stream URLs
31
     * (including file paths). It will use the output stream for
32
     * both output and error streams if no error stream is passed in.
33
     *
34
     * If neither is passed in, stdout and stderr are used.
35
     *
36
     * @param resource|string|null $outputStream
37
     * @param resource|string|null $errorStream
38
     * @throws \Akamai\Open\EdgeGrid\Exception\HandlerException\IOException
39
     */
40 19
    public function __construct($outputStream = null, $errorStream = null)
41
    {
42 19
        $errorStreamException = null;
43 19 View Code Duplication
        if (!is_resource($errorStream) && $errorStream !== null) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across 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...
44 3
            $fp = @fopen($errorStream, 'ab+');
45 3
            if (!$fp) {
46 2
                $errorStreamException = new IOException('Unable to use error stream: ' . (string) $errorStream);
47
            }
48 3
            $errorStream = $fp;
49
        }
50
51 19 View Code Duplication
        if (!is_resource($outputStream) && $outputStream !== null) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across 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...
52 6
            $fp = @fopen($outputStream, 'ab+');
53 6
            if (!$fp) {
54 2
                throw new IOException('Unable to use output stream: ' . (string) $outputStream);
55
            }
56 4
            $outputStream = $fp;
57
        }
58
59 17
        if ($errorStreamException instanceof \Exception) {
60 1
            throw $errorStreamException;
61
        }
62
63 16
        if ($outputStream !== null && $errorStream === null) {
64 1
            $errorStream = $outputStream;
65
        }
66
67 16
        if ($outputStream === null && $errorStream === null) {
68 11
            $errorStream = fopen('php://stderr', 'ab');
69
        }
70
71 16
        if ($outputStream === null) {
72 11
            $outputStream = fopen('php://output', 'ab');
73
        }
74
75 16
        $this->outputStream = $outputStream;
76 16
        $this->errorStream = $errorStream;
77 16
    }
78
79
    /**
80
     * Handle the request/response
81
     *
82
     * @param callable $handler
83
     * @return \Closure
84
     */
85 14
    public function __invoke(callable $handler)
86
    {
87
        $colors = [
88 14
            'red' => '',
89
            'yellow' => '',
90
            'cyan' => '',
91
            'reset' => '',
92
        ];
93
94 14 View Code Duplication
        if (PHP_SAPI === 'cli') {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across 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...
95
            $colors = [
96 14
                'red' => "\x1b[31;01m",
97
                'yellow' => "\x1b[33;01m",
98
                'cyan' => "\x1b[36;01m",
99
                'reset' => "\x1b[39;49;00m",
100
            ];
101
        }
102
103
        return function (
104
            \Psr\Http\Message\RequestInterface $request,
105
            array $config
106
        ) use (
107 14
            $handler,
108 14
            $colors
109
        ) {
110 14
            fwrite($this->outputStream, "{$colors['cyan']}===> [VERBOSE] Request: \n");
111 14
            fwrite($this->outputStream, "{$colors['yellow']}" . $this->getBody($request));
112 14
            fwrite($this->outputStream, "{$colors['reset']}\n");
113
114 14
            return $handler($request, $config)->then(
115
                function (\Psr\Http\Message\ResponseInterface $response) use ($colors) {
116 11
                    $statusCode = $response->getStatusCode();
117 11
                    if ($statusCode > 299 && $statusCode < 400) {
118 1
                        fwrite($this->outputStream, "{$colors['cyan']}===> [VERBOSE] Redirected: ");
119 1
                        fwrite($this->outputStream, $response->getHeader('Location')[0]);
120 1
                        fwrite($this->outputStream, "{$colors['reset']}\n");
121
                    } else {
122 11
                        $responseBody = $this->getBody($response);
123
124 11
                        if ($statusCode > 399 && $statusCode < 600) {
125 3
                            fwrite($this->errorStream, "{$colors['red']}===> [ERROR] An error occurred: \n");
126 3
                            fwrite($this->errorStream, "{$colors['yellow']}" . $responseBody);
127 3
                            fwrite($this->errorStream, "{$colors['reset']}\n");
128
                        } else {
129 9
                            fwrite($this->outputStream, "{$colors['cyan']}===> [VERBOSE] Response: \n");
130 9
                            fwrite($this->outputStream, "{$colors['yellow']}" . $responseBody);
131 9
                            fwrite($this->outputStream, "{$colors['reset']}\n");
132
                        }
133
                    }
134
135 11
                    return $response;
136 14
                },
137 14
                function (\Exception $reason) use ($colors) {
138 3
                    fwrite($this->outputStream, "{$colors['red']}===> [ERROR] An error occurred: \n");
139 3
                    fwrite($this->outputStream, "{$colors['yellow']}");
140
141 3
                    $code = $reason->getCode();
142 3
                    if (!empty($code)) {
143 2
                        $code .= ': ';
144
                    }
145
146 3
                    $message = $reason->getMessage();
147
148 3
                    fwrite($this->outputStream, ((!empty($code)) ? $code : '') . $message);
149
150 3
                    $response = $reason instanceof \GuzzleHttp\Exception\RequestException
151 3
                        ? $reason->getResponse()
152 3
                        : false;
153
154 3
                    if ($response instanceof \Psr\Http\Message\ResponseInterface) {
155 2
                        $body = $response->getBody()->getContents();
156 2
                        if (!empty($body)) {
157 1
                            fwrite($this->outputStream, "\n{$colors['yellow']}" . $body);
158
                        }
159
                    }
160
161 3
                    fwrite($this->outputStream, "{$colors['reset']}\n");
162
163 3
                    return new \GuzzleHttp\Promise\RejectedPromise($reason);
164 14
                }
165
            );
166 14
        };
167
    }
168
169
    /**
170
     * Get response body
171
     *
172
     * @param \Psr\Http\Message\MessageInterface $message
173
     *
174
     * @return string
175
     */
176 14
    protected function getBody(\Psr\Http\Message\MessageInterface $message)
177
    {
178 14
        $body = trim($message->getBody());
179
180 14
        if ($message->getBody()->getSize() === 0 || empty($body)) {
181 14
            if ($message instanceof \Psr\Http\Message\ResponseInterface) {
182 1
                return 'No response body returned';
183
            }
184 14
            return 'No request body sent';
185
        }
186 10
        $result = json_decode($body);
187 10
        if ($result !== null) {
188 7
            return json_encode($result, JSON_PRETTY_PRINT);
189
        }
190
191 3
        return $body;
192
    }
193
}
194