parent
a1eb17e4fd
commit
7a1da5b9ab
10 changed files with 346 additions and 21 deletions
@ -1,5 +1,5 @@ |
|||||||
|
|
||||||
package org.springblade.system.config; |
package org.springblade.system.user.config; |
||||||
|
|
||||||
|
|
||||||
import lombok.AllArgsConstructor; |
import lombok.AllArgsConstructor; |
||||||
@ -0,0 +1,45 @@ |
|||||||
|
package org.springblade.system.user.config; |
||||||
|
|
||||||
|
import lombok.extern.slf4j.Slf4j; |
||||||
|
import org.redisson.Redisson; |
||||||
|
import org.redisson.api.RedissonClient; |
||||||
|
import org.redisson.config.Config; |
||||||
|
import org.springframework.beans.factory.annotation.Value; |
||||||
|
import org.springframework.context.annotation.Bean; |
||||||
|
import org.springframework.context.annotation.Configuration; |
||||||
|
|
||||||
|
/** |
||||||
|
* redisson配置类 |
||||||
|
* @author ytl |
||||||
|
* @since 2022-10-13 15:11 |
||||||
|
*/ |
||||||
|
@Slf4j |
||||||
|
@Configuration |
||||||
|
public class RedissonConfig { |
||||||
|
@Value("${spring.redis.host}") |
||||||
|
private String host; |
||||||
|
|
||||||
|
@Value("${spring.redis.port}") |
||||||
|
private String port; |
||||||
|
|
||||||
|
@Value("${spring.redis.password}") |
||||||
|
private String password; |
||||||
|
|
||||||
|
@Bean |
||||||
|
public RedissonClient redissonClient(){ |
||||||
|
Config config = new Config(); |
||||||
|
|
||||||
|
config.useSingleServer() |
||||||
|
.setAddress("redis://" + host + ":" + port) |
||||||
|
.setDatabase(0) |
||||||
|
.setPingConnectionInterval(2000); |
||||||
|
config.setLockWatchdogTimeout(10000L); |
||||||
|
try{ |
||||||
|
return Redisson.create(config); |
||||||
|
}catch (Exception e){ |
||||||
|
log.error("创建redisson连接错误"); |
||||||
|
return null; |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
} |
||||||
@ -0,0 +1,27 @@ |
|||||||
|
package org.springblade.system.user.mettinghandler; |
||||||
|
|
||||||
|
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper; |
||||||
|
import lombok.extern.slf4j.Slf4j; |
||||||
|
import org.springblade.system.user.entity.Train; |
||||||
|
import org.springblade.system.user.service.ITrainService; |
||||||
|
import org.springframework.beans.factory.annotation.Autowired; |
||||||
|
import org.springframework.stereotype.Component; |
||||||
|
|
||||||
|
/** |
||||||
|
* @author ytl |
||||||
|
* @since 2022-10-13 16:11 |
||||||
|
*/ |
||||||
|
@Slf4j |
||||||
|
@Component("mettingEndHandler") |
||||||
|
public class MettingEndHandler implements RedissonDelayQueuHandlle<String> { |
||||||
|
@Autowired |
||||||
|
private ITrainService trainService; |
||||||
|
|
||||||
|
@Override |
||||||
|
public void execute(String id) { |
||||||
|
LambdaUpdateWrapper<Train> wrapper = new LambdaUpdateWrapper<Train>(); |
||||||
|
wrapper.eq(Train::getId, id).set(Train::getStatus, 2); |
||||||
|
trainService.update(wrapper); |
||||||
|
log.info("有会议结束了,会议id:{}", id); |
||||||
|
} |
||||||
|
} |
||||||
@ -0,0 +1,48 @@ |
|||||||
|
package org.springblade.system.user.mettinghandler; |
||||||
|
|
||||||
|
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; |
||||||
|
import lombok.extern.slf4j.Slf4j; |
||||||
|
import org.springblade.resource.enums.SysTypeEnum; |
||||||
|
import org.springblade.resource.feign.IMessageClient; |
||||||
|
import org.springblade.system.user.entity.Train; |
||||||
|
import org.springblade.system.user.entity.TrainPerson; |
||||||
|
import org.springblade.system.user.service.ITrainPersonService; |
||||||
|
import org.springblade.system.user.service.ITrainService; |
||||||
|
import org.springframework.beans.factory.annotation.Autowired; |
||||||
|
import org.springframework.stereotype.Component; |
||||||
|
|
||||||
|
import java.util.List; |
||||||
|
|
||||||
|
/** |
||||||
|
* @author ytl |
||||||
|
* @since 2022-10-13 16:09 |
||||||
|
*/ |
||||||
|
@Slf4j |
||||||
|
@Component("mettingRemindHandler") |
||||||
|
public class MettingRemindHandler implements RedissonDelayQueuHandlle<String>{ |
||||||
|
@Autowired |
||||||
|
private ITrainService trainService; |
||||||
|
|
||||||
|
@Autowired |
||||||
|
private ITrainPersonService trainPersonService; |
||||||
|
|
||||||
|
@Autowired |
||||||
|
private IMessageClient messageClient; |
||||||
|
|
||||||
|
@Override |
||||||
|
public void execute(String id) { |
||||||
|
LambdaQueryWrapper<TrainPerson> wrapper = new LambdaQueryWrapper<>(); |
||||||
|
wrapper.eq(TrainPerson::getTrainId, id); |
||||||
|
List<TrainPerson> list = trainPersonService.list(wrapper); |
||||||
|
Train train = trainService.getById(id); |
||||||
|
// if (list.size() > 0) {
|
||||||
|
// list.forEach(person -> {
|
||||||
|
// messageClient.event(SysTypeEnum.INFORM.getValue(), "会议提醒",
|
||||||
|
// "您有新的会议将在" + train.getDuration() + "分钟后开始,请准时参加!", 1, 5, person.getPersonName(), "/train/project");
|
||||||
|
// });
|
||||||
|
// }
|
||||||
|
// messageClient.event(SysTypeEnum.INFORM.getValue(), "会议提醒",
|
||||||
|
// "您有新的会议将在" + train.getDuration() + "分钟后开始,请准时参加!", 1, 5, train.getTeacherName(), "/train/project");
|
||||||
|
log.info("有会议即将开始,会议id:{}", id); |
||||||
|
} |
||||||
|
} |
||||||
@ -0,0 +1,6 @@ |
|||||||
|
package org.springblade.system.user.mettinghandler; |
||||||
|
|
||||||
|
public interface RedissonDelayQueuHandlle<T> { |
||||||
|
void execute(T t); |
||||||
|
|
||||||
|
} |
||||||
@ -0,0 +1,27 @@ |
|||||||
|
package org.springblade.system.user.util; |
||||||
|
|
||||||
|
import lombok.AllArgsConstructor; |
||||||
|
import lombok.Getter; |
||||||
|
import lombok.NoArgsConstructor; |
||||||
|
|
||||||
|
/** |
||||||
|
* @author ytl |
||||||
|
* @since 2022-10-13 15:59 |
||||||
|
*/ |
||||||
|
|
||||||
|
@Getter |
||||||
|
@NoArgsConstructor |
||||||
|
@AllArgsConstructor |
||||||
|
public enum QueueEnum { |
||||||
|
METTING_REMAIND("METTING_REMAIND" ,"会议即将开始", "mettingRemindHandler"), |
||||||
|
METTING_END("METTING_END", "会议结束了" ,"mettingEndHandler"); |
||||||
|
|
||||||
|
//延迟队列key
|
||||||
|
private String code; |
||||||
|
|
||||||
|
//中文描述
|
||||||
|
private String name; |
||||||
|
|
||||||
|
//具体业务的bean
|
||||||
|
private String beanId; |
||||||
|
} |
||||||
@ -0,0 +1,60 @@ |
|||||||
|
package org.springblade.system.user.util; |
||||||
|
|
||||||
|
|
||||||
|
import lombok.extern.slf4j.Slf4j; |
||||||
|
import org.springblade.system.user.mettinghandler.RedissonDelayQueuHandlle; |
||||||
|
import org.springframework.beans.factory.annotation.Autowired; |
||||||
|
import org.springframework.boot.CommandLineRunner; |
||||||
|
import org.springframework.context.ApplicationContext; |
||||||
|
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor; |
||||||
|
import org.springframework.stereotype.Component; |
||||||
|
|
||||||
|
import java.util.concurrent.TimeUnit; |
||||||
|
|
||||||
|
/** |
||||||
|
* 系统启动后自动启动,监听延迟队列 |
||||||
|
* @author ytl |
||||||
|
* @since 2022-10-13 15:55 |
||||||
|
*/ |
||||||
|
@Slf4j |
||||||
|
@Component |
||||||
|
public class RedisDelayQueueRunner implements CommandLineRunner { |
||||||
|
@Autowired |
||||||
|
private RedisDelayQueueUtil redisDelayQueueUtil; |
||||||
|
|
||||||
|
@Autowired |
||||||
|
private ApplicationContext context; |
||||||
|
|
||||||
|
//spring封装的
|
||||||
|
@Autowired |
||||||
|
private ThreadPoolTaskExecutor threadPoolTaskExecutor; |
||||||
|
|
||||||
|
@Override |
||||||
|
public void run(String... args) throws Exception { |
||||||
|
|
||||||
|
threadPoolTaskExecutor.execute(() -> { |
||||||
|
while (true) { |
||||||
|
QueueEnum[] queueEnums = QueueEnum.values(); |
||||||
|
for (QueueEnum en : queueEnums) { |
||||||
|
try { |
||||||
|
String value = (String)redisDelayQueueUtil.getDelayQueue(en.getCode()); |
||||||
|
if (value != null){ |
||||||
|
RedissonDelayQueuHandlle<Object> bean = (RedissonDelayQueuHandlle<Object>)context.getBean(en.getBeanId()); |
||||||
|
bean.execute(value); |
||||||
|
} |
||||||
|
|
||||||
|
} catch (Exception e) { |
||||||
|
log.error("延迟队列监控失败"); |
||||||
|
} |
||||||
|
try { |
||||||
|
TimeUnit.MILLISECONDS.sleep(500); |
||||||
|
} catch (InterruptedException e) { |
||||||
|
e.printStackTrace(); |
||||||
|
} |
||||||
|
} |
||||||
|
} |
||||||
|
}); |
||||||
|
|
||||||
|
log.info("延迟队列监听成功"); |
||||||
|
} |
||||||
|
} |
||||||
@ -0,0 +1,91 @@ |
|||||||
|
package org.springblade.system.user.util; |
||||||
|
|
||||||
|
import lombok.NonNull; |
||||||
|
import lombok.extern.slf4j.Slf4j; |
||||||
|
|
||||||
|
import org.apache.commons.lang.StringUtils; |
||||||
|
import org.redisson.api.RBlockingDeque; |
||||||
|
import org.redisson.api.RDelayedQueue; |
||||||
|
import org.redisson.api.RedissonClient; |
||||||
|
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean; |
||||||
|
import org.springframework.stereotype.Component; |
||||||
|
|
||||||
|
import javax.annotation.Resource; |
||||||
|
import java.util.Objects; |
||||||
|
import java.util.concurrent.TimeUnit; |
||||||
|
|
||||||
|
/** |
||||||
|
* redisson延迟队列工具类 |
||||||
|
* @author ytl |
||||||
|
* @since 2022-10-13 15:24 |
||||||
|
*/ |
||||||
|
@Slf4j |
||||||
|
@Component |
||||||
|
@ConditionalOnBean(RedissonClient.class) |
||||||
|
public class RedisDelayQueueUtil { |
||||||
|
@Resource |
||||||
|
private RedissonClient redissonClient; |
||||||
|
|
||||||
|
/** |
||||||
|
* 添加到延迟队列 |
||||||
|
* @param value 值 |
||||||
|
* @param delayTime 延迟时间 |
||||||
|
* @param timeUnit 时间单位 |
||||||
|
* @param queueCode 队列键 |
||||||
|
* @param <T> |
||||||
|
* @return |
||||||
|
*/ |
||||||
|
public <T> boolean addDelayQueue(@NonNull T value, @NonNull long delayTime, |
||||||
|
@NonNull TimeUnit timeUnit, @NonNull String queueCode){ |
||||||
|
if (StringUtils.isBlank(queueCode) || Objects.isNull(value)) { |
||||||
|
return false; |
||||||
|
} |
||||||
|
|
||||||
|
try{ |
||||||
|
RBlockingDeque<Object> blockingDeque = redissonClient.getBlockingDeque(queueCode); |
||||||
|
RDelayedQueue<Object> delayedQueue = redissonClient.getDelayedQueue(blockingDeque); |
||||||
|
delayedQueue.offer(value, delayTime, timeUnit); |
||||||
|
log.info("添加延时队列成功,队列键:{},值:{},延迟时间:{}", queueCode, value, timeUnit.toSeconds(delayTime)); |
||||||
|
} catch (Exception e) { |
||||||
|
log.error("添加延时队列失败,{}", e.getMessage()); |
||||||
|
} |
||||||
|
|
||||||
|
return true; |
||||||
|
} |
||||||
|
|
||||||
|
/** |
||||||
|
* 获取延迟队列值 |
||||||
|
* @param queueCode |
||||||
|
* @param <T> |
||||||
|
* @return |
||||||
|
* @throws Exception |
||||||
|
*/ |
||||||
|
public <T> T getDelayQueue(@NonNull String queueCode) throws Exception{ |
||||||
|
if (StringUtils.isBlank(queueCode)) { |
||||||
|
return null; |
||||||
|
} |
||||||
|
|
||||||
|
RBlockingDeque<Object> blockingDeque = redissonClient.getBlockingDeque(queueCode); |
||||||
|
RDelayedQueue<Object> delayedQueue = redissonClient.getDelayedQueue(blockingDeque); |
||||||
|
|
||||||
|
T value = (T)blockingDeque.poll(); |
||||||
|
return value; |
||||||
|
} |
||||||
|
|
||||||
|
/** |
||||||
|
* 删除指定队列中的消息 |
||||||
|
* @param o |
||||||
|
* @param queueCode |
||||||
|
* @return |
||||||
|
*/ |
||||||
|
public boolean removeDelayQueue(@NonNull Object o, @NonNull String queueCode){ |
||||||
|
if (StringUtils.isBlank(queueCode) || Objects.isNull(o)) { |
||||||
|
return false; |
||||||
|
} |
||||||
|
|
||||||
|
RBlockingDeque<Object> blockingDeque = redissonClient.getBlockingDeque(queueCode); |
||||||
|
RDelayedQueue<Object> delayedQueue = redissonClient.getDelayedQueue(blockingDeque); |
||||||
|
boolean flag = delayedQueue.remove(o); |
||||||
|
return flag; |
||||||
|
} |
||||||
|
} |
||||||
Loading…
Reference in new issue