option to purge individual feeds

This commit is contained in:
Martin Rotter 2025-01-08 10:16:23 +01:00
parent fe4f9914c5
commit 07740a0328
8 changed files with 43 additions and 34 deletions

View file

@ -529,6 +529,26 @@ bool FeedsModel::markItemCleared(RootItem* item, bool clean_read_only) {
return true; return true;
} }
bool FeedsModel::purgeArticles(const QList<Feed*>& feeds) {
auto database = qApp->database()->driver()->connection(metaObject()->className());
try {
bool anything_purged = DatabaseQueries::purgeFeedArticles(database, feeds);
if (anything_purged) {
reloadCountsOfWholeModel();
emit reloadMessageListRequested(false);
return true;
}
}
catch (const ApplicationException& ex) {
qCriticalNN << LOGSEC_CORE
<< "Purging of articles from feeds failed with error:" << QUOTE_W_SPACE_DOT(ex.message());
}
return false;
}
QVariant FeedsModel::data(const QModelIndex& index, int role) const { QVariant FeedsModel::data(const QModelIndex& index, int role) const {
switch (role) { switch (role) {
case Qt::ItemDataRole::FontRole: { case Qt::ItemDataRole::FontRole: {

View file

@ -111,6 +111,7 @@ class RSSGUARD_DLLSPEC FeedsModel : public QAbstractItemModel {
// Feeds operations. // Feeds operations.
bool markItemRead(RootItem* item, RootItem::ReadStatus read); bool markItemRead(RootItem* item, RootItem::ReadStatus read);
bool markItemCleared(RootItem* item, bool clean_read_only); bool markItemCleared(RootItem* item, bool clean_read_only);
bool purgeArticles(const QList<Feed *> &feeds);
// Signals that properties (probably counts) // Signals that properties (probably counts)
// of ALL items have changed. // of ALL items have changed.

View file

@ -634,18 +634,27 @@ bool DatabaseQueries::removeUnwantedArticlesFromFeed(const QSqlDatabase& db,
return rows_deleted > 0; return rows_deleted > 0;
} }
bool DatabaseQueries::purgeFeedMessages(const QSqlDatabase& database, const Feed* feed) { bool DatabaseQueries::purgeFeedArticles(const QSqlDatabase& database, const QList<Feed*>& feeds) {
QSqlQuery q(database); QSqlQuery q(database);
q.setForwardOnly(true); auto feed_clauses = boolinq::from(feeds)
q.prepare(QSL("DELETE FROM Messages " .select([](Feed* feed) {
"WHERE " return QSL("("
" Messages.account_id = :account_id AND " "Messages.feed = '%1' AND "
" Messages.feed = :feed AND " "Messages.account_id = %2 AND "
" Messages.is_important = 0")); "Messages.is_important = 0"
")")
.arg(feed->customId(), QString::number(feed->getParentServiceRoot()->accountId()));
})
.toStdList();
q.bindValue(QSL(":feed"), feed->customId()); qDebugNN << feed_clauses;
q.bindValue(QSL(":account_id"), feed->getParentServiceRoot()->accountId());
QStringList feed_str_clauses = FROM_STD_LIST(QStringList, feed_clauses);
QString feed_clause = feed_str_clauses.join(QSL(" OR "));
q.setForwardOnly(true);
q.prepare(QSL("DELETE FROM Messages WHERE %1;").arg(feed_clause));
if (!q.exec()) { if (!q.exec()) {
throw ApplicationException(q.lastError().text()); throw ApplicationException(q.lastError().text());

View file

@ -76,7 +76,7 @@ class RSSGUARD_DLLSPEC DatabaseQueries {
const Feed::ArticleIgnoreLimit& feed_setup, const Feed::ArticleIgnoreLimit& feed_setup,
const Feed::ArticleIgnoreLimit& app_setup); const Feed::ArticleIgnoreLimit& app_setup);
static bool purgeFeedMessages(const QSqlDatabase& database, const Feed* feed); static bool purgeFeedArticles(const QSqlDatabase& database, const QList<Feed*>& feeds);
static bool purgeMessage(const QSqlDatabase& db, int message_id); static bool purgeMessage(const QSqlDatabase& db, int message_id);
static bool purgeImportantMessages(const QSqlDatabase& db); static bool purgeImportantMessages(const QSqlDatabase& db);
static bool purgeReadMessages(const QSqlDatabase& db); static bool purgeReadMessages(const QSqlDatabase& db);

View file

@ -500,7 +500,7 @@ void FormMain::updateFeedButtonsAvailability() {
m_ui->m_actionBackupDatabaseSettings->setEnabled(!critical_action_running); m_ui->m_actionBackupDatabaseSettings->setEnabled(!critical_action_running);
m_ui->m_actionCleanupDatabase->setEnabled(!critical_action_running); m_ui->m_actionCleanupDatabase->setEnabled(!critical_action_running);
m_ui->m_actionClearSelectedItems->setEnabled(anything_selected); m_ui->m_actionClearSelectedItems->setEnabled(anything_selected);
m_ui->m_actionPurgeSelectedItems->setEnabled(feed_selected); m_ui->m_actionPurgeSelectedItems->setEnabled(feed_selected || category_selected || service_selected);
m_ui->m_actionDeleteSelectedItem->setEnabled(!critical_action_running && anything_selected); m_ui->m_actionDeleteSelectedItem->setEnabled(!critical_action_running && anything_selected);
m_ui->m_actionEditSelectedItem->setEnabled(!critical_action_running && anything_selected); m_ui->m_actionEditSelectedItem->setEnabled(!critical_action_running && anything_selected);
m_ui->m_actionEditChildFeeds->setEnabled(!critical_action_running && (service_selected || category_selected)); m_ui->m_actionEditChildFeeds->setEnabled(!critical_action_running && (service_selected || category_selected));

View file

@ -266,9 +266,7 @@ void FeedsView::purgeSelectedFeeds() {
return; return;
} }
for (auto* it : selectedFeeds(true)) { m_sourceModel->purgeArticles(selectedFeeds(true));
it->purgeArticles();
}
} }
void FeedsView::clearAllItems() { void FeedsView::clearAllItems() {
@ -989,6 +987,7 @@ QMenu* FeedsView::initializeContextMenuFeeds(RootItem* clicked_item) {
<< qApp->mainForm()->m_ui->m_actionCopyUrlSelectedFeed << qApp->mainForm()->m_ui->m_actionCopyUrlSelectedFeed
<< qApp->mainForm()->m_ui->m_actionMarkSelectedItemsAsRead << qApp->mainForm()->m_ui->m_actionMarkSelectedItemsAsRead
<< qApp->mainForm()->m_ui->m_actionMarkSelectedItemsAsUnread << qApp->mainForm()->m_ui->m_actionMarkSelectedItemsAsUnread
<< qApp->mainForm()->m_ui->m_actionPurgeSelectedItems
<< qApp->mainForm()->m_ui->m_actionDeleteSelectedItem); << qApp->mainForm()->m_ui->m_actionDeleteSelectedItem);
auto cat_add = clicked_item->getParentServiceRoot()->supportsCategoryAdding(); auto cat_add = clicked_item->getParentServiceRoot()->supportsCategoryAdding();

View file

@ -113,24 +113,6 @@ QVariant Feed::data(int column, int role) const {
} }
} }
void Feed::purgeArticles() {
auto database = qApp->database()->driver()->connection(metaObject()->className());
try {
bool anything_purged = DatabaseQueries::purgeFeedMessages(database, this);
if (anything_purged) {
getParentServiceRoot()->updateCounts(true);
getParentServiceRoot()->itemChanged(getParentServiceRoot()->getSubTree());
getParentServiceRoot()->requestReloadMessageList(false);
}
}
catch (const ApplicationException& ex) {
qCriticalNN << LOGSEC_CORE << "Purging of articles from feed" << QUOTE_W_SPACE(customId())
<< "failed with error:" << QUOTE_W_SPACE_DOT(ex.message());
}
}
int Feed::autoUpdateInterval() const { int Feed::autoUpdateInterval() const {
return m_autoUpdateInterval; return m_autoUpdateInterval;
} }

View file

@ -71,8 +71,6 @@ class RSSGUARD_DLLSPEC Feed : public RootItem {
virtual bool isFetching() const; virtual bool isFetching() const;
virtual QVariant data(int column, int role) const; virtual QVariant data(int column, int role) const;
void purgeArticles();
void setCountOfAllMessages(int count_all_messages); void setCountOfAllMessages(int count_all_messages);
void setCountOfUnreadMessages(int count_unread_messages); void setCountOfUnreadMessages(int count_unread_messages);