#6: implement IMAP IDLE (RFC 2177) and CONDSTORE (RFC 7162)
This commit is contained in:
1 parent
0ec0698079
commit
6b1e4dc00a
20 files changed
+539
-95
No files matched your search
@@ -0,0 +1,72 @@
|
||||
package usecase
|
||||
|
||||
import (
|
||||
"sync"
|
||||
|
||||
"github.com/emersion/go-imap/v2"
|
||||
"github.com/emersion/go-imap/v2/imapserver"
|
||||
)
|
||||
|
||||
// MailboxTrackerManager maintains imapserver.MailboxTracker instances per folder ID.
|
||||
// This allows active IMAP sessions to receive real-time notifications when emails arrive,
|
||||
// flags change, or messages are expunged (IDLE / RFC 2177).
|
||||
type MailboxTrackerManager struct {
|
||||
mu sync.RWMutex
|
||||
trackers map[string]*imapserver.MailboxTracker
|
||||
}
|
||||
|
||||
func NewMailboxTrackerManager() *MailboxTrackerManager {
|
||||
return &MailboxTrackerManager{
|
||||
trackers: make(map[string]*imapserver.MailboxTracker),
|
||||
}
|
||||
}
|
||||
|
||||
// GetTracker retrieves or initializes the MailboxTracker for folderID.
|
||||
func (m *MailboxTrackerManager) GetTracker(folderID string, initialNumMessages uint32) *imapserver.MailboxTracker {
|
||||
m.mu.Lock()
|
||||
defer m.mu.Unlock()
|
||||
|
||||
tracker, ok := m.trackers[folderID]
|
||||
if !ok {
|
||||
tracker = imapserver.NewMailboxTracker(initialNumMessages)
|
||||
m.trackers[folderID] = tracker
|
||||
}
|
||||
return tracker
|
||||
}
|
||||
|
||||
// NotifyNumMessages informs all sessions watching folderID of a new EXISTS count.
|
||||
func (m *MailboxTrackerManager) NotifyNumMessages(folderID string, n uint32) {
|
||||
m.mu.RLock()
|
||||
tracker, ok := m.trackers[folderID]
|
||||
m.mu.RUnlock()
|
||||
|
||||
if ok {
|
||||
tracker.QueueNumMessages(n)
|
||||
}
|
||||
}
|
||||
|
||||
// NotifyMessageFlags informs sessions watching folderID of updated flags on a message.
|
||||
func (m *MailboxTrackerManager) NotifyMessageFlags(folderID string, seqNum uint32, uid uint32, flags []string, source *imapserver.SessionTracker) {
|
||||
m.mu.RLock()
|
||||
tracker, ok := m.trackers[folderID]
|
||||
m.mu.RUnlock()
|
||||
|
||||
if ok {
|
||||
imapFlags := make([]imap.Flag, len(flags))
|
||||
for i, f := range flags {
|
||||
imapFlags[i] = imap.Flag(f)
|
||||
}
|
||||
tracker.QueueMessageFlags(seqNum, imap.UID(uid), imapFlags, source)
|
||||
}
|
||||
}
|
||||
|
||||
// NotifyExpunge informs sessions watching folderID that seqNum was expunged.
|
||||
func (m *MailboxTrackerManager) NotifyExpunge(folderID string, seqNum uint32) {
|
||||
m.mu.RLock()
|
||||
tracker, ok := m.trackers[folderID]
|
||||
m.mu.RUnlock()
|
||||
|
||||
if ok {
|
||||
tracker.QueueExpunge(seqNum)
|
||||
}
|
||||
}
|
||||
Reference in new issue
Block a user