-
Notifications
You must be signed in to change notification settings - Fork 8.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Personalisation] Notifications API MVP #140743
Comments
Pinging @elastic/kibana-core (Team:Core) |
Pinging @elastic/kibana-app-services (Team:AppServicesSv) |
Thanks for getting this started! Overall I'm particularly interested in how we can prevent connector-specific concepts from leaking into the API, since the idea is that we will eventually have a longer term platform-provided concept of connectors. With that in mind, a few initial thoughts:
I'm unsure if the benefits we get from a
I'd imagine that eventually we'd want that dependency to be inverted, so that there's a user-settings-service (perhaps similar to uiSettings), that the Notifications plugin would register these settings into and read from. Plus we might run into some circular dependency issues -- if Notifications need to read user profile to get settings from Security, Security won't be able to update preferences if it lives in Notifications.
Maybe we could start by just returning an error from the Notifications service so that the consuming application (Cases) could decide what to do with it? E.g. maybe they want to throw a toast notification or render an inline message mentioning that users have not been notified? idk...
I'd vote 'no' on all of these items for MVP/Phase1 if we don't have a strong need for them 🙂 That way we keep it as simple as possible so we aren't locking ourselves into too many decisions before @elastic/kibana-app-services starts getting more involved. |
I think that the process of notifying should not block HTTP requests. A case should be created/updated even if the user is not notified (error while sending an email) or notifications are not configured. I think the error should surface somewhere else. Ideally, in the admin notification UI page if there is one. Cases could also show a callout on the all cases page informing the user that notifications are not properly configured and cases cannot notify assignees. This would require the notification plugin (or the plugin responsible for the notification configuration) to expose from the start method of the plugin side of the plugin a boolean where cases can check and act accordingly. |
my initial remarks and comments (note: I did not look at @lukeelmers's reply to not be influenced)
For the initial MVP of the revamped NC, idk. For the old/initial purpose of the notification service, this was a mandatory requirement. Now, it was not about using, per example, slack's
Given the suggested architecture, I agree that it can only be a plugin. Now I have to ask: are we sure we'll never need to use this API from Core services at some point? (and if we do, do we know how we will technically be able to do so? IOC with registration API as we do for telemetry collectors?)
Why not allow consumers to register their notification types, as it's done for EBT for example? It seems like the proper isolation of concerns, and would avoid problem in code ownership where other contributors need to update the notification plugin to add their new types?
The problem with any enhanced text format is that is introduce a tight coupling between the notification and the connector. E.g depending if a given notification will be sent via mail or to slack, the actual formatting capabilities aren't the same.
Meaning what in term of impact on the design/API surface, exactly? Note that this highly depends on the next point,
Excellent question. Supporting only prebuild messages would allow to somehow solve the RTF/i18n problematic, as it would be handled internally by the notification API (you can have a formatter per connector for instance). Now, I suspect that in practice, it may not be sufficient (or would force to introduce hundreds of notification types very quickly), but I lack the proper vision to understand exactly what we're planning to do long term.
Also something that should absolutely be decided in the initial design. More globally, what's the relations between a
Maybe I don't understand, but if we don't, we're bound to have a single connector for all and every notification types, don't we? |
There are multiple opinions regarding multi-person notifications. Initially, I added it cause I saw it as a feature that could be interesting from a functional standpoint, and also because we have it "for free" with the current Also, seeing as though this parameter will likely not change for each "notification action", I believe it's probably better to add it at a later phase and to have it as a configuration param. I'll update the API accordingly.
@luke I was imagining it more as a layer on top of Security:
The question I ask myself is: imagine the case where a user has not yet customised their notification preferences. How will the User Profile UI know which notification types (and channels) are there, to present the different checkboxes? We could hardcode it somewhere in an Enumeration, or as @pgayvallet suggests, I suppose we can allow consumers to register new notification types and store them ?in memory? (how does it work for EBT?). The later seems a lot more flexible, but it's probably harder to implement. Don't know what's the best strategy from an MVP standpoint. That is unless the user preferences itself is backed by some sort of saved object that allows storing meta information about the preferences that exist. @arisonl ? @pgayvallet thanks for the insight in RTF/i18n problematic. The API surface depends on it:
Anyway, these approaches are not mutually exclusive, we could start with a service method for A) for the MVP, and then add new methods to the service for B) and C) at a later phase.
Sorry, the question is not very clear. I was imagining a scenario where, for instance, an organisation had a couple different Slack workspaces, and they wanted to send notifications to users that are in either of these spaces. In that line, my question was whether it would be interesting to support configurations such as:
So in fact, the question I was asking myself was more: Configuration-wise, for a given notification type (e.g. case assignment), should we support more than one connector of the same "type" (e.g. slack)? I imagine it wouldn't be too hard, and this way we are covered if presented with such scenario. |
I think we're not speaking of the same thing. As I said previously, I wasn't referring to notifications 'shared' between users (e.g a multi-users message in slack), but the capability to send notifications to a list / group of different users at the same time and using a single notification API call. Now, if that's not required for the MVP, great.
I think the problem remains here: what if the Note that the problem may not be in the current issue's proposed design, but in the fact that the security plugin is currently a single block doing too many things (similar to the cloud plugin for instance).
Thanks, it's clearer now. Then I would say it looks fairly easy to add later in a non-breaking way (change config structure to allow both a string or an array of string), in which case, if not required for the MVP, we can probably ignore it for now? |
Who will generate the backlink to Kibana? Will this be done automatically inside of the service or does it have to be done by consumers who will have to append the link to the |
I think it should be the responsibility of the consumers because they want to link to different pages in Kibana. For example in Cases, we would like to add a backlink to the case the user got assigned. |
The idea was to keep the API as simple as possible, so the accepted message will be plain text. Thus, the API will not check whether text contains a link. |
As discussed offline today, and I've also spoken with few people about Alerting Connectors today, would like to propose the following: We would create a plugins.notifications.email.send({
to: 'abc@gmail.com',
textBody: 'You were tagged in a case ...',
// more fields ...
}); From the current technical limitations, it is best for now to use Alerting email Connectors, especially the pre-configured cloud email connector, and Alerting Action, which is executed immediately (without putting it into the Task Manager queue). Would be great if we could just provide the Like above caseAssignmentNotificationConnectors, registerNotificationType, etc... As it is not clear if the Notifications Center will have a concept of "connectors", and "notifications" in the Notifications Center will be way more complex persistent entities. IMO, would be great for now if Cases could just use the // Once case was assigned
const {email, fullName, locale} = await plugins.users.loadProfile(assigneeId);
await plugins.notifications.email.send({
to: email,
textBody: localizeNotificationMessage(locale, fullName, caseId),
}); In the future, we could provide the email sending as some fundamental service from Core, then notifications email service could just be thought of as a temporary proxy for that: plugins.notifications.email.send = (params) => core.email.send(params); |
No strong feelings from me one way or the other, but this approach makes sense to me. I'm +1 on anything we can do to avoid tying this API too closely to concepts that may change later. Connectors is the obvious one, but I suppose you could say the same for Notifications. Also, IIRC we are not considering localization part of the MVP, so that wouldn't be necessary for now. @cnasikas what do you think of this proposal?
TBH I'm not sold on the idea of email being a core service, especially if we imagine a SaaS future where we could potentially have a standalone service for something like this. But that's outside the scope of this discussion, and not something we need to reach alignment on now. |
I also favor not tying closely concepts that may change later. Cases still need to bulk get the user profiles to get the email assignees which is ok.
Regarding executing immediately, I believe we should not go with this approach and use the task manager. Cases' endpoints should not be blocked to send an email. If the notification service does not use the task manager, consumers (Cases) will have to use the task manager leading to multiple implementations of the same task. Lastly, If in the future the notification service decides to use the task manager, Cases need to stop using the task manager to avoid creating two jobs: one for Cases and one for the notification service. In the long run, it will be better if the notification service uses the task manager and have control of how notifications are being sent.
A case can have multiple assignees. I think we should take that into consideration and let the |
Agreed. The other benefit we get from this approach is that we will transparently retry sending these emails when there's a transient error once we start supporting at-least-once action runs. |
That's a good point. For the time being the name of the new plugin is pretty much the only mention we have about
Sorry if my description was confusing, I was talking about a
Indeed, the API is going to accept a list of recipients, and it will schedule a single bulk action with the list of all the executions. |
Thank you, @gsoldevila, and sorry for the confusion! |
@cnasikas @kobelb @gsoldevila I was hoping we can execute an action immediately, using the Or am I missing something? Do we gain something by scheduling a task in the Task Manager? Or does it have to do with UI Kibana and Background Task Kibana split, where UI Kibana does not know how to execute an Action?
@cnasikas What do you mean here exactly? The execution should still be async, hence can run in the background: async sendNotifications() {
plugins.notifications.email.sendPlainTextEmail(opts).catch(() => {}); // No "await" - executes in background.
}
Curious, why should any of them use the Task Manager? Ideally, the current abstraction should "just send an email" and there should be no assumptions from Cases of how it is implemented under-the-hood.
In the long run, it is not even clear if the Notifications Service/Center will be part of Kibana, maybe it will be a standalone cloud service. Hence, I'm curious, why do you think it should use the Task Manager?
Currently, as far as I understand, we are not re-sending. And we should not optimize for that, as Notifications Center might not even be implemented in Kibana, but as a standalone service. And Email Service might not use Connectors in the future. |
Currently, we get a few concrete benefits from scheduling a task in task-manager:
It's also aligned with our future long-term vision and allows us to make the email sending be performed by the Kibana process that is only responsible for running background-tasks. |
This will result in emails not being sent if the Kibana node crashes at the wrong time. We should NOT do this. |
It will need to wait for saved object to be stored. My example above shows how to make it truly async. In any case, it is up the Cases team how much async they want it. Whether they want to block the user until the saved object is stored or not. For the
What kind of errors will it try to overcome? I assume those would be connector specific errors, like if it cannot execute an action at all for some reason? Is there a way to specify on which kind of errors it will re-try, so we don't end up sending multiple emails for the same notification? I assume it will not handle email specific semantics, like debounced emails?
This a good point. Essentially what I was asking above:
I guess the immediate Which means, we have to create saved objects, otherwise it will be refactored to that in the future anyways. |
I feel like I'm missing something. Are we really so concerned about the additional time that it will take to persist a single saved object that we're willing to risk these emails not being sent? This approach also means that any errors that are thrown when sending the email will be swallowed. The user will never know if their email didn't send.
In all other situations where we send emails, we've decided to persist a saved-object to increase the likelihood that the emails are sent. Is there something special about this situation that makes you think we should change our approach?
At the moment, the email connector is rather naive about retries, and it will retry on any error that is thrown when sending the email. We can definitely improve on this in the future. It is possible that we will end up sending multiple emails for the same notification.
We aren't certain about the future of |
I don't have an opinion here, if Cases team wants to block while waiting on saved object save, fine with me. (I guess people mean different things by async.) From what I understand, we need a saved object in any case, as that is the mechanism how Task Manager will communicate from UI Kibana to Background Task Kibana. Regarding email retries:
Curious, what are the other places in Kibana where we send emails? |
Anything is possible with enough time and developer effort.
It definitely can.
Alerting rules send emails when various conditions are hit. |
Overview
In the scope of personalisation & collaboration, we need a way to notify users when they are linked to a certain entity / event:
@mentioned
somewhere in the Kibana UI.The personalisation & collaboration initiative is likely going to have multiple use cases impacting different solutions and plugins. The goal of this issue is to describe an API that will act as a centralised place for all these use cases to send notifications.
The Notifications API will rely on 2 basic building blocks:
Slack
notifications for Case mentions, andSlack + Email
notifications for Case assignments.Notification flow (draft)
Here's the sequence diagram describing the Email notification flow (MVP):
Q & A
QUESTION: Do we want to support multi-person notifications? e.g: do we want to send emails to multiple recipients at once? do we want to send MPIMs (Multi Person Instant Messages) through slack?
From a functional standpoint, there are scenarios in which it could be interesting to have multi person notifications, e.g. sending the same Case assignment email to multiple users at once, fostering communication between them. From a technical standpoint, this feature is currently supported by certain connectors (e.g. Email) but not yet supported (there's an implementation gap) by others (e.g. Slack). Since the feature might be interesting in some use cases, we could expose agroupIfPossible?: boolean
parameter in the future to drive this behaviour (with a default offalse
).QUESTION: Will the Notifications API be a part of the Core services?
QUESTION: Will the Notifications API be a REST endpoint or a programatic service?
NotificationsService
, which will provide convenient methods for plugins and solutions to send notifications. Nothing prevents us from exposing HTTP endpoints for that service at a later phase if the need arises.QUESTION: Case assignment might be the first use case, but the roadmap foresees multiple notification types in the future. Where do we store the list of notification types?
NotificationsService
will need that knowledge in its logic.NotificationsService
could expose a couple of methods toread
andupdate
the notification preferences for the current user.QUESTION: Rich text formats. What formatting options will the notifications API support? Is it acceptable to send notifications in plain text?
mrkdwn
syntax (a subset of Markdown language).QUESTION: Should the API support localised notification messages?
QUESTION: Can new notification types be dynamically added by other plugins?
QUESTION: Should the API support dynamic messages or only prebuilt ones? If we have to send the exact same messages over and over, perhaps it could be interesting to have some sort of
NotificationPayloadBuilder
which, given aMessageId
, could build the payload to send to each connector. This would require an interface to manage predefined messages though.QUESTION: How do we determine the connector to be used for each notification channel?
Cloud deployments have a preconfigured email connector, so we could hardcode its ID for MVP. However, this is not very flexible, and it does not cover self-managed deployments. We should probably:add new settings inkibana.yaml
or use SavedObjects (along with a UI to manage them?)or some combination of the aboveQUESTION: Do we want to support using different connectors for each notification type? E.g.
emailConnectorA
for @mentions,emailConnectorB
for Case assignment?QUESTION: How do we let administrators (or users) know that notifications will NOT work because they have not been properly configured? Note that the appropriate connectors need to be configured in Kibana, and the
NotificationsService
must know which connector(s) to use for each type.Notifications API specification
Only after answering all of the above questions can we propose a convenient contract for the
NotificationsService
.Here I'll try to reflect the current state of proposed API (subject to change as the technical design evolves):
The text was updated successfully, but these errors were encountered: