RedisConnectionMonitor.java

RedisConnectionMonitor.java

用于监控 Redis 连接状态,特别是在服务器端定时关闭连接时进行诊断。

复制代码
package further.common.conf.redis;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;

/**
 * Redis 连接健康检查和监控
 * <p>
 * 用于监控 Redis 连接状态,特别是在服务器端定时关闭连接时进行诊断。
 * </p>
 *
 * @author ZengWenFeng
 * @date 2025.12.20
 * @mobile 13805029595
 * @email 117791303@QQ.com
 */
@Component
public class RedisConnectionMonitor
{
	private static final Logger logger = LoggerFactory.getLogger(RedisConnectionMonitor.class);

	@Autowired
	private RedisTemplate<Object, Object> redisTemplate;

	/**
	 * 每5分钟检查一次 Redis 连接健康状态
	 */
	@Scheduled(fixedRate = 300000) // 5分钟 = 300000毫秒
	public void checkConnectionHealth()
	{
		try
		{
			// 执行 PING 命令检查连接
			String result = redisTemplate.getConnectionFactory().getConnection().ping();
			if ("PONG".equals(result))
			{
				logger.debug("Redis 连接健康检查通过: {}", result);
			}
			else
			{
				logger.warn("Redis 连接健康检查异常,返回: {}", result);
			}
		}
		catch (Exception e)
		{
			logger.error("Redis 连接健康检查失败,可能连接已断开: {}", e.getMessage());
			// Lettuce 会自动重连,这里只记录日志
		}
	}

	/**
	 * 每天 4:55 执行一次连接检查(在 5:01 断开前)
	 * 用于诊断是否在 5 点有定时任务
	 */
	@Scheduled(cron = "0 55 4 * * ?")
	public void preDisconnectCheck()
	{
		logger.info("========== Redis 连接预检查(5点前) ==========");
		try
		{
			String result = redisTemplate.getConnectionFactory().getConnection().ping();
			logger.info("Redis 连接正常: {}", result);
		}
		catch (Exception e)
		{
			logger.error("Redis 连接异常: {}", e.getMessage(), e);
		}
		logger.info("=============================================");
	}

	/**
	 * 每天 5:05 执行一次连接检查(在 5:01 断开后)
	 * 用于确认连接是否已自动重连
	 */
	@Scheduled(cron = "0 5 5 * * ?")
	public void postDisconnectCheck()
	{
		logger.info("========== Redis 连接后检查(5点后) ==========");
		try
		{
			String result = redisTemplate.getConnectionFactory().getConnection().ping();
			logger.info("Redis 连接已恢复: {}", result);
		}
		catch (Exception e)
		{
			logger.error("Redis 连接仍未恢复: {}", e.getMessage(), e);
		}
		logger.info("=============================================");
	}
}
复制代码
2025-12-20 05:01:12.121 [lettuce-nioEventLoop-16-1] INFO  io.lettuce.core.protocol.CommandHandler - null Unexpected exception during request: java.io.IOException: 远程主机强迫关闭了一个现有的连接。
java.io.IOException: 远程主机强迫关闭了一个现有的连接。
	at sun.nio.ch.SocketDispatcher.read0(Native Method)
	at sun.nio.ch.SocketDispatcher.read(SocketDispatcher.java:43)
	at sun.nio.ch.IOUtil.readIntoNativeBuffer(IOUtil.java:223)
	at sun.nio.ch.IOUtil.read(IOUtil.java:192)
	at sun.nio.ch.SocketChannelImpl.read(SocketChannelImpl.java:378)
	at io.netty.buffer.PooledByteBuf.setBytes(PooledByteBuf.java:253)
	at io.netty.buffer.AbstractByteBuf.writeBytes(AbstractByteBuf.java:1134)
	at io.netty.channel.socket.nio.NioSocketChannel.doReadBytes(NioSocketChannel.java:350)
	at io.netty.channel.nio.AbstractNioByteChannel$NioByteUnsafe.read(AbstractNioByteChannel.java:151)
	at io.netty.channel.nio.NioEventLoop.processSelectedKey(NioEventLoop.java:719)
	at io.netty.channel.nio.NioEventLoop.processSelectedKeysOptimized(NioEventLoop.java:655)
	at io.netty.channel.nio.NioEventLoop.processSelectedKeys(NioEventLoop.java:581)
	at io.netty.channel.nio.NioEventLoop.run(NioEventLoop.java:493)
	at io.netty.util.concurrent.SingleThreadEventExecutor$4.run(SingleThreadEventExecutor.java:989)
	at io.netty.util.internal.ThreadExecutorMap$2.run(ThreadExecutorMap.java:74)
	at io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
	at java.lang.Thread.run(Thread.java:750)



The method setMaxWait(int, TimeUnit) is undefined for the type GenericObjectPoolConfig<capture#4-of ?>

The method setTimeBetweenEvictionRuns(int, TimeUnit) is undefined for the type GenericObjectPoolConfig<capture#7-of ?>

The method commandTimeout(Duration) in the type LettucePoolingClientConfiguration.LettucePoolingClientConfigurationBuilder is not applicable for the arguments (int, TimeUnit)

The final field RedisConfig.FastJson2JsonRedisSerializer<T>.objectMapper cannot be assigned

登飞来峰 北宋·王安石 飞来山上千寻塔,闻说鸡鸣见日升.不畏浮云遮望眼,只缘身在最高层。

相关推荐
言慢行善6 小时前
sqlserver模糊查询问题
java·数据库·sqlserver
专吃海绵宝宝菠萝屋的派大星6 小时前
使用Dify对接自己开发的mcp
java·服务器·前端
大数据新鸟6 小时前
操作系统之虚拟内存
java·服务器·网络
Tong Z6 小时前
常见的限流算法和实现原理
java·开发语言
凭君语未可6 小时前
Java 中的实现类是什么
java·开发语言
He少年6 小时前
【基础知识、Skill、Rules和MCP案例介绍】
java·前端·python
克里斯蒂亚诺更新6 小时前
myeclipse的pojie
java·ide·myeclipse
迷藏4947 小时前
**eBPF实战进阶:从零构建网络流量监控与过滤系统**在现代云原生架构中,**网络可观测性**和**安全隔离**已成为
java·网络·python·云原生·架构
迷藏4947 小时前
**发散创新:基于Solid协议的Web3.0去中心化身份认证系统实战解析**在Web3.
java·python·web3·去中心化·区块链
qq_433502187 小时前
Codex cli 飞书文档创建进阶实用命令 + Skill 创建&使用 小白完整教程
java·前端·飞书