From 17b724cbb77aba24e64e59e3c06cdc6040a742d9 Mon Sep 17 00:00:00 2001 From: dheeraj Date: Tue, 14 Jun 2016 18:43:39 +0530 Subject: [PATCH 1/5] Adding keySize functionality for MultiMaps --- .../java/org/redisson/RedissonListMultimap.java | 13 +++++++++++++ .../java/org/redisson/RedissonMultimap.java | 5 +++++ .../java/org/redisson/RedissonSetMultimap.java | 13 +++++++++++++ src/main/java/org/redisson/core/RMultimap.java | 5 +++++ .../java/org/redisson/core/RMultimapAsync.java | 8 ++++++++ .../org/redisson/RedissonListMultimapTest.java | 17 +++++++++++++++++ .../org/redisson/RedissonSetMultimapTest.java | 16 ++++++++++++++++ 7 files changed, 77 insertions(+) diff --git a/src/main/java/org/redisson/RedissonListMultimap.java b/src/main/java/org/redisson/RedissonListMultimap.java index d2e9db44e..6669727d7 100644 --- a/src/main/java/org/redisson/RedissonListMultimap.java +++ b/src/main/java/org/redisson/RedissonListMultimap.java @@ -65,6 +65,19 @@ public class RedissonListMultimap extends RedissonMultimap implement "return size; ", Arrays.asList(getName())); } + + public Future keySizeAsync() { + return commandExecutor.evalReadAsync(getName(), codec, RedisCommands.EVAL_INTEGER, + "local keys = redis.call('hgetall', KEYS[1]); " + + "local size = 0; " + + "for i, v in ipairs(keys) do " + + "if i % 2 == 0 then " + + "size = size + 1; " + + "end;" + + "end; " + + "return size; ", + Arrays.asList(getName())); + } public Future containsKeyAsync(Object key) { try { diff --git a/src/main/java/org/redisson/RedissonMultimap.java b/src/main/java/org/redisson/RedissonMultimap.java index 1075b2e33..d2372124e 100644 --- a/src/main/java/org/redisson/RedissonMultimap.java +++ b/src/main/java/org/redisson/RedissonMultimap.java @@ -79,6 +79,11 @@ public abstract class RedissonMultimap extends RedissonExpirable implement public int size() { return get(sizeAsync()); } + + @Override + public int keySize() { + return get(keySizeAsync()); + } @Override public boolean isEmpty() { diff --git a/src/main/java/org/redisson/RedissonSetMultimap.java b/src/main/java/org/redisson/RedissonSetMultimap.java index 3989bb762..94b2a3954 100644 --- a/src/main/java/org/redisson/RedissonSetMultimap.java +++ b/src/main/java/org/redisson/RedissonSetMultimap.java @@ -69,6 +69,19 @@ public class RedissonSetMultimap extends RedissonMultimap implements Arrays.asList(getName())); } + public Future keySizeAsync() { + return commandExecutor.evalReadAsync(getName(), codec, RedisCommands.EVAL_INTEGER, + "local keys = redis.call('hgetall', KEYS[1]); " + + "local size = 0; " + + "for i, v in ipairs(keys) do " + + "if i % 2 == 0 then " + + "size = size + 1; " + + "end;" + + "end; " + + "return size; ", + Arrays.asList(getName())); + } + public Future containsKeyAsync(Object key) { try { byte[] keyState = codec.getMapKeyEncoder().encode(key); diff --git a/src/main/java/org/redisson/core/RMultimap.java b/src/main/java/org/redisson/core/RMultimap.java index 7f39b53ce..338bcc9c6 100644 --- a/src/main/java/org/redisson/core/RMultimap.java +++ b/src/main/java/org/redisson/core/RMultimap.java @@ -162,6 +162,11 @@ public interface RMultimap extends RExpirable, RMultimapAsync { * vice versa. However, adding to the returned set is not possible. */ Set keySet(); + + /** + * Returns the count of distinct keys in this multimap. + */ + int keySize(); /** * Returns a view collection containing the value from each key-value diff --git a/src/main/java/org/redisson/core/RMultimapAsync.java b/src/main/java/org/redisson/core/RMultimapAsync.java index 5c64da558..b9710df71 100644 --- a/src/main/java/org/redisson/core/RMultimapAsync.java +++ b/src/main/java/org/redisson/core/RMultimapAsync.java @@ -123,6 +123,14 @@ public interface RMultimapAsync extends RExpirableAsync { Future> removeAllAsync(Object key); Future> getAllAsync(K key); + + + /** + * Returns the number of key-value pairs in this multimap. + * + * @return + */ + Future keySizeAsync(); /** * Removes keys from map by one operation diff --git a/src/test/java/org/redisson/RedissonListMultimapTest.java b/src/test/java/org/redisson/RedissonListMultimapTest.java index e6f6eeec0..b541bd405 100644 --- a/src/test/java/org/redisson/RedissonListMultimapTest.java +++ b/src/test/java/org/redisson/RedissonListMultimapTest.java @@ -131,6 +131,23 @@ public class RedissonListMultimapTest extends BaseTest { assertThat(s).isEmpty(); assertThat(map.size()).isEqualTo(1); } + + @Test + public void testKeySize() { + RListMultimap map = redisson.getListMultimap("test1"); + map.put(new SimpleKey("0"), new SimpleValue("1")); + map.put(new SimpleKey("0"), new SimpleValue("2")); + map.put(new SimpleKey("1"), new SimpleValue("4")); + + assertThat(map.keySize()).isEqualTo(2); + + assertThat(map.fastRemove(new SimpleKey("0"))).isEqualTo(1); + + List s = map.get(new SimpleKey("0")); + assertThat(s).isEmpty(); + assertThat(map.size()).isEqualTo(1); + } + @Test public void testPut() { diff --git a/src/test/java/org/redisson/RedissonSetMultimapTest.java b/src/test/java/org/redisson/RedissonSetMultimapTest.java index c30256c53..8780503a0 100644 --- a/src/test/java/org/redisson/RedissonSetMultimapTest.java +++ b/src/test/java/org/redisson/RedissonSetMultimapTest.java @@ -131,6 +131,22 @@ public class RedissonSetMultimapTest extends BaseTest { assertThat(s).isEmpty(); assertThat(map.size()).isEqualTo(0); } + + @Test + public void testKeySize() { + RSetMultimap map = redisson.getSetMultimap("test1"); + map.put(new SimpleKey("0"), new SimpleValue("1")); + map.put(new SimpleKey("0"), new SimpleValue("2")); + map.put(new SimpleKey("1"), new SimpleValue("3")); + + assertThat(map.size()).isEqualTo(2); + + map.fastRemove(new SimpleKey("0")); + + Set s = map.get(new SimpleKey("0")); + assertThat(s).isEmpty(); + assertThat(map.size()).isEqualTo(1); + } @Test public void testPut() { From 15a69f0fc42eaf543451aef46cf72f90ef9c4a50 Mon Sep 17 00:00:00 2001 From: dheeraj Date: Wed, 15 Jun 2016 02:17:55 +0530 Subject: [PATCH 2/5] Adding keySize functionality for MultiMaps - Improvements --- .../java/org/redisson/RedissonListMultimap.java | 13 +------------ src/main/java/org/redisson/RedissonMultimap.java | 8 ++++++-- src/main/java/org/redisson/RedissonSetMultimap.java | 13 +------------ 3 files changed, 8 insertions(+), 26 deletions(-) diff --git a/src/main/java/org/redisson/RedissonListMultimap.java b/src/main/java/org/redisson/RedissonListMultimap.java index 6669727d7..5fd88ac8e 100644 --- a/src/main/java/org/redisson/RedissonListMultimap.java +++ b/src/main/java/org/redisson/RedissonListMultimap.java @@ -66,18 +66,7 @@ public class RedissonListMultimap extends RedissonMultimap implement Arrays.asList(getName())); } - public Future keySizeAsync() { - return commandExecutor.evalReadAsync(getName(), codec, RedisCommands.EVAL_INTEGER, - "local keys = redis.call('hgetall', KEYS[1]); " + - "local size = 0; " + - "for i, v in ipairs(keys) do " + - "if i % 2 == 0 then " + - "size = size + 1; " + - "end;" + - "end; " + - "return size; ", - Arrays.asList(getName())); - } + public Future containsKeyAsync(Object key) { try { diff --git a/src/main/java/org/redisson/RedissonMultimap.java b/src/main/java/org/redisson/RedissonMultimap.java index d2372124e..8c64a592f 100644 --- a/src/main/java/org/redisson/RedissonMultimap.java +++ b/src/main/java/org/redisson/RedissonMultimap.java @@ -255,8 +255,12 @@ public abstract class RedissonMultimap extends RedissonExpirable implement "return redis.call('persist', KEYS[1]); ", Arrays.asList(getName())); } - - + + public Future keySizeAsync() { + return commandExecutor.readAsync(getName(), LongCodec.INSTANCE, RedisCommands.HLEN, getName()); + } + + MapScanResult scanIterator(InetSocketAddress client, long startPos) { Future> f = commandExecutor.readAsync(client, getName(), new ScanCodec(codec, StringCodec.INSTANCE), RedisCommands.HSCAN, getName(), startPos); return get(f); diff --git a/src/main/java/org/redisson/RedissonSetMultimap.java b/src/main/java/org/redisson/RedissonSetMultimap.java index 94b2a3954..74ee7a333 100644 --- a/src/main/java/org/redisson/RedissonSetMultimap.java +++ b/src/main/java/org/redisson/RedissonSetMultimap.java @@ -69,18 +69,7 @@ public class RedissonSetMultimap extends RedissonMultimap implements Arrays.asList(getName())); } - public Future keySizeAsync() { - return commandExecutor.evalReadAsync(getName(), codec, RedisCommands.EVAL_INTEGER, - "local keys = redis.call('hgetall', KEYS[1]); " + - "local size = 0; " + - "for i, v in ipairs(keys) do " + - "if i % 2 == 0 then " + - "size = size + 1; " + - "end;" + - "end; " + - "return size; ", - Arrays.asList(getName())); - } + public Future containsKeyAsync(Object key) { try { From e6209a195fd5f5a9804637f465ddaec478481de0 Mon Sep 17 00:00:00 2001 From: Nikita Date: Thu, 16 Jun 2016 11:09:07 +0300 Subject: [PATCH 3/5] RedissonCache refactored --- .../redisson/spring/cache/RedissonCache.java | 19 ------------------- 1 file changed, 19 deletions(-) diff --git a/src/main/java/org/redisson/spring/cache/RedissonCache.java b/src/main/java/org/redisson/spring/cache/RedissonCache.java index 5c17e466d..31efe95a9 100644 --- a/src/main/java/org/redisson/spring/cache/RedissonCache.java +++ b/src/main/java/org/redisson/spring/cache/RedissonCache.java @@ -17,13 +17,8 @@ package org.redisson.spring.cache; import java.io.IOException; import java.lang.reflect.Constructor; -import java.util.Map; import java.util.concurrent.Callable; -import java.util.concurrent.ConcurrentHashMap; -import java.util.concurrent.ConcurrentMap; import java.util.concurrent.TimeUnit; -import java.util.concurrent.locks.Lock; -import java.util.concurrent.locks.ReentrantLock; import org.redisson.RedissonClient; import org.redisson.core.RLock; @@ -40,8 +35,6 @@ import org.springframework.cache.support.SimpleValueWrapper; */ public class RedissonCache implements Cache { - private final ConcurrentMap valueLoaderLocks = new ConcurrentHashMap(); - private RMapCache mapCache; private final RMap map; @@ -130,18 +123,6 @@ public class RedissonCache implements Cache { return new SimpleValueWrapper(value); } - public Lock getLock(Object key) { - Lock lock = valueLoaderLocks.get(key); - if (lock == null) { - Lock newlock = new ReentrantLock(); - lock = valueLoaderLocks.putIfAbsent(key, newlock); - if (lock == null) { - lock = newlock; - } - } - return lock; - } - public T get(Object key, Callable valueLoader) { Object value = map.get(key); if (value == null) { From 6d524b08549cd09ac38b24980015f37788859c3c Mon Sep 17 00:00:00 2001 From: Nikita Date: Thu, 16 Jun 2016 11:10:24 +0300 Subject: [PATCH 4/5] RedissonMultimap.keySet.size fixed --- src/main/java/org/redisson/RedissonMultimap.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/org/redisson/RedissonMultimap.java b/src/main/java/org/redisson/RedissonMultimap.java index ee28b1938..0d02efcf0 100644 --- a/src/main/java/org/redisson/RedissonMultimap.java +++ b/src/main/java/org/redisson/RedissonMultimap.java @@ -281,7 +281,7 @@ public abstract class RedissonMultimap extends RedissonExpirable implement @Override public int size() { - return RedissonMultimap.this.size(); + return RedissonMultimap.this.keySize(); } @Override From 69ac43ca0ef6a0645d9128d2171b496288d28538 Mon Sep 17 00:00:00 2001 From: Nikita Date: Thu, 16 Jun 2016 13:38:03 +0300 Subject: [PATCH 5/5] required sync added --- .../org/redisson/connection/MasterSlaveEntry.java | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/src/main/java/org/redisson/connection/MasterSlaveEntry.java b/src/main/java/org/redisson/connection/MasterSlaveEntry.java index 0fe9871a0..1e3cdefff 100644 --- a/src/main/java/org/redisson/connection/MasterSlaveEntry.java +++ b/src/main/java/org/redisson/connection/MasterSlaveEntry.java @@ -291,8 +291,10 @@ public class MasterSlaveEntry { this.config.getSlaveSubscriptionConnectionMinimumIdleSize(), this.config.getSlaveSubscriptionConnectionPoolSize(), connectionManager, mode); if (freezed) { - entry.setFreezed(freezed); - entry.setFreezeReason(FreezeReason.SYSTEM); + synchronized (entry) { + entry.setFreezed(freezed); + entry.setFreezeReason(FreezeReason.SYSTEM); + } } return slaveBalancer.add(entry); } @@ -350,8 +352,10 @@ public class MasterSlaveEntry { public void unfreeze() { masterEntry.resetFailedAttempts(); - masterEntry.setFreezed(false); - masterEntry.setFreezeReason(null); + synchronized (masterEntry) { + masterEntry.setFreezed(false); + masterEntry.setFreezeReason(null); + } } public void shutdownMasterAsync() {