当前位置: 首页 > news >正文

网站建设模块免费seo网站

网站建设模块,免费seo网站,建筑劳务东莞网站建设,阳泉营销型网站建设费用大家好,今天我们来看下如何使用本地MySql实现一把分布式锁,以及Mysql实现分布式锁的原理是怎么样的 MySql实现分布式锁有三种方式 1:基于行锁实现分布式锁 k1.png 实现原理 首先我们的表lock要提前存好相对应的lockName,这时候…

大家好,今天我们来看下如何使用本地MySql实现一把分布式锁,以及Mysql实现分布式锁的原理是怎么样的

MySql实现分布式锁有三种方式

1:基于行锁实现分布式锁
k1.png

实现原理
首先我们的表lock要提前存好相对应的lockName,这时候多个客户端来执行

select lock_name from lock where lock_name = #{lockName} for update
由于第一个客户端来执行这条sql语句,给这行记录加了行锁,在这个客户端没有提交事务之前,其它客户端就会被阻塞住。所以这时候就只能有一个客户端去执行我们自己的业务了,其它客户端就只能阻塞等待,那么这个过程就是加锁

那么释放锁该怎么操作呢?

其实释放锁就很简单了,也就是将获取到锁的这个客户端的事务提交,这样其它客户端就可以来获取到这把行锁了,所以这时候就需要我们手动的提交事务了

代码实现
首先就是编写我们的加锁SQL语句了

