mongodb load document and increment counter

Viewed 1218

Maybe this sounds bit strange but i will ask it.

In my application i store posts in my collection called posts. It looks like this

{
   _id: 123,
   name: "somename",
   surname: "somesurname",
   img: "path/to/img",
   views: 0
}

So is it possible in mongodb to increase the views everytime that document gets loaded? Or do i need an workaround?

My other solution is after i fetch all data with .find() or .aggregate() to map all the _ids and execute an update query with $in to increase everywhere the views by 1. I hope you know what i mean.

But i think its kinda in-efficient, because i need 2 querys. I was also thinking about, instead of using querys like .find(), to use update querys and return the new document with new: true. Is this possible, can somebody help me here?

2 Answers

There is nothing 100% native OTB within MongoDB, but here are some approaches I recommend:

Option 1: Application Data Layer (Recommended)

Standardize this on the data layer of your application. On every access operation (that you deem to be a notable "view"), remember the IDs of the retrieved posts, and after you server the request, run a multi-update to increment this number.

This "multi-update" approach will make sure that you're minimizing your increment update ops. You can even "remember" these in memory and run the updates in batch just once in a while (assuming you're OK that "views" might be out of date by a few minutes).

You do not want to have your API wait on this data increment operation, because you will slow down all your read operations. If you need to return data with updated numbers, then updated them in memory before returning, but still do the DB views update after serving the request.

Why I strongly recommend this option: there will always be cases when you'll read the post, but not want to increment the "view" counter, like when you're doing internal analytics, or checking data for other internal operations. There are also cases when you'll just do an update, which is not a strict "view", but you'll want to update the view counter, because you're still serving the result for "viewing". So maintaining logical "Data Layer" control over what is really a view, is a very good practice.

Option 2: Use Mongo Stitch

If you were using something like Mongo Stitch (https://docs.mongodb.com/stitch/), this offers such functionality naturally (https://docs.mongodb.com/stitch/triggers/#database-trigger), but then you might as well handle much of your application with this additional layer (if it's even available to you).

Option 3: Use MongoDB Stored JavaScript

In SQL DBs you would use triggers, and the closest thing in "raw" MongoDB is "Stored JavaScript", BUT there is no natural way (AFAIK) to trigger this stored JS on document access, so you'd have to integrate this into something like Option 1 anyway, so it's just a noteworthy solution mention.

Related