Pergunta

I have recently been assigned a task to develop a notification engine. For the notifications we are going to use Push Notification. I am looking for the best possible solution for the engine because in future we have to scale the application to other devices also. Following are some details of the project

Backend: Backend of the application is developed in Ruby on Rails as webservices

Devices that will have push Notification iPhone, Android, Pebble (smart watch), Web application

Current Solution: Currently, we are thinking to make a back-end database table for notifications. A worker class in Rails will run after 1 minute and it will push all the notifications to the devices stored in the database. From the webservice methods, we will insert the data in the notification table.

For pushing notications we do not want to use services like UrbanShip. We are only going to implement them using Ruby Gems. Currently, we made a small demo based on GCM gem for android push noticiations.

Questions: Is my approach to the solution is correct ? or is there any better solution for this kind of problem.

EDIT:

I think that my previous description of the problem was a little confusing.

Ultimately we are going to use GEMS in Ruby to send push notifications. Forexample for iOS we are going to use Houston or Grocer gem and for Android GCM.

Problem: We need some database tables where we will store notifications so that the GEMS (mentioned above) can use them to send the notification to users. Now, to fill the database tables we need to write the logic somewhere so that we can insert the notification in the table.

Forexample, lets say that when a user first registers in the application we send him a notification. Now, to do this we need to write the code for adding the notification in the Register function.

like

public void Register()
{
   //Registration logic

   //Add a notification in the notification table
}

Now, this is a problem because we need to add the notification logic in all the functions that need to send notification. Is there any other good solution in ROR or in general ? Some design pattern ?

Foi útil?

Solução

I've spent a fair amount of time looking at Ruby based push notification solutions. The best one is RPush https://github.com/rpush/rpush. RPush is very well tested at this point (We use it to send millions of notifications), and handles a lot of difficult edge cases well. I wouldn't recommend building your own from scratch since there are so many potential pitfalls and edge cases. RPush doesn't support Pebble or Web App notifications, but could be extended to do so.

If you decide to explore other alternatives, make sure they:

  1. Handle closed connections gracefully for APNS - In many cases, Apple may close the connection to their server, and your push notification library must handle this correctly otherwise thousands of subsequent notifications can go undelivered

  2. Communicate with Apple's feedback service - Apple requires you to poll one of their endpoints for a list of devices to stop sending notifications to. If you fail to do this, you can get rate limited.

  3. Can send notifications at a fast enough rate for your requirements.

Outside of Ruby, the best push notification libraries seem to be PushSharp (C#), and Node-Apn (NodeJS, iOS only)

Finally, it sounds like you have specific needs that require you to do this yourself. But for others, I would strongly encourage you to use a 3rd party services. Reliably sending push notifications at a high volume is difficult and there are many 3rd party services that will do it for you at low cost. For instance, UrbanAirship, Parse, and OneSignal (My service) are all great 3rd party solutions.

Update to address revised question:

The best design pattern is to have a a second daemon process or Cron Job that handles message delivery. It's not practical to try to do this inside of a Ruby on Rails application.

The RoR application can insert rows into the Notification table as a queue like you describe. Then the daemon process or cron job can fetch notifications from the queue and deliver them.

If you use RPush, this is the pattern that it follows. It comes with both a Gem to load into your Rails application that inserts notifications onto a database queue, as well as a daemon that you keep running on your server that periodically checks for new notifications to send and delivers any that get queued up.

Outras dicas

I wonder if this question is still open or you already have a solution, but I'd like to propose this gem I've recently published: https://github.com/calonso/ruby-push-notifications

It's really simple to use, flexible enough to fit your architecture and works!

At the moment is just the gem itself, but I'm working on building a whole Rails plugin around it, with all the tables structure and stuff. You can see some work in progress here: https://github.com/calonso/rails-push-notifications

This article describes a very simple but fairly comprehensive approach to handling push notifications on your Rails backend.

In a nutshell:

  1. Implement a Device model together with some controller actions to record users's device tokens in your DB.
  2. Create a Notification model, which in the article is a Redis list but you can also use ActiveRecord if you don't really want to use Redis.
  3. Create a background worker that is actively running through the incoming notifications and sending them as push notifications. The article mentions grocer and GCM to send them to iOS and Android respectively but you can also use other useful gems such as rpush, houston, etc.

Having a separate worker processing notifications is a good idea because you don't want to be constantly opening and closing connections to Apple and Google's servers with the risk of getting locked out, since it might look like a Denial of Service attack (depending on the frequency of your notifications).

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top