From 0b9767651bd28b0570f49b97b5e8185e56014ce4 Mon Sep 17 00:00:00 2001 From: Antonio Scandurra Date: Fri, 20 Aug 2021 14:44:36 +0200 Subject: [PATCH] Provide a consistent ordering for channel messages based on their ID Co-Authored-By: Nathan Sobo --- zed/src/channel.rs | 33 ++++++++++++++++++++++++++------- 1 file changed, 26 insertions(+), 7 deletions(-) diff --git a/zed/src/channel.rs b/zed/src/channel.rs index 0ce147113c..fe683b728c 100644 --- a/zed/src/channel.rs +++ b/zed/src/channel.rs @@ -7,7 +7,8 @@ use gpui::{ AsyncAppContext, Entity, ModelContext, ModelHandle, MutableAppContext, WeakModelHandle, }; use std::{ - collections::{hash_map, HashMap, VecDeque}, + cmp::Ordering, + collections::{hash_map, BTreeSet, HashMap}, sync::Arc, }; use zrpc::{ @@ -29,8 +30,7 @@ pub struct ChannelDetails { pub struct Channel { details: ChannelDetails, - first_message_id: Option, - messages: VecDeque, + messages: BTreeSet, pending_messages: Vec, next_local_message_id: u64, rpc: Arc, @@ -135,7 +135,6 @@ impl Channel { Self { details, rpc, - first_message_id: None, messages: Default::default(), pending_messages: Default::default(), next_local_message_id: 0, @@ -163,7 +162,7 @@ impl Channel { .binary_search_by_key(&local_id, |msg| msg.local_id) { let body = this.pending_messages.remove(i).body; - this.messages.push_back(ChannelMessage { + this.messages.insert(ChannelMessage { id: response.message_id, sender_id: current_user_id, body, @@ -178,7 +177,7 @@ impl Channel { Ok(()) } - pub fn messages(&self) -> &VecDeque { + pub fn messages(&self) -> &BTreeSet { &self.messages } @@ -200,7 +199,7 @@ impl Channel { .payload .message .ok_or_else(|| anyhow!("empty message"))?; - self.messages.push_back(message.into()); + self.messages.insert(message.into()); cx.notify(); Ok(()) } @@ -224,3 +223,23 @@ impl From for ChannelMessage { } } } + +impl PartialOrd for ChannelMessage { + fn partial_cmp(&self, other: &Self) -> Option { + Some(self.cmp(other)) + } +} + +impl Ord for ChannelMessage { + fn cmp(&self, other: &Self) -> Ordering { + self.id.cmp(&other.id) + } +} + +impl PartialEq for ChannelMessage { + fn eq(&self, other: &Self) -> bool { + self.id == other.id + } +} + +impl Eq for ChannelMessage {}