基于SpringBoot,MybatisPlus与MySql实现简易分布式锁

本文详细介绍了如何在Java中设计数据库表(包括lock_info表结构),使用Mapper、Entity和Service进行数据操作,以及实现分布式锁功能的验证过程。
摘要由CSDN通过智能技术生成

1. 数据库表设计

DROP TABLE IF EXISTS `lock_info`;
CREATE TABLE `lock_info` (
  `id` bigint(20) NOT NULL,
  `expiration_time` datetime NOT NULL,
  `status` int(11) NOT NULL,
  `tag` varchar(255) NOT NULL,
  PRIMARY KEY (`id`),
  UNIQUE KEY `uk_tag` (`tag`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;

2. Mapper代码示例

@Mapper
public interface LockInfoMapper  extends BaseMapper<LockInfoEntity>{
    /** 
     * 分页查询指定行数据
     *
     * @param page 分页参数
     * @param wrapper 动态查询条件
     * @return 分页对象列表
     */
    IPage<LockInfoEntity> selectByPage(IPage<LockInfoEntity> page , @Param(Constants.WRAPPER) Wrapper<LockInfoEntity> wrapper);

    LockInfoEntity findByTag(String tag);

    int deleteByTag(String tag);
}

3.Entity代码示例

@Data
@TableName("lock_info")
public class LockInfoEntity implements Serializable,Cloneable{
     public final static Integer LOCKED_STATUS = 1;
     public final static Integer UNLOCKED_STATUS = 0;
    /**  */
    @TableId
    private Long id ;
    /**  */
    private Date expirationTime ;
    /**  */
    private Integer status ;
    /**  */
    private String tag ;

     public LockInfoEntity(String tag, Date expirationTime, Integer status) {
         this.tag = tag;
         this.expirationTime = expirationTime;
         this.status = status;
     }
}

4.Service代码示例

@Override
     @Transactional(rollbackFor = Throwable.class)
     public boolean tryLock(String tag, Integer expiredSeconds) {
         if (StringUtils.isEmpty(tag)) {
             throw new NullPointerException();
         }
         LockInfoEntity lockItem = lockInfoMapper.findByTag(tag);
         if (Objects.isNull(lockItem)) {
             lockInfoMapper.insert(new LockInfoEntity(tag, this.addSeconds(new Date(), expiredSeconds), LockInfoEntity.LOCKED_STATUS));
             return true;
         } else {
             Date expiredTime = lockItem.getExpirationTime();
             Date now = new Date();
             if (expiredTime.before(now)) {
                 lockItem.setExpirationTime(this.addSeconds(now, expiredSeconds));
                 lockInfoMapper.updateById(lockItem);
                 return true;
             }
         }
         return false;
     }

     @Override
     public boolean unlock(String tag) {
         if (StringUtils.isEmpty(tag)) {
             throw new NullPointerException();
         }
         int cnt = lockInfoMapper.deleteByTag(tag);
         return cnt==1 ? true : false;
     }

    private Date addSeconds(Date date, Integer seconds) {
        if (Objects.isNull(seconds)){
            seconds = DEFAULT_EXPIRED_SECONDS;
        }
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(date);
        calendar.add(Calendar.SECOND, seconds);
        return calendar.getTime();
    }

5. 分布式锁功能验证代码示例、

    @GetMapping("/test")
    public String testBusiness(@RequestParam String tag, @RequestParam Integer expiredSeconds) {
        if (lockService.tryLock(tag, expiredSeconds)) {
            try {
                //do something
                Thread.sleep(3000);
            } catch (Exception e) {

            } finally {
                lockService.unlock(tag);
            }
            return "获取锁成功,tag是:" + tag;
        }
        return "当前tag:" + tag + "已经存在锁,请稍后重试!";
    }

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

u010303355

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值