自定义注解@RedisLock分布式锁用法及原理

前言

最近开发公司的项目,遇到了分布式的场景,即,同一条数据可能被多台服务器或者说多个线程同时修改,此时可能会出现分布式事务的问题,随即封装了redis分布式锁的注解。

场景分析

前提:我的银行卡有0元钱,现在有A,B两个人,想分别给我转10元钱
分析:
假如A,B通过读数据库,同时发现我的余额是0,这时,
线程A,会给我设置:
余额 = 10 + 0
线程B,会给我设置:
余额 = 10 + 0

最后,我的卡上收到了两个人的转账,但是最后金额居然只有10元!!这是怎么回事?
其实原因就在于多个线程,对一条数据同时进行了操作。如果我们可以设置一下,在修改的方法上面加一个锁,每次修改之前,(A)先拿到这个锁,再去做修改方法,此时,其他(B)线程想要修改的时候,看到锁已经不再,需要等待锁释放,然后再去执行,就保证了A,B先后依此执行,数据依此累加就没问题了。

解决办法

基于代码的可移植性,我将分布式锁做成了注解,大家如果有需要,可以直接将jar包拿过去做相应的修改即可,jar包下载地址(链接:https://pan.baidu.com/s/1hBn-...
提取码:1msl):

注解使用说明:
1.在需要添加分布式锁的方法上面加上@RedisLock
如果key不添加,则默认锁方法第一个参数param的id字段,如果需要指定锁某个字段,则@RedisLock(key = "code")
2.如果方法没有参数,则不可使用RedisLock锁

 @RedisLock
public void updateData( Data param){
    
}

下面详细分析一下封装的源码:

先看一下项目结构(总共就4个类):

clipboard.png

  //RedisLock注解类:没什么好解释的

  /**
 * Created by liuliang on 2018/10/15.
 */
@Target({ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
public @interface RedisLock {
    //被锁的数据的id
     String key() default "";

     //唤醒时间
     long acquireTimeout() default 6000L;

     //超时时间
     long timeout() default 6000L;
}
 //----------------------类分割线---------------------
//RedisService 一个简单的操作redis的类,封装了加锁和释放锁的方法

/**
 * Created by liuliang on 2018/10/15.
 */
@Service
public class RedisService {
@Autowired
StringRedisTemplate stringRedisTemplate;
@Resource(name = "stringRedisTemplate")
@Autowired
ValueOperations valOpsStr;

@Autowired
RedisTemplate redisTemplate;

@Resou
  • 0
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Dubbo是一种高性能、轻量级的开源Java RPC框架。@dubboservice是Dubbo框架中的一个注解,用于标记服务提供者的实现类。具体来说,@dubboservice注解可以用于标记一个类,表示这个类实现了某个接口,并且可以被Dubbo框架自动扫描到,注册为一个服务提供者。 @dubboservice注解有以下几个参数: 1. interfaceClass:服务接口类,必填参数。 2. version:服务版本号,可以填写多个版本号,用逗号分隔。 3. group:服务分组,可以填写多个分组,用逗号分隔。 4. delay:服务延迟暴露的时间,单位为毫秒,默认值为0。 5. executes:服务执行器的个数,即服务并发执行的线程数,默认值为0,表示不限制。 6. actives:服务的最大并发调用数,默认值为0,表示不限制。 7. timeout:服务调用超时时间,单位为毫秒,默认值为0,表示不设置超时时间。 8. retries:服务调用失败时的重试次数,默认值为2。 9. loadbalance:服务负载均衡策略,默认值为"random",可以设置为"roundrobin"、"leastactive"等。 10. async:是否异步调用服务,默认值为false。 11. onreturn:服务调用完成后执行的方法,可以是服务提供者的任意一个方法。 12. onthrow:服务调用出错后执行的方法,可以是服务提供者的任意一个方法。 下面是一个使用@dubboservice注解的示例: ```java @Service public class UserServiceImpl implements UserService { @Override @DubboService(version = "1.0.0", group = "user") public User getUserById(Long id) { // 查询用户信息的具体实现 } } ```

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值