From 8f88b78eeb86800986c4b356b75bb8582786adf2 Mon Sep 17 00:00:00 2001 From: Mark Paluch Date: Fri, 14 Jul 2017 15:02:33 +0200 Subject: [PATCH] =?UTF-8?q?DATAREDIS-661=20-=20Refactor=20RedisServerComma?= =?UTF-8?q?nds.getConfig(=E2=80=A6)=20output=20to=20Properties.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Use Properties instead of List of Strings arranged as sequence of key-value pairs to improve value lookup. Properties allows direct value lookup whereas the List previously required List scanning for an index and another index access to retrieve the actual value. Original Pull Request: #255 --- .../DefaultStringRedisConnection.java | 49 ++++++--------- .../DefaultedRedisClusterConnection.java | 2 +- .../connection/DefaultedRedisConnection.java | 2 +- .../RedisClusterServerCommands.java | 2 +- .../redis/connection/RedisServerCommands.java | 2 +- .../redis/connection/convert/Converters.java | 61 ++++++++++++++----- .../jedis/JedisClusterServerCommands.java | 9 +-- .../connection/jedis/JedisServerCommands.java | 57 +++++++++-------- .../lettuce/LettuceClusterServerCommands.java | 8 +-- .../connection/lettuce/LettuceConverters.java | 21 ------- .../lettuce/LettuceServerCommands.java | 11 ++-- .../KeyspaceEventMessageListener.java | 15 ++--- .../AbstractConnectionIntegrationTests.java | 19 ++---- ...ultStringRedisConnectionPipelineTests.java | 7 ++- ...tStringRedisConnectionPipelineTxTests.java | 3 +- .../DefaultStringRedisConnectionTests.java | 19 ++---- .../DefaultStringRedisConnectionTxTests.java | 3 +- .../connection/RedisConnectionUnitTests.java | 2 +- .../jedis/JedisClusterConnectionTests.java | 34 +++-------- .../LettuceClusterConnectionTests.java | 35 +++-------- .../core/RedisKeyValueAdapterUnitTests.java | 4 +- 21 files changed, 165 insertions(+), 200 deletions(-) diff --git a/src/main/java/org/springframework/data/redis/connection/DefaultStringRedisConnection.java b/src/main/java/org/springframework/data/redis/connection/DefaultStringRedisConnection.java index 73095226a..459aff3f7 100644 --- a/src/main/java/org/springframework/data/redis/connection/DefaultStringRedisConnection.java +++ b/src/main/java/org/springframework/data/redis/connection/DefaultStringRedisConnection.java @@ -1,12 +1,12 @@ /* - * Copyright 2011-2016 the original author or authors. - * + * Copyright 2011-2017 the original author or authors. + * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at - * + * * http://www.apache.org/licenses/LICENSE-2.0 - * + * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. @@ -15,17 +15,8 @@ */ package org.springframework.data.redis.connection; -import java.util.ArrayList; -import java.util.Collection; -import java.util.HashMap; -import java.util.LinkedHashMap; -import java.util.LinkedList; -import java.util.List; -import java.util.Map; +import java.util.*; import java.util.Map.Entry; -import java.util.Properties; -import java.util.Queue; -import java.util.Set; import java.util.concurrent.TimeUnit; import org.apache.commons.logging.Log; @@ -52,7 +43,7 @@ import org.springframework.util.Assert; /** * Default implementation of {@link StringRedisConnection}. - * + * * @author Costin Leau * @author Jennifer Hickey * @author Christoph Strobl @@ -122,7 +113,7 @@ public class DefaultStringRedisConnection implements StringRedisConnection, Deco /** * Constructs a new DefaultStringRedisConnection instance. Uses {@link StringRedisSerializer} as * underlying serializer. - * + * * @param connection Redis connection */ public DefaultStringRedisConnection(RedisConnection connection) { @@ -131,7 +122,7 @@ public class DefaultStringRedisConnection implements StringRedisConnection, Deco /** * Constructs a new DefaultStringRedisConnection instance. - * + * * @param connection Redis connection * @param serializer String serializer */ @@ -308,8 +299,8 @@ public class DefaultStringRedisConnection implements StringRedisConnection, Deco return result; } - public List getConfig(String pattern) { - List results = delegate.getConfig(pattern); + public Properties getConfig(String pattern) { + Properties results = delegate.getConfig(pattern); if (isFutureConversion()) { addResultConverter(identityConverter); } @@ -939,7 +930,7 @@ public class DefaultStringRedisConnection implements StringRedisConnection, Deco return result; } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisKeyCommands#ttl(byte[]) */ @@ -953,7 +944,7 @@ public class DefaultStringRedisConnection implements StringRedisConnection, Deco return result; } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisKeyCommands#ttl(byte[], java.util.concurrent.TimeUnit) */ @@ -1351,7 +1342,7 @@ public class DefaultStringRedisConnection implements StringRedisConnection, Deco return result; } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisKeyCommands#pTtl(byte[]) */ @@ -1366,7 +1357,7 @@ public class DefaultStringRedisConnection implements StringRedisConnection, Deco return result; } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisKeyCommands#pTtl(byte[], java.util.concurrent.TimeUnit) */ @@ -2103,7 +2094,7 @@ public class DefaultStringRedisConnection implements StringRedisConnection, Deco return result; } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.StringRedisConnection#ttl(java.lang.String) */ @@ -2112,7 +2103,7 @@ public class DefaultStringRedisConnection implements StringRedisConnection, Deco return ttl(serialize(key)); } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.StringRedisConnection#ttl(java.lang.String, java.util.concurrent.TimeUnit) */ @@ -2743,7 +2734,7 @@ public class DefaultStringRedisConnection implements StringRedisConnection, Deco return pExpireAt(serialize(key), unixTimeInMillis); } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.StringRedisConnection#pTtl(java.lang.String) */ @@ -2752,7 +2743,7 @@ public class DefaultStringRedisConnection implements StringRedisConnection, Deco return pTtl(serialize(key)); } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.StringRedisConnection#pTtl(java.lang.String, java.util.concurrent.TimeUnit) */ @@ -2835,7 +2826,7 @@ public class DefaultStringRedisConnection implements StringRedisConnection, Deco } /* - * + * */ @Override public Cursor zScan(byte[] key, ScanOptions options) { @@ -2863,7 +2854,7 @@ public class DefaultStringRedisConnection implements StringRedisConnection, Deco /** * Specifies if pipelined and tx results should be deserialized to Strings. If false, results of * {@link #closePipeline()} and {@link #exec()} will be of the type returned by the underlying connection - * + * * @param deserializePipelineAndTxResults Whether or not to deserialize pipeline and tx results */ public void setDeserializePipelineAndTxResults(boolean deserializePipelineAndTxResults) { diff --git a/src/main/java/org/springframework/data/redis/connection/DefaultedRedisClusterConnection.java b/src/main/java/org/springframework/data/redis/connection/DefaultedRedisClusterConnection.java index 3312ee205..9fbefc428 100644 --- a/src/main/java/org/springframework/data/redis/connection/DefaultedRedisClusterConnection.java +++ b/src/main/java/org/springframework/data/redis/connection/DefaultedRedisClusterConnection.java @@ -100,7 +100,7 @@ public interface DefaultedRedisClusterConnection extends RedisClusterConnection, /** @deprecated in favor of {@link RedisConnection#serverCommands()}. */ @Override @Deprecated - default List getConfig(RedisClusterNode node, String pattern) { + default Properties getConfig(RedisClusterNode node, String pattern) { return serverCommands().getConfig(node, pattern); } diff --git a/src/main/java/org/springframework/data/redis/connection/DefaultedRedisConnection.java b/src/main/java/org/springframework/data/redis/connection/DefaultedRedisConnection.java index 0d286e16c..7eb8edf26 100644 --- a/src/main/java/org/springframework/data/redis/connection/DefaultedRedisConnection.java +++ b/src/main/java/org/springframework/data/redis/connection/DefaultedRedisConnection.java @@ -1107,7 +1107,7 @@ public interface DefaultedRedisConnection extends RedisConnection { /** @deprecated in favor of {@link RedisConnection#serverCommands()}. */ @Override @Deprecated - default List getConfig(String pattern) { + default Properties getConfig(String pattern) { return serverCommands().getConfig(pattern); } diff --git a/src/main/java/org/springframework/data/redis/connection/RedisClusterServerCommands.java b/src/main/java/org/springframework/data/redis/connection/RedisClusterServerCommands.java index 7c5c1b698..4aa8a6004 100644 --- a/src/main/java/org/springframework/data/redis/connection/RedisClusterServerCommands.java +++ b/src/main/java/org/springframework/data/redis/connection/RedisClusterServerCommands.java @@ -97,7 +97,7 @@ public interface RedisClusterServerCommands extends RedisServerCommands { * @return * @see RedisServerCommands#getConfig(String) */ - List getConfig(RedisClusterNode node, String pattern); + Properties getConfig(RedisClusterNode node, String pattern); /** * @param node must not be {@literal null}. diff --git a/src/main/java/org/springframework/data/redis/connection/RedisServerCommands.java b/src/main/java/org/springframework/data/redis/connection/RedisServerCommands.java index e9c5d9cee..082c33773 100644 --- a/src/main/java/org/springframework/data/redis/connection/RedisServerCommands.java +++ b/src/main/java/org/springframework/data/redis/connection/RedisServerCommands.java @@ -148,7 +148,7 @@ public interface RedisServerCommands { * @return * @see Redis Documentation: CONFIG GET */ - List getConfig(String pattern); + Properties getConfig(String pattern); /** * Set server configuration for {@code param} to {@code value}. diff --git a/src/main/java/org/springframework/data/redis/connection/convert/Converters.java b/src/main/java/org/springframework/data/redis/connection/convert/Converters.java index e88d61cfb..9941a9c67 100644 --- a/src/main/java/org/springframework/data/redis/connection/convert/Converters.java +++ b/src/main/java/org/springframework/data/redis/connection/convert/Converters.java @@ -1,5 +1,5 @@ /* - * Copyright 2013-2016 the original author or authors. + * Copyright 2013-2017 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -15,16 +15,9 @@ */ package org.springframework.data.redis.connection.convert; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.Collection; -import java.util.Collections; -import java.util.LinkedHashMap; -import java.util.LinkedHashSet; -import java.util.List; -import java.util.Map; -import java.util.Properties; -import java.util.Set; +import lombok.RequiredArgsConstructor; + +import java.util.*; import java.util.concurrent.TimeUnit; import org.springframework.core.convert.converter.Converter; @@ -50,8 +43,6 @@ import org.springframework.util.NumberUtils; import org.springframework.util.ObjectUtils; import org.springframework.util.StringUtils; -import lombok.RequiredArgsConstructor; - /** * Common type converters * @@ -70,6 +61,7 @@ abstract public class Converters { private static final Converter STRING_TO_DATA_TYPE = new StringToDataTypeConverter(); private static final Converter, Properties> MAP_TO_PROPERTIES = MapToPropertiesConverter.INSTANCE; private static final Converter STRING_TO_CLUSTER_NODE_CONVERTER; + private static final Converter, Properties> STRING_LIST_TO_PROPERTIES_CONVERTER; private static final Map flagLookupMap; static { @@ -172,6 +164,21 @@ abstract public class Converters { } }; + + STRING_LIST_TO_PROPERTIES_CONVERTER = input -> { + + Assert.notNull(input, "Input list must not be null!"); + Assert.isTrue(input.size() % 2 == 0, "Input list must contain an even number of entries!"); + + Properties properties = new Properties(); + + for (int i = 0; i < input.size(); i += 2) { + + properties.setProperty(input.get(i), input.get(i + 1)); + } + + return properties; + }; } public static Boolean stringToBoolean(String s) { @@ -224,7 +231,7 @@ abstract public class Converters { /** * Converts lines from the result of {@code CLUSTER NODES} into {@link RedisClusterNode}s. * - * @param clusterNodes + * @param lines * @return * @since 1.7 */ @@ -302,7 +309,7 @@ abstract public class Converters { /** * Creates a new {@link Converter} to convert from seconds to the given {@link TimeUnit}. - * + * * @param timeUnit muist not be {@literal null}. * @return * @since 1.8 @@ -378,6 +385,29 @@ abstract public class Converters { return DistanceConverterFactory.INSTANCE.forMetric(metric); } + /** + * Converts array outputs with key-value sequences (such as produced by {@code CONFIG GET}) from a {@link List} to + * {@link Properties}. + * + * @param input must not be {@literal null}. + * @return the mapped result. + * @since 2.0 + */ + public static Properties toProperties(List input) { + return STRING_LIST_TO_PROPERTIES_CONVERTER.convert(input); + } + + /** + * Returns a converter to convert array outputs with key-value sequences (such as produced by {@code CONFIG GET}) from + * a {@link List} to {@link Properties}. + * + * @return the converter. + * @since 2.0 + */ + public static Converter, Properties> listToPropertiesConverter() { + return STRING_LIST_TO_PROPERTIES_CONVERTER; + } + /** * @author Christoph Strobl * @since 1.8 @@ -436,5 +466,4 @@ abstract public class Converters { return new GeoResults>(values, source.getAverageDistance().getMetric()); } } - } diff --git a/src/main/java/org/springframework/data/redis/connection/jedis/JedisClusterServerCommands.java b/src/main/java/org/springframework/data/redis/connection/jedis/JedisClusterServerCommands.java index 48c73caba..17e0748f9 100644 --- a/src/main/java/org/springframework/data/redis/connection/jedis/JedisClusterServerCommands.java +++ b/src/main/java/org/springframework/data/redis/connection/jedis/JedisClusterServerCommands.java @@ -300,7 +300,7 @@ class JedisClusterServerCommands implements RedisClusterServerCommands { * @see org.springframework.data.redis.connection.RedisServerCommands#getConfig(java.lang.String) */ @Override - public List getConfig(final String pattern) { + public Properties getConfig(final String pattern) { List>> mapResult = connection.getClusterCommandExecutor() .executeCommandOnAllNodes((JedisClusterCommandCallback>) client -> client.configGet(pattern)) @@ -316,7 +316,7 @@ class JedisClusterServerCommands implements RedisClusterServerCommands { } } - return result; + return Converters.toProperties(result); } /* @@ -324,10 +324,11 @@ class JedisClusterServerCommands implements RedisClusterServerCommands { * @see org.springframework.data.redis.connection.RedisClusterServerCommands#getConfig(org.springframework.data.redis.connection.RedisClusterNode, java.lang.String) */ @Override - public List getConfig(RedisClusterNode node, final String pattern) { + public Properties getConfig(RedisClusterNode node, final String pattern) { return connection.getClusterCommandExecutor().executeCommandOnSingleNode( - (JedisClusterCommandCallback>) client -> client.configGet(pattern), node).getValue(); + (JedisClusterCommandCallback) client -> Converters.toProperties(client.configGet(pattern)), node) + .getValue(); } /* diff --git a/src/main/java/org/springframework/data/redis/connection/jedis/JedisServerCommands.java b/src/main/java/org/springframework/data/redis/connection/jedis/JedisServerCommands.java index 8b83afe5a..aa03ee502 100644 --- a/src/main/java/org/springframework/data/redis/connection/jedis/JedisServerCommands.java +++ b/src/main/java/org/springframework/data/redis/connection/jedis/JedisServerCommands.java @@ -21,6 +21,7 @@ import java.util.Properties; import org.springframework.data.redis.connection.RedisNode; import org.springframework.data.redis.connection.RedisServerCommands; import org.springframework.data.redis.connection.ReturnType; +import org.springframework.data.redis.connection.convert.Converters; import org.springframework.data.redis.connection.jedis.JedisConnection.JedisResult; import org.springframework.data.redis.core.types.RedisClientInfo; import org.springframework.util.Assert; @@ -39,7 +40,7 @@ class JedisServerCommands implements RedisServerCommands { this.connection = connection; } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#bgReWriteAof() */ @@ -60,7 +61,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#bgSave() */ @@ -81,7 +82,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#lastSave() */ @@ -102,7 +103,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#save() */ @@ -123,7 +124,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#dbSize() */ @@ -144,7 +145,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#flushDb() */ @@ -165,7 +166,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#flushAll() */ @@ -186,7 +187,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#info() */ @@ -207,7 +208,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#info(java.lang.String) */ @@ -226,7 +227,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#shutdown() */ @@ -247,7 +248,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#shutdown(org.springframework.data.redis.connection.RedisServerCommands.ShutdownOption) */ @@ -262,28 +263,30 @@ class JedisServerCommands implements RedisServerCommands { connection.eval(String.format(SHUTDOWN_SCRIPT, option.name()).getBytes(), ReturnType.STATUS, 0); } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#getConfig(java.lang.String) */ @Override - public List getConfig(String param) { + public Properties getConfig(String param) { try { if (isPipelined()) { - pipeline(connection.newJedisResult(connection.getPipeline().configGet(param))); + pipeline(connection.newJedisResult(connection.getPipeline().configGet(param), + Converters.listToPropertiesConverter())); return null; } if (isQueueing()) { - transaction(connection.newJedisResult(connection.getTransaction().configGet(param))); + transaction(connection.newJedisResult(connection.getTransaction().configGet(param), + Converters.listToPropertiesConverter())); return null; } - return connection.getJedis().configGet(param); + return Converters.toProperties(connection.getJedis().configGet(param)); } catch (Exception ex) { throw convertJedisAccessException(ex); } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#setConfig(java.lang.String, java.lang.String) */ @@ -304,7 +307,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#resetConfigStats() */ @@ -325,7 +328,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#time() */ @@ -349,7 +352,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#killClient(java.lang.String, int) */ @@ -369,7 +372,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#setClientName(byte[]) */ @@ -383,7 +386,7 @@ class JedisServerCommands implements RedisServerCommands { connection.getJedis().clientSetname(name); } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#getClientName() */ @@ -397,7 +400,7 @@ class JedisServerCommands implements RedisServerCommands { return connection.getJedis().clientGetname(); } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#getClientList() */ @@ -410,7 +413,7 @@ class JedisServerCommands implements RedisServerCommands { return JedisConverters.toListOfRedisClientInformation(this.connection.getJedis().clientList()); } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#slaveOf(java.lang.String, int) */ @@ -428,7 +431,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#slaveOfNoOne() */ @@ -445,7 +448,7 @@ class JedisServerCommands implements RedisServerCommands { } } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#migrate(byte[], org.springframework.data.redis.connection.RedisNode, int, org.springframework.data.redis.connection.RedisServerCommands.MigrateOption) */ @@ -454,7 +457,7 @@ class JedisServerCommands implements RedisServerCommands { migrate(key, target, dbIndex, option, Long.MAX_VALUE); } - /* + /* * (non-Javadoc) * @see org.springframework.data.redis.connection.RedisServerCommands#migrate(byte[], org.springframework.data.redis.connection.RedisNode, int, org.springframework.data.redis.connection.RedisServerCommands.MigrateOption, long) */ diff --git a/src/main/java/org/springframework/data/redis/connection/lettuce/LettuceClusterServerCommands.java b/src/main/java/org/springframework/data/redis/connection/lettuce/LettuceClusterServerCommands.java index 3a79bf9ef..fa4b44640 100644 --- a/src/main/java/org/springframework/data/redis/connection/lettuce/LettuceClusterServerCommands.java +++ b/src/main/java/org/springframework/data/redis/connection/lettuce/LettuceClusterServerCommands.java @@ -226,7 +226,7 @@ class LettuceClusterServerCommands extends LettuceServerCommands implements Redi * @see org.springframework.data.redis.connection.lettuce.LettuceServerCommands#getConfig(java.lang.String) */ @Override - public List getConfig(final String pattern) { + public Properties getConfig(final String pattern) { List>> mapResult = executeCommandOnAllNodes(client -> client.configGet(pattern)) .getResults(); @@ -241,7 +241,7 @@ class LettuceClusterServerCommands extends LettuceServerCommands implements Redi } } - return result; + return Converters.toProperties(result); } /* @@ -249,8 +249,8 @@ class LettuceClusterServerCommands extends LettuceServerCommands implements Redi * @see org.springframework.data.redis.connection.RedisClusterServerCommands#getConfig(org.springframework.data.redis.connection.RedisClusterNode, java.lang.String) */ @Override - public List getConfig(RedisClusterNode node, final String pattern) { - return executeCommandOnSingleNode(client -> client.configGet(pattern), node).getValue(); + public Properties getConfig(RedisClusterNode node, final String pattern) { + return executeCommandOnSingleNode(client -> Converters.toProperties(client.configGet(pattern)), node).getValue(); } /* diff --git a/src/main/java/org/springframework/data/redis/connection/lettuce/LettuceConverters.java b/src/main/java/org/springframework/data/redis/connection/lettuce/LettuceConverters.java index c474220c8..48f0cb42b 100644 --- a/src/main/java/org/springframework/data/redis/connection/lettuce/LettuceConverters.java +++ b/src/main/java/org/springframework/data/redis/connection/lettuce/LettuceConverters.java @@ -811,27 +811,6 @@ abstract public class LettuceConverters extends Converters { return geoArgs; } - /** - * Convert {@code CONFIG GET} output from a {@link List} to {@link Properties}. - * - * @param input must not be {@literal null}. - * @return the mapped result. - */ - public static Properties toProperties(List input) { - - Assert.notNull(input, "Input list must not be null!"); - Assert.isTrue(input.size() % 2 == 0, "Input list must contain an even number of entries!"); - - Properties properties = new Properties(); - - for (int i = 0; i < input.size(); i += 2) { - - properties.setProperty(input.get(i), input.get(i + 1)); - } - - return properties; - } - /** * Get {@link Converter} capable of {@link Set} of {@link Byte} into {@link GeoResults}. * diff --git a/src/main/java/org/springframework/data/redis/connection/lettuce/LettuceServerCommands.java b/src/main/java/org/springframework/data/redis/connection/lettuce/LettuceServerCommands.java index a8e476414..f610deeee 100644 --- a/src/main/java/org/springframework/data/redis/connection/lettuce/LettuceServerCommands.java +++ b/src/main/java/org/springframework/data/redis/connection/lettuce/LettuceServerCommands.java @@ -24,6 +24,7 @@ import java.util.Properties; import org.springframework.dao.DataAccessException; import org.springframework.data.redis.connection.RedisNode; import org.springframework.data.redis.connection.RedisServerCommands; +import org.springframework.data.redis.connection.convert.Converters; import org.springframework.data.redis.connection.lettuce.LettuceConnection.LettuceResult; import org.springframework.data.redis.connection.lettuce.LettuceConnection.LettuceTxResult; import org.springframework.data.redis.core.types.RedisClientInfo; @@ -276,17 +277,19 @@ class LettuceServerCommands implements RedisServerCommands { * @see org.springframework.data.redis.connection.RedisServerCommands#getConfig(java.lang.String) */ @Override - public List getConfig(String param) { + public Properties getConfig(String param) { try { if (isPipelined()) { - pipeline(connection.newLettuceResult(getAsyncConnection().configGet(param))); + pipeline( + connection.newLettuceResult(getAsyncConnection().configGet(param), Converters.listToPropertiesConverter())); return null; } if (isQueueing()) { - transaction(connection.newLettuceTxResult(getConnection().configGet(param))); + transaction( + connection.newLettuceTxResult(getConnection().configGet(param), Converters.listToPropertiesConverter())); return null; } - return getConnection().configGet(param); + return Converters.toProperties(getConnection().configGet(param)); } catch (Exception ex) { throw convertLettuceAccessException(ex); } diff --git a/src/main/java/org/springframework/data/redis/listener/KeyspaceEventMessageListener.java b/src/main/java/org/springframework/data/redis/listener/KeyspaceEventMessageListener.java index 4b9e66b57..ab9535bb9 100644 --- a/src/main/java/org/springframework/data/redis/listener/KeyspaceEventMessageListener.java +++ b/src/main/java/org/springframework/data/redis/listener/KeyspaceEventMessageListener.java @@ -15,7 +15,7 @@ */ package org.springframework.data.redis.listener; -import java.util.List; +import java.util.Properties; import org.springframework.beans.factory.DisposableBean; import org.springframework.beans.factory.InitializingBean; @@ -27,8 +27,9 @@ import org.springframework.util.StringUtils; /** * Base {@link MessageListener} implementation for listening to Redis keyspace notifications. - * + * * @author Christoph Strobl + * @author Mark Paluch * @since 1.7 */ public abstract class KeyspaceEventMessageListener implements MessageListener, InitializingBean, DisposableBean { @@ -39,7 +40,7 @@ public abstract class KeyspaceEventMessageListener implements MessageListener, I /** * Creates new {@link KeyspaceEventMessageListener}. - * + * * @param listenerContainer must not be {@literal null}. */ public KeyspaceEventMessageListener(RedisMessageListenerContainer listenerContainer) { @@ -64,7 +65,7 @@ public abstract class KeyspaceEventMessageListener implements MessageListener, I /** * Handle the actual message - * + * * @param message never {@literal null}. */ protected abstract void doHandleMessage(Message message); @@ -81,9 +82,9 @@ public abstract class KeyspaceEventMessageListener implements MessageListener, I try { - List config = connection.getConfig("notify-keyspace-events"); + Properties config = connection.getConfig("notify-keyspace-events"); - if (config.size() == 2 && !StringUtils.hasText(config.get(1))) { + if (!StringUtils.hasText(config.getProperty("notify-keyspace-events"))) { connection.setConfig("notify-keyspace-events", keyspaceNotificationsConfigParameter); } @@ -97,7 +98,7 @@ public abstract class KeyspaceEventMessageListener implements MessageListener, I /** * Register instance within the container. - * + * * @param container never {@literal null}. */ protected void doRegister(RedisMessageListenerContainer container) { diff --git a/src/test/java/org/springframework/data/redis/connection/AbstractConnectionIntegrationTests.java b/src/test/java/org/springframework/data/redis/connection/AbstractConnectionIntegrationTests.java index d0852aa9c..6fb1f475e 100644 --- a/src/test/java/org/springframework/data/redis/connection/AbstractConnectionIntegrationTests.java +++ b/src/test/java/org/springframework/data/redis/connection/AbstractConnectionIntegrationTests.java @@ -27,18 +27,7 @@ import static org.springframework.data.redis.connection.RedisGeoCommands.Distanc import static org.springframework.data.redis.connection.RedisGeoCommands.GeoRadiusCommandArgs.*; import static org.springframework.data.redis.core.ScanOptions.*; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.Collection; -import java.util.Collections; -import java.util.HashMap; -import java.util.HashSet; -import java.util.LinkedHashSet; -import java.util.List; -import java.util.Map; -import java.util.Properties; -import java.util.Set; -import java.util.UUID; +import java.util.*; import java.util.concurrent.BlockingDeque; import java.util.concurrent.CountDownLatch; import java.util.concurrent.LinkedBlockingDeque; @@ -89,7 +78,7 @@ import org.springframework.test.annotation.ProfileValueSourceConfiguration; /** * Base test class for AbstractConnection integration tests - * + * * @author Costin Leau * @author Jennifer Hickey * @author Christoph Strobl @@ -915,10 +904,10 @@ public abstract class AbstractConnectionIntegrationTests { } @SuppressWarnings("unchecked") - @Test + @Test // DATAREDIS-661 public void testGetConfig() { actual.add(connection.getConfig("*")); - List config = (List) getResults().get(0); + Properties config = (Properties) getResults().get(0); assertTrue(!config.isEmpty()); } diff --git a/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionPipelineTests.java b/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionPipelineTests.java index 2e250da7e..e39efb904 100644 --- a/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionPipelineTests.java +++ b/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionPipelineTests.java @@ -22,6 +22,7 @@ import java.util.Collections; import java.util.List; import java.util.Properties; +import org.apache.commons.collections.MapUtils; import org.junit.Before; import org.junit.Test; import org.springframework.data.geo.Distance; @@ -29,7 +30,7 @@ import org.springframework.data.redis.connection.RedisGeoCommands.DistanceUnit; /** * Unit test of {@link DefaultStringRedisConnection} that executes commands in a pipeline - * + * * @author Jennifer Hickey * @author Christoph Strobl * @author Ninad Divadkar @@ -218,9 +219,9 @@ public class DefaultStringRedisConnectionPipelineTests extends DefaultStringRedi super.testGetBit(); } - @Test + @Test // DATAREDIS-661 public void testGetConfig() { - List results = Collections.singletonList("bar"); + Properties results = MapUtils.toProperties(Collections.singletonMap("foo", "bar")); doReturn(Arrays.asList(new Object[] { results })).when(nativeConnection).closePipeline(); super.testGetConfig(); } diff --git a/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionPipelineTxTests.java b/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionPipelineTxTests.java index 728cd9b9f..822120703 100644 --- a/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionPipelineTxTests.java +++ b/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionPipelineTxTests.java @@ -23,6 +23,7 @@ import java.util.Collections; import java.util.List; import java.util.Properties; +import org.apache.commons.collections.MapUtils; import org.junit.Before; import org.junit.Test; import org.springframework.data.geo.Distance; @@ -224,7 +225,7 @@ public class DefaultStringRedisConnectionPipelineTxTests extends DefaultStringRe @Test public void testGetConfig() { - List results = Collections.singletonList("bar"); + Properties results = MapUtils.toProperties(Collections.singletonMap("foo", "bar")); doReturn(Arrays.asList(new Object[] { Arrays.asList(new Object[] { results }) })).when(nativeConnection) .closePipeline(); super.testGetConfig(); diff --git a/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionTests.java b/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionTests.java index 1313b5a21..5e39173b2 100644 --- a/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionTests.java +++ b/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionTests.java @@ -18,18 +18,10 @@ package org.springframework.data.redis.connection; import static org.junit.Assert.*; import static org.mockito.Mockito.*; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.Collections; -import java.util.HashMap; -import java.util.HashSet; -import java.util.LinkedHashSet; -import java.util.List; -import java.util.Map; -import java.util.Properties; -import java.util.Set; +import java.util.*; import java.util.concurrent.TimeUnit; +import org.apache.commons.collections.MapUtils; import org.junit.Before; import org.junit.Test; import org.mockito.Mock; @@ -53,10 +45,11 @@ import org.springframework.data.redis.serializer.StringRedisSerializer; /** * Unit test of {@link DefaultStringRedisConnection} - * + * * @author Jennifer Hickey * @auhtor Christoph Strobl * @author Ninad Divadkar + * @author Mark Paluch */ public class DefaultStringRedisConnectionTests { @@ -302,9 +295,9 @@ public class DefaultStringRedisConnectionTests { verifyResults(Arrays.asList(new Object[] { true })); } - @Test + @Test // DATAREDIS-661 public void testGetConfig() { - List results = Collections.singletonList("bar"); + Properties results = MapUtils.toProperties(Collections.singletonMap("foo", "bar")); doReturn(results).when(nativeConnection).getConfig("foo"); actual.add(connection.getConfig("foo")); verifyResults(Arrays.asList(new Object[] { results })); diff --git a/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionTxTests.java b/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionTxTests.java index 84512fd4e..f62a24010 100644 --- a/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionTxTests.java +++ b/src/test/java/org/springframework/data/redis/connection/DefaultStringRedisConnectionTxTests.java @@ -22,6 +22,7 @@ import java.util.Collections; import java.util.List; import java.util.Properties; +import org.apache.commons.collections.MapUtils; import org.junit.Before; import org.junit.Test; import org.springframework.data.geo.Distance; @@ -205,7 +206,7 @@ public class DefaultStringRedisConnectionTxTests extends DefaultStringRedisConne @Test public void testGetConfig() { - List results = Collections.singletonList("bar"); + Properties results = MapUtils.toProperties(Collections.singletonMap("foo", "bar")); doReturn(Arrays.asList(new Object[] { results })).when(nativeConnection).exec(); super.testGetConfig(); } diff --git a/src/test/java/org/springframework/data/redis/connection/RedisConnectionUnitTests.java b/src/test/java/org/springframework/data/redis/connection/RedisConnectionUnitTests.java index 1c4ed68b2..5bf436bda 100644 --- a/src/test/java/org/springframework/data/redis/connection/RedisConnectionUnitTests.java +++ b/src/test/java/org/springframework/data/redis/connection/RedisConnectionUnitTests.java @@ -556,7 +556,7 @@ public class RedisConnectionUnitTests { return delegate.expireAt(key, unixTime); } - public List getConfig(String pattern) { + public Properties getConfig(String pattern) { return delegate.getConfig(pattern); } diff --git a/src/test/java/org/springframework/data/redis/connection/jedis/JedisClusterConnectionTests.java b/src/test/java/org/springframework/data/redis/connection/jedis/JedisClusterConnectionTests.java index 6966befda..6665e326d 100644 --- a/src/test/java/org/springframework/data/redis/connection/jedis/JedisClusterConnectionTests.java +++ b/src/test/java/org/springframework/data/redis/connection/jedis/JedisClusterConnectionTests.java @@ -1785,42 +1785,28 @@ public class JedisClusterConnectionTests implements ClusterConnectionTests { assertThat(properties.getProperty("used_memory"), nullValue()); } - @Test // DATAREDIS-315 + @Test // DATAREDIS-315, DATAREDIS-661 public void getConfigShouldLoadCumulatedConfiguration() { - List result = clusterConnection.getConfig("*max-*-entries*"); + Properties result = clusterConnection.getConfig("*max-*-entries*"); // config get *max-*-entries on redis 3.0.7 returns 8 entries per node while on 3.2.0-rc3 returns 6. // @link https://github.com/spring-projects/spring-data-redis/pull/187 - assertThat(result.size() % 6, is(0)); - for (int i = 0; i < result.size(); i++) { + assertThat(result.size() % 3, is(0)); - if (i % 2 == 0) { - assertThat(result.get(i), startsWith(CLUSTER_HOST)); - } else { - assertThat(result.get(i), not(startsWith(CLUSTER_HOST))); - } + for (Object o : result.keySet()) { + + assertThat(o.toString(), startsWith(CLUSTER_HOST)); + assertThat(result.getProperty(o.toString()), not(startsWith(CLUSTER_HOST))); } } - @Test // DATAREDIS-315 + @Test // DATAREDIS-315, DATAREDIS-661 public void getConfigShouldLoadConfigurationOfSpecificNode() { - List result = clusterConnection.getConfig(new RedisClusterNode(CLUSTER_HOST, SLAVEOF_NODE_1_PORT), "*"); + Properties result = clusterConnection.getConfig(new RedisClusterNode(CLUSTER_HOST, SLAVEOF_NODE_1_PORT), "*"); - ListIterator it = result.listIterator(); - Integer valueIndex = null; - while (it.hasNext()) { - - String cur = it.next(); - if (cur.equals("slaveof")) { - valueIndex = it.nextIndex(); - break; - } - } - - assertThat(valueIndex, notNullValue()); - assertThat(result.get(valueIndex), endsWith("7379")); + assertThat(result.getProperty("slaveof"), endsWith("7379")); } @Test // DATAREDIS-315 diff --git a/src/test/java/org/springframework/data/redis/connection/lettuce/LettuceClusterConnectionTests.java b/src/test/java/org/springframework/data/redis/connection/lettuce/LettuceClusterConnectionTests.java index 1e4860e4a..5d0fec692 100644 --- a/src/test/java/org/springframework/data/redis/connection/lettuce/LettuceClusterConnectionTests.java +++ b/src/test/java/org/springframework/data/redis/connection/lettuce/LettuceClusterConnectionTests.java @@ -34,7 +34,6 @@ import java.util.Collections; import java.util.HashMap; import java.util.LinkedHashMap; import java.util.List; -import java.util.ListIterator; import java.util.Map; import java.util.Properties; import java.util.Set; @@ -1799,42 +1798,28 @@ public class LettuceClusterConnectionTests implements ClusterConnectionTests { assertThat(properties.getProperty("used_memory"), nullValue()); } - @Test // DATAREDIS-315 + @Test // DATAREDIS-315, DATAREDIS-661 public void getConfigShouldLoadCumulatedConfiguration() { - List result = clusterConnection.getConfig("*max-*-entries*"); + Properties result = clusterConnection.getConfig("*max-*-entries*"); // config get *max-*-entries on redis 3.0.7 returns 8 entries per node while on 3.2.0-rc3 returns 6. // @link https://github.com/spring-projects/spring-data-redis/pull/187 - assertThat(result.size() % 6, is(0)); - for (int i = 0; i < result.size(); i++) { + assertThat(result.size() % 3, is(0)); - if (i % 2 == 0) { - assertThat(result.get(i), startsWith(CLUSTER_HOST)); - } else { - assertThat(result.get(i), not(startsWith(CLUSTER_HOST))); - } + for (Object o : result.keySet()) { + + assertThat(o.toString(), startsWith(CLUSTER_HOST)); + assertThat(result.getProperty(o.toString()), not(startsWith(CLUSTER_HOST))); } } - @Test // DATAREDIS-315 + @Test // DATAREDIS-315, DATAREDIS-661 public void getConfigShouldLoadConfigurationOfSpecificNode() { - List result = clusterConnection.getConfig(new RedisClusterNode(CLUSTER_HOST, SLAVEOF_NODE_1_PORT), "*"); + Properties result = clusterConnection.getConfig(new RedisClusterNode(CLUSTER_HOST, SLAVEOF_NODE_1_PORT), "*"); - ListIterator it = result.listIterator(); - Integer valueIndex = null; - while (it.hasNext()) { - - String cur = it.next(); - if (cur.equals("slaveof")) { - valueIndex = it.nextIndex(); - break; - } - } - - assertThat(valueIndex, notNullValue()); - assertThat(result.get(valueIndex), endsWith("7379")); + assertThat(result.getProperty("slaveof"), endsWith("7379")); } @Test // DATAREDIS-315 diff --git a/src/test/java/org/springframework/data/redis/core/RedisKeyValueAdapterUnitTests.java b/src/test/java/org/springframework/data/redis/core/RedisKeyValueAdapterUnitTests.java index b82fc475a..27fe95852 100644 --- a/src/test/java/org/springframework/data/redis/core/RedisKeyValueAdapterUnitTests.java +++ b/src/test/java/org/springframework/data/redis/core/RedisKeyValueAdapterUnitTests.java @@ -19,6 +19,7 @@ package org.springframework.data.redis.core; import static org.hamcrest.CoreMatchers.*; import static org.junit.Assert.*; import static org.mockito.Mockito.*; +import static org.mockito.Mockito.any; import static org.springframework.test.util.ReflectionTestUtils.*; import java.util.Arrays; @@ -26,6 +27,7 @@ import java.util.Collections; import java.util.LinkedHashSet; import java.util.concurrent.atomic.AtomicReference; +import org.apache.commons.collections.MapUtils; import org.junit.After; import org.junit.Before; import org.junit.Test; @@ -70,7 +72,7 @@ public class RedisKeyValueAdapterUnitTests { when(jedisConnectionFactoryMock.getConnection()).thenReturn(redisConnectionMock); when(redisConnectionMock.getConfig("notify-keyspace-events")) - .thenReturn(Arrays.asList("notify-keyspace-events", "KEA")); + .thenReturn(MapUtils.toProperties(Collections.singletonMap("notify-keyspace-events", "KEA"))); context = new RedisMappingContext(new MappingConfiguration(new IndexConfiguration(), new KeyspaceConfiguration())); context.afterPropertiesSet();