1

Some processes at the same time read table. Each process takes on one task. Is it possbile don't use LOCK table in this case ?

db.session.execute('LOCK TABLE "Task"')
query = db.session.query(models.Task).order_by(models.Task.ordr).limit(1)
    for row in query:
        task = row
        db.session.delete(row)
 db.session.commit()

1 Answer 1

1

By locking table you use pessimistic approach to concurrency.

Alterntively, intead of locking the table, you can be optimistic about the things going the right way. I would wrap the code to retrieve a task to work on in a continues retry statement with error handling in case the commit fails because some other process already removed this very task this process tried to get.

Something like this, perhaps:

def get_next_task():
    session = ...
    task = None
    while not(task):
        try:
            query = session.query(models.Task).order_by(models.Task.ordr).limit(1)
                for row in query:
                    task = row
                    session.delete(row)
            session.commit()
            if not(task):
                return # no more tasks found
        except TODO_FIND_PROPER_EXCEPTION_TO_HANDLE as _exc:
            pass # or log the statement

    # maybe need to make_transient
    return task

Whether this solution is better will depend on the use case, though.

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.