watchInboxNotifications watches for new inbox notifications and sends them to the client. The client can specify a list of target IDs to filter the notifications. @Summary Watch for new inbox notifications @ID watch-for-new-inbox-notifications @Security CoderSessionToken @Produce json @Tags Notifica
(rw http.ResponseWriter, r *http.Request)
| 117 | // @Success 200 {object} codersdk.GetInboxNotificationResponse |
| 118 | // @Router /api/v2/notifications/inbox/watch [get] |
| 119 | func (api *API) watchInboxNotifications(rw http.ResponseWriter, r *http.Request) { |
| 120 | p := httpapi.NewQueryParamParser() |
| 121 | vals := r.URL.Query() |
| 122 | |
| 123 | var ( |
| 124 | ctx = r.Context() |
| 125 | apikey = httpmw.APIKey(r) |
| 126 | |
| 127 | targets = p.UUIDs(vals, []uuid.UUID{}, "targets") |
| 128 | templates = p.UUIDs(vals, []uuid.UUID{}, "templates") |
| 129 | readStatus = p.String(vals, "all", "read_status") |
| 130 | format = p.String(vals, notificationFormatMarkdown, "format") |
| 131 | logger = api.Logger.Named("inbox_notifications_watcher") |
| 132 | ) |
| 133 | p.ErrorExcessParams(vals) |
| 134 | if len(p.Errors) > 0 { |
| 135 | httpapi.Write(ctx, rw, http.StatusBadRequest, codersdk.Response{ |
| 136 | Message: "Query parameters have invalid values.", |
| 137 | Validations: p.Errors, |
| 138 | }) |
| 139 | return |
| 140 | } |
| 141 | |
| 142 | if !slices.Contains([]string{ |
| 143 | string(database.InboxNotificationReadStatusAll), |
| 144 | string(database.InboxNotificationReadStatusRead), |
| 145 | string(database.InboxNotificationReadStatusUnread), |
| 146 | }, readStatus) { |
| 147 | httpapi.Write(ctx, rw, http.StatusBadRequest, codersdk.Response{ |
| 148 | Message: "starting_before query parameter should be any of 'all', 'read', 'unread'.", |
| 149 | }) |
| 150 | return |
| 151 | } |
| 152 | |
| 153 | notificationCh := make(chan codersdk.InboxNotification, 10) |
| 154 | |
| 155 | closeInboxNotificationsSubscriber, err := api.Pubsub.SubscribeWithErr(pubsub.InboxNotificationForOwnerEventChannel(apikey.UserID), |
| 156 | pubsub.HandleInboxNotificationEvent( |
| 157 | func(ctx context.Context, payload pubsub.InboxNotificationEvent, err error) { |
| 158 | if err != nil { |
| 159 | api.Logger.Error(ctx, "inbox notification event", slog.Error(err)) |
| 160 | return |
| 161 | } |
| 162 | |
| 163 | // HandleInboxNotificationEvent cb receives all the inbox notifications - without any filters excepted the user_id. |
| 164 | // Based on query parameters defined above and filters defined by the client - we then filter out the |
| 165 | // notifications we do not want to forward and discard it. |
| 166 | |
| 167 | // filter out notifications that don't match the targets |
| 168 | if len(targets) > 0 { |
| 169 | for _, target := range targets { |
| 170 | if isFound := slices.Contains(payload.InboxNotification.Targets, target); !isFound { |
| 171 | return |
| 172 | } |
| 173 | } |
| 174 | } |
| 175 | |
| 176 | // filter out notifications that don't match the templates |
nothing calls this directly
no test coverage detected