You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
def_increment_provider_generation(ctx, rp):
"""Increments the supplied provider's generation value, supplying the currently-known generation. Returns whether the increment succeeded. :param ctx: `nova.context.RequestContext` that contains an oslo_db Session :param rp: `ResourceProvider` whose generation should be updated. :returns: The new resource provider generation value if successful. :raises nova.exception.ConcurrentUpdateDetected: if another thread updated the same resource provider's view of its inventory or allocations in between the time when this object was originally read and the call to set the inventory. """rp_gen=rp.generationnew_generation=rp_gen+1# 注意这里的更新条件,通过id及generation匹配upd_stmt=_RP_TBL.update().where(sa.and_(
_RP_TBL.c.id==rp.id,
_RP_TBL.c.generation==rp_gen)).values(
generation=(new_generation))
res=ctx.session.execute(upd_stmt)
# 如果rowcount为0,说明已经不是之前的RP了ifres.rowcount!=1:
raiseexception.ConcurrentUpdateDetectedreturnnew_generation
1. 背景
最近,在处理Nova Metadata并发更新的问题(bug/1650188)的时候,发现Resource Provider的并发控制机制在最开始就考虑,是通过乐观锁的机制实现并发控制的,简单的说就是:
其实,这个方式就是我们常说的乐观并发控制(OCC, Optimistic Concurrency Control,也称作乐观锁)机制。
2. 详细流程
用户通过API对Resource Provider的资源进行更新时,会传入一个generation参数
在最终的数据刷新时,完成事务提交前,会对generation进行刷新,例如对于本例中的traits更新,对应的代码在这里:nova/objects/resource_provider.py#def _set_traits,相当于做了一次检查,如果generation和用户预期的一致,更新成功,如果更新失败,则会raise并发更新失败的error。
如上图所示,如果操作A和操作B并发的请求进来,当A请求成功后,刷新了genration,这样,当B进行刷新的时候,就会刷新失败。
在Placement中,在对Resource Provider下的资源(例如allocation、inventory、trait等)进行修改时,均会对resource provider的generation进行刷新。我们看下实现的细节:
3. 参考
The text was updated successfully, but these errors were encountered: