Subversion Repositories Scribus

Rev

Rev 24055 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | RSS feed


#include "scdlmgr.h"
#include "scdlthread.h"
#include "scpaths.h"

#include <QDebug>
#include <QDir>
#include <QFileInfo>
#include <QNetworkReply>
#include <QNetworkRequest>
#include <QUrl>


ScDLThread::ScDLThread(QObject *parent) : QThread(parent)
{
        connect(this, SIGNAL(runSignal()), this, SLOT(runSlot()));
}

void ScDLThread::run()
{
        emit runSignal();
}

void ScDLThread::addURL(const QUrl &url, bool overwrite, const QString& location, const QString& destinationLocation)
{
        //qDebug()<<"ScDLThread::addURL:"<<url;
        if (!urlOK(url))
                return;
        QString l(QDir::cleanPath(location));
        if (!l.endsWith("/"))
                l += "/";
        m_downloadQueue.enqueue(qMakePair(url, l));
        ++m_totalCount;
}

void ScDLThread::addURLs(const QStringList &urlList, bool overwrite, const QString& location, const QString& destinationLocation)
{
        //qDebug()<<"ScDLThread::addURLs:"<<urlList;
        m_urlList=urlList;
        QString l(QDir::cleanPath(location));
        if (!l.endsWith("/"))
                l += "/";
        for (const QString& u : qAsConst(m_urlList))
        {
                QUrl url(u);
                if (!urlOK(u))
                        return;
                m_downloadQueue.enqueue(qMakePair(url, l));
                ++m_totalCount;
        }
}

void ScDLThread::startDownloads()
{
        if (m_downloadQueue.isEmpty())
        {
                //qDebug()<<"No more downloads left";
                emit finished();
                return;
        }
        start();
}

QString ScDLThread::saveFileName(const QUrl &url, const QString& location, bool overwrite)
{
        QDir d(location);
        QString path = url.path();
        QString basename = QFileInfo(path).fileName();
        if (location.isEmpty() || !d.exists())
        {
                if (basename.isEmpty())
                        basename = "download";
                basename = ScPaths::downloadDir() + basename;
        }
        else
        {
                basename = location + basename;
        }
        if (!overwrite && QFile::exists(basename))
        {
                // already exists, don't overwrite
                int i = 0;
                basename += '.';
                while (QFile::exists(basename + QString::number(i)))
                        ++i;
                basename += QString::number(i);
        }
        return basename;
}

void ScDLThread::startNextDownload()
{
        if (m_downloadQueue.isEmpty())
        {
                //qDebug()<<downloadedCount<<"/"<<totalCount<<"files downloaded successfully";
                m_downloadedCount=m_totalCount=0;
                emit finished();
                return;
        }
        QPair<QUrl, QString> urlPair=m_downloadQueue.dequeue();

        QString filename = saveFileName(urlPair.first, urlPair.second, true);
        if (filename.isEmpty())
        {
                qDebug()<<"File name empty for url:"<<urlPair.first.toEncoded().constData();
                return;
        }
        m_output.setFileName(filename);
        if (!m_output.open(QIODevice::WriteOnly))
        {
                //qDebug()<<"Problem opening save file '"<<qPrintable(filename)<<"' for download '"
                //         <<urlPair.first.toEncoded().constData()<<"': "<<qPrintable(output.errorString());

                startNextDownload();
                return;
        }
        emit fileStarted(m_output.fileName());
        QNetworkRequest request(urlPair.first);
        //QNetworkReply *nwr=manager.head(request);
        //qDebug()<<nwr->url()<<nwr->rawHeaderList();
        //connect(&manager, SIGNAL(finished(QNetworkReply*)), this, SLOT(replyFinished(QNetworkReply*)));
        m_currentDownload = m_manager.get(request);
        connect(m_currentDownload, SIGNAL(finished()), this, SLOT(downloadFinished()));
        connect(m_currentDownload, SIGNAL(readyRead()), this, SLOT(downloadReadyRead()));
        connect(m_currentDownload, SIGNAL(downloadProgress(qint64,qint64)),this,SIGNAL(fileDownloadProgress(qint64,qint64)));

        //qDebug()<<"Downloading:"<<urlPair.first.toEncoded().constData();
}

void ScDLThread::downloadFinished()
{
        m_output.close();
        if (m_currentDownload->error())
        {
/*
                if(currentDownload->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt() == 301 || currentDownload->rawHeaderList().contains("Location"))
                        qDebug()<<currentDownload->header(QNetworkRequest::LocationHeader).toString();
                if(currentDownload->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt() == 302 || currentDownload->rawHeaderList().contains("Location"))
                        qDebug()<<currentDownload->header(QNetworkRequest::LocationHeader).toString();
                if(currentDownload->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt() == 307 || currentDownload->rawHeaderList().contains("Location"))
                        qDebug()<<currentDownload->header(QNetworkRequest::LocationHeader).toString();

                QUrl redirectUrl = currentDownload->attribute(QNetworkRequest::RedirectionTargetAttribute).toUrl();
                qDebug()<<redirectUrl;
*/

                qDebug()<<"Failed: "<<qPrintable(m_currentDownload->errorString());
                emit fileFailed(m_output.fileName());
                if (m_output.exists())
                        m_output.remove();
        }
        else
        {
                //qDebug()<<"Saving file:"<<qPrintable(output.fileName());
                ++m_downloadedCount;
                emit fileReceived(m_output.fileName());
        }
        m_currentDownload->deleteLater();
        startNextDownload();
}

void ScDLThread::replyFinished(QNetworkReply* reply)
{
        qDebug()<<"replyFinished";
        QVariant possibleRedirectUrl =reply->attribute(QNetworkRequest::RedirectionTargetAttribute);
        QUrl urlRedirectedTo = possibleRedirectUrl.toUrl();
        QString text;
        /* If the URL is not empty, we're being redirected. */
        if(!urlRedirectedTo.isEmpty())
        {
                qDebug()<<reply->header(QNetworkRequest::LocationHeader);
                text = QString("QNAMRedirect::replyFinished: Redirected to ").append(urlRedirectedTo.toString());
                addURL(text, true, ScPaths::downloadDir(), ScPaths::downloadDir());
                /* We'll do another request to the redirection url. */
        //      this->_qnam->get(QNetworkRequest(_urlRedirectedTo));
        }
        else
        {
                /*
                 * We weren't redirected anymore
                 * so we arrived to the final destination...
                 */

                text = QString("QNAMRedirect::replyFinished: Arrived to ").append(reply->url().toString());
                urlRedirectedTo.clear();
        }
        qDebug()<<text;
        /* Clean up. */
        reply->deleteLater();
}


void ScDLThread::downloadReadyRead()
{
        m_output.write(m_currentDownload->readAll());
}

void ScDLThread::runSlot()
{
        startNextDownload();
}

bool ScDLThread::urlOK(const QUrl& url)
{
        //TODO: Add some more URL checks
        return !(!url.isValid() || url.isEmpty() || url.host().isEmpty());
}