Creating notifications via the API

Hi, a quick question: Can you send notifications to users with the API? (or another way).
In the documentation, I found how to GET notifications of the user, how to mark them as read, but not how to POST some. If it isn’t possible, I guess there is always to possibility of using private messages instead.
I would appreciate any input on this. Thanks.

2 Likes

I think it would take a plugin. What kind of notification do you want? Can you describe your use case?

2 Likes

Typically, replacing the email notifications from an external service with Discourse notifications. The service would be provided for free to members (*). This would allow to centralize everything towards Discourse, and to give an incentive to log (regularly) to the forum. That was the idea I had in mind. I’m not sure if it makes sense or not, or if there are flaws in the reasoning. I’m open to every suggestion / criticism.

[ (*): Members = forum participants. At least people registered to the forum. Remains to be seen if there is a minimum participation or trust level required, or if registering is enough. ]

The plugin would receive the information and trigger notifications in Discourse? Notifications can be (more easily) done from a plugin?

2 Likes

I can imagine a plugin that added a route and you could push a load with the user id (or email address), a url, and a title that would create a notification. I don’t think that you could do it without a plugin, but I’ve not looked that closely at the code.

I just yesterday started to consider adding notifications to a plugin that I’m developing,so I’m not that familiar with how it works.

3 Likes

I’m planning a similar plugin myself, centering my website non-email notifications around Discourse, which you can then subscribe to via MessageBus and have a central push notification configuration.

What I’m planning is just having a custom endpoint for creating custom notifications, after seeing these snippets I think it’s feasible.

For creating a custom notification:
https://github.com/discourse/discourse-code-review/blob/master/lib/discourse_code_review/state/commit_approval.rb#L168-L173

For customizing how the notification item is displayed on the notification list:
https://github.com/discourse/discourse-code-review/blob/master/assets/javascripts/discourse/widgets/code-review-commit-approved-notification-item.js.es6

If there were a core API for creating the notification, I think this notification item widget could be done on a theme component, which would be even simpler.

4 Likes

I don’t know how potentially more complicated it may be to do, but wouldn’t it make sense to add notifications creation directly to the API? Maybe the team would be open to do this, or be open to a PR (if someone can and is willing to do this)?

2 Likes

It’s not documented yet, but there is a create notification api endpoint:

 POST /notifications(.:format) notifications#create {:format=>/(json|html|\*\/\*)/}

You might be able to use the custom notification type instead of having to create your own.

5 Likes

That’s great! Thank you.

So, if I understand it correctly, with the endpoint, if there’s a need for overriding DefaultNotificationItem then a plugin would still be needed just to register the additional notification type to be used in a custom widget?

Notification.types[:following] = 800

(from https://github.com/paviliondev/discourse-follow/blob/master/plugin.rb#L23)

Using the custom type it will be rendered using https://github.com/discourse/discourse/blob/master/app/assets/javascripts/discourse/app/widgets/custom-notification-item.js, so for overriding the destination url a custom widget would still be needed?

I saw one plugin overriding “custom-notification-item” in a similar scenario, is it safe to just override url when there’s something specific on data and fallback to
this._super.url otherwise?

2 Likes

Thanks, @renato!

Here’s what I’ve got.

Notification.create!(
  notification_type: Notification.types[:custom],
  user_id: 1,
  topic_id: nil,
  post_number: nil,
  high_priority: true,
  data: {
    message: 'pfaffmanager.title',
    display_username: 'pfaffman',
    topic_title: 'my title'
  }.to_json
)

I see the notication, but, predictably, (EDIT:) NOTHING happens if I click. Also (not obvious to me until I did it), the message is a I18n, not an arbitrary string. . . ). What I’d like is to be able to put the URL to the model that called it.

2 Likes

I suppose you meant “nothing” happens?
If you could click it and be redirected to an URL you joined through the API, that would be amazing, indeed.

2 Likes

The DefaultNotificationItem creates a url automatically if you fill data.badge_id, topic_id or data.group_id.

I tested this approach and it works. Just fill data.url and use this in a theme component:

  api.reopenWidget("custom-notification-item", {
      url(data) {
          return data.url || this._super(data);
      }
  })
4 Likes

I don’t get this to work…

POST https://XXX/notifications
Api-Key:XXX
Api-Username:system
Content-Type:application/json
Accept:application/json

{
    "notification_type":9,
    "user_id": 123,
    "post_number": 1,
    "topic_id": 956,
    "data": {
        "topic_title": "Test",
        "original_post_id": 2222,
        "original_post_type": 1,
        "original_username": "User.Name",
        "revision_number": 1,
        "display_username": "Text"
            }

}

I get as response:


{
  "errors": [
    "Data can't be blank"
  ],
  "error_type": "record_invalid"
}

Formatting error, misunderstanding? Or am I missing something in data?

I can’t really reverse engineer this from the web - Or is this API called somewhere?

1 Like

You need to encode the data value.

e.g.:

"data": "{\"topic_title\":\"Test\",\"original_post_id\":2222,\"original_post_type\":1,\"original_username\":\"User.Name\",\"revision_number\":1,\"display_username\":\"Text\"}"
4 Likes