简体   繁体   English

Spring Data Redis-大量插入

[英]Spring Data Redis - Mass Inserts

I have the following question: 我有以下问题:

I have a Java a service reading from a queue and pushing data to Redis (SADD). 我有一个Java服务,它从队列中读取数据并将数据推送到Redis(SADD)。 We originally used Jedis, but I wanted to give it a try to lettuce. 我们最初使用Jedis,但我想尝试一下生菜。 Right now I am facing some performance issues which I believe that is because of the amount of data we are pushing. 目前,我面临一些性能问题,我认为这是因为我们要推送的数据量很大。

We use spring data redis, and we have a Java POJO we are storing as a JSON. 我们使用spring数据redis,并且有一个Java POJO被存储为JSON。 The code we have to do the insertion looks like: 我们必须执行插入的代码如下所示:

public void add(final UUID uuid, final MyPojo... values) {
        final String key = getKey(uuid);
        final long startTime = System.currentTimeMillis();
        final List<Object> response = redisTemplate.executePipelined(new SessionCallback<List<Object>>() {
            @Override
            public <K, V> List<Object> execute(final RedisOperations<K, V> operations) throws DataAccessException {
                final BoundSetOperations setOperations = operations.boundSetOps((K) key);
                setOperations.add(values);
                setOperations.expire(expiration, expirationUnit);
                return null;
            }
        });
        final Long added = (Long) response.get(0);
        final Boolean expirationSet = (Boolean) response.get(1);
        if (added != values.length || !expirationSet) {
            final String msg = String.format("Error executing commands: Added %d, expected = %d. Expiration set = %b", added, values.length, expirationSet);
            throw new DataIntegrityViolationException(msg);
        }
        if (log.isInfoEnabled()) {
            log.info("add took = {} millis", (System.currentTimeMillis() - startTime));
        }
    }

The Connection factory looks like: 连接工厂看起来像:

final ClientResources clientResources = DefaultClientResources.builder()
                .ioThreadPoolSize(4)
                .computationThreadPoolSize(4)
                .build();

final LettuceConnectionFactory connectionFactory = new LettuceConnectionFactory();
connectionFactory.setHostName(getRedis().getHostname());
connectionFactory.setPort(getRedis().getPort());
connectionFactory.setShareNativeConnection(true);
connectionFactory.setTimeout(30000);
connectionFactory.setClientResources(clientResources);

Some SADD operations are taking too long (around 10s) ... My main question is... is there any improvement that I can apply to improve the performance? 一些SADD操作花费的时间太长(大约10s)...我的主要问题是...我可以应用任何改进来改善性能吗? Maybe partitioning the data, and send a pre-defined number of values at a time? 也许对数据进行分区,然后一次发送预定义数量的值? What else can I try? 我还能尝试什么?

I had the same issue few weeks ago. 几周前我遇到了同样的问题。

Loss of performance can be caused by variety of reasons. 性能下降可能是由多种原因引起的。

First of all I would suggest to exclude network issue. 首先,我建议排除网络问题。 This article can be helpful to understand the reasons of latency problem. 本文有助于理解延迟问题的原因。 Also, if you are using remote Redis instance, try to measure time of operations with local instance. 另外,如果您正在使用远程Redis实例,请尝试评估使用本地实例的操作时间。

Secondly, you could definitely try redission . 其次,您绝对可以尝试重 That helped me when I had performance issues with Jedis and lettuce, and their API is great. 当我遇到Jedis和生菜的性能问题时,这对我很有帮助,并且它们的API很棒。 And they have PRO version as well(which is in some cases 44x faster). 而且它们还具有PRO版本(在某些情况下,速度要快44倍)。

Another reason could be serialization/deserialization part. 另一个原因可能是序列化/反序列化部分。 You can take a look at codecs that are being used in Redisson, and use them in your application(FstCodec is, you know, fast). 您可以看一下Redisson中正在使用的编解码器 ,并在您的应用程序中使用它们(您知道FstCodec很快)。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM