fix: notify recipients for forwarded messages

This commit is contained in:
richjohnrambo
2026-09-23 15:18:27 +08:00
parent 134ac8580e
commit 7d4bc4d049
2 changed files with 141 additions and 5 deletions
+84 -5
View File
@@ -26,6 +26,7 @@ import (
"github.com/tinode/chat/server/logs"
"github.com/tinode/chat/server/media"
"github.com/tinode/chat/server/moderation"
"github.com/tinode/chat/server/push"
realnamealiyun "github.com/tinode/chat/server/realname/aliyun"
"github.com/tinode/chat/server/store"
"github.com/tinode/chat/server/store/types"
@@ -2761,6 +2762,10 @@ func serveIMFavoriteForward(wrt http.ResponseWriter, req *http.Request) {
results = append(results, result)
continue
}
msg.SeqId = saved.SeqId
if !saved.Duplicate {
broadcastHTTPForwardMessage(principal.TenantID, msg, saved.MarkedReadBySender)
}
result := map[string]any{"target_topic": target, "favorite_id": favoriteID, "status": "sent", "seq": saved.SeqId, "client_mid": clientMid}
mergeForwardCommentResult(result, commentResult)
results = append(results, result)
@@ -2895,7 +2900,9 @@ func serveIMMessageForward(wrt http.ResponseWriter, req *http.Request) {
continue
}
forwarded.SeqId = saved.SeqId
broadcastHTTPForwardMessage(principal.TenantID, forwarded)
if !saved.Duplicate {
broadcastHTTPForwardMessage(principal.TenantID, forwarded, saved.MarkedReadBySender)
}
item := map[string]any{
"sources": bundle["source_refs"],
"target_topic": target,
@@ -2986,7 +2993,9 @@ func serveIMMessageForward(wrt http.ResponseWriter, req *http.Request) {
continue
}
forwarded.SeqId = saved.SeqId
broadcastHTTPForwardMessage(principal.TenantID, forwarded)
if !saved.Duplicate {
broadcastHTTPForwardMessage(principal.TenantID, forwarded, saved.MarkedReadBySender)
}
item := map[string]any{
"source": map[string]any{"topic": sourceTopic, "seq": int64(source.Seq)},
"target_topic": target,
@@ -5374,7 +5383,9 @@ func publishGroupAnnouncementTextMessage(ctx context.Context, tenantID types.Ten
if saved != nil && saved.SeqId > 0 {
msg.SeqId = saved.SeqId
}
broadcastHTTPForwardMessage(tenantID, msg)
if saved == nil || !saved.Duplicate {
broadcastHTTPForwardMessage(tenantID, msg, saved == nil || saved.MarkedReadBySender)
}
return nil
}
@@ -9483,7 +9494,9 @@ func saveForwardCommentMessage(ctx context.Context, principal *imPrincipal, targ
}
if saved != nil {
msg.SeqId = saved.SeqId
broadcastHTTPForwardMessage(principal.TenantID, msg)
if !saved.Duplicate {
broadcastHTTPForwardMessage(principal.TenantID, msg, saved.MarkedReadBySender)
}
result["comment_status"] = "sent"
result["comment_seq"] = saved.SeqId
return result
@@ -9786,7 +9799,7 @@ func prepareHTTPForwardMessage(tenantID types.TenantID, msg *types.Message) erro
return nil
}
func broadcastHTTPForwardMessage(tenantID types.TenantID, msg *types.Message) {
func broadcastHTTPForwardMessage(tenantID types.TenantID, msg *types.Message, markedReadBySender bool) {
if globals.hub == nil || msg == nil || msg.SeqId <= 0 || msg.Topic == "" {
return
}
@@ -9813,6 +9826,7 @@ func broadcastHTTPForwardMessage(tenantID types.TenantID, msg *types.Message) {
logs.Warn.Printf("im message forward: hub route queue full topic=%s seq=%d", msg.Topic, msg.SeqId)
}
broadcastHTTPForwardPresence(tenantID, msg, timestamp)
sendPushForHTTPForwardMessage(tenantID, msg, markedReadBySender, timestamp)
}
func broadcastHTTPForwardPresence(tenantID types.TenantID, msg *types.Message, timestamp time.Time) {
@@ -9855,6 +9869,71 @@ func broadcastHTTPForwardPresence(tenantID types.TenantID, msg *types.Message, t
}
}
func sendPushForHTTPForwardMessage(tenantID types.TenantID, msg *types.Message, markedReadBySender bool, timestamp time.Time) {
if msg == nil || msg.SeqId <= 0 || msg.Topic == "" || store.Topics == nil {
return
}
subs, err := store.Topics.GetSubs(tenantID, msg.Topic, nil)
if err != nil {
logs.Warn.Printf("im message forward: load recipients topic=%s seq=%d: %v", msg.Topic, msg.SeqId, err)
return
}
contentType, _ := msg.Head["mime"].(string)
receipt := &push.Receipt{
TenantID: tenantID,
To: make(map[types.Uid]push.Recipient, len(subs)),
Payload: push.Payload{
What: push.ActMsg,
Silent: false,
Topic: msg.Topic,
From: types.ParseUid(msg.From).UserId(),
Timestamp: timestamp,
SeqId: msg.SeqId,
ContentType: contentType,
Content: msg.Content,
},
}
fromUid := types.ParseUid(msg.From)
for _, sub := range subs {
uid := types.ParseUid(sub.User)
mode := sub.ModeWant & sub.ModeGiven
if uid.IsZero() || !mode.IsPresencer() || !mode.IsReader() {
continue
}
delivered := httpForwardDeliveredCount(tenantID, uid)
if uid == fromUid && delivered == 0 {
delivered = 1
}
recipient := push.Recipient{
Delivered: delivered,
Silent: types.GetTopicCat(msg.Topic) == types.TopicCatGrp && boolFromAny(groupPrivateMap(sub.Private)["mute_notifications"]),
ShouldIncrementUnreadCountInCache: uid != fromUid || !markedReadBySender,
}
receipt.To[uid] = recipient
}
if len(receipt.To) > 0 {
sendPush(receipt)
}
}
func httpForwardDeliveredCount(tenantID types.TenantID, uid types.Uid) int {
delivered := 0
if globals.sessionStore != nil {
globals.sessionStore.Range(func(_ string, sess *Session) bool {
if sess != nil && !sess.isCluster() && !sess.isProxy() && sess.tenantID == tenantID && sess.uid == uid {
delivered++
}
return true
})
}
if presence, err := store.GetUserPresence(tenantID, uid); err != nil {
logs.Warn.Printf("im message forward: read presence uid=%s: %v", uid.UserId(), err)
} else if presence != nil && presence.Online && presence.SessionCount > delivered {
delivered = presence.SessionCount
}
return delivered
}
func forwardedMessageHead(msg *types.Message, clientMid string) types.KVMap {
head := types.KVMap{}
if msg != nil {