一、问题描述

PLC每10分钟向我的服务器推送一条现场监测数据。现需实现自动化监控PLC的状态,并在数据库中实时更新其状态,以确保对PLC运行状况的即时了解与记录。

二、解决思路

每次接收到数据时,将推送数据中的 PLC 设备编号存储到 Redis 缓存中,并为其设置一个 10 分钟的 TTL(生存时间)。在后续接收到数据时,更新该设备编号的缓存记录。利用 Redis 自带的缓存过期事件监听功能,当检测到 PLC 设备编号缓存过期时,自动触发相关业务处理流程,例如将设备状态更新为离线状态,并发送设备离线报警信息等.

三、操作步骤(Redis 缓存过期事件监听使用教程)

1. 引入依赖

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>

2. 开启 Redis 过期事件监听

在这里插入图片描述

# 启用缓存过期事件监听
notify-keyspace-events Ex

3. 配置 Redis

@Configuration
public class RedisListenerConfig {

    /**
     * Redis 消息侦听器容器
     *
     * @param connectionFactory 连接工厂
     * @return {@link RedisMessageListenerContainer }
     */
    @Bean
    public RedisMessageListenerContainer redisMessageListenerContainer(RedisConnectionFactory connectionFactory) {
        RedisMessageListenerContainer container = new RedisMessageListenerContainer();
        container.setConnectionFactory(connectionFactory);
        return container;
    }

    /**
     * 设备 ID 缓存过期侦听器
     *
     * @param container 容器
     * @return {@link DeviceIdKeyExpirationListener }
     */
    @Bean
    public DeviceIdKeyExpirationListener deviceIdKeyExpirationListener(RedisMessageListenerContainer container) {
        // 配置监听器只监听 `deviceId:*` 键
        DeviceIdKeyExpirationListener listener = new DeviceIdKeyExpirationListener(container);
        container.addMessageListener(listener, new ChannelTopic("__keyevent@0__:expired"));
        return listener;
    }
}

4. 自定义Redis 消息监听器

@Slf4j
public class DeviceIdKeyExpirationListener extends KeyExpirationEventMessageListener {

    public DeviceIdKeyExpirationListener(RedisMessageListenerContainer listenerContainer) {
        super(listenerContainer);
    }

    @Override
    public void onMessage(Message message, byte[] pattern) {
        String deviceId = message.toString();
        if (deviceId.startsWith("deviceId:")) {
            log.error("设备【{}】离线", deviceId);

            // 处理离线后的处理逻辑
        }
    }
}

四、测试

1. 写入缓存

	@GetMapping("/hello")
    public void  helloTest() {
        redisTemplate.opsForValue().set("deviceId:1", "true", Duration.ofMinutes(1));
        redisTemplate.opsForValue().set("deviceId:2", "true", Duration.ofMinutes(2));
        redisTemplate.opsForValue().set("deviceId:3", "true", Duration.ofMinutes(3));
        redisTemplate.opsForValue().set("deviceId:4", "true", Duration.ofMinutes(4));
        redisTemplate.opsForValue().set("deviceId:5", "true", Duration.ofMinutes(5));
    }

2. 观察控制台输出日志

在这里插入图片描述
此时,Redis 缓存过期事件监听配置成功。

Logo

魔乐社区(Modelers.cn) 是一个中立、公益的人工智能社区,提供人工智能工具、模型、数据的托管、展示与应用协同服务,为人工智能开发及爱好者搭建开放的学习交流平台。社区通过理事会方式运作,由全产业链共同建设、共同运营、共同享有,推动国产AI生态繁荣发展。

更多推荐