diff options
| author | Linus Jahn <lnj@kaidan.im> | 2022-04-07 16:22:34 +0200 |
|---|---|---|
| committer | Linus Jahn <lnj@kaidan.im> | 2022-05-20 17:27:13 +0200 |
| commit | 62e2248c30d72ff9c8e2a9acc265d8c39f3c83ca (patch) | |
| tree | 1281cfa9d4d2363c569ccac9ee8718e13afaf4d6 /src/client | |
| parent | f10146c7b298ef0cb04794452b0807c2b7a6910d (diff) | |
| download | qxmpp-62e2248c30d72ff9c8e2a9acc265d8c39f3c83ca.tar.gz | |
Add MessageHandler interface
Diffstat (limited to 'src/client')
| -rw-r--r-- | src/client/QXmppClient.cpp | 43 | ||||
| -rw-r--r-- | src/client/QXmppClient.h | 1 | ||||
| -rw-r--r-- | src/client/QXmppClientExtension.cpp | 13 | ||||
| -rw-r--r-- | src/client/QXmppClientExtension.h | 2 | ||||
| -rw-r--r-- | src/client/QXmppMessageHandler.cpp | 19 | ||||
| -rw-r--r-- | src/client/QXmppMessageHandler.h | 21 |
6 files changed, 98 insertions, 1 deletions
diff --git a/src/client/QXmppClient.cpp b/src/client/QXmppClient.cpp index a90fafed..104d94e4 100644 --- a/src/client/QXmppClient.cpp +++ b/src/client/QXmppClient.cpp @@ -14,6 +14,7 @@ #include "QXmppFutureUtils_p.h" #include "QXmppLogger.h" #include "QXmppMessage.h" +#include "QXmppMessageHandler.h" #include "QXmppOutgoingClient.h" #include "QXmppPacket_p.h" #include "QXmppRosterManager.h" @@ -126,6 +127,32 @@ bool process(const QList<QXmppClientExtension *> &extensions, const QDomElement } +namespace QXmpp::Private::MessagePipeline { + +bool process(QXmppClient *client, const QList<QXmppClientExtension *> &extensions, QXmppMessage &&message) +{ + for (auto *extension : extensions) { + if (auto *messageHandler = dynamic_cast<QXmppMessageHandler *>(extension)) { + if (messageHandler->handleMessage(message)) { + return true; + } + } + } + return false; +} + +bool process(QXmppClient *client, const QList<QXmppClientExtension *> &extensions, const QDomElement &element) +{ + if (element.tagName() != "message") { + return false; + } + QXmppMessage message; + message.parse(element); + return process(client, extensions, std::move(message)); +} + +} + /// /// \typedef QXmppClient::IqResult /// @@ -808,13 +835,27 @@ void QXmppClient::injectIq(const QDomElement &element, const std::optional<QXmpp } /// +/// Processes the message with message handlers and emits messageReceived as a fallback. +/// +bool QXmppClient::injectMessage(QXmppMessage &&message) +{ + auto handled = MessagePipeline::process(this, d->extensions, std::move(message)); + if (!handled) { + // no extension handled the message + emit messageReceived(message); + } + return handled; +} + +/// /// Give extensions a chance to handle incoming stanzas. /// void QXmppClient::_q_elementReceived(const QDomElement &element, bool &handled) { // The stanza comes directly from the XMPP stream, so it's not end-to-end // encrypted and there's no e2ee metadata (std::nullopt). - handled = StanzaPipeline::process(d->extensions, element, std::nullopt); + handled = StanzaPipeline::process(d->extensions, element, std::nullopt) || + MessagePipeline::process(this, d->extensions, element); } void QXmppClient::_q_reconnect() diff --git a/src/client/QXmppClient.h b/src/client/QXmppClient.h index 47b71706..82ac7d7b 100644 --- a/src/client/QXmppClient.h +++ b/src/client/QXmppClient.h @@ -309,6 +309,7 @@ public Q_SLOTS: private: void injectIq(const QDomElement &element, const std::optional<QXmppE2eeMetadata> &e2eeMetadata); + bool injectMessage(QXmppMessage &&message); private Q_SLOTS: void _q_elementReceived(const QDomElement &element, bool &handled); diff --git a/src/client/QXmppClientExtension.cpp b/src/client/QXmppClientExtension.cpp index 67f79889..f71e9163 100644 --- a/src/client/QXmppClientExtension.cpp +++ b/src/client/QXmppClientExtension.cpp @@ -119,3 +119,16 @@ void QXmppClientExtension::injectIq(const QDomElement &element, const std::optio { client()->injectIq(element, e2eeMetadata); } + +/// +/// Injects a message stanza into the client. +/// +/// The stanza is processed by the client with all extensions implementing +/// MessageHandler. +/// +/// \since QXmpp 1.5 +/// +bool QXmppClientExtension::injectMessage(QXmppMessage &&message) +{ + return client()->injectMessage(std::move(message)); +} diff --git a/src/client/QXmppClientExtension.h b/src/client/QXmppClientExtension.h index 3ba348d9..6dd1607a 100644 --- a/src/client/QXmppClientExtension.h +++ b/src/client/QXmppClientExtension.h @@ -13,6 +13,7 @@ class QDomElement; class QXmppClient; class QXmppClientExtensionPrivate; +class QXmppMessage; class QXmppStream; /// @@ -45,6 +46,7 @@ protected: virtual void setClient(QXmppClient *client); void injectIq(const QDomElement &element, const std::optional<QXmppE2eeMetadata> &e2eeMetadata); + bool injectMessage(QXmppMessage &&message); private: QXmppClientExtensionPrivate *const d; diff --git a/src/client/QXmppMessageHandler.cpp b/src/client/QXmppMessageHandler.cpp new file mode 100644 index 00000000..b6e4505c --- /dev/null +++ b/src/client/QXmppMessageHandler.cpp @@ -0,0 +1,19 @@ +// SPDX-FileCopyrightText: 2022 Linus Jahn <lnj@kaidan.im> +// +// SPDX-License-Identifier: LGPL-2.1-or-later + +/// +/// \class QXmppMessageHandler +/// +/// Interface for handling messages. +/// +/// \since QXmpp 1.5 +/// + +/// +/// \fn QXmppMessageHandler::handleMessage() +/// +/// Handles the message. +/// +/// \returns Whether the message has been handled and no other extensions should process it. +/// diff --git a/src/client/QXmppMessageHandler.h b/src/client/QXmppMessageHandler.h new file mode 100644 index 00000000..2335e56e --- /dev/null +++ b/src/client/QXmppMessageHandler.h @@ -0,0 +1,21 @@ +// SPDX-FileCopyrightText: 2022 Linus Jahn <lnj@kaidan.im> +// +// SPDX-License-Identifier: LGPL-2.1-or-later + +#ifndef QXMPPMESSAGEHANDLER_H +#define QXMPPMESSAGEHANDLER_H + +#include "QXmppExtension.h" +#include "QXmppMessage.h" + +#include <variant> + +#include <QFuture> + +class QXMPP_EXPORT QXmppMessageHandler : public QXmppExtension +{ +public: + virtual bool handleMessage(const QXmppMessage &) = 0; +}; + +#endif // QXMPPMESSAGEHANDLER_H |
