File indexing completed on 2024-05-12 16:23:40

0001 // SPDX-FileCopyrightText: 2020 Jonah BrĂ¼chert <jbb@kaidan.im>
0002 // SPDX-FileCopyrightText: 2020 Rinigus <rinigus.git@gmail.com>
0003 //
0004 // SPDX-License-Identifier: GPL-2.0-or-later
0005 
0006 #include "bookmarkshistorymodel.h"
0007 #include "browsermanager.h"
0008 
0009 #include <QDateTime>
0010 #include <QDebug>
0011 #include <QSqlError>
0012 
0013 #include <QCoroFuture>
0014 #include <QCoroTask>
0015 
0016 constexpr int QUERY_LIMIT = 1000;
0017 
0018 BookmarksHistoryModel::BookmarksHistoryModel(QObject *parent)
0019     : QAbstractListModel(parent)
0020 {
0021     connect(BrowserManager::instance(), &BrowserManager::databaseTableChanged, this, &BookmarksHistoryModel::onDatabaseChanged);
0022 }
0023 
0024 QHash<int, QByteArray> BookmarksHistoryModel::roleNames() const {
0025     return {
0026         {Id, "id"},
0027         {Url, "url"},
0028         {Title, "title"},
0029         {Icon, "iconName"},
0030         {LastVisitedDelta, "lastVisitedDelte"}
0031     };
0032 }
0033 
0034 QVariant BookmarksHistoryModel::data(const QModelIndex &index, int role) const
0035 {
0036     auto &item = m_entries.at(index.row());
0037     switch (role) {
0038     case Role::Id:
0039         return item.id;
0040     case Role::Title:
0041         return item.title;
0042     case Role::Url:
0043         return item.url;
0044     case Role::Icon:
0045         return item.icon;
0046     case Role::LastVisitedDelta:
0047         return item.lastVisitedDelta;
0048     }
0049 
0050     Q_UNREACHABLE();
0051 }
0052 
0053 void BookmarksHistoryModel::setActive(bool a)
0054 {
0055     if (m_active == a)
0056         return;
0057     m_active = a;
0058     if (m_active)
0059         fetchData();
0060     else
0061         clear();
0062 
0063     Q_EMIT activeChanged();
0064 }
0065 
0066 void BookmarksHistoryModel::setBookmarks(bool b)
0067 {
0068     if (m_bookmarks == b)
0069         return;
0070     m_bookmarks = b;
0071     fetchData();
0072     Q_EMIT bookmarksChanged();
0073 }
0074 
0075 void BookmarksHistoryModel::setHistory(bool h)
0076 {
0077     if (m_history == h)
0078         return;
0079     m_history = h;
0080     fetchData();
0081     Q_EMIT historyChanged();
0082 }
0083 
0084 void BookmarksHistoryModel::setFilter(const QString &f)
0085 {
0086     if (m_filter == f)
0087         return;
0088     m_filter = f;
0089     fetchData();
0090     Q_EMIT filterChanged();
0091 }
0092 
0093 void BookmarksHistoryModel::onDatabaseChanged(const QString &table)
0094 {
0095     if ((table == QLatin1String("bookmarks") && m_bookmarks) || (table == QLatin1String("history") && m_history))
0096         fetchData();
0097 }
0098 
0099 void BookmarksHistoryModel::fetchData()
0100 {
0101     if (!m_active)
0102         return;
0103 
0104     auto future = [history = m_history, bookmarks = m_bookmarks, filter = m_filter]() mutable -> QCoro::Task<std::vector<BookmarksHistoryRecord>> {
0105         auto db = BrowserManager::instance()
0106                 ->databaseManager()
0107                 ->database();
0108 
0109         const qint64 currentTimeInUnix = QDateTime::currentSecsSinceEpoch();
0110 
0111         if (filter.isEmpty()) {
0112             // No clue why this works
0113             filter = QStringLiteral("");
0114         }
0115 
0116         if (bookmarks && history) {
0117             co_return co_await db->getResults<BookmarksHistoryRecord>(
0118                 QStringLiteral("SELECT rowid AS id, url, title, icon, ? - lastVisited AS lastVisitedDelta "
0119                                "FROM (SELECT * FROM bookmarks UNION SELECT * FROM history) "
0120                                "WHERE url LIKE '%' || ? || '%' OR title LIKE '%' || ? || '%' "
0121                                "LIMIT %1").arg(QUERY_LIMIT),
0122                     currentTimeInUnix, filter, filter);
0123         } else if (bookmarks) {
0124             co_return co_await db->getResults<BookmarksHistoryRecord>(
0125                 QStringLiteral("SELECT rowid AS id, url, title, icon, ? - lastVisited AS lastVisitedDelta "
0126                                "FROM bookmarks "
0127                                "WHERE url LIKE '%' || ? || '%' OR title LIKE '%' || ? || '%'"),
0128                     currentTimeInUnix, filter, filter);
0129         } else if (history) {
0130             co_return co_await db->getResults<BookmarksHistoryRecord>(
0131                 QStringLiteral("SELECT rowid AS id, url, title, icon, ? - lastVisited AS lastVisitedDelta "
0132                                "FROM history "
0133                                "WHERE url LIKE '%' || ? || '%' OR title LIKE '%' || ? || '%'"
0134                                "LIMIT  %1").arg(QUERY_LIMIT),
0135                     currentTimeInUnix, filter, filter);
0136         }
0137 
0138         co_return {};
0139     }();
0140 
0141     QCoro::connect(std::move(future), this, [this](auto result) {
0142         if (m_entries == result) {
0143             return;
0144         }
0145 
0146         beginResetModel();
0147         m_entries = std::move(result);
0148         endResetModel();
0149     });
0150 }
0151 
0152 void BookmarksHistoryModel::clear()
0153 {
0154     beginResetModel();
0155     m_entries.clear();
0156     endResetModel();
0157 }
0158 
0159 #include "moc_bookmarkshistorymodel.cpp"