Home  >  Article  >  Database  >  How to solve the memory leak error caused by using lettuce to start redis

How to solve the memory leak error caused by using lettuce to start redis

王林
王林forward
2023-05-29 09:01:172344browse

Redis uses lettuce.

LEAK: hashedwheelTimer.release() was not called before it's garbage-collected. Enable advanced leak

Memory leak. In fact, it is caused by insufficient memory.

Find the window->preferences->Java->Installed JRE in eclispe, click the Edit button on the right, and fill in the following values ​​in the "Default VM Arguments" option in the editing interface .

-Xms64m -Xmx128m

It can be solved if the memory is adjusted to be large enough.

The other method cannot solve it. I don’t know if the method is set incorrectly

1. Open the eclipse configuration file eclipse.ini and change -Xmx (the value represents the maximum amount of memory that the jvm can use)

2. Run When using a java program, select run->run configuration->arguments and enter -Xms100M -Xmx800M (-Xms represents the memory size allocated when the jvm starts, and -Xmx represents the maximum amount of memory that can be allocated).

Supplement: Redis connection pool Lettuce pitfall record

1. Introduction

Recently, we have frequently deployed projects in different test environments. However, many Redis problems were encountered during the construction and deployment process. The project is based on SpringBoot2.1.12. SpringBoot2.1.X integrated jar package Spring-data-redis-start uses Lettuce as the Redis connection pool.

SpringBoot1.x uses Jedis as the redis client connection pool by default.

SpringBoot2.x, spring-data-redis uses Lettuce as the redis client driver connection pool by default.

2. Pitfall scenario

A certain master node in the running environment Redis cluster is unstable and cannot be connected, causing the SpringBoot application to report an error when connecting to Redis and a connection timeout error.

3. Solution

Rewrite the RedisConnectionFactory Bean, based on Spring-data-redis. You need to set "Cancel verification of cluster node membership": .validateClusterNodeMembership(false).

1. redis configuration

spring:
 redis:
   cluster:
     nodes:
     - ${redis.host.cluster} #redis集群ip-port
   password: ${redis.password}
   timeout: 5000 #连接超时时间
   lettuce:
     pool:
       max-active: 10 #连接池最大连接数
       max-wait: -1 #连接池最大阻塞时间
       max-idle: 5 #连接池中最大空闲连接
       min-idle: 1 #连接池中最小空闲连接
redis:
 cluster:
   enabled: true

2. Config configuration class

@Data
@Component
@ConditionalOnProperty(name = "redis.cluster.enabled", havingValue = "true", matchIfMissing = false)
public class RedisConfig {
    @Autowired
    RedisProperties redisProperties;
    // 在构建LettuceConnectionFactory时,如果不使用内置的destroyMethod,可能会导致Redis连接早于其它Bean被销毁
    @Bean(destroyMethod = "destroy")
    public RedisConnectionFactory newLettuceConnectionFactory() {
        // 配置用于开启自适应刷新和定时刷新。如自适应刷新不开启,Redis集群变更时将会导致连接异常
        ClusterTopologyRefreshOptions clusterTopologyRefreshOptions = ClusterTopologyRefreshOptions.builder()
                .enablePeriodicRefresh(Duration.ofSeconds(60))// 开启周期刷新(默认60秒)
                .enableAdaptiveRefreshTriggers(RefreshTrigger.ASK_REDIRECT,RefreshTrigger.UNKNOWN_NODE)// 开启自适应刷新
                .build();
        ClusterClientOptions clusterClientOptions = ClusterClientOptions.builder()
                                 .topologyRefreshOptions(clusterTopologyRefreshOptions)//拓扑刷新
                                 .disconnectedBehavior(ClientOptions.DisconnectedBehavior.REJECT_COMMANDS)
                                 .autoReconnect(true)
                                 .socketOptions(SocketOptions.builder().keepAlive(true).build())
                       .validateClusterNodeMembership(false)// 取消校验集群节点的成员关系
                                 .build();
        LettuceClientConfiguration clientConfig = LettuceClientConfiguration.builder()
                .clientOptions(clusterClientOptions)
                                .readFrom(ReadFrom.SLAVE_PREFERRED)
                                .build();
        return new LettuceConnectionFactory(getClusterConfiguration(), clientConfig);
    }
    
    private  RedisClusterConfiguration getClusterConfiguration() {
        RedisProperties.Cluster clusterProperties = redisProperties.getCluster();
        RedisClusterConfiguration config = new RedisClusterConfiguration(clusterProperties.getNodes());
        if (clusterProperties.getMaxRedirects() != null) {
            config.setMaxRedirects(clusterProperties.getMaxRedirects());
        }
        if (redisProperties.getPassword() != null) {
            config.setPassword(RedisPassword.of(redisProperties.getPassword()));
        }
        return config;
    }
}

Note:

RedisClusterConfiguration getClusterConfiguration() requires setting Password , otherwise SpringBoot starts and reports an authentication error:

"io.lettuce.core.RedisCommandExecutionException: NOAUTH Authentication required"

is as follows:

In addition, lettuce -The version of the core jar package cannot be too low to prevent some configuration items from being supported. The above configuration is lettuce-core-5.18.RELEASE.jar.

The above is the detailed content of How to solve the memory leak error caused by using lettuce to start redis. For more information, please follow other related articles on the PHP Chinese website!

Statement:
This article is reproduced at:yisu.com. If there is any infringement, please contact admin@php.cn delete