diff --git a/plugins/sms/conversationsdbusinterface.cpp b/plugins/sms/conversationsdbusinterface.cpp index 93ce0151a..1a60d94ac 100644 --- a/plugins/sms/conversationsdbusinterface.cpp +++ b/plugins/sms/conversationsdbusinterface.cpp @@ -169,7 +169,20 @@ void ConversationsDbusInterface::updateConversation(const qint64& conversationID } qCDebug(KDECONNECT_CONVERSATIONS) << "Requesting conversation with ID" << conversationID << "from remote"; conversationsWaitingForMessages.insert(conversationID); - m_smsInterface.requestConversation(conversationID); + + // Request a window of messages + qint64 rangeStartTimestamp; + qint64 numberToRequest; + if (m_conversations.contains(conversationID) && m_conversations[conversationID].count() > 0) { + rangeStartTimestamp = m_conversations[conversationID].first().date(); // Request starting from the oldest-available message + numberToRequest = m_conversations[conversationID].count(); // Request an increasing number of messages by requesting more equal to the amount we have + } else { + rangeStartTimestamp = -1; // Value < 0 indicates to return the newest messages + numberToRequest = MIN_NUMBER_TO_REQUEST; // Start off with a small batch + } + if (numberToRequest < MIN_NUMBER_TO_REQUEST) { numberToRequest = MIN_NUMBER_TO_REQUEST; } + m_smsInterface.requestConversation(conversationID, rangeStartTimestamp, numberToRequest); + while (conversationsWaitingForMessages.contains(conversationID)) { waitingForMessages.wait(&waitingForMessagesLock); } diff --git a/plugins/sms/conversationsdbusinterface.h b/plugins/sms/conversationsdbusinterface.h index 7fb9c4623..dbdec31dd 100644 --- a/plugins/sms/conversationsdbusinterface.h +++ b/plugins/sms/conversationsdbusinterface.h @@ -25,6 +25,11 @@ class Device; Q_DECLARE_LOGGING_CATEGORY(KDECONNECT_CONVERSATIONS) +// There is some amount of overhead and delay to making a request, so make sure to request at least a few +#define MIN_NUMBER_TO_REQUEST 25 +// Some low-water mark after which we want to fill the cache +#define CACHE_LOW_WATER_MARK_PERCENT 10 + class ConversationsDbusInterface : public QDBusAbstractAdaptor { @@ -44,8 +49,8 @@ public: QList getConversation(const qint64& conversationID) const; /** - * Get all of the messages in the requested conversation from the remote device - * TODO: Make interface capable of requesting smaller window of messages + * Get some new messages for the requested conversation from the remote device + * Requests a quantity of new messages equal to the current number of messages in the conversation */ void updateConversation(const qint64& conversationID); diff --git a/plugins/sms/requestconversationworker.cpp b/plugins/sms/requestconversationworker.cpp index 5e5dbb8c8..b9038f7c7 100644 --- a/plugins/sms/requestconversationworker.cpp +++ b/plugins/sms/requestconversationworker.cpp @@ -44,13 +44,24 @@ void RequestConversationWorker::handleRequestConversation() size_t numHandled = replyForConversation(messagesList, start, howMany); if (numHandled < howMany) { + // In this case, the cache wasn't able to satisfy the request fully. Get more. + size_t numRemaining = howMany - numHandled; - // If we don't have enough messages in cache, go get some more - // TODO: Make Android interface capable of requesting small window of messages parent->updateConversation(conversationID); messagesList = parent->getConversation(conversationID); - //ConversationsDbusInterface::getConversation blocks until it sees new messages in the requested conversation + //ConversationsDbusInterface::updateConversation blocks until it sees new messages in the requested conversation replyForConversation(messagesList, start + numHandled, numRemaining); + } else { + // The cache was able to fully satisfy the request but we need to check that it isn't running dry + + size_t numCachedMessages = messagesList.count(); + size_t requestEnd = start + numHandled; + size_t numRemainingMessages = numCachedMessages - requestEnd; + double percentRemaining = ((double) numRemainingMessages / numCachedMessages) * 100; + + if (percentRemaining < CACHE_LOW_WATER_MARK_PERCENT || numRemainingMessages < MIN_NUMBER_TO_REQUEST) { + parent->updateConversation(conversationID); + } } Q_EMIT finished(); diff --git a/plugins/sms/smsplugin.cpp b/plugins/sms/smsplugin.cpp index c1e011e54..77a6a2b15 100644 --- a/plugins/sms/smsplugin.cpp +++ b/plugins/sms/smsplugin.cpp @@ -102,10 +102,12 @@ void SmsPlugin::requestAllConversations() sendPacket(np); } -void SmsPlugin::requestConversation (const qint64& conversationID) const +void SmsPlugin::requestConversation (const qint64 conversationID, const qint64 rangeStartTimestamp, const qint64 numberToRequest) const { NetworkPacket np(PACKET_TYPE_SMS_REQUEST_CONVERSATION); np.set(QStringLiteral("threadID"), conversationID); + np.set(QStringLiteral("rangeStartTimestamp"), rangeStartTimestamp); + np.set(QStringLiteral("numberToRequest"), numberToRequest); sendPacket(np); } diff --git a/plugins/sms/smsplugin.h b/plugins/sms/smsplugin.h index 5b77c54ec..e117ec881 100644 --- a/plugins/sms/smsplugin.h +++ b/plugins/sms/smsplugin.h @@ -105,9 +105,12 @@ /** * Packet sent to request all the messages in a particular conversation * - * The body should contain the key "threadID" mapping to the threadID being requested - * For example: - * { "threadID": 203 } + * The following fields are available: + * "threadID": // (Required) ThreadID to request + * "rangeStartTimestamp": // (Optional) Millisecond epoch timestamp indicating the start of the range from which to return messages + * "numberToRequest": // (Optional) Number of messages to return, starting from rangeStartTimestamp. + * // May return fewer than expected if there are not enough or more than expected if many + * // messages have the same timestamp. */ #define PACKET_TYPE_SMS_REQUEST_CONVERSATION QStringLiteral("kdeconnect.sms.request_conversation") @@ -161,9 +164,11 @@ public Q_SLOTS: /** * Send a request to the remote for a particular conversation * - * TODO: Make interface capable of requesting limited window of messages + * @param conversationID The conversation to query + * @param rangeStartTimestamp Return messages with timestamp >= this value. Value <= 0 indicates no limit. + * @param numberToRequest Request this many messages. May return more, may return less. Value <= 0 indicates no limit. */ - Q_SCRIPTABLE void requestConversation(const qint64& conversationID) const; + Q_SCRIPTABLE void requestConversation(const qint64 conversationID, const qint64 rangeStartTimestamp = -1, const qint64 numberToRequest = -1) const; Q_SCRIPTABLE void launchApp();