Reputation: 1498
I am using Rails 4.2.1 and Mongoid 4.0.0
I have a User
model, which embeds the Following
model. The effect I am trying to reach is:
{
username: # This is the id
...
followings: [
{
_id:
username:
datetime:
}
]
}
I do not want followings
to contain entries with the same username. How to achieve this?
I have tried two methods:
I put validates :username, presence: true, uniqueness: true
in the code for Following
model. But this validation is global - If I have John and Sam as two users, and John follows Sam, then when Sam wants to follow John, there is an error of duplication.
I added an index in the User
model:
index ({ 'followings.username': 1 }, { unique: true, drop_dups: true })
The problem with this approach is that, when I create a user John, the followings field for him will have a username null
, and then if I create a user Sam, an error is thrown because the null
username is duplicated:
E11000 duplicate key error index: myapp_development.users.$followings.username_1 dup key: { : null }
Really appreciate any help
Upvotes: 1
Views: 212
Reputation: 1498
Well, it turns out that due to fragmentation issue, this way of modeling User
and Following
will cause a growing size of the document, and does not make the best use of the 'Rich document' feature, and will impair the performance. From MongoDB doc:
In general, embedding provides better performance for read operations, as well as the ability to request and retrieve related data in a single database operation. Embedded data models make it possible to update related data in a single atomic write operation.
However, embedding related data in documents may lead to situations where documents grow after creation. With the MMAPv1 storage engine, document growth can impact write performance and lead to data fragmentation.
So I learned a lesson. Not being considerable enough before. So I will abandon this way of modeling and separate them out into different collections.
Upvotes: 1