@Slf4j @Aspect @Component public class DistributedLockAspect { private final ExpressionParser parser = new SpelExpressionParser(); private final DefaultParameterNameDiscoverer discoverer = new DefaultParameterNameDiscoverer(); @Autowired private RedissonClient redissonClient; @Around("@annotation(distributedLock)") public Object lock(ProceedingJoinPoint joinPoint, DistributedLock distributedLock) throws Throwable { // 使用spel解析注解中定义的key String keyValue = parseKeyValue(joinPoint, distributedLock.value()); // 拼接出锁名称 String lockName = connectLockName(distributedLock.keyPrefix(), keyValue, distributedLock.separator()); // 获取锁 RLock lock = getLock(distributedLock.lockModel(), lockName); try { if (lock.tryLock(distributedLock.waitLockMSec(), distributedLock.lockExpireMSec(), TimeUnit.MILLISECONDS)) { log.info("获取锁:{}", lockName); return joinPoint.proceed(); } throw new LockException(distributedLock.message()); } finally { lock.unlock(); } } private RLock getLock(DistributedLock.LockModel lockModel, String lockName) { switch (lockModel) { case FAIR: //公平锁 return redissonClient.getFairLock(lockName); case READ: //读之前加读锁,读锁的作用就是等待该lockkey释放写锁以后再读 return redissonClient.getReadWriteLock(lockName).readLock(); case WRITE: //写之前加写锁,写锁加锁成功,读锁只能等待 return redissonClient.getReadWriteLock(lockName).writeLock(); case REENTRANT: default: //可重入锁 return redissonClient.getLock(lockName); } } private String connectLockName(String prefix, String key, String separator) { if (StringUtils.isNotBlank(prefix)) { return prefix + separator + key; } return key; } private String parseKeyValue(ProceedingJoinPoint joinPoints, String elExpr) { MethodSignature methodSignature = (MethodSignature) joinPoints.getSignature(); Method method = methodSignature.getMethod(); //获取方法的参数值 Object[] args = joinPoints.getArgs(); EvaluationContext context = new StandardEvaluationContext(); String[] params = discoverer.getParameterNames(method); if (params != null) { for (int i = 0; i < params.length; i++) { context.setVariable(params[i], args[i]); } } //根据spel表达式获取值 Expression expression = parser.parseExpression(elExpr); Object value = expression.getValue(context); if (value != null) { return value.toString(); } return "defaultLockKey"; } }解释一下这段代码
时间: 2023-05-21 07:02:04 浏览: 83
这段代码是一个基于Spring AOP实现的分布式锁切面,它使用了Redisson作为分布式锁的实现。在使用@DistributedLock注解的方法上,会拦截方法的执行,获取注解中定义的key值,拼接出锁名称,然后获取对应的锁。如果获取锁成功,则执行方法,否则抛出LockException异常。其中,锁的类型可以是可重入锁、公平锁、读锁或写锁,可以通过注解中的lockModel属性指定。
相关问题
@Component @Slf4j public class AppRouter { @Autowired private AppService appService;}
您的第一个问题是关于一个名为 AppRouter 的类的注解和依赖注入方法。@Component 表示该类是一个 Spring 组件,在 Spring 容器中可以被管理和调用。@Slf4j 表示该类使用了 Lombok 的日志库,在编译时会自动生成日志相关的代码,使得开发者在代码中可以方便地打印日志。@Autowired 表示该类中的 appService 属性是一个被 Spring 容器托管的服务,可以自动注入到该类中,从而方便该类中使用该服务的方法。
@Slf4j @Component public class FMSGCallBack implements HCNetSDK.FMSGCallBack_V31 { @Autowired private RedisService redisService; redisService 报空指针异常
这个问题可能是因为你没有将 RedisService 注入到 FMSGCallBack 类中。你可以检查一下 FMSGCallBack 类是否被正确地注入到 Spring 容器中,并且 RedisService 是否被正确地注入到 FMSGCallBack 类中。
另外,如果你要在非 Spring 管理的类中使用 Spring 管理的 Bean,你可以通过 ApplicationContext 的 getBean 方法获取 Bean 对象,而不是使用 @Autowired 注解注入。可以尝试一下这个方法:
```
@Slf4j
@Component
public class FMSGCallBack implements HCNetSDK.FMSGCallBack_V31 {
private RedisService redisService;
@Override
public void invoke(NativeLong lCommand, HCNetSDK.NET_DVR_ALARMER pAlarmer, Pointer pAlarmInfo, int dwBufLen, Pointer pUser) {
// 通过 ApplicationContext 获取 RedisService Bean
ApplicationContext context = SpringContextUtil.getApplicationContext();
redisService = context.getBean(RedisService.class);
// 使用 redisService 对象进行操作
redisService.xxx();
}
}
```
这里通过 SpringContextUtil 工具类获取了 ApplicationContext,然后通过 ApplicationContext 获取了 RedisService Bean 对象,最终使用这个对象进行操作。注意,这里需要将 RedisService 类型传入 getBean 方法中。
相关推荐
![zip](https://img-home.csdnimg.cn/images/20210720083736.png)
![jar](https://img-home.csdnimg.cn/images/20210720083455.png)
![pdf](https://img-home.csdnimg.cn/images/20210720083512.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)