MAM fixes

- don't send first request for timestamp -60
- only open conversation for messages within last 24h
- always show latest message in conversation tabs
This commit is contained in:
fiaxh 2017-08-18 00:46:40 +02:00
parent 299f52df3a
commit dff8e08669
4 changed files with 36 additions and 25 deletions

View file

@ -27,7 +27,7 @@ public class ConversationManager : StreamInteractionModule, Object {
stream_interactor.add_module(this);
stream_interactor.account_added.connect(on_account_added);
stream_interactor.get_module(MucManager.IDENTITY).joined.connect(on_groupchat_joined);
stream_interactor.get_module(MessageProcessor.IDENTITY).pre_message_received.connect(on_message_received);
stream_interactor.get_module(MessageProcessor.IDENTITY).message_received.connect(on_message_received);
stream_interactor.get_module(MessageProcessor.IDENTITY).message_sent.connect(on_message_sent);
}
@ -107,7 +107,7 @@ public class ConversationManager : StreamInteractionModule, Object {
}
}
private void on_message_received(Entities.Message message, Xmpp.Message.Stanza message_stanza, Conversation conversation) {
private void on_message_received(Entities.Message message, Conversation conversation) {
conversation.last_active = message.time;
start_conversation(conversation);
}
@ -129,4 +129,4 @@ public class ConversationManager : StreamInteractionModule, Object {
}
}
}
}

View file

@ -45,7 +45,8 @@ public class MessageProcessor : StreamInteractionModule, Object {
on_message_received(account, message);
});
stream_interactor.module_manager.get_module(account, Xmpp.Xep.MessageArchiveManagement.Module.IDENTITY).feature_available.connect( (stream) => {
stream.get_module(Xep.MessageArchiveManagement.Module.IDENTITY).query_archive(stream, null, account.mam_earliest_synced.add_minutes(-1), null);
DateTime start_time = account.mam_earliest_synced.to_unix() > 60 ? account.mam_earliest_synced.add_minutes(-1) : account.mam_earliest_synced;
stream.get_module(Xep.MessageArchiveManagement.Module.IDENTITY).query_archive(stream, null, start_time, null);
});
}
@ -102,15 +103,21 @@ public class MessageProcessor : StreamInteractionModule, Object {
if ((is_uuid && !db.contains_message_by_stanza_id(new_message.stanza_id, conversation.account)) ||
(!is_uuid && !db.contains_message(new_message, conversation.account))) {
stream_interactor.get_module(MessageStorage.IDENTITY).add_message(new_message, conversation);
if (new_message.direction == Entities.Message.DIRECTION_SENT) {
message_sent(new_message, conversation);
} else {
message_received(new_message, conversation);
bool is_mam_message = Xep.MessageArchiveManagement.MessageFlag.get_flag(stanza) != null;
bool is_recent = new_message.local_time.compare(new DateTime.now_utc().add_hours(-24)) > 0;
if (!is_mam_message || is_recent) {
print(new_message.local_time.to_string() + "\n");
if (new_message.direction == Entities.Message.DIRECTION_SENT) {
message_sent(new_message, conversation);
} else {
message_received(new_message, conversation);
}
}
Core.XmppStream? stream = stream_interactor.get_stream(conversation.account);
Xep.MessageArchiveManagement.Flag? mam_flag = stream != null ? stream.get_flag(Xep.MessageArchiveManagement.Flag.IDENTITY) : null;
if (Xep.MessageArchiveManagement.MessageFlag.get_flag(stanza) != null || (mam_flag != null && mam_flag.cought_up == true)) {
if (is_mam_message || (mam_flag != null && mam_flag.cought_up == true)) {
conversation.account.mam_earliest_synced = new_message.local_time;
}
}

View file

@ -11,7 +11,7 @@ public class MessageStorage : StreamInteractionModule, Object {
private StreamInteractor stream_interactor;
private Database db;
private HashMap<Conversation, Gee.List<Message>> messages = new HashMap<Conversation, Gee.List<Entities.Message>>(Conversation.hash_func, Conversation.equals_func);
private HashMap<Conversation, Gee.TreeSet<Message>> messages = new HashMap<Conversation, Gee.TreeSet<Message>>(Conversation.hash_func, Conversation.equals_func);
public static void start(StreamInteractor stream_interactor, Database db) {
MessageStorage m = new MessageStorage(stream_interactor, db);
@ -31,16 +31,18 @@ public class MessageStorage : StreamInteractionModule, Object {
public Gee.List<Message> get_messages(Conversation conversation, int count = 50) {
init_conversation(conversation);
if (messages[conversation].size > 0) {
return messages[conversation][int.max(messages[conversation].size - count - 1, 0) : messages[conversation].size];
Gee.List<Message> ret = new ArrayList<Message>(Message.equals_func);
foreach (Message message in messages[conversation]) {
if (ret.size >= count) break;
ret.add(message);
}
return new ArrayList<Message>();
return ret;
}
public Message? get_last_message(Conversation conversation) {
init_conversation(conversation);
if (messages[conversation].size > 0) {
return messages[conversation][messages[conversation].size - 1];
return messages[conversation].first();
}
return null;
}
@ -52,17 +54,19 @@ public class MessageStorage : StreamInteractionModule, Object {
public Message? get_message_by_id(string stanza_id, Conversation conversation) {
init_conversation(conversation);
for (int i = messages[conversation].size - 1; i > 0; i--) {
if (messages[conversation][i].stanza_id == stanza_id) return messages[conversation][i];
foreach (Message message in messages[conversation]) {
if (message.stanza_id == stanza_id) return message;
}
return null;
}
private void init_conversation(Conversation conversation) {
if (!messages.has_key(conversation)) {
messages[conversation] = db.get_messages(conversation.counterpart, conversation.account, Util.get_message_type_for_conversation(conversation), 50, null);
messages[conversation] = new Gee.TreeSet<Message>((a, b) => { return -1 * a.local_time.compare(b.local_time); });
Gee.List<Message> db_messages = db.get_messages(conversation.counterpart, conversation.account, Util.get_message_type_for_conversation(conversation), 50, null);
messages[conversation].add_all(db_messages);
}
}
}
}
}

View file

@ -45,19 +45,19 @@ public abstract class ConversationRow : ListBoxRow {
x_button.clicked.connect(on_x_button_clicked);
update_name(Util.get_conversation_display_name(stream_interactor, conversation));
Entities.Message message = stream_interactor.get_module(MessageStorage.IDENTITY).get_last_message(conversation);
if (message != null) {
message_received(message);
}
message_received();
}
public void update() {
update_time();
}
public void message_received(Entities.Message message) {
update_message(message.body.replace("\n", " "));
update_time(message.time.to_local());
public void message_received(Entities.Message? m = null) {
Entities.Message? message = stream_interactor.get_module(MessageStorage.IDENTITY).get_last_message(conversation);
if (message != null) {
update_message(message.body.replace("\n", " "));
update_time(message.time.to_local());
}
}
public void set_avatar(Pixbuf pixbuf, int scale_factor = 1) {