Completed
Pull Request — master (#53)
by Rick
02:35
created

GuzzleRequestHandler::post()   A

Complexity

Conditions 3
Paths 9

Size

Total Lines 19
Code Lines 12

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 6
CRAP Score 4.125

Importance

Changes 0
Metric Value
dl 0
loc 19
ccs 6
cts 12
cp 0.5
rs 9.4285
c 0
b 0
f 0
cc 3
eloc 12
nc 9
nop 2
crap 4.125
1
<?php
2
3
declare(strict_types=1);
4
5
namespace unreal4u\TelegramAPI;
6
7
8
use GuzzleHttp\Client;
9
use GuzzleHttp\ClientInterface;
10
use GuzzleHttp\Exception\ClientException;
11
use GuzzleHttp\Exception\RequestException;
12
use React\Promise\PromiseInterface;
13
use Psr\Http\Message\ResponseInterface;
14
use Psr\Log\LoggerInterface;
15
use React\Promise\Deferred;
16
use unreal4u\TelegramAPI\InternalFunctionality\DummyLogger;
17
use unreal4u\TelegramAPI\InternalFunctionality\TelegramRawData;
18
19
class GuzzleRequestHandler implements RequestHandlerInterface
20
{
21
    /**
22
     * @var LoggerInterface
23
     */
24
    protected $logger;
25
26
    /**
27
     * @var ClientInterface
28
     */
29
    protected $httpClient;
30
31
    /**
32
     * GuzzleRequestHandler constructor.
33
     *
34
     * @param ClientInterface $client
35
     * @param LoggerInterface $logger
36
     */
37 39
    public function __construct(?ClientInterface $client = null, LoggerInterface $logger = null)
38
    {
39 39
        if ($logger === null) {
40 23
            $logger = new DummyLogger();
41
        }
42 39
        $this->logger = $logger;
43
44 39
        if ($client === null) {
45 39
            $client = new Client();
46
        }
47 39
        $this->httpClient = $client;
48 39
    }
49
50
    /**
51
     * @param string $uri
52
     *
53
     * @return ResponseInterface
54
     */
55
    public function get(string $uri): ResponseInterface
56
    {
57
        return $this->httpClient->get($uri);
58
    }
59
60
    /**
61
     * This is the method that actually makes the call, which can be easily overwritten so that our unit tests can work
62
     *
63
     * @param string $uri
64
     * @param array $formData
65
     *
66
     * @return TelegramRawData
67
     */
68 23
    public function post(string $uri, array $formData = []): TelegramRawData
69
    {
70 23
        $e = null;
71 23
        $this->logger->debug('About to perform HTTP call to Telegram\'s API');
72
        try {
73 23
            $response = $this->httpClient->post($uri, $formData);
74 23
            $this->logger->debug('Got response back from Telegram, applying json_decode');
75
        }
76
        catch (ClientException $e) {
77
            $response = $e->getResponse();
78
            // It can happen that we have a network problem, in such case, we can't do nothing about it, so rethrow
79
            if (empty($response)) {
80
                throw $e;
81
            }
82
        }
83
        finally {
84 23
            return new TelegramRawData((string) $response->getBody(), $e);
85
        }
86
    }
87
88
    /**
89
     * @param string $uri
90
     * @param array $formData
91
     *
92
     * @return PromiseInterface
93
     */
94
    public function postAsync(string $uri, array $formData = []): PromiseInterface
95
    {
96
        $this->logger->debug('About to perform async HTTP call to Telegram\'s API');
97
        $deferred = new Deferred();
98
99
        $promise = $this->httpClient->postAsync($uri, $formData);
100
        $promise->then(function (ResponseInterface $response) use ($deferred) {
101
            $deferred->resolve(new TelegramRawData((string) $response->getBody()));
102
        },
103
            function (RequestException $exception) use ($deferred) {
104
                if (!empty($exception->getResponse()->getBody())) {
105
	                $deferred->resolve(new TelegramRawData((string) $exception->getResponse()
106
		                ->getBody(), $exception));
107
                } else {
108
	                $deferred->reject($exception);
109
                }
110
            });
111
112
        return $deferred->promise();
113
    }
114
115
    /**
116
     * @param string $uri
117
     *
118
     * @return PromiseInterface
119
     */
120
    public function getAsync(string $uri): PromiseInterface
121
    {
122
        $this->logger->debug('About to perform async HTTP call to Telegram\'s API');
123
        $deferred = new Deferred();
124
125
        $promise = $this->httpClient->getAsync($uri);
126
        $promise->then(function (ResponseInterface $response) use ($deferred) {
127
            $deferred->resolve(new TelegramRawData((string) $response->getBody()));
128
        },
129
            function (RequestException $exception) use ($deferred) {
130
                if (!empty($exception->getResponse()->getBody())) {
131
	                $deferred->resolve(new TelegramRawData((string) $exception->getResponse()
132
		                ->getBody(), $exception));
133
                } else {
134
	                $deferred->reject($exception);
135
                }
136
            });
137
138
        return $deferred->promise();
139
    }
140
}
141