package graph import ( "sync" "gogs.dmsc.dev/arp/graph/model" "gorm.io/gorm" ) // This file will not be regenerated automatically. // // It serves as dependency injection for your app, add any dependencies you require // here. // TaskEvent represents a task event for subscriptions type TaskEvent struct { Task *model.Task UserID uint // The user who should receive this event (assignee) EventType string // "created", "updated", "deleted" } // MessageEvent represents a message event for subscriptions type MessageEvent struct { Message *model.Message ReceiverIDs []uint // IDs of users who should receive this event } // Resolver is the main resolver struct type Resolver struct { DB *gorm.DB // Pub/Sub channels for subscriptions (slice of channels per user for multiple subscriptions) taskSubscribers map[uint][]chan TaskEvent // keyed by user ID taskSubscribersMu sync.RWMutex messageSubscribers map[uint][]chan MessageEvent // keyed by user ID messageSubscribersMu sync.RWMutex } // NewResolver creates a new resolver with initialized pub/sub func NewResolver(db *gorm.DB) *Resolver { return &Resolver{ DB: db, taskSubscribers: make(map[uint][]chan TaskEvent), messageSubscribers: make(map[uint][]chan MessageEvent), } } // SubscribeToTasks registers a user for task events and returns their event channel // Each subscription gets its own channel to avoid competition between goroutines func (r *Resolver) SubscribeToTasks(userID uint) <-chan TaskEvent { r.taskSubscribersMu.Lock() defer r.taskSubscribersMu.Unlock() ch := make(chan TaskEvent, 10) r.taskSubscribers[userID] = append(r.taskSubscribers[userID], ch) return ch } // PublishTaskEvent sends a task event to all subscribers for the assignee func (r *Resolver) PublishTaskEvent(task *model.Task, assigneeID *uint, eventType string) { if assigneeID == nil { return // No assignee, no one to notify } event := TaskEvent{ Task: task, UserID: *assigneeID, EventType: eventType, } r.taskSubscribersMu.RLock() defer r.taskSubscribersMu.RUnlock() // Send to all channels for this user for _, ch := range r.taskSubscribers[event.UserID] { select { case ch <- event: default: // Channel full, skip event } } } // SubscribeToMessages registers a user for message events and returns their event channel // Each subscription gets its own channel to avoid competition between goroutines func (r *Resolver) SubscribeToMessages(userID uint) <-chan MessageEvent { r.messageSubscribersMu.Lock() defer r.messageSubscribersMu.Unlock() ch := make(chan MessageEvent, 10) r.messageSubscribers[userID] = append(r.messageSubscribers[userID], ch) return ch } // PublishMessageEvent sends a message event to all subscribers who are receivers func (r *Resolver) PublishMessageEvent(message *model.Message, receiverIDs []uint) { event := MessageEvent{ Message: message, ReceiverIDs: receiverIDs, } r.messageSubscribersMu.RLock() defer r.messageSubscribersMu.RUnlock() for _, userID := range receiverIDs { // Send to all channels for this user for _, ch := range r.messageSubscribers[userID] { select { case ch <- event: default: // Channel full, skip event } } } }