Some common code moved.

This commit is contained in:
Martin Rotter 2017-09-22 10:08:19 +02:00
parent e194a3ef08
commit de548750e2
18 changed files with 291 additions and 134 deletions

View File

@ -1480,6 +1480,49 @@ Assignment DatabaseQueries::getCategories(QSqlDatabase db, int account_id, bool*
return categories;
}
bool DatabaseQueries::overwriteInoreaderAccount(QSqlDatabase db, const QString& username, const QString& access_token,
const QString& refresh_token, int batch_size, int account_id) {
QSqlQuery query(db);
query.prepare("UPDATE InoreaderAccounts "
"SET username = :username, access_token = :access_token, refresh_token = :refresh_token , msg_limit = :msg_limit "
"WHERE id = :id;");
query.bindValue(QSL(":username"), username);
query.bindValue(QSL(":access_token"), access_token);
query.bindValue(QSL(":refresh_token"), refresh_token);
query.bindValue(QSL(":id"), account_id);
query.bindValue(QSL(":msg_limit"), batch_size);
if (query.exec()) {
return true;
}
else {
qWarning("Inoreader: Updating account failed: '%s'.", qPrintable(query.lastError().text()));
return false;
}
}
bool DatabaseQueries::createInoreaderAccount(QSqlDatabase db, int id_to_assign, const QString& username,
const QString& access_token, const QString& refresh_token, int batch_size) {
QSqlQuery q(db);
q.prepare("INSERT INTO InoreaderAccounts (id, username, access_token, refresh_token, msg_limit) "
"VALUES (:id, :username, :access_token, :refresh_token, :msg_limit);");
q.bindValue(QSL(":id"), id_to_assign);
q.bindValue(QSL(":username"), username);
q.bindValue(QSL(":access_token"), access_token);
q.bindValue(QSL(":refresh_token"), refresh_token);
q.bindValue(QSL(":msg_limit"), batch_size);
if (q.exec()) {
return true;
}
else {
qWarning("Inoreader: Inserting of new account failed: '%s'.", qPrintable(q.lastError().text()));
return false;
}
}
Assignment DatabaseQueries::getTtRssFeeds(QSqlDatabase db, int account_id, bool* ok) {
Assignment feeds;

View File

@ -78,6 +78,12 @@ class DatabaseQueries {
int auto_update_interval);
static Assignment getCategories(QSqlDatabase db, int account_id, bool* ok = nullptr);
// Inoreader account.
static bool overwriteInoreaderAccount(QSqlDatabase db, const QString& username, const QString& access_token,
const QString& refresh_token, int batch_size, int account_id);
static bool createInoreaderAccount(QSqlDatabase db, int id_to_assign, const QString& username,
const QString& access_token, const QString& refresh_token, int batch_size);
// ownCloud account.
static QList<ServiceRoot*> getOwnCloudAccounts(QSqlDatabase db, bool* ok = nullptr);
static bool deleteOwnCloudAccount(QSqlDatabase db, int account_id);

View File

@ -229,6 +229,37 @@ void ServiceRoot::requestItemRemoval(RootItem* item) {
emit itemRemovalRequested(item);
}
QMap<int, QVariant> ServiceRoot::storeCustomFeedsData() {
QMap<int, QVariant> custom_data;
foreach (const Feed* feed, getSubTreeFeeds()) {
QVariantMap feed_custom_data;
feed_custom_data.insert(QSL("auto_update_interval"), feed->autoUpdateInitialInterval());
feed_custom_data.insert(QSL("auto_update_type"), feed->autoUpdateType());
custom_data.insert(feed->customId(), feed_custom_data);
}
return custom_data;
}
void ServiceRoot::restoreCustomFeedsData(const QMap<int, QVariant>& data, const QHash<int, Feed*>& feeds) {
QMapIterator<int, QVariant> i(data);
while (i.hasNext()) {
i.next();
const int custom_id = i.key();
if (feeds.contains(custom_id)) {
Feed* feed = feeds.value(custom_id);
QVariantMap feed_custom_data = i.value().toMap();
feed->setAutoUpdateInitialInterval(feed_custom_data.value(QSL("auto_update_interval")).toInt());
feed->setAutoUpdateType(static_cast<Feed::AutoUpdateType>(feed_custom_data.value(QSL("auto_update_type")).toInt()));
}
}
}
void ServiceRoot::syncIn() {
QIcon original_icon = icon();

View File

@ -203,8 +203,8 @@ class ServiceRoot : public RootItem {
void itemRemovalRequested(RootItem* item);
private:
virtual QMap<int, QVariant> storeCustomFeedsData() = 0;
virtual void restoreCustomFeedsData(const QMap<int, QVariant>& data, const QHash<int, Feed*>& feeds) = 0;
virtual QMap<int, QVariant> storeCustomFeedsData();
virtual void restoreCustomFeedsData(const QMap<int, QVariant>& data, const QHash<int, Feed*>& feeds);
private:
RecycleBin* m_recycleBin;

View File

@ -19,13 +19,15 @@
#ifndef INOREADER_DEFINITIONS_H
#define INOREADER_DEFINITIONS_H
#define INOREADER_OAUTH_PORT 12885
#define INOREADER_OAUTH_SCOPE "read write"
#define INOREADER_OAUTH_TOKEN_URL "https://www.inoreader.com/oauth2/token"
#define INOREADER_OAUTH_AUTH_URL "https://www.inoreader.com/oauth2/auth"
#define INOREADER_OAUTH_CLI_ID "1000000604"
#define INOREADER_OAUTH_CLI_KEY "gsStoZ3aAoQJCgQxoFSuXkWI7Sly87yK"
#define INOREADER_REFRESH_TOKEN_KEY "refresh_token"
#define INOREADER_ACCESS_TOKEN_KEY "access_token"
#define INOREADER_OAUTH_PORT 12885
#define INOREADER_OAUTH_SCOPE "read write"
#define INOREADER_OAUTH_TOKEN_URL "https://www.inoreader.com/oauth2/token"
#define INOREADER_OAUTH_AUTH_URL "https://www.inoreader.com/oauth2/auth"
#define INOREADER_OAUTH_CLI_ID "1000000604"
#define INOREADER_OAUTH_CLI_KEY "gsStoZ3aAoQJCgQxoFSuXkWI7Sly87yK"
#define INOREADER_REFRESH_TOKEN_KEY "refresh_token"
#define INOREADER_ACCESS_TOKEN_KEY "access_token"
#define INOREADER_DEFAULT_BATCH_SIZE 900
#define INOREADER_MAX_BATCH_SIZE 999
#endif // INOREADER_DEFINITIONS_H

View File

@ -21,23 +21,35 @@
#include "gui/guiutilities.h"
#include "miscellaneous/application.h"
#include "miscellaneous/iconfactory.h"
#include "services/inoreader/definitions.h"
#include "services/inoreader/inoreaderserviceroot.h"
FormEditInoreaderAccount::FormEditInoreaderAccount(QWidget* parent) : QDialog(parent), m_editableRoot(nullptr) {
FormEditInoreaderAccount::FormEditInoreaderAccount(QWidget* parent) : QDialog(parent),
m_network(new InoreaderNetworkFactory(this)), m_editableRoot(nullptr) {
m_ui.setupUi(this);
GuiUtilities::applyDialogProperties(*this, qApp->icons()->miscIcon(QSL("inoreader")));
m_ui.m_lblTestResult->setStatus(WidgetWithStatus::StatusType::Information,
tr("Not tested yet."),
tr("Not tested yet."));
m_ui.m_lblTestResult->label()->setWordWrap(true);
m_ui.m_spinLimitMessages->setValue(INOREADER_DEFAULT_BATCH_SIZE);
m_ui.m_spinLimitMessages->setMinimum(1);
m_ui.m_spinLimitMessages->setMaximum(INOREADER_MAX_BATCH_SIZE);
connect(m_ui.m_btnTestSetup, &QPushButton::clicked, this, &FormEditInoreaderAccount::testSetup);
connect(&m_network, &InoreaderNetworkFactory::accessGranted, [this]() {
connect(m_ui.m_buttonBox, &QDialogButtonBox::accepted, this, &FormEditInoreaderAccount::onClickedOk);
connect(m_ui.m_buttonBox, &QDialogButtonBox::rejected, this, &FormEditInoreaderAccount::onClickedCancel);
connect(m_network, &InoreaderNetworkFactory::accessGranted, [this]() {
m_ui.m_lblTestResult->setStatus(WidgetWithStatus::StatusType::Ok,
tr("Tested successfully. You may be prompted to login once more."),
tr("Your access was approved."));
});
connect(&m_network, &InoreaderNetworkFactory::error, [this](const QString& err) {
connect(m_network, &InoreaderNetworkFactory::tokensRefreshed, [this]() {
m_ui.m_lblTestResult->setStatus(WidgetWithStatus::StatusType::Ok,
tr("Access tokens refreshed, it seems okay."),
tr("Your access was approved."));
});
connect(m_network, &InoreaderNetworkFactory::error, [this](const QString& err) {
m_ui.m_lblTestResult->setStatus(WidgetWithStatus::StatusType::Error,
tr("There is error. %1").arg(err),
tr("There was error during testing."));
@ -47,19 +59,43 @@ FormEditInoreaderAccount::FormEditInoreaderAccount(QWidget* parent) : QDialog(pa
FormEditInoreaderAccount::~FormEditInoreaderAccount() {}
void FormEditInoreaderAccount::testSetup() {
if (m_network.isLoggedIn()) {
if (m_network->isLoggedIn()) {
m_ui.m_lblTestResult->setStatus(WidgetWithStatus::StatusType::Information,
tr("Access granted successfully."),
tr("Access granted successfully."));
}
else {
m_network.logIn();
m_network->logIn();
m_ui.m_lblTestResult->setStatus(WidgetWithStatus::StatusType::Progress,
tr("Requested access approval. Respond to it, please."),
tr("Access approval was requested via OAuth 2.0 protocol."));
}
}
void FormEditInoreaderAccount::onClickedOk() {
bool editing_account = true;
if (m_editableRoot == nullptr) {
// We want to confirm newly created account.
// So save new account into DB, setup its properties.
m_editableRoot = new InoreaderServiceRoot();
editing_account = false;
}
m_editableRoot->network()->setBatchSize(m_ui.m_spinLimitMessages->value());
m_editableRoot->saveAccountDataToDatabase();
accept();
if (editing_account) {
m_editableRoot->completelyRemoveAllData();
m_editableRoot->syncIn();
}
}
void FormEditInoreaderAccount::onClickedCancel() {
reject();
}
InoreaderServiceRoot* FormEditInoreaderAccount::execForCreate() {
setWindowTitle(tr("Add new Inoreader account"));
exec();

View File

@ -42,10 +42,12 @@ class FormEditInoreaderAccount : public QDialog {
private slots:
void testSetup();
void onClickedOk();
void onClickedCancel();
private:
Ui::FormEditInoreaderAccount m_ui;
InoreaderNetworkFactory m_network;
InoreaderNetworkFactory* m_network;
InoreaderServiceRoot* m_editableRoot;
};

View File

@ -29,9 +29,6 @@
<height>16777215</height>
</size>
</property>
<property name="suffix">
<string> = unlimited</string>
</property>
<property name="minimum">
<number>-1</number>
</property>

View File

@ -19,6 +19,62 @@
#include "services/inoreader/inoreaderserviceroot.h"
#include "miscellaneous/application.h"
#include "miscellaneous/databasequeries.h"
#include "services/inoreader/inoreaderentrypoint.h"
#include "services/inoreader/network/inoreadernetworkfactory.h"
InoreaderServiceRoot::InoreaderServiceRoot(RootItem* parent) : ServiceRoot(parent) {}
InoreaderServiceRoot::~InoreaderServiceRoot() {}
void InoreaderServiceRoot::updateTitle() {
setTitle(m_network->username() + QSL(" (Inoreader)"));
}
void InoreaderServiceRoot::saveAccountDataToDatabase() {
QSqlDatabase database = qApp->database()->connection(metaObject()->className(), DatabaseFactory::FromSettings);
if (accountId() != NO_PARENT_CATEGORY) {
if (DatabaseQueries::overwriteInoreaderAccount(database, m_network->username(), m_network->accessToken(),
m_network->refreshToken(), m_network->batchSize(),
accountId())) {
updateTitle();
itemChanged(QList<RootItem*>() << this);
}
}
else {
bool saved;
int id_to_assign = DatabaseQueries::createAccount(database, code(), &saved);
if (saved) {
if (DatabaseQueries::createInoreaderAccount(database, id_to_assign,
m_network->username(), m_network->accessToken(),
m_network->refreshToken(), m_network->batchSize())) {
setId(id_to_assign);
setAccountId(id_to_assign);
updateTitle();
}
}
}
}
bool InoreaderServiceRoot::supportsFeedAdding() const {
return true;
}
bool InoreaderServiceRoot::supportsCategoryAdding() const {
return false;
}
void InoreaderServiceRoot::start(bool freshly_activated) {}
void InoreaderServiceRoot::stop() {}
QString InoreaderServiceRoot::code() const {
return InoreaderEntryPoint().code();
}
void InoreaderServiceRoot::addNewFeed(const QString& url) {}
void InoreaderServiceRoot::addNewCategory() {}

View File

@ -22,7 +22,7 @@
#include "services/abstract/serviceroot.h"
#include "services/inoreader/network/inoreadernetworkfactory.h"
class InoreaderNetworkFactory;
class InoreaderServiceRoot : public ServiceRoot {
Q_OBJECT
@ -31,8 +31,34 @@ class InoreaderServiceRoot : public ServiceRoot {
explicit InoreaderServiceRoot(RootItem* parent = nullptr);
virtual ~InoreaderServiceRoot();
void saveAccountDataToDatabase();
void setNetwork(InoreaderNetworkFactory* network);
InoreaderNetworkFactory* network() const;
bool supportsFeedAdding() const;
bool supportsCategoryAdding() const;
void start(bool freshly_activated);
void stop();
QString code() const;
public slots:
void addNewFeed(const QString& url);
void addNewCategory();
private slots:
void updateTitle();
private:
InoreaderNetworkFactory m_network;
InoreaderNetworkFactory* m_network;
};
inline void InoreaderServiceRoot::setNetwork(InoreaderNetworkFactory* network) {
m_network = network;
}
inline InoreaderNetworkFactory* InoreaderServiceRoot::network() const {
return m_network;
}
#endif // INOREADERSERVICEROOT_H

View File

@ -29,21 +29,34 @@
#include <QOAuthHttpServerReplyHandler>
#include <QUrl>
InoreaderNetworkFactory::InoreaderNetworkFactory(QObject* parent) : QObject(parent) {
InoreaderNetworkFactory::InoreaderNetworkFactory(QObject* parent) : QObject(parent),
m_batchSize(INOREADER_DEFAULT_BATCH_SIZE), m_oauth2(new QOAuth2AuthorizationCodeFlow(this)) {
initializeOauth();
}
bool InoreaderNetworkFactory::isLoggedIn() const {
return m_oauth2.expirationAt() > QDateTime::currentDateTime() && m_oauth2.status() == QAbstractOAuth::Status::Granted;
return m_oauth2->expirationAt() > QDateTime::currentDateTime() && m_oauth2->status() == QAbstractOAuth::Status::Granted;
}
QString InoreaderNetworkFactory::username() const {
return m_username;
}
int InoreaderNetworkFactory::batchSize() const {
return m_batchSize;
}
void InoreaderNetworkFactory::setBatchSize(int batch_size) {
m_batchSize = batch_size;
}
void InoreaderNetworkFactory::logIn() {
if (!m_oauth2.expirationAt().isNull() && m_oauth2.expirationAt() <= QDateTime::currentDateTime() && !m_refreshToken.isEmpty()) {
if (!m_oauth2->expirationAt().isNull() && m_oauth2->expirationAt() <= QDateTime::currentDateTime() && !m_refreshToken.isEmpty()) {
// We have some refresh token which expired.
m_oauth2.refreshAccessToken();
m_oauth2->refreshAccessToken();
}
else {
m_oauth2.grant();
m_oauth2->grant();
}
}
@ -53,48 +66,50 @@ void InoreaderNetworkFactory::logInIfNeeded() {
}
}
void InoreaderNetworkFactory::tokensReceived(QVariantMap tokens) {
qDebug() << "Inoreader: Tokens received:" << tokens;
if (tokens.contains(INOREADER_ACCESS_TOKEN_KEY)) {
m_accessToken = tokens.value(INOREADER_ACCESS_TOKEN_KEY).toString();
}
if (tokens.contains(INOREADER_REFRESH_TOKEN_KEY)) {
m_refreshToken = tokens.value(INOREADER_REFRESH_TOKEN_KEY).toString();
}
emit tokensRefreshed();
}
void InoreaderNetworkFactory::initializeOauth() {
auto oauth_reply_handler = new QOAuthHttpServerReplyHandler(INOREADER_OAUTH_PORT, this);
// Full redirect URL is thus "http://localhost.8080/".
// Full redirect URL is thus "http://localhost:INOREADER_OAUTH_PORT/".
oauth_reply_handler->setCallbackPath(QSL(""));
oauth_reply_handler->setCallbackText(tr("Access to your Inoreader session was granted, you "
"can now <b>close this window and go back to RSS Guard</b>."));
m_oauth2.setAccessTokenUrl(QUrl(INOREADER_OAUTH_TOKEN_URL));
m_oauth2.setAuthorizationUrl(QUrl(INOREADER_OAUTH_AUTH_URL));
m_oauth2.setClientIdentifier(INOREADER_OAUTH_CLI_ID);
m_oauth2.setClientIdentifierSharedKey(INOREADER_OAUTH_CLI_KEY);
m_oauth2.setContentType(QAbstractOAuth::ContentType::Json);
m_oauth2.setNetworkAccessManager(SilentNetworkAccessManager::instance());
m_oauth2.setReplyHandler(oauth_reply_handler);
m_oauth2.setUserAgent(APP_USERAGENT);
m_oauth2.setScope(INOREADER_OAUTH_SCOPE);
m_oauth2->setAccessTokenUrl(QUrl(INOREADER_OAUTH_TOKEN_URL));
m_oauth2->setAuthorizationUrl(QUrl(INOREADER_OAUTH_AUTH_URL));
m_oauth2->setClientIdentifier(INOREADER_OAUTH_CLI_ID);
m_oauth2->setClientIdentifierSharedKey(INOREADER_OAUTH_CLI_KEY);
m_oauth2->setContentType(QAbstractOAuth::ContentType::Json);
m_oauth2->setNetworkAccessManager(SilentNetworkAccessManager::instance());
m_oauth2->setReplyHandler(oauth_reply_handler);
m_oauth2->setUserAgent(APP_USERAGENT);
m_oauth2->setScope(INOREADER_OAUTH_SCOPE);
connect(&m_oauth2, &QOAuth2AuthorizationCodeFlow::statusChanged, [=](QAbstractOAuth::Status status) {
connect(m_oauth2, &QOAuth2AuthorizationCodeFlow::statusChanged, [=](QAbstractOAuth::Status status) {
qDebug("Inoreader: Status changed to '%d'.", (int)status);
});
connect(oauth_reply_handler, &QOAuthHttpServerReplyHandler::tokensReceived, [this](QVariantMap tokens) {
qDebug() << "Inoreader: Tokens received:" << tokens;
if (tokens.contains(QSL(INOREADER_REFRESH_TOKEN_KEY))) {
m_refreshToken = tokens.value(QSL(INOREADER_REFRESH_TOKEN_KEY)).toString();
}
if (tokens.contains(QSL(INOREADER_ACCESS_TOKEN_KEY))) {
m_accessToken = tokens.value(QSL(INOREADER_ACCESS_TOKEN_KEY)).toString();
}
emit tokensRefreshed();
});
m_oauth2.setModifyParametersFunction([&](QAbstractOAuth::Stage stage, QVariantMap* parameters) {
connect(oauth_reply_handler, &QOAuthHttpServerReplyHandler::tokensReceived, this, &InoreaderNetworkFactory::tokensReceived);
m_oauth2->setModifyParametersFunction([&](QAbstractOAuth::Stage stage, QVariantMap* parameters) {
qDebug() << "Inoreader: Set modify parameters for stage" << (int)stage << "called: \n" << parameters;
});
connect(&m_oauth2, &QOAuth2AuthorizationCodeFlow::granted, [=]() {
connect(m_oauth2, &QOAuth2AuthorizationCodeFlow::granted, [=]() {
qDebug("Inoreader: Oauth2 granted.");
emit accessGranted();
});
connect(&m_oauth2, &QOAuth2AuthorizationCodeFlow::error, [=](QString err, QString error_description, QUrl uri) {
connect(m_oauth2, &QOAuth2AuthorizationCodeFlow::error, [=](QString err, QString error_description, QUrl uri) {
Q_UNUSED(err)
Q_UNUSED(uri)
@ -102,7 +117,15 @@ void InoreaderNetworkFactory::initializeOauth() {
m_accessToken = m_refreshToken = QString();
emit error(error_description);
});
connect(&m_oauth2, &QOAuth2AuthorizationCodeFlow::authorizeWithBrowser, [](const QUrl& url) {
connect(m_oauth2, &QOAuth2AuthorizationCodeFlow::authorizeWithBrowser, [](const QUrl& url) {
qApp->web()->openUrlInExternalBrowser(url.toString());
});
}
QString InoreaderNetworkFactory::refreshToken() const {
return m_refreshToken;
}
QString InoreaderNetworkFactory::accessToken() const {
return m_accessToken;
}

View File

@ -31,6 +31,15 @@ class InoreaderNetworkFactory : public QObject {
bool isLoggedIn() const;
QString username() const;
// Gets/sets the amount of messages to obtain during single feed update.
int batchSize() const;
void setBatchSize(int batch_size);
QString accessToken() const;
QString refreshToken() const;
public slots:
void logIn();
void logInIfNeeded();
@ -40,13 +49,18 @@ class InoreaderNetworkFactory : public QObject {
void tokensRefreshed();
void error(QString& description);
private slots:
void tokensReceived(QVariantMap tokens);
private:
void initializeOauth();
private:
QOAuth2AuthorizationCodeFlow m_oauth2;
int m_batchSize;
QString m_username;
QString m_accessToken;
QString m_refreshToken;
QOAuth2AuthorizationCodeFlow* m_oauth2;
};
#endif // INOREADERNETWORKFACTORY_H

View File

@ -238,37 +238,6 @@ void OwnCloudServiceRoot::addNewFeed(const QString& url) {
void OwnCloudServiceRoot::addNewCategory() {}
QMap<int, QVariant> OwnCloudServiceRoot::storeCustomFeedsData() {
QMap<int, QVariant> custom_data;
foreach (const Feed* feed, getSubTreeFeeds()) {
QVariantMap feed_custom_data;
feed_custom_data.insert(QSL("auto_update_interval"), feed->autoUpdateInitialInterval());
feed_custom_data.insert(QSL("auto_update_type"), feed->autoUpdateType());
custom_data.insert(feed->customId(), feed_custom_data);
}
return custom_data;
}
void OwnCloudServiceRoot::restoreCustomFeedsData(const QMap<int, QVariant>& data, const QHash<int, Feed*>& feeds) {
QMapIterator<int, QVariant> i(data);
while (i.hasNext()) {
i.next();
const int custom_id = i.key();
if (feeds.contains(custom_id)) {
Feed* feed = feeds.value(custom_id);
QVariantMap feed_custom_data = i.value().toMap();
feed->setAutoUpdateInitialInterval(feed_custom_data.value(QSL("auto_update_interval")).toInt());
feed->setAutoUpdateType(static_cast<Feed::AutoUpdateType>(feed_custom_data.value(QSL("auto_update_type")).toInt()));
}
}
}
RootItem* OwnCloudServiceRoot::obtainNewTreeForSyncIn() const {
OwnCloudGetFeedsCategoriesResponse feed_cats_response = m_network->feedsCategories();

View File

@ -60,8 +60,6 @@ class OwnCloudServiceRoot : public ServiceRoot, public CacheForServiceRoot {
void addNewCategory();
private:
QMap<int, QVariant> storeCustomFeedsData();
void restoreCustomFeedsData(const QMap<int, QVariant>& data, const QHash<int, Feed*>& feeds);
RootItem* obtainNewTreeForSyncIn() const;
void loadFromDatabase();

View File

@ -183,15 +183,6 @@ void StandardServiceRoot::checkArgumentsForFeedAdding() {
}
}
QMap<int, QVariant> StandardServiceRoot::storeCustomFeedsData() {
return QMap<int, QVariant>();
}
void StandardServiceRoot::restoreCustomFeedsData(const QMap<int, QVariant>& data, const QHash<int, Feed*>& feeds) {
Q_UNUSED(feeds)
Q_UNUSED(data)
}
QString StandardServiceRoot::processFeedUrl(const QString& feed_url) {
if (feed_url.startsWith(QL1S(URI_SCHEME_FEED_SHORT))) {
QString without_feed_prefix = feed_url.mid(5);

View File

@ -81,9 +81,6 @@ class StandardServiceRoot : public ServiceRoot {
QList<QAction*> m_serviceMenu;
QList<QAction*> m_feedContextMenu;
QAction* m_actionFeedFetchMetadata;
QMap<int, QVariant> storeCustomFeedsData();
void restoreCustomFeedsData(const QMap<int, QVariant>& data, const QHash<int, Feed*>& feeds);
};
#endif // STANDARDSERVICEROOT_H

View File

@ -294,34 +294,3 @@ RootItem* TtRssServiceRoot::obtainNewTreeForSyncIn() const {
return nullptr;
}
}
QMap<int, QVariant> TtRssServiceRoot::storeCustomFeedsData() {
QMap<int, QVariant> custom_data;
foreach (const Feed* feed, getSubTreeFeeds()) {
QVariantMap feed_custom_data;
feed_custom_data.insert(QSL("auto_update_interval"), feed->autoUpdateInitialInterval());
feed_custom_data.insert(QSL("auto_update_type"), feed->autoUpdateType());
custom_data.insert(feed->customId(), feed_custom_data);
}
return custom_data;
}
void TtRssServiceRoot::restoreCustomFeedsData(const QMap<int, QVariant>& data, const QHash<int, Feed*>& feeds) {
QMapIterator<int, QVariant> i(data);
while (i.hasNext()) {
i.next();
const int custom_id = i.key();
if (feeds.contains(custom_id)) {
Feed* feed = feeds.value(custom_id);
QVariantMap feed_custom_data = i.value().toMap();
feed->setAutoUpdateInitialInterval(feed_custom_data.value(QSL("auto_update_interval")).toInt());
feed->setAutoUpdateType(static_cast<Feed::AutoUpdateType>(feed_custom_data.value(QSL("auto_update_type")).toInt()));
}
}
}

View File

@ -65,9 +65,6 @@ class TtRssServiceRoot : public ServiceRoot, public CacheForServiceRoot {
private:
RootItem* obtainNewTreeForSyncIn() const;
QMap<int, QVariant> storeCustomFeedsData();
void restoreCustomFeedsData(const QMap<int, QVariant>& data, const QHash<int, Feed*>& feeds);
void loadFromDatabase();
QAction* m_actionSyncIn;