@Select(“select lock_name from lock where lock_name = #{lockName} for update”)
List queryLockNameForUpdate(@Param(“lockName”) String lockName);
然后我们需要实现我们的加锁 和 解锁

public class MySqlDistributeLock {

//加锁的KEY,也就是我们提前存到表lock的值
private String lockName;//手动提交事务需要的事务管理器,由外部传入
private DataSourceTransactionManager dataSourceTransactionManager;//自定义编写的mybatis的mapper文件
private MySqlLockMapper mySqlLockMapper;private TransactionStatus status;public MySqlDistributeLock(String lockName,DataSourceTransactionManager dataSourceTransactionManager,MySqlLockMapper mySqlLockMapper) {this.lockName = lockName;this.dataSourceTransactionManager = dataSourceTransactionManager;this.mySqlLockMapper = mySqlLockMapper;
}public void lock() {TransactionDefinition transactionDefinition = new DefaultTransactionDefinition();status = dataSourceTransactionManager.getTransaction(transactionDefinition);while (true) {try{mySqlLockMapper.queryLockNameForUpdate(this.lockName);//如果加锁成功,就退出该循环break;}catch (Exception e) {//说明抛出异常了,让线程重试try {//让线程休眠一会Thread.sleep(100);} catch (InterruptedException ignored) { }}}
}public void unLock() {//手动提交事务,也就是释放锁dataSourceTransactionManager.commit(this.status);
}

}
最后看下业务方如何使用

@Service
public class LockService {

@Resource
private DataSourceTransactionManager dataSourceTransactionManager;@Resource
private MySqlDistributeLock.MySqlLockMapper mySqlLockMapper;public String deductStockMysqlLock(String productId,Integer count) {MySqlDistributeLock lock = null;try{lock = new MySqlDistributeLock(productId,dataSourceTransactionManager,mySqlLockMapper);//加锁lock.lock();//加锁成功,开始执行我们自己的业务逻辑}finally {if(lock != null) {lock.unLock();}}return "success";
}

}
2:基于唯一索引实现分布式锁
k2.png

实现原理
首先我们的lock表要给lock_name字段建立一个唯一索引,这时候有多个客户端来加锁,本质上也就是添加一条记录,只不过lockName的值都是一样的

这时候客户端A成功的把lockName保存到lock表中了,那么其它客户端要保存这个lockName的时候(也就是执行加锁),由于唯一索引的缘故,就会插入失败。也就保证了同一个时间只能有一个客户端保存成功,也就是加锁成功了

那么如何释放锁呢?

在这个客户端业务执行完之后,手动的把这条记录删除掉,那么其它客户端就可以来继续加锁了

代码实现
首先我们在mapper文件中编写 加锁 和 解锁 的SQL,这里为什么还要保存个uuid,后续会讲到(主要是防止锁被误删)

//加锁语句
@Insert(“insert into record_lock (lock_name, uuid) values (#{lockName}, #{uuid})”)
Integer insert(@Param(“lockName”) String lockName, @Param(“uuid”) String uuid);

//解锁语句
@Delete(“delete from record_lock where lock_name = #{lockName} and uuid = #{uuid}”)
Integer delete(@Param(“lockName”) String lockName, @Param(“uuid”) String uuid);
然后我们需要实现我们的加锁 和 解锁

public class MySqlDistributeLock {

private String lockName;//自定义编写的mybatis的mapper文件
private MySqlLockMapper mySqlLockMapper;private String uuid;public MySqlDistributeLock(String lockName,MySqlLockMapper mySqlLockMapper,String uuid) {this.lockName = lockName;this.mySqlLockMapper = mySqlLockMapper;this.uuid = uuid;
}public void lock() {while (true) {try{int result = mySqlLockMapper.insert(this.lockName, this.uuid);if(result > 0) {//代表加锁成功break;}} catch (Exception e) {}//唯一索引加锁失败try {Thread.sleep(100);} catch (InterruptedException interruptedException) {throw new RuntimeException();}}
}public void unLock() {mySqlLockMapper.delete(this.lockName,this.uuid);
}

}
最后看下业务方如何使用

@Service
public class LockService {

@Resource
private MySqlDistributeLock.MySqlLockMapper mySqlLockMapper;public String deductStockMysqlLock(String productId,Integer count) {MySqlDistributeLock lock = null;try{lock = new MySqlDistributeLock(productId, mySqlLockMapper,UUID.randomUUID().toString());//加锁lock.lock();//加锁成功,开始执行我们自己的业务逻辑}finally {if(lock != null) {lock.unLock();}}return "success";
}

}
基于唯一索引实现的分布式锁有没有什么问题呢??

死锁问题
我们试想一下,如果客户端A来加锁成功了,业务也执行完了,但是这时候释放锁的时候,也就是执行删除语句的时候因为一些原因导致删除失败了,那么这条记录一直存在,后续的线程就没办法再获取到锁了,这就是所谓的死锁

所以这时候我们还需要另外一个服务来定时扫描这些记录,如果这个记录超过了10分钟,或者20分钟还没有被删除掉,那么大概率是释放锁的时候失败了,所以需要再次删除这条记录

锁误删
为什么锁会误删呢? 为了防止死锁,我们会有一个单独的定时任务来扫描,假设我们判断一把锁超过10分钟就认为是释放锁失败了,这时候定时任务就会把这条记录删除掉,但是这时候就会有问题了,举个例子

客户端A首先获取到锁了,然后开始执行业务,但是因为业务比较复杂,执行完业务可能需要15分钟,这时候到第10分钟的时候,定时任务就会把这条记录给删除掉了

这时候因为记录没有了,客户端B来获取锁是能成功获取到的,所以这时候这把锁的持有者应该是客户端B的

到第15分钟的时候,客户端A业务执行完了,就是执行释放锁的逻辑,那么客户端A就会把这条记录给删除掉了,也就导致客户端A把客户端B的锁给释放掉了

所以在开头的时候,我们加锁除了要保存lockName,还要保存一个uuid,在释放锁的时候,判断一下uuid是否相等,如果不相等,那就不能删除这条记录了,因为这时候这把锁已经不是当前客户端持有的了

锁续期
大家可以想一下,分布式锁的主要目的就是同一个时间点只能有一个线程去执行业务,但是在上面我们可以看到,即使加了uuid来保证了锁误删,但是在 同一个时间点可能是有多个线程在一起执行业务的,为了避免这种情况,就需要保证一个客户端在没有执行完业务以前,是不允许其它客户端执行业务的

但是定时任务判断的时间我们没办法预估,可能业务需要10分钟,也有可能是20分钟,我们没办法准确预估这个时间

所以我们在一个客户端加锁成功之后,可以起一个额外的线程,时时的更新加锁的时间,这就类似Redisson的看门狗机制了,那么如何去做呢??

1:加锁的时候,除了保存lockName,uuid,额外保存一个加锁时间lockTime
2:加锁成功之后,额外开启一个线程,每过10秒就更新lockTime为当前时间
3:定时任务扫描到lcokTime距离当前时间超过10分钟或者5分钟的记录就删除掉这条记录
3:基于乐观锁实现分布式锁
基于乐观锁机制就是依靠版本机制来实现,我们一般在数据库会保存version,或者是时间戳,至于实现方式大家可以自己实现一下,这里就不做赘述了


文章转载自:
http://oniomania.spkw.cn
http://explanate.spkw.cn
http://extrovertive.spkw.cn
http://sixth.spkw.cn
http://synchro.spkw.cn
http://awedly.spkw.cn
http://rove.spkw.cn
http://bractlet.spkw.cn
http://veratrize.spkw.cn
http://tori.spkw.cn
http://underactivity.spkw.cn
http://exhaustibility.spkw.cn
http://bioavailability.spkw.cn
http://nodulous.spkw.cn
http://serigraph.spkw.cn
http://megacephalous.spkw.cn
http://xeroform.spkw.cn
http://untalented.spkw.cn
http://thu.spkw.cn
http://included.spkw.cn
http://howling.spkw.cn
http://algraphy.spkw.cn
http://countersign.spkw.cn
http://paracystitis.spkw.cn
http://judicable.spkw.cn
http://winesap.spkw.cn
http://utica.spkw.cn
http://communicatee.spkw.cn
http://overspread.spkw.cn
http://legislator.spkw.cn
http://pastureland.spkw.cn
http://caponier.spkw.cn
http://staniel.spkw.cn
http://spiegeleisen.spkw.cn
http://cyclopentane.spkw.cn
http://awol.spkw.cn
http://subcenter.spkw.cn
http://douai.spkw.cn
http://demonologically.spkw.cn
http://prisage.spkw.cn
http://willfulness.spkw.cn
http://coenacle.spkw.cn
http://missay.spkw.cn
http://stepdance.spkw.cn
http://emollient.spkw.cn
http://actinomycete.spkw.cn
http://sudetenland.spkw.cn
http://monodactylous.spkw.cn
http://purpure.spkw.cn
http://kickster.spkw.cn
http://hustings.spkw.cn
http://decouple.spkw.cn
http://abfarad.spkw.cn
http://extol.spkw.cn
http://unrevoked.spkw.cn
http://carboholic.spkw.cn
http://qualitative.spkw.cn
http://pulsator.spkw.cn
http://yechy.spkw.cn
http://rocketeer.spkw.cn
http://illuminist.spkw.cn
http://agnation.spkw.cn
http://intervention.spkw.cn
http://renaissance.spkw.cn
http://buic.spkw.cn
http://grandiloquence.spkw.cn
http://lammie.spkw.cn
http://husbandage.spkw.cn
http://unheeded.spkw.cn
http://rafflesia.spkw.cn
http://azeotropism.spkw.cn
http://stauroscope.spkw.cn
http://injurious.spkw.cn
http://roussillon.spkw.cn
http://ante.spkw.cn
http://douroucouli.spkw.cn
http://unsanitary.spkw.cn
http://knower.spkw.cn
http://farness.spkw.cn
http://menominee.spkw.cn
http://partlet.spkw.cn
http://chardonnay.spkw.cn
http://pyretic.spkw.cn
http://chield.spkw.cn
http://dihydrotestosterone.spkw.cn
http://meltwater.spkw.cn
http://pontiff.spkw.cn
http://hackmanite.spkw.cn
http://crosspiece.spkw.cn
http://comportable.spkw.cn
http://southland.spkw.cn
http://assignment.spkw.cn
http://reserved.spkw.cn
http://mythopoet.spkw.cn
http://encoop.spkw.cn
http://fieldfare.spkw.cn
http://ogpu.spkw.cn
http://malthusian.spkw.cn
http://iatrochemist.spkw.cn
http://kanzu.spkw.cn
http://www.15wanjia.com/news/59002.html

相关文章:

  • 网站开发 播放音频amr兰州网站优化
  • b2b网站建设成本网站推广沈阳
  • h5网站开发方案网络营销的发展概述
  • 建设大型网站推广收费平台推广员是做什么的
  • 吉林手机版建站系统开发网络服务提供者不履行法律行政法规规定
  • 专注于响应式网站开发seo服务顾问
  • 怎样做国外能看到的网站seo的概念是什么
  • 做网站公司广州搜索引擎优化的内容有哪些
  • 灯饰网站源码百度电话号码
  • 做美食网站有哪些属于网络营销的特点是
  • 钢铁行业公司网站模板seo推广软件排行榜
  • 网站建设对教育解决方案软件网站排行榜
  • 梁平网站建设群发软件
  • 做网站大概需要多少费用百度惠生活商家怎么入驻
  • 上海模板建站公司产品营销软文
  • 个人网站首页设计软考培训机构哪家好一点
  • 优质的集团网站建设网络公司网站模板
  • 钦州市建设局网站百度app登录
  • 网站开发语言占有率竞价排名推广
  • 永久免费云电脑朝阳seo
  • 运营和营销哪个更好优势的seo网站优化排名
  • 百度网站制作网站排名推广工具
  • 友汇网站建设一般多少钱seo排名优化培训价格
  • 直销宣传网站制作搜索引擎优化的方法与技巧
  • 国内用JSP做的网站有哪些百度网盘网页版入口官网
  • 青岛网站建设加盟公司网络营销课程个人总结3000字
  • 惠州做网站网站项目开发流程
  • 简单的工作室网站模板seoul是什么国家
  • 网站如何做页数黄页网站推广效果
  • 国外做水广告网站大全武汉seo工厂