HttpTransport::doFetch()   B
last analyzed

Complexity

Conditions 5
Paths 9

Size

Total Lines 26
Code Lines 15

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 15
CRAP Score 5.0061

Importance

Changes 0
Metric Value
c 0
b 0
f 0
dl 0
loc 26
ccs 15
cts 16
cp 0.9375
rs 8.439
cc 5
eloc 15
nc 9
nop 1
crap 5.0061
1
<?php
2
3
namespace TreeHouse\Feeder\Transport;
4
5
use GuzzleHttp\Client;
6
use GuzzleHttp\ClientInterface;
7
use GuzzleHttp\Exception\RequestException;
8
use GuzzleHttp\RequestOptions;
9
use Psr\Http\Message\ResponseInterface;
10
use TreeHouse\Feeder\Event\FetchProgressEvent;
11
use TreeHouse\Feeder\Exception\EmptyResponseException;
12
use TreeHouse\Feeder\Exception\TransportException;
13
use TreeHouse\Feeder\FeedEvents;
14
15
class HttpTransport extends AbstractTransport implements ProgressAwareInterface
16
{
17
    /**
18
     * @var ClientInterface
19
     */
20
    protected $client;
21
22
    /**
23
     * @var int
24
     */
25
    protected $size;
26
27
    /**
28
     * @var \DateTime
29
     */
30
    protected $lastModified;
31
32
    /**
33
     * @param string      $url
34
     * @param string|null $user
35
     * @param string|null $pass
36
     *
37
     * @return HttpTransport
38
     */
39 22
    public static function create($url, $user = null, $pass = null)
40
    {
41 22
        $client = new Client([
42
            'headers' => [
43 22
                'User-Agent' => static::getDefaultUserAgent(),
44 22
            ],
45 22
        ]);
46
47 22
        $conn = new Connection([
48 22
            'url' => $url,
49 22
            'user' => $user,
50 22
            'pass' => $pass,
51 22
        ]);
52
53 22
        $transport = new static($conn);
54 22
        $transport->setClient($client);
55
56 22
        return $transport;
57
    }
58
59
    /**
60
     * @inheritdoc
61
     */
62 4
    public function __toString()
63
    {
64 4
        return $this->getUrl();
65 2
    }
66
67
    /**
68
     * @throws \LogicException When url is not defined
69
     *
70
     * @return string
71
     */
72 22
    public function getUrl()
73
    {
74 22
        if (!isset($this->connection['url'])) {
75 2
            throw new \LogicException('No url defined');
76
        }
77
78 20
        return $this->connection['url'];
79
    }
80
81
    /**
82
     * @param string $url
83
     */
84 2
    public function setUrl($url)
85
    {
86 2
        $this->connection['url'] = $url;
87 2
    }
88
89
    /**
90
     * @return string|null
91
     */
92 16
    public function getUser()
93
    {
94 16
        return isset($this->connection['user']) ? $this->connection['user'] : null;
95
    }
96
97
    /**
98
     * @return string|null
99
     */
100 4
    public function getPass()
101
    {
102 4
        return isset($this->connection['pass']) ? $this->connection['pass'] : null;
103
    }
104
105
    /**
106
     * @param ClientInterface $client
107
     */
108 22
    public function setClient(ClientInterface $client)
109
    {
110 22
        $this->client = $client;
111 22
    }
112
113
    /**
114
     * @return ClientInterface
115
     */
116
    public function getClient()
117
    {
118
        return $this->client;
119
    }
120
121
    /**
122
     * @inheritdoc
123
     */
124
    public function getLastModifiedDate()
125
    {
126
        return $this->lastModified;
127
    }
128
129
    /**
130
     * @return int|null
131
     */
132
    public function getSize()
133
    {
134
        return $this->size;
135
    }
136
137
    /**
138
     * @param ResponseInterface $response
139
     */
140 6
    public function onHeaders(ResponseInterface $response)
141
    {
142
        // set the modified date if we got it in the response
143 6
        if (!empty($lastModified = $response->getHeader('Last-Modified'))) {
144 6
            $this->lastModified = new \DateTime(reset($lastModified));
145 6
        }
146 6
    }
147
148
    /**
149
     * @param int $downloadSize
150
     * @param int $downloaded
151
     */
152 6
    public function onProgress($downloadSize, $downloaded)
153
    {
154 6
        $this->size = $downloadSize;
155
156 6
        $progressEvent = new FetchProgressEvent($downloaded, $downloadSize);
157 6
        $this->eventDispatcher->dispatch(FeedEvents::FETCH_PROGRESS, $progressEvent);
158 6
    }
159
160
    /**
161
     * @inheritdoc
162
     */
163 14
    protected function doFetch($destination)
164
    {
165 14
        if (!$this->client) {
166
            throw new \LogicException('No client set to use for downloading');
167
        }
168
169
        $options = [
170 14
            RequestOptions::SINK => $destination,
171 14
            RequestOptions::ON_HEADERS => [$this, 'onHeaders'],
172 14
            RequestOptions::PROGRESS => [$this, 'onProgress'],
173 14
        ];
174
175 14
        if ($user = $this->getUser()) {
176 2
            $options['auth'] = [$user, $this->getPass()];
177 2
        }
178
179
        try {
180 14
            $response = $this->client->request('GET', $this->getUrl(), $options);
181
182 12
            if ($response->getBody()->getSize() === 0) {
183 4
                throw new EmptyResponseException($response);
184
            }
185 14
        } catch (RequestException $e) {
186 2
            throw new TransportException(sprintf('Could not download feed: %s', $e->getMessage()), null, $e);
187
        }
188 8
    }
189
190
    /**
191
     * @inheritdoc
192
     */
193 14
    protected function isFresh($destination, \DateTime $maxAge = null)
194
    {
195 14
        return false;
196
    }
197
}
198