aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authordec05eba <dec05eba@protonmail.com>2020-11-01 13:24:16 +0100
committerdec05eba <dec05eba@protonmail.com>2020-11-01 13:24:16 +0100
commit13935702620305c5baaf6403417cc75a9b706fea (patch)
treece603c498c69b3d8bc88f944d016961689df7856
parent7292fe11254109266e7adb9937e5f0fa797711f6 (diff)
Matrix: create room immediately after receiving join response, instead of waiting for join sync message
-rw-r--r--TODO4
-rw-r--r--plugins/Matrix.hpp7
-rw-r--r--src/plugins/Matrix.cpp61
3 files changed, 60 insertions, 12 deletions
diff --git a/TODO b/TODO
index cb6624e..29f426c 100644
--- a/TODO
+++ b/TODO
@@ -130,4 +130,6 @@ Show marker beside pinned messages tab name if there are new pinned messages.
Make /logout work everywhere, not only in room message input.
Add a notifications tab to show messages that mention us in all rooms (and then press enter to go to that message in that room).
Disable message input in matrix when muted.
-Preview rooms? \ No newline at end of file
+Preview rooms?
+Instantly show messages posted by me until we receive our message from the server (use post response which includes event id).
+Get user displayname, avatar, room name, etc updates from /sync and update them in gui. \ No newline at end of file
diff --git a/plugins/Matrix.hpp b/plugins/Matrix.hpp
index 3d3c4b2..6a876d0 100644
--- a/plugins/Matrix.hpp
+++ b/plugins/Matrix.hpp
@@ -423,11 +423,14 @@ namespace QuickMedia {
PluginResult upload_file(RoomData *room, const std::string &filepath, UploadInfo &file_info, UploadInfo &thumbnail_info, std::string &err_msg);
void add_room(std::unique_ptr<RoomData> room);
void remove_room(const std::string &room_id);
+ void set_invite(const std::string &room_id, Invite invite);
+ // Returns true if an invite for |room_id| exists
+ bool remove_invite(const std::string &room_id);
DownloadResult download_json(rapidjson::Document &result, const std::string &url, std::vector<CommandArg> additional_args, bool use_browser_useragent = false, std::string *err_msg = nullptr) const;
private:
std::vector<std::unique_ptr<RoomData>> rooms;
std::unordered_map<std::string, size_t> room_data_by_id; // value is an index into |rooms|
- std::mutex room_data_mutex;
+ std::recursive_mutex room_data_mutex;
std::string user_id;
std::string username;
std::string access_token;
@@ -436,8 +439,10 @@ namespace QuickMedia {
std::string next_batch;
std::unordered_map<std::string, Invite> invites;
+ std::mutex invite_mutex;
std::thread sync_thread;
bool sync_running = false;
+ MatrixDelegate *delegate = nullptr;
};
} \ No newline at end of file
diff --git a/src/plugins/Matrix.cpp b/src/plugins/Matrix.cpp
index b8c2f89..d143e9a 100644
--- a/src/plugins/Matrix.cpp
+++ b/src/plugins/Matrix.cpp
@@ -641,6 +641,9 @@ namespace QuickMedia {
if(sync_running)
return;
+ assert(!this->delegate);
+ this->delegate = delegate;
+
sync_running = true;
sync_thread = std::thread([this, delegate]() {
const rapidjson::Value *next_batch_json;
@@ -690,6 +693,7 @@ namespace QuickMedia {
program_kill_in_thread(sync_thread.get_id());
if(sync_thread.joinable())
sync_thread.join();
+ delegate = nullptr;
}
bool Matrix::is_initial_sync_finished() const {
@@ -871,11 +875,9 @@ namespace QuickMedia {
}
}
- auto invites_it = invites.find(room_id_str);
- if(invites_it != invites.end()) {
+ if(remove_invite(room_id_str)) {
// TODO: Show leave type and reason and who caused the invite to be removed
delegate->remove_invite(room_id_str);
- invites.erase(invites_it);
}
if(is_new_room)
@@ -1597,7 +1599,7 @@ namespace QuickMedia {
std::string room_id_str(room_id.GetString(), room_id.GetStringLength());
delegate->add_invite(room_id_str, invite);
- invites[room_id_str] = std::move(invite);
+ set_invite(room_id_str, std::move(invite));
break;
}
}
@@ -1617,11 +1619,9 @@ namespace QuickMedia {
continue;
std::string room_id_str(room_id.GetString(), room_id.GetStringLength());
- auto invites_it = invites.find(room_id_str);
- if(invites_it != invites.end()) {
+ if(remove_invite(room_id_str)) {
// TODO: Show leave type and reason and who caused the invite to be removed
delegate->remove_invite(room_id_str);
- invites.erase(invites_it);
}
const rapidjson::Value &timeline_json = GetMember(it.value, "timeline");
@@ -2532,6 +2532,7 @@ namespace QuickMedia {
}
PluginResult Matrix::join_room(const std::string &room_id) {
+ assert(delegate);
std::vector<CommandArg> additional_args = {
{ "-X", "POST" },
{ "-H", "content-type: application/json" },
@@ -2541,6 +2542,31 @@ namespace QuickMedia {
std::string server_response;
DownloadResult download_result = download_to_string(homeserver + "/_matrix/client/r0/join/" + room_id, server_response, std::move(additional_args), use_tor, true);
+ if(download_result == DownloadResult::OK) {
+ std::lock_guard<std::mutex> invite_lock(invite_mutex);
+ auto invite_it = invites.find(room_id);
+ if(invite_it != invites.end()) {
+ std::lock_guard<std::recursive_mutex> lock(room_data_mutex);
+ RoomData *room = get_room_by_id(room_id);
+ if(!room) {
+ auto new_room = std::make_unique<RoomData>();
+ new_room->id = room_id;
+ new_room->set_name(invite_it->second.room_name);
+ new_room->set_avatar_url(invite_it->second.room_avatar_url);
+ room = new_room.get();
+ add_room(std::move(new_room));
+
+ delegate->join_room(room);
+ room->acquire_room_lock();
+ std::set<std::string> &room_tags = room->get_tags_unsafe();
+ if(room_tags.empty()) {
+ room_tags.insert(OTHERS_ROOM_TAG);
+ delegate->room_add_tag(room, OTHERS_ROOM_TAG);
+ }
+ room->release_room_lock();
+ }
+ }
+ }
return download_result_to_plugin_result(download_result);
}
@@ -2604,7 +2630,7 @@ namespace QuickMedia {
}
RoomData* Matrix::get_room_by_id(const std::string &id) {
- std::lock_guard<std::mutex> lock(room_data_mutex);
+ std::lock_guard<std::recursive_mutex> lock(room_data_mutex);
auto room_it = room_data_by_id.find(id);
if(room_it == room_data_by_id.end())
return nullptr;
@@ -2612,14 +2638,14 @@ namespace QuickMedia {
}
void Matrix::add_room(std::unique_ptr<RoomData> room) {
- std::lock_guard<std::mutex> lock(room_data_mutex);
+ std::lock_guard<std::recursive_mutex> lock(room_data_mutex);
room->index = rooms.size();
room_data_by_id.insert(std::make_pair(room->id, room->index));
rooms.push_back(std::move(room));
}
void Matrix::remove_room(const std::string &room_id) {
- std::lock_guard<std::mutex> lock(room_data_mutex);
+ std::lock_guard<std::recursive_mutex> lock(room_data_mutex);
auto room_it = room_data_by_id.find(room_id);
if(room_it == room_data_by_id.end())
return;
@@ -2630,6 +2656,21 @@ namespace QuickMedia {
room_data_by_id.erase(room_it);
}
+ void Matrix::set_invite(const std::string &room_id, Invite invite) {
+ std::lock_guard<std::mutex> lock(invite_mutex);
+ invites[room_id] = std::move(invite);
+ }
+
+ bool Matrix::remove_invite(const std::string &room_id) {
+ std::lock_guard<std::mutex> lock(invite_mutex);
+ auto invites_it = invites.find(room_id);
+ if(invites_it != invites.end()) {
+ invites.erase(invites_it);
+ return true;
+ }
+ return false;
+ }
+
DownloadResult Matrix::download_json(rapidjson::Document &result, const std::string &url, std::vector<CommandArg> additional_args, bool use_browser_useragent, std::string *err_msg) const {
if(download_to_json(url, result, std::move(additional_args), use_tor, use_browser_useragent, err_msg == nullptr) != DownloadResult::OK) {
// Cant get error since we parse directory to json. TODO: Make this work somehow?