refactor(server): extract inbox creation to bus listeners, add agent visibility filtering

- Move all CreateInboxItem calls from handlers to centralized inbox_listeners.go
- Enrich issue:updated payload with change context (assignee_changed, status_changed, prev values)
- Enrich comment:created payload with issue context (assignee info)
- Bus listeners handle: issue assign, unassign, reassign, status change, comment notification
- ListAgents filters private agents: only visible to owner_id or workspace admin
- Zero CreateInboxItem calls remain in handler package

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
Naiyuan Qing 2026-03-25 11:24:45 +08:00
parent 19504a217c
commit 759dd741bd
7 changed files with 279 additions and 125 deletions

View file

@ -98,27 +98,12 @@ func (h *Handler) CreateComment(w http.ResponseWriter, r *http.Request) {
}
resp := commentToResponse(comment)
h.publish(protocol.EventCommentCreated, uuidToString(issue.WorkspaceID), "member", userID, map[string]any{"comment": resp})
// Notify issue assignee about new comment (if assignee is a member and != commenter)
if issue.AssigneeType.Valid && issue.AssigneeID.Valid &&
issue.AssigneeType.String == "member" && uuidToString(issue.AssigneeID) != userID {
body := req.Content
inboxItem, inboxErr := h.Queries.CreateInboxItem(r.Context(), db.CreateInboxItemParams{
WorkspaceID: issue.WorkspaceID,
RecipientType: "member",
RecipientID: issue.AssigneeID,
Type: "mentioned",
Severity: "info",
IssueID: issue.ID,
Title: "New comment on: " + issue.Title,
Body: ptrToText(&body),
})
if inboxErr == nil {
h.publish(protocol.EventInboxNew, uuidToString(issue.WorkspaceID), "member", userID,
map[string]any{"item": inboxToResponse(inboxItem)})
}
}
h.publish(protocol.EventCommentCreated, uuidToString(issue.WorkspaceID), "member", userID, map[string]any{
"comment": resp,
"issue_title": issue.Title,
"issue_assignee_type": textToPtr(issue.AssigneeType),
"issue_assignee_id": uuidToPtr(issue.AssigneeID),
})
writeJSON(w, http.StatusCreated, resp)
}