rails new migrations generate create ruby-on-rails database-design

ruby-on-rails - new - rails db:migrate



DiseƱo de base de datos para almacenar notificaciones a los usuarios (5)

Estoy trabajando en un sitio web de la comunidad de literatura. ( screenshot ) Y estoy tratando de descubrir cómo notificar a los usuarios cuando alguien comenta algo que publicaron en el sitio, cuando alguien está viendo envíos, un nuevo artículo de literatura, etc.

Estoy intentando descubrir cómo estructurar la base de datos para almacenar esta información. He encontrado dos ideas posibles.

  1. Almacene un enlace al objeto de notificación obligatoria, un campo que describa el tipo de acción (nueva, actualización, etc.) de la que se está notificando al usuario. Esto hace que el código de visualización sea complejo, pero significa que puedo cambiar el funcionamiento de las notificaciones con bastante facilidad. Esto también aumenta los datos que necesito extraer de la base de datos a menos que use un campo de caché para volcar un hash de atributos relevantes en la tabla.

    • notifiable_type
    • notifiable_id
    • identidad de usuario
    • acción
    • notifiable_cache (opcional, almacena un hash de atributos seleccionados del objeto notificable)
  2. Trate las notificaciones como el correo electrónico y simplemente guárdelas en la base de datos con un asunto y un mensaje. Esto da como resultado una vista simple pero un modelo complejo y me impide cambiar fácilmente cómo funcionan las notificaciones.

    • identidad de usuario
    • título
    • mensaje

Estoy buscando otras ideas y comentarios sobre los dos que mencioné anteriormente.


Creo que tu primera opción es la mejor. Es más escalable que el segundo y le da la capacidad de buscar todas las notificaciones de un cierto tipo con bastante facilidad. La cantidad total de datos que va a guardar también será menor, ya que no tendrá que guardar mensajes completos para los usuarios.
Si cuida cómo escribe y diseña su código, no creo que sea demasiado complicado.

Sin embargo, si las notificaciones no cambian, la segunda opción puede ser más fácil de implementar.


Hace poco hice esto en el back-end de Rails de una aplicación de iOS y, básicamente, utilicé (2) una marca de tiempo pero la guardé en una lista de Redis indexada por el usuario. El esquema más débil (con todo básicamente rellenado en ''mensaje'') nos permite movernos mucho más rápido durante el desarrollo y las primeras versiones beta.

Además, dado que las notificaciones se borran de la lista de Redis, no hay que preocuparse por muchos mensajes antiguos en cuanto a cambiar los formatos, especialmente si se pueden eliminar mensajes ''antiguos''.


No estoy completamente seguro de cuál es el objetivo del campo de "acción" en el n. ° 1, pero si entiendo tu necesidad correctamente, esencialmente quieres que los usuarios se suscriban a una cola de notificaciones, ¿verdad? ¿Estas notificaciones están destinadas a ser enviadas al usuario por correo electrónico, o solo se muestran cuando inician sesión, o ambas?

Me sentiría tentado de pensar realmente en esto como una cola, donde estás "publicando" notificaciones, y los usuarios están "suscritos" a cualquier notificación con su user_id asociado. En un esquema relacional, es probable que desee utilizar algo como # 1, donde tiene una notificación con un tipo, asociado a un usuario. Indexe en user_id, por supuesto, para asegurarse de que pueda recibir sus notificaciones rápidamente. Si va a consultar mucho esto, almacenar en la memoria caché todo lo que necesita para visualizarlo tiene mucho sentido para que no tenga que unirse en ninguna otra tabla, eso es suponiendo que los datos de visualización no pueden cambiar después de la la notificación ha sido ''enviada''.

Sin embargo, si estas notificaciones no necesitan actualizarse en tiempo real mientras el usuario está en el sitio (por ejemplo, si se muestran al iniciar sesión o se envían por correo electrónico), puede consultar solo una vez cuando inicien sesión y almacenar en caché las notificaciones Si va a consultar esto constantemente en tiempo real para verificar nuevas notificaciones, y tiene muchos usuarios, esto eventualmente le causará problemas a medida que la mesa crezca. Puede fragmentarlo configurando tablas separadas para diferentes tipos de notificaciones, tal vez, o dividir por user_id, pero eso solo lo llevará hasta ahora.

También necesitarás asegurarte de podar la mesa. Es posible que deba agregar un indicador para indicar que el usuario ya ha visto la notificación, pero lo ideal es que, una vez que lo haya visto, pueda eliminarlo, y eso mantendrá la tabla pequeña.

Otra alternativa es mantener las notificaciones fuera de su rdbms. Considere mantener las notificaciones en memcached, por ejemplo, si la posibilidad de perderlas es aceptable (si el servidor se cae, por ejemplo). O consulte Redis ( http://code.google.com/p/redis/ ), lo que haría que este problema sea muy fácil: almacenar notificaciones, y crear un conjunto para cada usuario, y casi habrá terminado.

Solo algunos pensamientos, espero que sean útiles.


También estoy trabajando en un proyecto que utiliza notificaciones, no estoy seguro de si ya ha solucionado el suyo o si podría ayudar, pero esta es la estructura de la tabla que utilicé:

Notifications: - ID (PK) - recipient_id - sender_id - activity_type (''comment on a post'', ''sent friend request'', etc) - object_type (''post'', ''photo'', etc) - object_url (to provide a direct link to the object of the notification in HTML) - time_sent - is_unread


message : -id_message(pk) -to -from -subject -message -status (read,unread) reply_message : -id_reply(pk) -id_message -from -message -status (read,unread) notification : -id_user -id_notify(pk) -notify_type (message, or reply_message) -notify_desc (comment/reply on your message) -status (look,unlook) notify_detail : (for notify, when user reply or comment more than 1) -id_notify -id_sender -id_detail (input id_message, id_reply)

¿Qué tal esto? puedes mezclarlo con comentario o responder comentario.