aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--lib/connection.cpp10
-rw-r--r--lib/connection.h2
-rw-r--r--lib/events/roomcanonicalaliasevent.h86
-rw-r--r--lib/events/simplestateevents.h2
-rw-r--r--lib/room.cpp48
5 files changed, 129 insertions, 19 deletions
diff --git a/lib/connection.cpp b/lib/connection.cpp
index 5bddbb83..f3d31d2d 100644
--- a/lib/connection.cpp
+++ b/lib/connection.cpp
@@ -87,7 +87,7 @@ public:
QHash<QPair<QString, bool>, Room*> roomMap;
/// Mapping from serverparts to alias/room id mappings,
/// as of the last sync
- QHash<QString, QHash<QString, QString>> roomAliasMap;
+ QHash<QString, QString> roomAliasMap;
QVector<QString> roomIdsToForget;
QVector<Room*> firstTimeRooms;
QVector<QString> pendingStateRoomIds;
@@ -891,7 +891,7 @@ Room* Connection::room(const QString& roomId, JoinStates states) const
Room* Connection::roomByAlias(const QString& roomAlias, JoinStates states) const
{
- const auto id = d->roomAliasMap.value(serverPart(roomAlias)).value(roomAlias);
+ const auto id = d->roomAliasMap.value(roomAlias);
if (!id.isEmpty())
return room(id, states);
@@ -901,17 +901,15 @@ Room* Connection::roomByAlias(const QString& roomAlias, JoinStates states) const
}
void Connection::updateRoomAliases(const QString& roomId,
- const QString& aliasServer,
const QStringList& previousRoomAliases,
const QStringList& roomAliases)
{
- auto& aliasMap = d->roomAliasMap[aliasServer]; // Allocate if necessary
for (const auto& a : previousRoomAliases)
- if (aliasMap.remove(a) == 0)
+ if (d->roomAliasMap.remove(a) == 0)
qCWarning(MAIN) << "Alias" << a << "is not found (already deleted?)";
for (const auto& a : roomAliases) {
- auto& mappedId = aliasMap[a];
+ auto& mappedId = d->roomAliasMap[a];
if (!mappedId.isEmpty()) {
if (mappedId == roomId)
qCDebug(MAIN)
diff --git a/lib/connection.h b/lib/connection.h
index e4109fd4..c7e18c12 100644
--- a/lib/connection.h
+++ b/lib/connection.h
@@ -294,7 +294,7 @@ public:
/// This is used to maintain the internal index of room aliases.
/// It does NOT change aliases on the server,
/// \sa Room::setLocalAliases
- void updateRoomAliases(const QString& roomId, const QString& aliasServer,
+ void updateRoomAliases(const QString& roomId,
const QStringList& previousRoomAliases,
const QStringList& roomAliases);
Q_INVOKABLE Quotient::Room* invitation(const QString& roomId) const;
diff --git a/lib/events/roomcanonicalaliasevent.h b/lib/events/roomcanonicalaliasevent.h
new file mode 100644
index 00000000..3f89f639
--- /dev/null
+++ b/lib/events/roomcanonicalaliasevent.h
@@ -0,0 +1,86 @@
+// Contains code for RoomCanonicalAlias Event
+#pragma once
+
+#include "stateevent.h"
+
+namespace Quotient {
+namespace EventContent{
+ template <typename T1, typename T2>
+ class SimpleDualContent {
+ public:
+ using first_value_type = T1;
+ using second_value_type = T2;
+
+ template <typename TT1, typename TT2>
+ SimpleDualContent(QString Key1Name, TT1&& value1, QString Key2Name,
+ TT2&& value2)
+ : value1(std::forward<TT1>(value1))
+ , value2(std::forward<TT2>(value2))
+ , key1(std::move(Key1Name))
+ , key2(std::move(Key2Name))
+ { }
+
+ SimpleDualContent(const QJsonObject& json, QString key1Name,
+ QString key2Name)
+ : value1(fromJson<T1>(json[key1Name]))
+ , value2(fromJson<T2>(json[key2Name]))
+ , key1(std::move(key1Name))
+ , key2(std::move(key2Name))
+ { }
+
+ QJsonObject toJson() const
+ {
+ return { { key1, Quotient::toJson(value1) },
+ { key2, Quotient::toJson(value2) } };
+ }
+
+ public:
+ T1 value1;
+ T2 value2;
+
+ protected:
+ QString key1;
+ QString key2;
+ };
+} // namespace EventContent
+
+class RoomCanonicalAliasEvent
+ : public StateEvent<EventContent::SimpleDualContent<QString, QStringList>> {
+public:
+ DEFINE_EVENT_TYPEID("m.room.canonical_alias", RoomCanonicalAliasEvent)
+
+ explicit RoomCanonicalAliasEvent(const QJsonObject& obj)
+ : StateEvent(typeId(), obj, QStringLiteral("alias"),
+ QStringLiteral("alt_aliases"))
+ { }
+
+ RoomCanonicalAliasEvent(const QString& server, const QString& alias,
+ const QStringList& alt_aliases)
+ : StateEvent(typeId(), matrixTypeId(), server, QStringLiteral("alias"),
+ alias, QStringLiteral("alt_aliases"), alt_aliases)
+ { }
+
+ // For compatibility used at Room::setCanonicalAlias
+ explicit RoomCanonicalAliasEvent(const QString& value1)
+ : RoomCanonicalAliasEvent(value1, QStringList())
+ { }
+
+ // Because, MSC2432 specifies, that alt_aliases may be present
+ // without aliases as well
+ explicit RoomCanonicalAliasEvent(const QStringList& value2)
+ : RoomCanonicalAliasEvent(QString(), value2)
+ { }
+
+ template <typename T1, typename T2>
+ RoomCanonicalAliasEvent(T1&& value1, T2&& value2)
+ : StateEvent(typeId(), matrixTypeId(), QString(),
+ QStringLiteral("alias"), std::forward<T1>(value1),
+ QStringLiteral("alt_aliases"), std::forward<T2>(value2))
+ { }
+
+ QString alias() const { return content().value1; }
+
+ QStringList alt_aliases() const { return content().value2; }
+};
+REGISTER_EVENT_TYPE(RoomCanonicalAliasEvent)
+} // namespace Quotient \ No newline at end of file
diff --git a/lib/events/simplestateevents.h b/lib/events/simplestateevents.h
index eb1d2f7a..cde5b0fd 100644
--- a/lib/events/simplestateevents.h
+++ b/lib/events/simplestateevents.h
@@ -69,8 +69,6 @@ namespace EventContent {
// End of macro
DEFINE_SIMPLE_STATE_EVENT(RoomNameEvent, "m.room.name", QString, name)
-DEFINE_SIMPLE_STATE_EVENT(RoomCanonicalAliasEvent, "m.room.canonical_alias",
- QString, alias)
DEFINE_SIMPLE_STATE_EVENT(RoomTopicEvent, "m.room.topic", QString, topic)
class RoomAliasesEvent
diff --git a/lib/room.cpp b/lib/room.cpp
index b29f6f48..475c6570 100644
--- a/lib/room.cpp
+++ b/lib/room.cpp
@@ -56,6 +56,7 @@
#include "jobs/downloadfilejob.h"
#include "jobs/mediathumbnailjob.h"
#include "jobs/postreadmarkersjob.h"
+#include "events/roomcanonicalaliasevent.h"
#include <QtCore/QDir>
#include <QtCore/QHash>
@@ -107,6 +108,7 @@ public:
QHash<StateEventKey, const StateEventBase*> currentState;
/// Servers with aliases for this room except the one of the local user
/// \sa Room::remoteAliases
+ // This may not be required anymore
QSet<QString> aliasServers;
Timeline timeline;
@@ -432,12 +434,13 @@ QString Room::name() const
QStringList Room::localAliases() const
{
- return d
- ->getCurrentState<RoomAliasesEvent>(
- connection()->domain())
- ->aliases();
+ QStringList result(d
+ ->getCurrentState<RoomCanonicalAliasEvent>()->alias());
+ result += d->getCurrentState<RoomCanonicalAliasEvent>()->alt_aliases();
+ return result;
}
+// Not sure about this function, maybe it is no more required
QStringList Room::remoteAliases() const
{
QStringList result;
@@ -1697,8 +1700,7 @@ void Room::setCanonicalAlias(const QString& newAlias)
void Room::setLocalAliases(const QStringList& aliases)
{
- d->requestSetState<RoomAliasesEvent>(connection()->homeserver().authority(),
- aliases);
+ d->requestSetState<RoomCanonicalAliasEvent>(aliases);
}
void Room::setTopic(const QString& newTopic)
@@ -2368,14 +2370,40 @@ Room::Changes Room::processStateEvent(const RoomEvent& e)
oldStateEvent
? static_cast<const RoomAliasesEvent*>(oldStateEvent)->aliases()
: QStringList();
- connection()->updateRoomAliases(id(), ae.stateKey(),
- previousAliases, ae.aliases());
+ connection()->updateRoomAliases(id(), previousAliases, ae.aliases());
return OtherChange;
// clang-format off
}
- , [this] (const RoomCanonicalAliasEvent& evt) {
- setObjectName(evt.alias().isEmpty() ? d->id : evt.alias());
+ , [this, oldStateEvent] (const RoomCanonicalAliasEvent& cae) {
+ // clang-format on
+ setObjectName(cae.alias().isEmpty() ? d->id : cae.alias());
+ QString previousCanonicalAlias =
+ oldStateEvent
+ ? static_cast<const RoomCanonicalAliasEvent*>(oldStateEvent)
+ ->alias()
+ : QString();
+
+ auto previousAltAliases =
+ oldStateEvent
+ ? static_cast<const RoomCanonicalAliasEvent*>(oldStateEvent)
+ ->alt_aliases()
+ : QStringList();
+
+ if (!previousCanonicalAlias.isEmpty()) {
+ previousAltAliases.push_back(previousCanonicalAlias);
+ }
+
+ const auto previousAliases = std::move(previousAltAliases);
+
+ auto newAliases = cae.alt_aliases();
+
+ if (!cae.alias().isEmpty()) {
+ newAliases.push_front(cae.alias());
+ }
+
+ connection()->updateRoomAliases(id(), previousAliases, newAliases);
return CanonicalAliasChange;
+ // clang-format off
}
, [] (const RoomTopicEvent&) {
return TopicChange;