Ubuntu Download Manager  0.6.0
A session-wide downloading service
 All Classes Namespaces Files Functions Typedefs Enumerations Enumerator
download_impl.cpp
Go to the documentation of this file.
1 /*
2  * Copyright 2013-2014 Canonical Ltd.
3  *
4  * This library is free software; you can redistribute it and/or
5  * modify it under the terms of version 3 of the GNU Lesser General Public
6  * License as published by the Free Software Foundation.
7  *
8  * This program is distributed in the hope that it will be useful,
9  * but WITHOUT ANY WARRANTY; without even the implied warranty of
10  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11  * General Public License for more details.
12  *
13  * You should have received a copy of the GNU Lesser General Public
14  * License along with this library; if not, write to the
15  * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
16  * Boston, MA 02110-1301, USA.
17  */
18 
20 #include "download_impl.h"
21 
22 namespace Ubuntu {
23 
24 namespace DownloadManager {
25 
26 using namespace Logging;
27 
28 DownloadImpl::DownloadImpl(const QDBusConnection& conn,
29  const QString& servicePath,
30  const QDBusObjectPath& objectPath,
31  QObject* parent)
32  : Download(parent),
33  _id(objectPath.path()),
34  _conn(conn),
35  _servicePath(servicePath) {
36 
37  _dbusInterface = new DownloadInterface(servicePath,
38  _id, conn);
39 
40  // fwd all the signals but the error one
41  auto connected = connect(_dbusInterface, &DownloadInterface::canceled,
42  this, &Download::canceled);
43 
44  if (!connected) {
45  Logger::log(Logger::Critical,
46  "Could not connect to signal DownloadInterface::canceled");
47  }
48 
49  connected = connect(_dbusInterface, &DownloadInterface::finished,
50  this, &Download::finished);
51  if (!connected) {
52  Logger::log(Logger::Critical,
53  "Could not connect to signal &DownloadInterface::finished");
54  }
55 
56  connected = connect(_dbusInterface, &DownloadInterface::paused,
57  this, &Download::paused);
58  if (!connected) {
59  Logger::log(Logger::Critical,
60  "Could not connect to signal DownloadInterface::paused");
61  }
62 
63  connected = connect(_dbusInterface, &DownloadInterface::processing,
64  this, &Download::processing);
65  if (!connected) {
66  Logger::log(Logger::Critical,
67  "Could not connect to signal DownloadInterface::processing");
68  }
69 
70  connected = connect(_dbusInterface, static_cast<void(DownloadInterface::*)
71  (qulonglong, qulonglong)>(&DownloadInterface::progress),
72  this, static_cast<void(Download::*)
73  (qulonglong, qulonglong)>(&Download::progress));
74  if (!connected) {
75  Logger::log(Logger::Critical,
76  "Could not connect to signal &DownloadInterface::progress");
77  }
78 
79  connected = connect(_dbusInterface, &DownloadInterface::resumed,
80  this, &Download::resumed);
81  if (!connected) {
82  Logger::log(Logger::Critical,
83  "Could not connect to signal &DownloadInterface::resumed");
84  }
85 
86  connected = connect(_dbusInterface, &DownloadInterface::started,
87  this, &Download::started);
88  if (!connected) {
89  Logger::log(Logger::Critical,
90  "Could not connect to signal &DownloadInterface::started");
91  }
92 
93  // connect to the different type of errors that will later be converted to
94  // the error type to be used by the client.
95  connected = connect(_dbusInterface, &DownloadInterface::httpError,
96  this, &DownloadImpl::onHttpError);
97  if (!connected) {
98  Logger::log(Logger::Critical,
99  "Could not connect to signal &DownloadInterface::httpError");
100  }
101 
102  connected = connect(_dbusInterface, &DownloadInterface::networkError,
103  this, &DownloadImpl::onNetworkError);
104  if (!connected) {
105  Logger::log(Logger::Critical,
106  "Could not connect to signal &DownloadInterface::networkError");
107  }
108 
109  connected = connect(_dbusInterface, &DownloadInterface::processError,
110  this, &DownloadImpl::onProcessError);
111  if (!connected) {
112  Logger::log(Logger::Critical,
113  "Could not connect to signal &DownloadInterface::processError");
114  }
115 
116  connected = connect(_dbusInterface, &DownloadInterface::authError,
117  this, &DownloadImpl::onAuthError);
118  if (!connected) {
119  Logger::log(Logger::Critical,
120  "Could not connect to signal &DownloadInterface::authError");
121  }
122 }
123 
124 DownloadImpl::DownloadImpl(const QDBusConnection& conn, Error* err, QObject* parent)
125  : Download(parent),
126  _isError(true),
127  _lastError(err),
128  _conn(conn) {
129 }
130 
131 DownloadImpl::~DownloadImpl() {
132  delete _lastError;
133  delete _dbusInterface;
134 }
135 
136 void
137 DownloadImpl::setLastError(Error* err) {
138  Logger::log(Logger::Debug,
139  QString("Download{%1} setLastError(%2)").arg(_id).arg(
140  err->errorString()));
141  if (_lastError != nullptr) {
142  delete _lastError;
143  }
144  _lastError = err;
145  _isError = true;
146  emit Download::error(err);
147 }
148 
149 void
150 DownloadImpl::setLastError(const QDBusError& err) {
151  setLastError(new DBusError(err, this));
152 }
153 
154 void
155 DownloadImpl::start() {
156  Logger::log(Logger::Debug, QString("Download{%1} start())").arg(_id));
157  QDBusPendingCall call =
158  _dbusInterface->start();
159  auto watcher = new DownloadPCW(_conn, _servicePath,
160  call, this);
161  Q_UNUSED(watcher);
162 }
163 
164 void
165 DownloadImpl::pause() {
166  Logger::log(Logger::Debug, QString("Download{%1} pause())").arg(_id));
167  QDBusPendingCall call =
168  _dbusInterface->pause();
169  auto watcher = new DownloadPCW(_conn, _servicePath,
170  call, this);
171  Q_UNUSED(watcher);
172 }
173 
174 void
175 DownloadImpl::resume() {
176  Logger::log(Logger::Debug, QString("Download{%1} resume())").arg(_id));
177  QDBusPendingCall call =
178  _dbusInterface->resume();
179  auto watcher = new DownloadPCW(_conn, _servicePath,
180  call, this);
181  Q_UNUSED(watcher);
182 }
183 
184 void
185 DownloadImpl::cancel() {
186  Logger::log(Logger::Debug, QString("Download{%1} cancel())").arg(_id));
187  QDBusPendingCall call =
188  _dbusInterface->cancel();
189  auto watcher = new DownloadPCW(_conn, _servicePath,
190  call, this);
191  Q_UNUSED(watcher);
192 }
193 
194 void
195 DownloadImpl::allowMobileDownload(bool allowed) {
196  Logger::log(Logger::Debug,
197  QString("Download{%1} allowMobileDownload%2())").arg(_id).arg(allowed));
198  QDBusPendingReply<> reply =
199  _dbusInterface->allowGSMDownload(allowed);
200  // block, the call should be fast enough
201  reply.waitForFinished();
202  if (reply.isError()) {
203  Logger::log(Logger::Error, "Error when setting mobile data usage");
204  setLastError(reply.error());
205  }
206 }
207 
208 bool
209 DownloadImpl::isMobileDownloadAllowed() {
210  Logger::log(Logger::Debug,
211  QString("Download{%1} isMobileDownloadAllowed").arg(_id));
212  QDBusPendingReply<bool> reply =
213  _dbusInterface->isGSMDownloadAllowed();
214  // block, the call should be fast enough
215  reply.waitForFinished();
216  if (reply.isError()) {
217  Logger::log(Logger::Error, "Error when querying mobile data usage");
218  setLastError(reply.error());
219  return false;
220  } else {
221  auto result = reply.value();
222  return result;
223  }
224 }
225 
226 void
227 DownloadImpl::setDestinationDir(const QString& path) {
228  Logger::log(Logger::Debug, QString("Dowmload{%1} setDestinationDir(%2)")
229  .arg(_id).arg(path));
230  QDBusPendingReply<> reply =
231  _dbusInterface->setDestinationDir(path);
232  // block, the call should be fast enough
233  reply.waitForFinished();
234  if (reply.isError()) {
235  Logger::log(Logger::Error, "Error setting the download directory");
236  setLastError(reply.error());
237  }
238 }
239 
240 void
241 DownloadImpl::setHeaders(QMap<QString, QString> headers) {
242  Logger::log(Logger::Debug,
243  QString("Download {%1} setHeaders(%2)").arg(_id), headers);
244 
245  QDBusPendingReply<> reply =
246  _dbusInterface->setHeaders(headers);
247  // block, the call should be fast enough
248  reply.waitForFinished();
249  if (reply.isError()) {
250  Logger::log(Logger::Error, "Error setting the download headers");
251  setLastError(reply.error());
252  }
253 }
254 
255 QMap<QString, QString>
256 DownloadImpl::headers() {
257  Logger::log(Logger::Debug, QString("Download{%1} headers()").arg(_id));
258  QDBusPendingReply<QMap<QString, QString> > reply =
259  _dbusInterface->headers();
260  // block, the call should be fast enough
261  reply.waitForFinished();
262  if (reply.isError()) {
263  Logger::log(Logger::Error, "Error querying the download headers");
264  setLastError(reply.error());
265  QMap<QString, QString> empty;
266  return empty;
267  } else {
268  auto result = reply.value();
269  return result;
270  }
271 }
272 
273 
274 void
275 DownloadImpl::setThrottle(qulonglong speed) {
276  Logger::log(Logger::Debug,
277  QString("Download{%1} setThrottle(%2)").arg(_id).arg(speed));
278  QDBusPendingReply<> reply =
279  _dbusInterface->setThrottle(speed);
280  // block, the call should be fast enough
281  reply.waitForFinished();
282  if (reply.isError()) {
283  Logger::log(Logger::Error, "Error setting the download throttle");
284  setLastError(reply.error());
285  }
286 }
287 
288 qulonglong
289 DownloadImpl::throttle() {
290  Logger::log(Logger::Debug, QString("Download{%1} throttle()").arg(_id));
291  QDBusPendingReply<qulonglong> reply =
292  _dbusInterface->throttle();
293  // block, the call is fast enough
294  reply.waitForFinished();
295  if (reply.isError()) {
296  Logger::log(Logger::Error, "Error querying the download throttle");
297  setLastError(reply.error());
298  return 0;
299  } else {
300  auto result = reply.value();
301  return result;
302  }
303 }
304 
305 QString
306 DownloadImpl::id() const {
307  return _id;
308 }
309 
310 QVariantMap
311 DownloadImpl::metadata() {
312  Logger::log(Logger::Debug, QString("Download{%1} metadata()").arg(_id));
313  QDBusPendingReply<QVariantMap> reply =
314  _dbusInterface->metadata();
315  // block the call is fast enough
316  reply.waitForFinished();
317  if (reply.isError()) {
318  Logger::log(Logger::Error, "Error querying the download metadata");
319  QVariantMap emptyResult;
320  setLastError(reply.error());
321  return emptyResult;
322  } else {
323  auto result = reply.value();
324  return result;
325  }
326 }
327 
328 qulonglong
329 DownloadImpl::progress() {
330  Logger::log(Logger::Debug, QString("Download{%1} progress()").arg(_id));
331  QDBusPendingReply<qulonglong> reply =
332  _dbusInterface->progress();
333  // block call should be fast enough
334  reply.waitForFinished();
335  if (reply.isError()) {
336  Logger::log(Logger::Error, "Error querying the download progress");
337  setLastError(reply.error());
338  return 0;
339  } else {
340  auto result = reply.value();
341  return result;
342  }
343 }
344 
345 qulonglong
346 DownloadImpl::totalSize() {
347  Logger::log(Logger::Debug, QString("Download{%1} totalSize()").arg(_id));
348  QDBusPendingReply<qulonglong> reply =
349  _dbusInterface->totalSize();
350  // block call should be fast enough
351  reply.waitForFinished();
352  if (reply.isError()) {
353  Logger::log(Logger::Error, "Error querying the download size");
354  setLastError(reply.error());
355  return 0;
356  } else {
357  auto result = reply.value();
358  return result;
359  }
360 }
361 
362 bool
363 DownloadImpl::isError() const {
364  return _isError;
365 }
366 
367 Error*
368 DownloadImpl::error() const {
369  return _lastError;
370 }
371 
372 void
373 DownloadImpl::onHttpError(HttpErrorStruct errStruct) {
374  auto err = new HttpError(errStruct, this);
375  setLastError(err);
376 }
377 
378 void
379 DownloadImpl::onNetworkError(NetworkErrorStruct errStruct) {
380  auto err = new NetworkError(errStruct, this);
381  setLastError(err);
382 }
383 
384 void
385 DownloadImpl::onProcessError(ProcessErrorStruct errStruct) {
386  auto err = new ProcessError(errStruct, this);
387  setLastError(err);
388 }
389 
390 void
391 DownloadImpl::onAuthError(AuthErrorStruct errStruct) {
392  auto err = new AuthError(errStruct, this);
393  setLastError(err);
394 }
395 
396 } // DownloadManager
397 
398 } // Ubuntu
void finished(const QString &path)
Download(QObject *parent=0)
Definition: download.h:53
void processing(const QString &path)
virtual Error * error() const =0
virtual qulonglong progress()=0