87 lines
2.2 KiB
Go
87 lines
2.2 KiB
Go
package logic
|
|
|
|
import (
|
|
"context"
|
|
|
|
"spark-server/internal/module/deliver/entity"
|
|
inboxlogic "spark-server/internal/module/inbox/logic"
|
|
syncentity "spark-server/internal/module/sync/entity"
|
|
"spark-server/internal/transport/tcp/protocol"
|
|
"spark-server/internal/transport/tcp/session"
|
|
)
|
|
|
|
type Mailbox interface {
|
|
Put(ctx context.Context, userID int64, eventType syncentity.EventType, conversationID int64, payload []byte) error
|
|
}
|
|
|
|
// InboxFanout updates Redis dialog ZSET then pushes to online sessions.
|
|
func InboxFanout(sessions session.Manager, inbox inboxlogic.Store, mailbox Mailbox) Handler {
|
|
push := SessionFanout(sessions)
|
|
return func(ctx context.Context, job *entity.Job) error {
|
|
if err := applyInbox(ctx, inbox, job); err != nil {
|
|
return err
|
|
}
|
|
if err := applyMailbox(ctx, mailbox, job); err != nil {
|
|
return err
|
|
}
|
|
return push(ctx, job)
|
|
}
|
|
}
|
|
|
|
func applyInbox(ctx context.Context, inbox inboxlogic.Store, job *entity.Job) error {
|
|
if inbox == nil || job == nil || job.ConversationID == 0 {
|
|
return nil
|
|
}
|
|
if len(job.Preview) > 0 {
|
|
if err := inbox.SetPreview(ctx, job.ConversationID, job.Preview); err != nil {
|
|
return err
|
|
}
|
|
}
|
|
if job.Cmd != 0 && job.Cmd != protocol.CmdMessage {
|
|
return nil
|
|
}
|
|
score := job.MsgID
|
|
for _, uid := range job.ToUserIDs {
|
|
if uid == job.FromUserID {
|
|
if err := inbox.TouchRead(ctx, uid, job.ConversationID, score); err != nil {
|
|
return err
|
|
}
|
|
continue
|
|
}
|
|
if err := inbox.TouchUnread(ctx, uid, job.ConversationID, score); err != nil {
|
|
return err
|
|
}
|
|
if err := inbox.IncrUnread(ctx, uid, job.ConversationID, 1); err != nil {
|
|
return err
|
|
}
|
|
}
|
|
return nil
|
|
}
|
|
|
|
func applyMailbox(ctx context.Context, mailbox Mailbox, job *entity.Job) error {
|
|
if mailbox == nil || job == nil || job.NotMailbox {
|
|
return nil
|
|
}
|
|
ev := mailboxEventType(job.Cmd)
|
|
if ev == 0 {
|
|
return nil
|
|
}
|
|
for _, uid := range job.ToUserIDs {
|
|
if err := mailbox.Put(ctx, uid, ev, job.ConversationID, job.Payload); err != nil {
|
|
return err
|
|
}
|
|
}
|
|
return nil
|
|
}
|
|
|
|
func mailboxEventType(cmd uint16) syncentity.EventType {
|
|
switch cmd {
|
|
case protocol.CmdRecallMessage:
|
|
return syncentity.EventRecall
|
|
case protocol.CmdDeleteMessage:
|
|
return syncentity.EventDelete
|
|
default:
|
|
return 0
|
|
}
|
|
}
|