0

A server is running multiple processes, process reads task from DB. Tasks contain status and _userid, which is external key for users collection. Look like like:

{
  _userid: ObjectId(),
  status: 'waiting',
  date: Date()
}

Status can be: 'waiting', 'in progress', 'finished'. For every user I need tasks to run ordered by date and only one at a time. How can I build a query that selects one task:

  1. If nothing 'in progress', select first with status 'waiting' and update status to 'in progress'
  2. If something is 'in progress', select task that has status 'waiting' and does not belong to _userid of any task that has status 'in progress' (reminder: only one at a time for every user). And also update status to 'in progress'

Is the query like this possible in MongoDB?

EDIT: For example, I've got a tasks in DB:

{
  _userid: ObjectId(1),
  status: 'waiting',
  date: Date(1)
},
{
  _userid: ObjectId(1),
  status: 'waiting',
  date: Date(2)
},
{
  _userid: ObjectId(2),
  status: 'waiting',
  date: Date(3)
},
{
  _userid: ObjectId(2),
  status: 'waiting',
  date: Date(4)
}

In this case, first task should be chosen from tasks, because everything is 'waiting'. After first task has been chosen it becomes 'in progress':

{
  _userid: ObjectId(1),
  status: 'in progress',
  date: Date(1)
},
{
  _userid: ObjectId(1),
  status: 'waiting',
  date: Date(2)
},
{
  _userid: ObjectId(2),
  status: 'waiting',
  date: Date(3)
},
{
  _userid: ObjectId(2),
  status: 'waiting',
  date: Date(4)
}

Now, next task should be chosen with status 'waiting' and not with _userid: ObjectId(1). It will be ObjectId(2) with Date(3). After that we have 2 _userid 'in progress': ObjectId(1) and ObjectId(2), so next request should receive nothing.

{
  _userid: ObjectId(1),
  status: 'in progress',
  date: Date(1)
},
{
  _userid: ObjectId(1),
  status: 'waiting',
  date: Date(2)
},
{
  _userid: ObjectId(2),
  status: 'in progress',
  date: Date(3)
},
{
  _userid: ObjectId(2),
  status: 'waiting',
  date: Date(4)
}

When first task is finished it's status will be 'finished' and now query must receive second task for ObjectId(1), because it's status 'waiting' and nothing else runs for this ObjectId(1).

{
  _userid: ObjectId(1),
  status: 'finished',
  date: Date(1)
},
{
  _userid: ObjectId(1),
  status: 'in progress',
  date: Date(2)
},
{
  _userid: ObjectId(2),
  status: 'in progress',
  date: Date(3)
},
{
  _userid: ObjectId(2),
  status: 'waiting',
  date: Date(4)
}

EDIT 2: OK, irrelevant any more

  • What is the MongoDB version(x,y,z)? – Md Haidar Ali Khan Mar 4 at 10:19
  • @MdHaidarAliKhan Atlas says: Version 3.6.17 – Naryck Mar 4 at 11:16

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.