aboutsummaryrefslogtreecommitdiff
path: root/lib/uriresolver.cpp
diff options
context:
space:
mode:
authorKitsune Ral <Kitsune-Ral@users.sf.net>2020-07-19 16:12:09 +0200
committerKitsune Ral <Kitsune-Ral@users.sf.net>2020-07-19 16:12:09 +0200
commitaf329351289606f3cb1ef865cb0cbe61c1d1711b (patch)
tree41b1f00b496b07e0c1f7ea5d576beb2f52376693 /lib/uriresolver.cpp
parent227d7c0ba26c3eb3e7394e0a5b7cc79544db7515 (diff)
downloadlibquotient-af329351289606f3cb1ef865cb0cbe61c1d1711b.tar.gz
libquotient-af329351289606f3cb1ef865cb0cbe61c1d1711b.zip
MatrixUri->Uri: Extend to non-Matrix URIs
Diffstat (limited to 'lib/uriresolver.cpp')
-rw-r--r--lib/uriresolver.cpp110
1 files changed, 110 insertions, 0 deletions
diff --git a/lib/uriresolver.cpp b/lib/uriresolver.cpp
new file mode 100644
index 00000000..5052890b
--- /dev/null
+++ b/lib/uriresolver.cpp
@@ -0,0 +1,110 @@
+#include "uriresolver.h"
+
+#include "connection.h"
+#include "user.h"
+
+using namespace Quotient;
+
+UriResolveResult UriResolverBase::visitResource(Connection* account,
+ const Uri& uri)
+{
+ switch (uri.type()) {
+ case Uri::NonMatrix:
+ return visitNonMatrix(uri.toUrl()) ? UriResolved : CouldNotResolve;
+ case Uri::Invalid:
+ case Uri::Empty:
+ return InvalidUri;
+ default:;
+ }
+
+ if (!account)
+ return NoAccount;
+
+ switch (uri.type()) {
+ case Uri::UserId: {
+ if (uri.action() == "join")
+ return IncorrectAction;
+ auto* user = account->user(uri.primaryId());
+ Q_ASSERT(user != nullptr);
+ visitUser(user, uri.action());
+ return UriResolved;
+ }
+ case Uri::RoomId:
+ case Uri::RoomAlias: {
+ auto* room = uri.type() == Uri::RoomId
+ ? account->room(uri.primaryId())
+ : account->roomByAlias(uri.primaryId());
+ if (room != nullptr) {
+ visitRoom(room, uri.secondaryId());
+ return UriResolved;
+ }
+ if (uri.action() == "join") {
+ joinRoom(account, uri.primaryId(), uri.viaServers());
+ return UriResolved;
+ }
+ [[fallthrough]];
+ }
+ default:
+ return CouldNotResolve;
+ }
+}
+
+template <typename... FnTs>
+class StaticUriDispatcher : public UriResolverBase {
+public:
+ StaticUriDispatcher(const FnTs&... fns) : fns_(fns...) {}
+
+private:
+ void visitUser(User* user, const QString& action) override
+ {
+ std::get<0>(fns_)(user, action);
+ }
+ void visitRoom(Room* room, const QString& eventId) override
+ {
+ std::get<1>(fns_)(room, eventId);
+ }
+ void joinRoom(Connection* account, const QString& roomAliasOrId,
+ const QStringList& viaServers = {}) override
+ {
+ std::get<2>(fns_)(account, roomAliasOrId, viaServers);
+ }
+ bool visitNonMatrix(const QUrl& url) override
+ {
+ return std::get<3>(fns_)(url);
+ }
+
+ std::tuple<FnTs...> fns_;
+};
+
+UriResolveResult Quotient::visitResource(
+ Connection* account, const Uri& uri,
+ std::function<void(User*, QString)> userHandler,
+ std::function<void(Room*, QString)> roomEventHandler,
+ std::function<void(Connection*, QString, QStringList)> joinHandler,
+ std::function<bool(const QUrl&)> nonMatrixHandler)
+{
+ return StaticUriDispatcher(userHandler, roomEventHandler, joinHandler,
+ nonMatrixHandler)
+ .visitResource(account, uri);
+}
+
+void UriDispatcher::visitUser(User *user, const QString &action)
+{
+ emit userAction(user, action);
+}
+
+void UriDispatcher::visitRoom(Room *room, const QString &eventId)
+{
+ emit roomAction(room, eventId);
+}
+
+void UriDispatcher::joinRoom(Connection *account, const QString &roomAliasOrId, const QStringList &viaServers)
+{
+ emit joinAction(account, roomAliasOrId, viaServers);
+}
+
+bool UriDispatcher::visitNonMatrix(const QUrl &url)
+{
+ emit nonMatrixAction(url);
+ return true;
+}