Ignore conversation updates that arrive soon after marking as spam

Apparently there are race conditions in the gmessages app where it may
send a `SPAM_FOLDER` update and then `ACTIVE` immediately afterwards.
This commit is contained in:
Tulir Asokan 2024-04-16 15:48:00 +03:00
parent accd12a7aa
commit d0a8b8406c
2 changed files with 7 additions and 0 deletions

View file

@ -288,6 +288,7 @@ type Portal struct {
matrixMessages chan PortalMatrixMessage matrixMessages chan PortalMatrixMessage
cancelCreation atomic.Pointer[context.CancelCauseFunc] cancelCreation atomic.Pointer[context.CancelCauseFunc]
markedSpamAt time.Time
} }
var ( var (

View file

@ -1119,6 +1119,9 @@ func (user *User) syncConversation(v *gmproto.Conversation, source string) {
Logger() Logger()
log.Debug().Any("conversation_data", convCopy).Msg("Got conversation update") log.Debug().Any("conversation_data", convCopy).Msg("Got conversation update")
ctx := log.WithContext(context.TODO()) ctx := log.WithContext(context.TODO())
if updateType == gmproto.ConversationStatus_SPAM_FOLDER || updateType == gmproto.ConversationStatus_BLOCKED_FOLDER {
portal.markedSpamAt = time.Now()
}
if cancel := portal.cancelCreation.Load(); cancel != nil { if cancel := portal.cancelCreation.Load(); cancel != nil {
if updateType == gmproto.ConversationStatus_SPAM_FOLDER || updateType == gmproto.ConversationStatus_BLOCKED_FOLDER { if updateType == gmproto.ConversationStatus_SPAM_FOLDER || updateType == gmproto.ConversationStatus_BLOCKED_FOLDER {
(*cancel)(fmt.Errorf("conversation was moved to spam")) (*cancel)(fmt.Errorf("conversation was moved to spam"))
@ -1161,6 +1164,9 @@ func (user *User) syncConversation(v *gmproto.Conversation, source string) {
if v.Participants == nil { if v.Participants == nil {
log.Debug().Msg("Not syncing conversation with nil participants") log.Debug().Msg("Not syncing conversation with nil participants")
return return
} else if time.Since(portal.markedSpamAt) < 1*time.Minute {
log.Warn().Msg("Dropping conversation update due to suspected race condition")
return
} }
if source == "event" { if source == "event" {
go func() { go func() {