HttpDownloader.cpp Example File
http/src/HttpDownloader.cpp
#include "HttpDownloader.hpp"
#include <QtCore/QDir>
#include <QtCore/QFile>
#include <QtCore/QFileInfo>
#include <QtNetwork/QAuthenticator>
#include <QtNetwork/QNetworkReply>
#include <QtNetwork/QSslError>
HttpDownloader::HttpDownloader(QObject *parent)
: QObject(parent), m_startDownloadPossible(true), m_statusText(tr("Please enter the URL of a file you want to download.")), m_file(0), m_reply(0)
{
connect(&m_qnam, SIGNAL(authenticationRequired(QNetworkReply*,QAuthenticator*)),
this, SLOT(slotAuthenticationRequired(QNetworkReply*,QAuthenticator*)));
connect(&m_qnam, SIGNAL(sslErrors(QNetworkReply*,QList<QSslError>)),
this, SLOT(sslErrors(QNetworkReply*,QList<QSslError>)));
}
HttpDownloader::~HttpDownloader()
{
delete m_file;
delete m_reply;
}
bool HttpDownloader::startDownloadPossible() const
{
return m_startDownloadPossible;
}
void HttpDownloader::setStartDownloadPossible(bool possible)
{
if (possible != m_startDownloadPossible) {
m_startDownloadPossible = possible;
emit startDownloadPossibleChanged();
}
}
QString HttpDownloader::statusText() const
{
return m_statusText;
}
MessageBoxController* HttpDownloader::messageBoxController() const
{
return const_cast<MessageBoxController*>(&m_messageBoxController);
}
AuthenticationDialogController *HttpDownloader::authenticationDialogController() const
{
return const_cast<AuthenticationDialogController*>(&m_authenticationDialogController);
}
void HttpDownloader::startDownload(const QString &url)
{
m_url = url;
const QFileInfo fileInfo(m_url.path());
m_fileName = fileInfo.fileName();
if (m_fileName.isEmpty())
m_fileName = "index.html";
const QString actualFileName = "tmp/" + m_fileName;
if (QFile::exists(actualFileName)) {
const MessageBoxController::Result result = m_messageBoxController.exec(tr("HTTP"),
tr("There already exists a file called %1 in "
"the target directory.\nOverwrite?").arg(m_fileName),
tr("Overwrite"), tr("Cancel"));
if (result == MessageBoxController::Button2) {
return;
}
QFile::remove(actualFileName);
}
m_file = new QFile(actualFileName);
if (!m_file->open(QIODevice::WriteOnly)) {
m_messageBoxController.exec(tr("HTTP"), tr("Unable to save the file %1: %2.").arg(m_fileName).arg(m_file->errorString()), tr("Ok"), QString());
delete m_file;
m_file = 0;
return;
}
setStartDownloadPossible(false);
startRequest();
}
void HttpDownloader::startRequest()
{
m_reply = m_qnam.get(QNetworkRequest(m_url));
connect(m_reply, SIGNAL(finished()), this, SLOT(httpFinished()));
connect(m_reply, SIGNAL(readyRead()), this, SLOT(httpReadyRead()));
}
void HttpDownloader::httpFinished()
{
m_file->flush();
m_file->close();
const QVariant redirectionTarget = m_reply->attribute(QNetworkRequest::RedirectionTargetAttribute);
if (m_reply->error()) {
m_messageBoxController.exec(tr("HTTP"), tr("Download failed: %1.").arg(m_reply->errorString()), tr("Ok"), QString());
setStartDownloadPossible(true);
} else if (!redirectionTarget.isNull()) {
const QUrl newUrl = m_url.resolved(redirectionTarget.toUrl());
const MessageBoxController::Result result = m_messageBoxController.exec(tr("HTTP"), tr("Redirect to %1 ?").arg(newUrl.toString()), tr("Yes"), tr("No"));
if (result == MessageBoxController::Button1) {
m_url = newUrl;
m_reply->deleteLater();
m_file->open(QIODevice::WriteOnly);
m_file->resize(0);
startRequest();
return;
} else {
setStartDownloadPossible(true);
}
} else {
const QFileInfo actualDir(*m_file);
m_statusText = tr("Downloaded %1 to %2.").arg(m_fileName).arg(actualDir.absolutePath());
emit statusTextChanged();
setStartDownloadPossible(true);
}
m_reply->deleteLater();
m_reply = 0;
delete m_file;
m_file = 0;
}
void HttpDownloader::httpReadyRead()
{
if (m_file) {
m_file->write(m_reply->readAll());
}
}
void HttpDownloader::slotAuthenticationRequired(QNetworkReply*, QAuthenticator *authenticator)
{
const QString siteString = tr("%1 at %2").arg(authenticator->realm()).arg(m_url.host());
if (m_authenticationDialogController.exec(siteString, m_url.userName(), m_url.password())) {
authenticator->setUser(m_authenticationDialogController.user());
authenticator->setPassword(m_authenticationDialogController.password());
}
}
void HttpDownloader::sslErrors(QNetworkReply*, const QList<QSslError> &errors)
{
QString errorString;
foreach (const QSslError &error, errors) {
if (!errorString.isEmpty())
errorString += "\n";
errorString += " " + error.errorString();
}
const MessageBoxController::Result result = m_messageBoxController.exec(tr("HTTP"),
tr("One or more SSL errors have occurred:\n%1").arg(errorString),
tr("Ignore"), tr("Abort"));
if (result == MessageBoxController::Button1) {
m_reply->ignoreSslErrors();
}
}