A website I'm creating lets users have a unique subdomain on the site eg; gaz123.mywebsite.com.
They enter their subdomain when they register on the site. In the code before I create the account record I check that the subdomain they've chosen doesn't already exist. This is just a simple query against accounts with the same subdomain. If this returns a zero count then I proceed and create the account with that subdomain.
I have placed a lock() command around the two MongoDB commands ie; check that the subdomain is available and then create the account. Then I release the lock.
lock( m_oLockMe)
{
if( SubdomainIsFree( oRegisterModel.SubDomain))
{
CreateAccount( oRegisterModel);
}
}
Is this how you would do it? Is there another way that is better? Why?
Thanks
This is not a good way - you lose scalability here. I'd do this with atomic findAndModify
. First you'll need to establish unique index on subdomain
field:
db.subdomains.ensureIndex({subdomain: 1}, {unique: true})
This is needed for upsert to not generate duplicates. Then you'll do this:
r = db.subdomains.findAndModify({query: {used: false, subdomain: <subdomain>}, update: {$set: {used: true}}, new: true, upsert: true})
This will either return document which represents free subdomain or throw duplicate key error which means the subdomain is used. For free subdomain this will also atomically set used
to true
so it's guaranteed only a single findAndModify
operation will get the same document.