File indexing completed on 2024-04-14 03:58:30

0001 /*
0002     loader.cpp
0003     SPDX-FileCopyrightText: 2001, 2002, 2003 Frerich Raabe <raabe@kde.org>
0004 
0005     SPDX-License-Identifier: BSD-2-Clause
0006 */
0007 
0008 #include "loader.h"
0009 #include "dataretriever.h"
0010 #include "documentsource.h"
0011 #include "feed.h"
0012 #include "global.h"
0013 #include "loaderutil_p.h"
0014 #include "parsercollection.h"
0015 
0016 #include <QUrl>
0017 
0018 
0019 #include <syndication_debug.h>
0020 
0021 namespace Syndication
0022 {
0023 struct SYNDICATION_NO_EXPORT Loader::LoaderPrivate {
0024     LoaderPrivate()
0025     {
0026     }
0027 
0028     ~LoaderPrivate()
0029     {
0030         delete retriever;
0031     }
0032 
0033     DataRetriever *retriever = nullptr;
0034     Syndication::ErrorCode lastError = Success;
0035     int retrieverError = 0;
0036     QUrl discoveredFeedURL;
0037     QUrl url;
0038 };
0039 
0040 Loader *Loader::create()
0041 {
0042     return new Loader;
0043 }
0044 
0045 Loader *Loader::create(QObject *object, const char *slot)
0046 {
0047     Loader *loader = create();
0048     connect(loader, SIGNAL(loadingComplete(Syndication::Loader *, Syndication::FeedPtr, Syndication::ErrorCode)), object, slot);
0049     return loader;
0050 }
0051 
0052 Loader::Loader()
0053     : d(new LoaderPrivate)
0054 {
0055 }
0056 
0057 Loader::~Loader() = default;
0058 
0059 void Loader::loadFrom(const QUrl &url, DataRetriever *retriever)
0060 {
0061     if (d->retriever != nullptr) {
0062         return;
0063     }
0064 
0065     d->url = url;
0066     d->retriever = retriever;
0067 
0068     connect(d->retriever, &DataRetriever::dataRetrieved, this, &Loader::slotRetrieverDone);
0069 
0070     d->retriever->retrieveData(url);
0071 }
0072 
0073 int Loader::retrieverError() const
0074 {
0075     return d->retrieverError;
0076 }
0077 
0078 Syndication::ErrorCode Loader::errorCode() const
0079 {
0080     return d->lastError;
0081 }
0082 
0083 void Loader::abort()
0084 {
0085     if (d && d->retriever) {
0086         d->retriever->abort();
0087         delete d->retriever;
0088         d->retriever = nullptr;
0089     }
0090 
0091     Q_EMIT loadingComplete(this, FeedPtr(), Aborted);
0092     delete this;
0093 }
0094 
0095 QUrl Loader::discoveredFeedURL() const
0096 {
0097     return d->discoveredFeedURL;
0098 }
0099 
0100 void Loader::slotRetrieverDone(const QByteArray &data, bool success)
0101 {
0102     d->retrieverError = d->retriever->errorCode();
0103     ErrorCode status = Success;
0104     FeedPtr feed;
0105     delete d->retriever;
0106     d->retriever = nullptr;
0107 
0108     if (success) {
0109         DocumentSource src(data, d->url.url());
0110         feed = parserCollection()->parse(src);
0111 
0112         if (parserCollection()->lastError() != Syndication::Success) {
0113             status = parserCollection()->lastError();
0114             discoverFeeds(data);
0115         }
0116     } else {
0117         qCDebug(SYNDICATION_LOG) << "Retriever error:" << d->retrieverError;
0118         // retriever is a custom impl, so we set OtherRetrieverError
0119         status = OtherRetrieverError;
0120     }
0121 
0122     Q_EMIT loadingComplete(this, feed, status);
0123 
0124     delete this;
0125 }
0126 
0127 void Loader::discoverFeeds(const QByteArray &data)
0128 {
0129     const QUrl url = LoaderUtil::parseFeed(data, d->url);
0130     if (!url.isEmpty()) {
0131         d->discoveredFeedURL = url;
0132     }
0133 }
0134 
0135 } // namespace Syndication
0136 
0137 #include "moc_loader.cpp"