Request::flattenedHeaders()   A
last analyzed

Complexity

Conditions 2
Paths 2

Size

Total Lines 7
Code Lines 4

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 6
CRAP Score 2

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 2
eloc 4
c 1
b 0
f 0
nc 2
nop 0
dl 0
loc 7
ccs 6
cts 6
cp 1
crap 2
rs 10
1
<?php
2
3
namespace Yabacon\Paystack\Http;
4
5
use \Yabacon\Paystack\Contracts\RouteInterface;
6
use \Yabacon\Paystack;
7
8
class Request
9
{
10
    public $method;
11
    public $endpoint;
12
    public $body = '';
13
    public $headers = [];
14
    protected $response;
15
    protected $paystackObj;
16
17 9
    public function __construct($paystackObj = null)
18
    {
19 9
        $this->response = new Response();
20 9
        $this->response->setRequestObject($this);
21 9
        $this->paystackObj = $paystackObj;
22 9
        $this->response->forApi = !is_null($paystackObj);
23 9
        if ($this->response->forApi) {
24 5
            $this->headers['Content-Type'] = 'application/json';
25 5
        }
26 9
    }
27
28 1
    public function getResponse()
29
    {
30 1
        return $this->response;
31
    }
32
33 1
    public function flattenedHeaders()
34
    {
35 1
        $_ = [];
36 1
        foreach ($this->headers as $key => $value) {
37 1
            $_[] = $key . ": " . $value;
38 1
        }
39 1
        return $_;
40
    }
41
42
    public function send()
43
    {
44
        $this->attemptGuzzle();
45
        if (!$this->response->okay) {
46
            $this->attemptCurl();
47
        }
48
        if (!$this->response->okay) {
49
            $this->attemptFileGetContents();
50
        }
51
        return $this->response;
52
    }
53
54
    public function attemptGuzzle()
55
    {
56
        if (isset($this->paystackObj) && !$this->paystackObj->use_guzzle) {
57
            $this->response->okay = false;
58
            return;
59
        }
60
        if (class_exists('\\GuzzleHttp\\Exception\\BadResponseException')
61
            && class_exists('\\GuzzleHttp\\Exception\\ClientException')
62
            && class_exists('\\GuzzleHttp\\Exception\\ConnectException')
63
            && class_exists('\\GuzzleHttp\\Exception\\RequestException')
64
            && class_exists('\\GuzzleHttp\\Exception\\ServerException')
65
            && class_exists('\\GuzzleHttp\\Client')
66
            && class_exists('\\GuzzleHttp\\Psr7\\Request')
67
        ) {
68
            $request = new \GuzzleHttp\Psr7\Request(
69
                strtoupper($this->method),
70
                $this->endpoint,
71
                $this->headers,
72
                $this->body
73
            );
74
            $client = new \GuzzleHttp\Client();
75
            try {
76
                $psr7response = $client->send($request);
77
                $this->response->body = $psr7response->getBody()->getContents();
78
                $this->response->okay = true;
79
            } catch (\Exception $e) {
80
                if (($e instanceof \GuzzleHttp\Exception\BadResponseException
81
                    || $e instanceof \GuzzleHttp\Exception\ClientException
82
                    || $e instanceof \GuzzleHttp\Exception\ConnectException
83
                    || $e instanceof \GuzzleHttp\Exception\RequestException
84
                    || $e instanceof \GuzzleHttp\Exception\ServerException)
85
                ) {
86
                    if ($e->hasResponse()) {
87
                        $this->response->body = $e->getResponse()->getBody()->getContents();
88
                    }
89
                    $this->response->okay = true;
90
                }
91
                $this->response->messages[] = $e->getMessage();
92
            }
93
        }
94
    }
95
96
    public function attemptFileGetContents()
97
    {
98
        if (!Paystack::$fallback_to_file_get_contents) {
99
            return;
100
        }
101
        $context = stream_context_create(
102
            [
103
                'http'=>array(
104
                  'method'=>$this->method,
105
                  'header'=>$this->flattenedHeaders(),
106
                  'content'=>$this->body,
107
                  'ignore_errors' => true
108
                )
109
            ]
110
        );
111
        $this->response->body = file_get_contents($this->endpoint, false, $context);
112
        if ($this->response->body === false) {
113
            $this->response->messages[] = 'file_get_contents failed with response: \'' . error_get_last() . '\'.';
0 ignored issues
show
Bug introduced by
Are you sure error_get_last() of type array can be used in concatenation? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

113
            $this->response->messages[] = 'file_get_contents failed with response: \'' . /** @scrutinizer ignore-type */ error_get_last() . '\'.';
Loading history...
114
        } else {
115
            $this->response->okay = true;
116
        }
117
    }
118
119
    public function attemptCurl()
120
    {
121
        //open connection
122
        $ch = \curl_init();
123
        \curl_setopt($ch, \CURLOPT_URL, $this->endpoint);
0 ignored issues
show
Bug introduced by
It seems like $ch can also be of type false; however, parameter $ch of curl_setopt() does only seem to accept resource, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

123
        \curl_setopt(/** @scrutinizer ignore-type */ $ch, \CURLOPT_URL, $this->endpoint);
Loading history...
124
        ($this->method === RouteInterface::POST_METHOD) && \curl_setopt($ch, \CURLOPT_POST, true);
125
        ($this->method === RouteInterface::PUT_METHOD) && \curl_setopt($ch, \CURLOPT_CUSTOMREQUEST, 'PUT');
126
127
        if ($this->method !== RouteInterface::GET_METHOD) {
128
            \curl_setopt($ch, \CURLOPT_POSTFIELDS, $this->body);
129
        }
130
        \curl_setopt($ch, \CURLOPT_HTTPHEADER, $this->flattenedHeaders());
131
        \curl_setopt($ch, \CURLOPT_RETURNTRANSFER, 1);
132
        $this->response->forApi && \curl_setopt($ch, \CURLOPT_SSLVERSION, 6);
133
134
        $this->response->body = \curl_exec($ch);
0 ignored issues
show
Bug introduced by
It seems like $ch can also be of type false; however, parameter $ch of curl_exec() does only seem to accept resource, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

134
        $this->response->body = \curl_exec(/** @scrutinizer ignore-type */ $ch);
Loading history...
135
136
        if (\curl_errno($ch)) {
0 ignored issues
show
Bug introduced by
It seems like $ch can also be of type false; however, parameter $ch of curl_errno() does only seem to accept resource, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

136
        if (\curl_errno(/** @scrutinizer ignore-type */ $ch)) {
Loading history...
137
            $cerr = \curl_error($ch);
0 ignored issues
show
Bug introduced by
It seems like $ch can also be of type false; however, parameter $ch of curl_error() does only seem to accept resource, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

137
            $cerr = \curl_error(/** @scrutinizer ignore-type */ $ch);
Loading history...
138
            $this->response->messages[] = 'Curl failed with response: \'' . $cerr . '\'.';
139
        } else {
140
            $this->response->okay = true;
141
        }
142
143
        \curl_close($ch);
0 ignored issues
show
Bug introduced by
It seems like $ch can also be of type false; however, parameter $ch of curl_close() does only seem to accept resource, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

143
        \curl_close(/** @scrutinizer ignore-type */ $ch);
Loading history...
144
    }
145
}
146